diff options
Diffstat (limited to 'thirdparty')
137 files changed, 7261 insertions, 8644 deletions
diff --git a/thirdparty/README.md b/thirdparty/README.md index ffc8137819..19c155a2d4 100644 --- a/thirdparty/README.md +++ b/thirdparty/README.md @@ -214,7 +214,7 @@ Files extracted from upstream source: ## harfbuzz - Upstream: https://github.com/harfbuzz/harfbuzz -- Version: 5.1.0 (f1f2be776bcd994fa9262622e1a7098a066e5cf7, 2022) +- Version: 5.2.0 (4a1d891c6317d2c83e5f3c2607ec5f5ccedffcde, 2022) - License: MIT Files extracted from upstream source: @@ -276,7 +276,7 @@ Files extracted from upstream source: ## libpng - Upstream: http://libpng.org/pub/png/libpng.html -- Version: 1.6.37 (a40189cf881e9f0db80511c382292a5604c3c3d1, 2019) +- Version: 1.6.38 (0a158f3506502dfa23edfc42790dfaed82efba17, 2022) - License: libpng/zlib Files extracted from upstream source: @@ -378,8 +378,8 @@ Files extracted from upstream repository: - `minimp3_ex.h` - `LICENSE` -Some changes have been made in order to fix Windows on ARM build errors. -They are marked with `// -- GODOT start --` and `// -- GODOT end --` +Some changes have been made in order to fix Windows on ARM build errors, and +to solve some MSVC warnings. See the patches in the `patches` directory. ## miniupnpc @@ -535,7 +535,7 @@ Patch files are provided in `oidn/patches/`. ## openxr - Upstream: https://github.com/KhronosGroup/OpenXR-SDK -- Version: 1.0.23 (885a90f8934d84121344ba8e4aa5159d5b496e08, 2022) +- Version: 1.0.25 (c16a18c99740ea5dd251e3af117e0e5aea4ceaa9, 2022) - License: Apache 2.0 Files extracted from upstream source: @@ -656,7 +656,7 @@ instead of `miniz.h` as an external dependency. ## thorvg - Upstream: https://github.com/Samsung/thorvg -- Version: 0.8.1 (c4ccb1078f4390ec749ab8e05ba7e9e35f81285f, 2022) +- Version: 0.8.2 (496796f1e5e85bd5fbba36dae987edb1b3945592, 2022) - License: MIT Files extracted from upstream source: diff --git a/thirdparty/harfbuzz/src/OT/Layout/Common/Coverage.hh b/thirdparty/harfbuzz/src/OT/Layout/Common/Coverage.hh index e52a617c86..eef89a2879 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/Common/Coverage.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/Common/Coverage.hh @@ -206,7 +206,7 @@ struct Coverage template <typename IterableOut, hb_requires (hb_is_sink_of (IterableOut, hb_codepoint_t))> - void intersect_set (const hb_set_t &glyphs, IterableOut &intersect_glyphs) const + void intersect_set (const hb_set_t &glyphs, IterableOut&& intersect_glyphs) const { switch (u.format) { diff --git a/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat1.hh b/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat1.hh index 886babd2d1..82fd48dc50 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat1.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat1.hh @@ -88,7 +88,7 @@ struct CoverageFormat1_3 template <typename IterableOut, hb_requires (hb_is_sink_of (IterableOut, hb_codepoint_t))> - void intersect_set (const hb_set_t &glyphs, IterableOut &intersect_glyphs) const + void intersect_set (const hb_set_t &glyphs, IterableOut&& intersect_glyphs) const { unsigned count = glyphArray.len; for (unsigned i = 0; i < count; i++) diff --git a/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat2.hh b/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat2.hh index 4ddb2a73e4..974d094633 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat2.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/Common/CoverageFormat2.hh @@ -140,7 +140,7 @@ struct CoverageFormat2_4 template <typename IterableOut, hb_requires (hb_is_sink_of (IterableOut, hb_codepoint_t))> - void intersect_set (const hb_set_t &glyphs, IterableOut &intersect_glyphs) const + void intersect_set (const hb_set_t &glyphs, IterableOut&& intersect_glyphs) const { for (const auto& range : rangeRecord) { diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/Anchor.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/Anchor.hh index bfe6b36afd..49e76e7750 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/Anchor.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/Anchor.hh @@ -58,8 +58,7 @@ struct Anchor return_trace (bool (reinterpret_cast<Anchor *> (u.format1.copy (c->serializer)))); } return_trace (bool (reinterpret_cast<Anchor *> (u.format2.copy (c->serializer)))); - case 3: return_trace (bool (reinterpret_cast<Anchor *> (u.format3.copy (c->serializer, - c->plan->layout_variation_idx_map)))); + case 3: return_trace (u.format3.subset (c)); default:return_trace (false); } } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/AnchorFormat3.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/AnchorFormat3.hh index d77b4699be..2e30ab33c3 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/AnchorFormat3.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/AnchorFormat3.hh @@ -41,24 +41,54 @@ struct AnchorFormat3 *y += (this+yDeviceTable).get_y_delta (font, c->var_store, c->var_store_cache); } - AnchorFormat3* copy (hb_serialize_context_t *c, - const hb_map_t *layout_variation_idx_map) const + bool subset (hb_subset_context_t *c) const { - TRACE_SERIALIZE (this); - if (!layout_variation_idx_map) return_trace (nullptr); + TRACE_SUBSET (this); + auto *out = c->serializer->start_embed (*this); + if (unlikely (!out)) return_trace (false); + if (unlikely (!c->serializer->embed (format))) return_trace (false); + if (unlikely (!c->serializer->embed (xCoordinate))) return_trace (false); + if (unlikely (!c->serializer->embed (yCoordinate))) return_trace (false); - auto *out = c->embed<AnchorFormat3> (this); - if (unlikely (!out)) return_trace (nullptr); + unsigned x_varidx = xDeviceTable ? (this+xDeviceTable).get_variation_index () : HB_OT_LAYOUT_NO_VARIATIONS_INDEX; + if (c->plan->layout_variation_idx_delta_map->has (x_varidx)) + { + int delta = hb_second (c->plan->layout_variation_idx_delta_map->get (x_varidx)); + if (delta != 0) + { + if (!c->serializer->check_assign (out->xCoordinate, xCoordinate + delta, + HB_SERIALIZE_ERROR_INT_OVERFLOW)) + return_trace (false); + } + } - out->xDeviceTable.serialize_copy (c, xDeviceTable, this, 0, hb_serialize_context_t::Head, layout_variation_idx_map); - out->yDeviceTable.serialize_copy (c, yDeviceTable, this, 0, hb_serialize_context_t::Head, layout_variation_idx_map); + unsigned y_varidx = yDeviceTable ? (this+yDeviceTable).get_variation_index () : HB_OT_LAYOUT_NO_VARIATIONS_INDEX; + if (c->plan->layout_variation_idx_delta_map->has (y_varidx)) + { + int delta = hb_second (c->plan->layout_variation_idx_delta_map->get (y_varidx)); + if (delta != 0) + { + if (!c->serializer->check_assign (out->yCoordinate, yCoordinate + delta, + HB_SERIALIZE_ERROR_INT_OVERFLOW)) + return_trace (false); + } + } + + if (c->plan->all_axes_pinned) + return_trace (c->serializer->check_assign (out->format, 1, HB_SERIALIZE_ERROR_INT_OVERFLOW)); + + if (!c->serializer->embed (xDeviceTable)) return_trace (false); + if (!c->serializer->embed (yDeviceTable)) return_trace (false); + + out->xDeviceTable.serialize_copy (c->serializer, xDeviceTable, this, 0, hb_serialize_context_t::Head, c->plan->layout_variation_idx_delta_map); + out->yDeviceTable.serialize_copy (c->serializer, yDeviceTable, this, 0, hb_serialize_context_t::Head, c->plan->layout_variation_idx_delta_map); return_trace (out); } void collect_variation_indices (hb_collect_variation_indices_context_t *c) const { - (this+xDeviceTable).collect_variation_indices (c->layout_variation_indices); - (this+yDeviceTable).collect_variation_indices (c->layout_variation_indices); + (this+xDeviceTable).collect_variation_indices (c); + (this+yDeviceTable).collect_variation_indices (c); } }; diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/Common.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/Common.hh index e16c06729d..408197454f 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/Common.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/Common.hh @@ -22,7 +22,8 @@ template<typename Iterator, typename SrcLookup> static void SinglePos_serialize (hb_serialize_context_t *c, const SrcLookup *src, Iterator it, - const hb_map_t *layout_variation_idx_map); + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map, + bool all_axes_pinned); } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/MarkRecord.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/MarkRecord.hh index 7a514453ae..a7d489d2a5 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/MarkRecord.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/MarkRecord.hh @@ -9,7 +9,7 @@ struct MarkRecord { friend struct MarkArray; - protected: + public: HBUINT16 klass; /* Class defined for this mark */ Offset16To<Anchor> markAnchor; /* Offset to Anchor table--from diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat1.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat1.hh index 3cb207281d..ddf7313f94 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat1.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat1.hh @@ -127,6 +127,12 @@ struct PairPosFormat1_3 out->valueFormat[1] = newFormats.second; } + if (c->plan->all_axes_pinned) + { + out->valueFormat[0] = out->valueFormat[0].drop_device_table_flags (); + out->valueFormat[1] = out->valueFormat[1].drop_device_table_flags (); + } + hb_sorted_vector_t<hb_codepoint_t> new_coverage; + hb_zip (this+coverage, pairSet) diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat2.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat2.hh index a80fe0c226..83b093b988 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat2.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairPosFormat2.hh @@ -274,13 +274,19 @@ struct PairPosFormat2_4 out->valueFormat1 = newFormats.first; out->valueFormat2 = newFormats.second; + if (c->plan->all_axes_pinned) + { + out->valueFormat1 = out->valueFormat1.drop_device_table_flags (); + out->valueFormat2 = out->valueFormat2.drop_device_table_flags (); + } + for (unsigned class1_idx : + hb_range ((unsigned) class1Count) | hb_filter (klass1_map)) { for (unsigned class2_idx : + hb_range ((unsigned) class2Count) | hb_filter (klass2_map)) { unsigned idx = (class1_idx * (unsigned) class2Count + class2_idx) * (len1 + len2); - valueFormat1.copy_values (c->serializer, newFormats.first, this, &values[idx], c->plan->layout_variation_idx_map); - valueFormat2.copy_values (c->serializer, newFormats.second, this, &values[idx + len1], c->plan->layout_variation_idx_map); + valueFormat1.copy_values (c->serializer, out->valueFormat1, this, &values[idx], c->plan->layout_variation_idx_delta_map); + valueFormat2.copy_values (c->serializer, out->valueFormat2, this, &values[idx + len1], c->plan->layout_variation_idx_delta_map); } } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairSet.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairSet.hh index 4578fbd1d6..aa48d933c3 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairSet.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairSet.hh @@ -163,7 +163,7 @@ struct PairSet newFormats, len1, &glyph_map, - c->plan->layout_variation_idx_map + c->plan->layout_variation_idx_delta_map }; const PairValueRecord *record = &firstPairValueRecord; diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairValueRecord.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairValueRecord.hh index bd95abde16..3222477764 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairValueRecord.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/PairValueRecord.hh @@ -34,7 +34,7 @@ struct PairValueRecord const ValueFormat *newFormats; unsigned len1; /* valueFormats[0].get_len() */ const hb_map_t *glyph_map; - const hb_map_t *layout_variation_idx_map; + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map; }; bool subset (hb_subset_context_t *c, @@ -50,12 +50,12 @@ struct PairValueRecord closure->valueFormats[0].copy_values (s, closure->newFormats[0], closure->base, &values[0], - closure->layout_variation_idx_map); + closure->layout_variation_idx_delta_map); closure->valueFormats[1].copy_values (s, closure->newFormats[1], closure->base, &values[closure->len1], - closure->layout_variation_idx_map); + closure->layout_variation_idx_delta_map); return_trace (true); } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePos.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePos.hh index 702f578b3c..6dce3e6343 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePos.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePos.hh @@ -38,12 +38,16 @@ struct SinglePos void serialize (hb_serialize_context_t *c, const SrcLookup* src, Iterator glyph_val_iter_pairs, - const hb_map_t *layout_variation_idx_map) + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map, + bool all_axes_pinned) { if (unlikely (!c->extend_min (u.format))) return; unsigned format = 2; ValueFormat new_format = src->get_value_format (); + if (all_axes_pinned) + new_format = new_format.drop_device_table_flags (); + if (glyph_val_iter_pairs) format = get_format (glyph_val_iter_pairs); @@ -53,13 +57,13 @@ struct SinglePos src, glyph_val_iter_pairs, new_format, - layout_variation_idx_map); + layout_variation_idx_delta_map); return; case 2: u.format2.serialize (c, src, glyph_val_iter_pairs, new_format, - layout_variation_idx_map); + layout_variation_idx_delta_map); return; default:return; } @@ -84,8 +88,9 @@ static void SinglePos_serialize (hb_serialize_context_t *c, const SrcLookup *src, Iterator it, - const hb_map_t *layout_variation_idx_map) -{ c->start_embed<SinglePos> ()->serialize (c, src, it, layout_variation_idx_map); } + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map, + bool all_axes_pinned) +{ c->start_embed<SinglePos> ()->serialize (c, src, it, layout_variation_idx_delta_map, all_axes_pinned); } } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat1.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat1.hh index 7cbdf6dc6c..5a9dd58a63 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat1.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat1.hh @@ -87,7 +87,7 @@ struct SinglePosFormat1 const SrcLookup *src, Iterator it, ValueFormat newFormat, - const hb_map_t *layout_variation_idx_map) + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map) { if (unlikely (!c->extend_min (this))) return; if (unlikely (!c->check_assign (valueFormat, @@ -96,7 +96,7 @@ struct SinglePosFormat1 for (const hb_array_t<const Value>& _ : + it | hb_map (hb_second)) { - src->get_value_format ().copy_values (c, newFormat, src, &_, layout_variation_idx_map); + src->get_value_format ().copy_values (c, newFormat, src, &_, layout_variation_idx_delta_map); // Only serialize the first entry in the iterator, the rest are assumed to // be the same. break; @@ -126,7 +126,7 @@ struct SinglePosFormat1 ; bool ret = bool (it); - SinglePos_serialize (c->serializer, this, it, c->plan->layout_variation_idx_map); + SinglePos_serialize (c->serializer, this, it, c->plan->layout_variation_idx_delta_map, c->plan->all_axes_pinned); return_trace (ret); } }; diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat2.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat2.hh index 518fa9dcb0..8a6e8a42a6 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat2.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/SinglePosFormat2.hh @@ -99,7 +99,7 @@ struct SinglePosFormat2 const SrcLookup *src, Iterator it, ValueFormat newFormat, - const hb_map_t *layout_variation_idx_map) + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map) { auto out = c->extend_min (this); if (unlikely (!out)) return; @@ -109,7 +109,7 @@ struct SinglePosFormat2 + it | hb_map (hb_second) | hb_apply ([&] (hb_array_t<const Value> _) - { src->get_value_format ().copy_values (c, newFormat, src, &_, layout_variation_idx_map); }) + { src->get_value_format ().copy_values (c, newFormat, src, &_, layout_variation_idx_delta_map); }) ; auto glyphs = @@ -141,7 +141,7 @@ struct SinglePosFormat2 ; bool ret = bool (it); - SinglePos_serialize (c->serializer, this, it, c->plan->layout_variation_idx_map); + SinglePos_serialize (c->serializer, this, it, c->plan->layout_variation_idx_delta_map, c->plan->all_axes_pinned); return_trace (ret); } }; diff --git a/thirdparty/harfbuzz/src/OT/Layout/GPOS/ValueFormat.hh b/thirdparty/harfbuzz/src/OT/Layout/GPOS/ValueFormat.hh index b29f287bce..26a40f01a3 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GPOS/ValueFormat.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GPOS/ValueFormat.hh @@ -59,6 +59,24 @@ struct ValueFormat : HBUINT16 unsigned int get_len () const { return hb_popcount ((unsigned int) *this); } unsigned int get_size () const { return get_len () * Value::static_size; } + hb_vector_t<unsigned> get_device_table_indices () const { + unsigned i = 0; + hb_vector_t<unsigned> result; + unsigned format = *this; + + if (format & xPlacement) i++; + if (format & yPlacement) i++; + if (format & xAdvance) i++; + if (format & yAdvance) i++; + + if (format & xPlaDevice) result.push (i++); + if (format & yPlaDevice) result.push (i++); + if (format & xAdvDevice) result.push (i++); + if (format & yAdvDevice) result.push (i++); + + return result; + } + bool apply_value (hb_ot_apply_context_t *c, const void *base, const Value *values, @@ -145,30 +163,50 @@ struct ValueFormat : HBUINT16 unsigned int new_format, const void *base, const Value *values, - const hb_map_t *layout_variation_idx_map) const + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map) const { unsigned int format = *this; if (!format) return; - if (format & xPlacement) copy_value (c, new_format, xPlacement, *values++); - if (format & yPlacement) copy_value (c, new_format, yPlacement, *values++); - if (format & xAdvance) copy_value (c, new_format, xAdvance, *values++); - if (format & yAdvance) copy_value (c, new_format, yAdvance, *values++); + HBINT16 *x_placement = nullptr, *y_placement = nullptr, *x_adv = nullptr, *y_adv = nullptr; + if (format & xPlacement) x_placement = copy_value (c, new_format, xPlacement, *values++); + if (format & yPlacement) y_placement = copy_value (c, new_format, yPlacement, *values++); + if (format & xAdvance) x_adv = copy_value (c, new_format, xAdvance, *values++); + if (format & yAdvance) y_adv = copy_value (c, new_format, yAdvance, *values++); - if (format & xPlaDevice) copy_device (c, base, values++, layout_variation_idx_map); - if (format & yPlaDevice) copy_device (c, base, values++, layout_variation_idx_map); - if (format & xAdvDevice) copy_device (c, base, values++, layout_variation_idx_map); - if (format & yAdvDevice) copy_device (c, base, values++, layout_variation_idx_map); + if (format & xPlaDevice) + { + add_delta_to_value (x_placement, base, values, layout_variation_idx_delta_map); + copy_device (c, base, values++, layout_variation_idx_delta_map, new_format, xPlaDevice); + } + + if (format & yPlaDevice) + { + add_delta_to_value (y_placement, base, values, layout_variation_idx_delta_map); + copy_device (c, base, values++, layout_variation_idx_delta_map, new_format, yPlaDevice); + } + + if (format & xAdvDevice) + { + add_delta_to_value (x_adv, base, values, layout_variation_idx_delta_map); + copy_device (c, base, values++, layout_variation_idx_delta_map, new_format, xAdvDevice); + } + + if (format & yAdvDevice) + { + add_delta_to_value (y_adv, base, values, layout_variation_idx_delta_map); + copy_device (c, base, values++, layout_variation_idx_delta_map, new_format, yAdvDevice); + } } - void copy_value (hb_serialize_context_t *c, - unsigned int new_format, - Flags flag, - Value value) const + HBINT16* copy_value (hb_serialize_context_t *c, + unsigned int new_format, + Flags flag, + Value value) const { // Filter by new format. - if (!(new_format & flag)) return; - c->copy (value); + if (!(new_format & flag)) return nullptr; + return reinterpret_cast<HBINT16 *> (c->copy (value)); } void collect_variation_indices (hb_collect_variation_indices_context_t *c, @@ -183,31 +221,40 @@ struct ValueFormat : HBUINT16 if (format & yAdvance) i++; if (format & xPlaDevice) { - (base + get_device (&(values[i]))).collect_variation_indices (c->layout_variation_indices); + (base + get_device (&(values[i]))).collect_variation_indices (c); i++; } if (format & ValueFormat::yPlaDevice) { - (base + get_device (&(values[i]))).collect_variation_indices (c->layout_variation_indices); + (base + get_device (&(values[i]))).collect_variation_indices (c); i++; } if (format & ValueFormat::xAdvDevice) { - (base + get_device (&(values[i]))).collect_variation_indices (c->layout_variation_indices); + (base + get_device (&(values[i]))).collect_variation_indices (c); i++; } if (format & ValueFormat::yAdvDevice) { - (base + get_device (&(values[i]))).collect_variation_indices (c->layout_variation_indices); + (base + get_device (&(values[i]))).collect_variation_indices (c); i++; } } + unsigned drop_device_table_flags () const + { + unsigned format = *this; + for (unsigned flag = xPlaDevice; flag <= yAdvDevice; flag = flag << 1) + format = format & ~flag; + + return format; + } + private: bool sanitize_value_devices (hb_sanitize_context_t *c, const void *base, const Value *values) const { @@ -236,9 +283,27 @@ struct ValueFormat : HBUINT16 return *static_cast<const Offset16To<Device> *> (value); } + void add_delta_to_value (HBINT16 *value, + const void *base, + const Value *src_value, + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map) const + { + if (!value) return; + unsigned varidx = (base + get_device (src_value)).get_variation_index (); + hb_pair_t<unsigned, int> *varidx_delta; + if (!layout_variation_idx_delta_map->has (varidx, &varidx_delta)) return; + + *value += hb_second (*varidx_delta); + } + bool copy_device (hb_serialize_context_t *c, const void *base, - const Value *src_value, const hb_map_t *layout_variation_idx_map) const + const Value *src_value, + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map, + unsigned int new_format, Flags flag) const { + // Filter by new format. + if (!(new_format & flag)) return true; + Value *dst_value = c->copy (*src_value); if (!dst_value) return false; @@ -246,7 +311,7 @@ struct ValueFormat : HBUINT16 *dst_value = 0; c->push (); - if ((base + get_device (src_value)).copy (c, layout_variation_idx_map)) + if ((base + get_device (src_value)).copy (c, layout_variation_idx_delta_map)) { c->add_link (*dst_value, c->pop_pack ()); return true; diff --git a/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubst.hh b/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubst.hh index 98f2f5fe7a..852ca3eac5 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubst.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubst.hh @@ -35,19 +35,17 @@ struct MultipleSubst } } - /* TODO This function is unused and not updated to 24bit GIDs. Should be done by using - * iterators. While at it perhaps using iterator of arrays of hb_codepoint_t instead. */ + template<typename Iterator, + hb_requires (hb_is_sorted_iterator (Iterator))> bool serialize (hb_serialize_context_t *c, - hb_sorted_array_t<const HBGlyphID16> glyphs, - hb_array_t<const unsigned int> substitute_len_list, - hb_array_t<const HBGlyphID16> substitute_glyphs_list) + Iterator it) { TRACE_SERIALIZE (this); if (unlikely (!c->extend_min (u.format))) return_trace (false); unsigned int format = 1; u.format = format; switch (u.format) { - case 1: return_trace (u.format1.serialize (c, glyphs, substitute_len_list, substitute_glyphs_list)); + case 1: return_trace (u.format1.serialize (c, it)); default:return_trace (false); } } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubstFormat1.hh b/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubstFormat1.hh index 89a04ec3b1..3b4bd11694 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubstFormat1.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GSUB/MultipleSubstFormat1.hh @@ -71,22 +71,31 @@ struct MultipleSubstFormat1_2 return_trace ((this+sequence[index]).apply (c)); } + template<typename Iterator, + hb_requires (hb_is_sorted_iterator (Iterator))> bool serialize (hb_serialize_context_t *c, - hb_sorted_array_t<const HBGlyphID16> glyphs, - hb_array_t<const unsigned int> substitute_len_list, - hb_array_t<const HBGlyphID16> substitute_glyphs_list) + Iterator it) { TRACE_SERIALIZE (this); + auto sequences = + + it + | hb_map (hb_second) + ; + auto glyphs = + + it + | hb_map_retains_sorting (hb_first) + ; if (unlikely (!c->extend_min (this))) return_trace (false); - if (unlikely (!sequence.serialize (c, glyphs.length))) return_trace (false); - for (unsigned int i = 0; i < glyphs.length; i++) + + if (unlikely (!sequence.serialize (c, sequences.length))) return_trace (false); + + for (auto& pair : hb_zip (sequences, sequence)) { - unsigned int substitute_len = substitute_len_list[i]; - if (unlikely (!sequence[i] - .serialize_serialize (c, substitute_glyphs_list.sub_array (0, substitute_len)))) + if (unlikely (!pair.second + .serialize_serialize (c, pair.first))) return_trace (false); - substitute_glyphs_list += substitute_len; } + return_trace (coverage.serialize_serialize (c, glyphs)); } diff --git a/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat1.hh b/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat1.hh index 4b17243d81..13665d7ba1 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat1.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat1.hh @@ -42,6 +42,11 @@ struct SingleSubstFormat1_3 hb_codepoint_t d = deltaGlyphID; hb_codepoint_t mask = get_mask (); + /* Help fuzzer avoid this function as much. */ + unsigned pop = (this+coverage).get_population (); + if (pop >= mask) + return; + hb_set_t intersection; (this+coverage).intersect_set (c->parent_active_glyphs (), intersection); @@ -52,7 +57,7 @@ struct SingleSubstFormat1_3 hb_codepoint_t max_before = intersection.get_max (); hb_codepoint_t min_after = (min_before + d) & mask; hb_codepoint_t max_after = (max_before + d) & mask; - if ((this+coverage).get_population () >= max_before - min_before && + if (pop >= max_before - min_before && ((min_before <= min_after && min_after <= max_before) || (min_before <= max_after && max_after <= max_before))) return; diff --git a/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat2.hh b/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat2.hh index fb1e90d03e..5416299754 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat2.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GSUB/SingleSubstFormat2.hh @@ -41,7 +41,6 @@ struct SingleSubstFormat2_4 | hb_map (hb_second) | hb_sink (c->output) ; - } void closure_lookups (hb_closure_lookups_context_t *c) const {} diff --git a/thirdparty/harfbuzz/src/OT/Layout/GSUB/SubstLookup.hh b/thirdparty/harfbuzz/src/OT/Layout/GSUB/SubstLookup.hh index 320685b868..d49dcc0e0f 100644 --- a/thirdparty/harfbuzz/src/OT/Layout/GSUB/SubstLookup.hh +++ b/thirdparty/harfbuzz/src/OT/Layout/GSUB/SubstLookup.hh @@ -119,19 +119,16 @@ struct SubstLookup : Lookup return_trace (false); } - bool serialize_multiple (hb_serialize_context_t *c, - uint32_t lookup_props, - hb_sorted_array_t<const HBGlyphID16> glyphs, - hb_array_t<const unsigned int> substitute_len_list, - hb_array_t<const HBGlyphID16> substitute_glyphs_list) + template<typename Iterator, + hb_requires (hb_is_sorted_iterator (Iterator))> + bool serialize (hb_serialize_context_t *c, + uint32_t lookup_props, + Iterator it) { TRACE_SERIALIZE (this); if (unlikely (!Lookup::serialize (c, SubTable::Multiple, lookup_props, 1))) return_trace (false); if (c->push<SubTable> ()->u.multiple. - serialize (c, - glyphs, - substitute_len_list, - substitute_glyphs_list)) + serialize (c, it)) { c->add_link (get_subtables<SubTable> ()[0], c->pop_pack ()); return_trace (true); diff --git a/thirdparty/harfbuzz/src/OT/glyf/CompositeGlyph.hh b/thirdparty/harfbuzz/src/OT/glyf/CompositeGlyph.hh index 98c2ee4e73..fc8e309bc9 100644 --- a/thirdparty/harfbuzz/src/OT/glyf/CompositeGlyph.hh +++ b/thirdparty/harfbuzz/src/OT/glyf/CompositeGlyph.hh @@ -105,6 +105,67 @@ struct CompositeGlyphRecord } } + unsigned compile_with_deltas (const contour_point_t &p_delta, + char *out) const + { + const HBINT8 *p = &StructAfter<const HBINT8> (flags); +#ifndef HB_NO_BEYOND_64K + if (flags & GID_IS_24BIT) + p += HBGlyphID24::static_size; + else +#endif + p += HBGlyphID16::static_size; + + unsigned len = get_size (); + unsigned len_before_val = (const char *)p - (const char *)this; + if (flags & ARG_1_AND_2_ARE_WORDS) + { + // no overflow, copy and update value with deltas + memcpy (out, this, len); + + const HBINT16 *px = reinterpret_cast<const HBINT16 *> (p); + HBINT16 *o = reinterpret_cast<HBINT16 *> (out + len_before_val); + o[0] = px[0] + roundf (p_delta.x); + o[1] = px[1] + roundf (p_delta.y); + } + else + { + int new_x = p[0] + roundf (p_delta.x); + int new_y = p[1] + roundf (p_delta.y); + if (new_x <= 127 && new_x >= -128 && + new_y <= 127 && new_y >= -128) + { + memcpy (out, this, len); + HBINT8 *o = reinterpret_cast<HBINT8 *> (out + len_before_val); + o[0] = new_x; + o[1] = new_y; + } + else + { + // int8 overflows after deltas applied + memcpy (out, this, len_before_val); + + //update flags + CompositeGlyphRecord *o = reinterpret_cast<CompositeGlyphRecord *> (out); + o->flags = flags | ARG_1_AND_2_ARE_WORDS; + out += len_before_val; + + HBINT16 new_value; + new_value = new_x; + memcpy (out, &new_value, HBINT16::static_size); + out += HBINT16::static_size; + + new_value = new_y; + memcpy (out, &new_value, HBINT16::static_size); + out += HBINT16::static_size; + + memcpy (out, p+2, len - len_before_val - 2); + len += 2; + } + } + return len; + } + protected: bool scaled_offsets () const { return (flags & (SCALED_COMPONENT_OFFSET | UNSCALED_COMPONENT_OFFSET)) == SCALED_COMPONENT_OFFSET; } @@ -288,6 +349,63 @@ struct CompositeGlyph return; glyph_chain.set_overlaps_flag (); } + + bool compile_bytes_with_deltas (const hb_bytes_t &source_bytes, + const contour_point_vector_t &deltas, + hb_bytes_t &dest_bytes /* OUT */) + { + if (source_bytes.length <= GlyphHeader::static_size || + header.numberOfContours != -1) + { + dest_bytes = hb_bytes_t (); + return true; + } + + unsigned source_len = source_bytes.length - GlyphHeader::static_size; + + /* try to allocate more memories than source glyph bytes + * in case that there might be an overflow for int8 value + * and we would need to use int16 instead */ + char *o = (char *) hb_calloc (source_len + source_len/2, sizeof (char)); + if (unlikely (!o)) return false; + + const CompositeGlyphRecord *c = reinterpret_cast<const CompositeGlyphRecord *> (source_bytes.arrayZ + GlyphHeader::static_size); + auto it = composite_iter_t (hb_bytes_t ((const char *)c, source_len), c); + + char *p = o; + unsigned i = 0, source_comp_len = 0; + for (const auto &component : it) + { + /* last 4 points in deltas are phantom points and should not be included */ + if (i >= deltas.length - 4) return false; + + unsigned comp_len = component.get_size (); + if (component.is_anchored ()) + { + memcpy (p, &component, comp_len); + p += comp_len; + } + else + { + unsigned new_len = component.compile_with_deltas (deltas[i], p); + p += new_len; + } + i++; + source_comp_len += comp_len; + } + + //copy instructions if any + if (source_len > source_comp_len) + { + unsigned instr_len = source_len - source_comp_len; + memcpy (p, (const char *)c + source_comp_len, instr_len); + p += instr_len; + } + + unsigned len = p - o; + dest_bytes = hb_bytes_t (o, len); + return true; + } }; diff --git a/thirdparty/harfbuzz/src/OT/glyf/Glyph.hh b/thirdparty/harfbuzz/src/OT/glyf/Glyph.hh index 3efe538f37..afcb5dc834 100644 --- a/thirdparty/harfbuzz/src/OT/glyf/Glyph.hh +++ b/thirdparty/harfbuzz/src/OT/glyf/Glyph.hh @@ -72,12 +72,117 @@ struct Glyph } } + void update_mtx (const hb_subset_plan_t *plan, + int xMin, int yMax, + const contour_point_vector_t &all_points) const + { + hb_codepoint_t new_gid = 0; + if (!plan->new_gid_for_old_gid (gid, &new_gid)) + return; + + unsigned len = all_points.length; + float leftSideX = all_points[len - 4].x; + float rightSideX = all_points[len - 3].x; + float topSideY = all_points[len - 2].y; + float bottomSideY = all_points[len - 1].y; + + int hori_aw = roundf (rightSideX - leftSideX); + if (hori_aw < 0) hori_aw = 0; + int lsb = roundf (xMin - leftSideX); + plan->hmtx_map->set (new_gid, hb_pair (hori_aw, lsb)); + + int vert_aw = roundf (topSideY - bottomSideY); + if (vert_aw < 0) vert_aw = 0; + int tsb = roundf (topSideY - yMax); + plan->vmtx_map->set (new_gid, hb_pair (vert_aw, tsb)); + } + + bool compile_header_bytes (const hb_subset_plan_t *plan, + const contour_point_vector_t &all_points, + hb_bytes_t &dest_bytes /* OUT */) const + { + GlyphHeader *glyph_header = nullptr; + if (all_points.length > 4) + { + glyph_header = (GlyphHeader *) hb_calloc (1, GlyphHeader::static_size); + if (unlikely (!glyph_header)) return false; + } + + int xMin, xMax; + xMin = xMax = roundf (all_points[0].x); + + int yMin, yMax; + yMin = yMax = roundf (all_points[0].y); + + for (unsigned i = 1; i < all_points.length - 4; i++) + { + float rounded_x = roundf (all_points[i].x); + float rounded_y = roundf (all_points[i].y); + xMin = hb_min (xMin, rounded_x); + xMax = hb_max (xMax, rounded_x); + yMin = hb_min (yMin, rounded_y); + yMax = hb_max (yMax, rounded_y); + } + + update_mtx (plan, xMin, yMax, all_points); + + /*for empty glyphs: all_points only include phantom points. + *just update metrics and then return */ + if (all_points.length == 4) + return true; + + glyph_header->numberOfContours = header->numberOfContours; + glyph_header->xMin = xMin; + glyph_header->yMin = yMin; + glyph_header->xMax = xMax; + glyph_header->yMax = yMax; + + dest_bytes = hb_bytes_t ((const char *)glyph_header, GlyphHeader::static_size); + return true; + } + + bool compile_bytes_with_deltas (const hb_subset_plan_t *plan, + hb_font_t *font, + const glyf_accelerator_t &glyf, + hb_bytes_t &dest_start, /* IN/OUT */ + hb_bytes_t &dest_end /* OUT */) const + { + contour_point_vector_t all_points, deltas; + get_points (font, glyf, all_points, &deltas, false); + + switch (type) { + case COMPOSITE: + if (!CompositeGlyph (*header, bytes).compile_bytes_with_deltas (dest_start, + deltas, + dest_end)) + return false; + break; + case SIMPLE: + if (!SimpleGlyph (*header, bytes).compile_bytes_with_deltas (all_points, + plan->flags & HB_SUBSET_FLAGS_NO_HINTING, + dest_end)) + return false; + break; + default: + /* set empty bytes for empty glyph + * do not use source glyph's pointers */ + dest_start = hb_bytes_t (); + dest_end = hb_bytes_t (); + break; + } + + return compile_header_bytes (plan, all_points, dest_start); + } + + /* Note: Recursively calls itself. * all_points includes phantom points */ template <typename accelerator_t> bool get_points (hb_font_t *font, const accelerator_t &glyf_accelerator, contour_point_vector_t &all_points /* OUT */, + contour_point_vector_t *deltas = nullptr, /* OUT */ + bool use_my_metrics = true, bool phantom_only = false, unsigned int depth = 0) const { @@ -130,10 +235,28 @@ struct Glyph phantoms[PHANTOM_BOTTOM].y = v_orig - (int) v_adv; } + if (deltas != nullptr && depth == 0 && type == COMPOSITE) + { + if (unlikely (!deltas->resize (points.length))) return false; + for (unsigned i = 0 ; i < points.length; i++) + deltas->arrayZ[i] = points.arrayZ[i]; + } + #ifndef HB_NO_VAR glyf_accelerator.gvar->apply_deltas_to_points (gid, font, points.as_array ()); #endif + // mainly used by CompositeGlyph calculating new X/Y offset value so no need to extend it + // with child glyphs' points + if (deltas != nullptr && depth == 0 && type == COMPOSITE) + { + for (unsigned i = 0 ; i < points.length; i++) + { + deltas->arrayZ[i].x = points.arrayZ[i].x - deltas->arrayZ[i].x; + deltas->arrayZ[i].y = points.arrayZ[i].y - deltas->arrayZ[i].y; + } + } + switch (type) { case SIMPLE: if (!inplace) @@ -148,11 +271,11 @@ struct Glyph comp_points.reset (); if (unlikely (!glyf_accelerator.glyph_for_gid (item.get_gid ()) .get_points (font, glyf_accelerator, comp_points, - phantom_only, depth + 1))) + deltas, use_my_metrics, phantom_only, depth + 1))) return false; /* Copy phantom points from component if USE_MY_METRICS flag set */ - if (item.is_use_my_metrics ()) + if (use_my_metrics && item.is_use_my_metrics ()) for (unsigned int i = 0; i < PHANTOM_COUNT; i++) phantoms[i] = comp_points[comp_points.length - PHANTOM_COUNT + i]; diff --git a/thirdparty/harfbuzz/src/OT/glyf/SimpleGlyph.hh b/thirdparty/harfbuzz/src/OT/glyf/SimpleGlyph.hh index 6df978cf13..b99665d6a0 100644 --- a/thirdparty/harfbuzz/src/OT/glyf/SimpleGlyph.hh +++ b/thirdparty/harfbuzz/src/OT/glyf/SimpleGlyph.hh @@ -206,6 +206,132 @@ struct SimpleGlyph && read_points (p, points_, end, &contour_point_t::y, FLAG_Y_SHORT, FLAG_Y_SAME); } + + static void encode_coord (int value, + uint8_t &flag, + const simple_glyph_flag_t short_flag, + const simple_glyph_flag_t same_flag, + hb_vector_t<uint8_t> &coords /* OUT */) + { + if (value == 0) + { + flag |= same_flag; + } + else if (value >= -255 && value <= 255) + { + flag |= short_flag; + if (value > 0) flag |= same_flag; + else value = -value; + + coords.push ((uint8_t)value); + } + else + { + int16_t val = value; + coords.push (val >> 8); + coords.push (val & 0xff); + } + } + + static void encode_flag (uint8_t &flag, + uint8_t &repeat, + uint8_t &lastflag, + hb_vector_t<uint8_t> &flags /* OUT */) + { + if (flag == lastflag && repeat != 255) + { + repeat = repeat + 1; + if (repeat == 1) + { + flags.push(flag); + } + else + { + unsigned len = flags.length; + flags[len-2] = flag | FLAG_REPEAT; + flags[len-1] = repeat; + } + } + else + { + repeat = 0; + flags.push (flag); + } + lastflag = flag; + } + + bool compile_bytes_with_deltas (const contour_point_vector_t &all_points, + bool no_hinting, + hb_bytes_t &dest_bytes /* OUT */) + { + if (header.numberOfContours == 0 || all_points.length <= 4) + { + dest_bytes = hb_bytes_t (); + return true; + } + //convert absolute values to relative values + unsigned num_points = all_points.length - 4; + hb_vector_t<hb_pair_t<int, int>> deltas; + deltas.resize (num_points); + + for (unsigned i = 0; i < num_points; i++) + { + deltas[i].first = i == 0 ? roundf (all_points[i].x) : roundf (all_points[i].x) - roundf (all_points[i-1].x); + deltas[i].second = i == 0 ? roundf (all_points[i].y) : roundf (all_points[i].y) - roundf (all_points[i-1].y); + } + + hb_vector_t<uint8_t> flags, x_coords, y_coords; + flags.alloc (num_points); + x_coords.alloc (2*num_points); + y_coords.alloc (2*num_points); + + uint8_t lastflag = 0, repeat = 0; + + for (unsigned i = 0; i < num_points; i++) + { + uint8_t flag = all_points[i].flag; + flag &= FLAG_ON_CURVE + FLAG_OVERLAP_SIMPLE; + + encode_coord (deltas[i].first, flag, FLAG_X_SHORT, FLAG_X_SAME, x_coords); + encode_coord (deltas[i].second, flag, FLAG_Y_SHORT, FLAG_Y_SAME, y_coords); + if (i == 0) lastflag = flag + 1; //make lastflag != flag for the first point + encode_flag (flag, repeat, lastflag, flags); + } + + unsigned len_before_instrs = 2 * header.numberOfContours + 2; + unsigned len_instrs = instructions_length (); + unsigned total_len = len_before_instrs + flags.length + x_coords.length + y_coords.length; + + if (!no_hinting) + total_len += len_instrs; + + char *p = (char *) hb_calloc (total_len, sizeof (char)); + if (unlikely (!p)) return false; + + const char *src = bytes.arrayZ + GlyphHeader::static_size; + char *cur = p; + memcpy (p, src, len_before_instrs); + + cur += len_before_instrs; + src += len_before_instrs; + + if (!no_hinting) + { + memcpy (cur, src, len_instrs); + cur += len_instrs; + } + + memcpy (cur, flags.arrayZ, flags.length); + cur += flags.length; + + memcpy (cur, x_coords.arrayZ, x_coords.length); + cur += x_coords.length; + + memcpy (cur, y_coords.arrayZ, y_coords.length); + + dest_bytes = hb_bytes_t (p, total_len); + return true; + } }; diff --git a/thirdparty/harfbuzz/src/OT/glyf/SubsetGlyph.hh b/thirdparty/harfbuzz/src/OT/glyf/SubsetGlyph.hh index 7ae8fe3078..7ddefc5a91 100644 --- a/thirdparty/harfbuzz/src/OT/glyf/SubsetGlyph.hh +++ b/thirdparty/harfbuzz/src/OT/glyf/SubsetGlyph.hh @@ -6,6 +6,9 @@ namespace OT { + +struct glyf_accelerator_t; + namespace glyf_impl { @@ -55,6 +58,17 @@ struct SubsetGlyph return_trace (true); } + bool compile_bytes_with_deltas (const hb_subset_plan_t *plan, + hb_font_t *font, + const glyf_accelerator_t &glyf) + { return source_glyph.compile_bytes_with_deltas (plan, font, glyf, dest_start, dest_end); } + + void free_compiled_bytes () + { + dest_start.fini (); + dest_end.fini (); + } + void drop_hints_bytes () { source_glyph.drop_hints_bytes (dest_start, dest_end); } diff --git a/thirdparty/harfbuzz/src/OT/glyf/glyf-helpers.hh b/thirdparty/harfbuzz/src/OT/glyf/glyf-helpers.hh index f51f7a81fc..181c33d06d 100644 --- a/thirdparty/harfbuzz/src/OT/glyf/glyf-helpers.hh +++ b/thirdparty/harfbuzz/src/OT/glyf/glyf-helpers.hh @@ -16,7 +16,7 @@ template<typename IteratorIn, typename IteratorOut, hb_requires (hb_is_source_of (IteratorIn, unsigned int)), hb_requires (hb_is_sink_of (IteratorOut, unsigned))> static void -_write_loca (IteratorIn it, bool short_offsets, IteratorOut dest) +_write_loca (IteratorIn&& it, bool short_offsets, IteratorOut&& dest) { unsigned right_shift = short_offsets ? 1 : 0; unsigned int offset = 0; diff --git a/thirdparty/harfbuzz/src/OT/glyf/glyf.hh b/thirdparty/harfbuzz/src/OT/glyf/glyf.hh index bcaf44fc1e..be2cb1d0dc 100644 --- a/thirdparty/harfbuzz/src/OT/glyf/glyf.hh +++ b/thirdparty/harfbuzz/src/OT/glyf/glyf.hh @@ -24,7 +24,6 @@ namespace OT { */ #define HB_OT_TAG_glyf HB_TAG('g','l','y','f') - struct glyf { friend struct glyf_accelerator_t; @@ -75,6 +74,9 @@ struct glyf hb_vector_t<glyf_impl::SubsetGlyph> glyphs; _populate_subset_glyphs (c->plan, &glyphs); + if (!c->plan->pinned_at_default) + _compile_subset_glyphs_with_deltas (c->plan, &glyphs); + auto padded_offsets = + hb_iter (glyphs) | hb_map (&glyf_impl::SubsetGlyph::padded_size) @@ -93,6 +95,8 @@ struct glyf } + if (!c->plan->pinned_at_default) + _free_compiled_subset_glyphs (&glyphs); if (unlikely (c->serializer->in_error ())) return_trace (false); return_trace (c->serializer->check_success (glyf_impl::_add_loca_and_head (c->plan, padded_offsets, @@ -102,6 +106,16 @@ struct glyf void _populate_subset_glyphs (const hb_subset_plan_t *plan, hb_vector_t<glyf_impl::SubsetGlyph> *glyphs /* OUT */) const; + + void + _compile_subset_glyphs_with_deltas (const hb_subset_plan_t *plan, + hb_vector_t<glyf_impl::SubsetGlyph> *glyphs /* OUT */) const; + + void _free_compiled_subset_glyphs (hb_vector_t<glyf_impl::SubsetGlyph> *glyphs) const + { + for (auto _ : *glyphs) + _.free_compiled_bytes (); + } protected: UnsizedArrayOf<HBUINT8> @@ -166,7 +180,7 @@ struct glyf_accelerator_t contour_point_vector_t all_points; bool phantom_only = !consumer.is_consuming_contour_points (); - if (unlikely (!glyph_for_gid (gid).get_points (font, *this, all_points, phantom_only))) + if (unlikely (!glyph_for_gid (gid).get_points (font, *this, all_points, nullptr, true, phantom_only))) return false; if (consumer.is_consuming_contour_points ()) @@ -389,6 +403,30 @@ glyf::_populate_subset_glyphs (const hb_subset_plan_t *plan, ; } +inline void +glyf::_compile_subset_glyphs_with_deltas (const hb_subset_plan_t *plan, + hb_vector_t<glyf_impl::SubsetGlyph> *glyphs /* OUT */) const +{ + OT::glyf_accelerator_t glyf (plan->source); + hb_font_t *font = hb_font_create (plan->source); + + hb_vector_t<hb_variation_t> vars; + vars.alloc (plan->user_axes_location->get_population ()); + + for (auto _ : *plan->user_axes_location) + { + hb_variation_t var; + var.tag = _.first; + var.value = _.second; + vars.push (var); + } + + hb_font_set_variations (font, vars.arrayZ, plan->user_axes_location->get_population ()); + for (auto& subset_glyph : *glyphs) + const_cast<glyf_impl::SubsetGlyph &> (subset_glyph).compile_bytes_with_deltas (plan, font, glyf); + + hb_font_destroy (font); +} } /* namespace OT */ diff --git a/thirdparty/harfbuzz/src/graph/classdef-graph.hh b/thirdparty/harfbuzz/src/graph/classdef-graph.hh new file mode 100644 index 0000000000..0bda76ac2f --- /dev/null +++ b/thirdparty/harfbuzz/src/graph/classdef-graph.hh @@ -0,0 +1,216 @@ +/* + * Copyright © 2022 Google, Inc. + * + * This is part of HarfBuzz, a text shaping library. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and its documentation for any purpose, provided that the + * above copyright notice and the following two paragraphs appear in + * all copies of this software. + * + * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN + * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH + * DAMAGE. + * + * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, + * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * Google Author(s): Garret Rieger + */ + +#include "graph.hh" +#include "../hb-ot-layout-common.hh" + +#ifndef GRAPH_CLASSDEF_GRAPH_HH +#define GRAPH_CLASSDEF_GRAPH_HH + +namespace graph { + +struct ClassDefFormat1 : public OT::ClassDefFormat1_3<SmallTypes> +{ + bool sanitize (graph_t::vertex_t& vertex) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + constexpr unsigned min_size = OT::ClassDefFormat1_3<SmallTypes>::min_size; + if (vertex_len < min_size) return false; + return vertex_len >= min_size + classValue.get_size () - classValue.len.get_size (); + } +}; + +struct ClassDefFormat2 : public OT::ClassDefFormat2_4<SmallTypes> +{ + bool sanitize (graph_t::vertex_t& vertex) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + constexpr unsigned min_size = OT::ClassDefFormat2_4<SmallTypes>::min_size; + if (vertex_len < min_size) return false; + return vertex_len >= min_size + rangeRecord.get_size () - rangeRecord.len.get_size (); + } +}; + +struct ClassDef : public OT::ClassDef +{ + template<typename It> + static bool add_class_def (gsubgpos_graph_context_t& c, + unsigned parent_id, + unsigned link_position, + It glyph_and_class, + unsigned max_size) + { + unsigned class_def_prime_id = c.graph.new_node (nullptr, nullptr); + auto& class_def_prime_vertex = c.graph.vertices_[class_def_prime_id]; + if (!make_class_def (c, glyph_and_class, class_def_prime_id, max_size)) + return false; + + auto* class_def_link = c.graph.vertices_[parent_id].obj.real_links.push (); + class_def_link->width = SmallTypes::size; + class_def_link->objidx = class_def_prime_id; + class_def_link->position = link_position; + class_def_prime_vertex.parents.push (parent_id); + + return true; + } + + template<typename It> + static bool make_class_def (gsubgpos_graph_context_t& c, + It glyph_and_class, + unsigned dest_obj, + unsigned max_size) + { + char* buffer = (char*) hb_calloc (1, max_size); + hb_serialize_context_t serializer (buffer, max_size); + OT::ClassDef_serialize (&serializer, glyph_and_class); + serializer.end_serialize (); + if (serializer.in_error ()) + { + hb_free (buffer); + return false; + } + + hb_bytes_t class_def_copy = serializer.copy_bytes (); + c.add_buffer ((char *) class_def_copy.arrayZ); // Give ownership to the context, it will cleanup the buffer. + + auto& obj = c.graph.vertices_[dest_obj].obj; + obj.head = (char *) class_def_copy.arrayZ; + obj.tail = obj.head + class_def_copy.length; + + hb_free (buffer); + return true; + } + + bool sanitize (graph_t::vertex_t& vertex) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + if (vertex_len < OT::ClassDef::min_size) return false; + switch (u.format) + { + case 1: return ((ClassDefFormat1*)this)->sanitize (vertex); + case 2: return ((ClassDefFormat2*)this)->sanitize (vertex); +#ifndef HB_NO_BORING_EXPANSION + // Not currently supported + case 3: + case 4: +#endif + default: return false; + } + } +}; + + +struct class_def_size_estimator_t +{ + template<typename It> + class_def_size_estimator_t (It glyph_and_class) + : gids_consecutive (true), num_ranges_per_class (), glyphs_per_class () + { + unsigned last_gid = (unsigned) -1; + for (auto p : + glyph_and_class) + { + unsigned gid = p.first; + unsigned klass = p.second; + + if (last_gid != (unsigned) -1 && gid != last_gid + 1) + gids_consecutive = false; + last_gid = gid; + + hb_set_t* glyphs; + if (glyphs_per_class.has (klass, &glyphs) && glyphs) { + glyphs->add (gid); + continue; + } + + hb_set_t new_glyphs; + new_glyphs.add (gid); + glyphs_per_class.set (klass, std::move (new_glyphs)); + } + + if (in_error ()) return; + + for (unsigned klass : glyphs_per_class.keys ()) + { + if (!klass) continue; // class 0 doesn't get encoded. + + const hb_set_t& glyphs = glyphs_per_class.get (klass); + hb_codepoint_t start = HB_SET_VALUE_INVALID; + hb_codepoint_t end = HB_SET_VALUE_INVALID; + + unsigned count = 0; + while (glyphs.next_range (&start, &end)) + count++; + + num_ranges_per_class.set (klass, count); + } + } + + // Incremental increase in the Coverage and ClassDef table size + // (worst case) if all glyphs associated with 'klass' were added. + unsigned incremental_coverage_size (unsigned klass) const + { + // Coverage takes 2 bytes per glyph worst case, + return 2 * glyphs_per_class.get (klass).get_population (); + } + + // Incremental increase in the Coverage and ClassDef table size + // (worst case) if all glyphs associated with 'klass' were added. + unsigned incremental_class_def_size (unsigned klass) const + { + // ClassDef takes 6 bytes per range + unsigned class_def_2_size = 6 * num_ranges_per_class.get (klass); + if (gids_consecutive) + { + // ClassDef1 takes 2 bytes per glyph, but only can be used + // when gids are consecutive. + return hb_min (2 * glyphs_per_class.get (klass).get_population (), class_def_2_size); + } + + return class_def_2_size; + } + + bool in_error () + { + if (num_ranges_per_class.in_error ()) return true; + if (glyphs_per_class.in_error ()) return true; + + for (const hb_set_t& s : glyphs_per_class.values ()) + { + if (s.in_error ()) return true; + } + return false; + } + + private: + bool gids_consecutive; + hb_hashmap_t<unsigned, unsigned> num_ranges_per_class; + hb_hashmap_t<unsigned, hb_set_t> glyphs_per_class; +}; + + +} + +#endif // GRAPH_CLASSDEF_GRAPH_HH diff --git a/thirdparty/harfbuzz/src/graph/coverage-graph.hh b/thirdparty/harfbuzz/src/graph/coverage-graph.hh index 1d9fd0eb5b..3c1022f090 100644 --- a/thirdparty/harfbuzz/src/graph/coverage-graph.hh +++ b/thirdparty/harfbuzz/src/graph/coverage-graph.hh @@ -56,6 +56,78 @@ struct CoverageFormat2 : public OT::Layout::Common::CoverageFormat2_4<SmallTypes struct Coverage : public OT::Layout::Common::Coverage { + static Coverage* clone_coverage (gsubgpos_graph_context_t& c, + unsigned coverage_id, + unsigned new_parent_id, + unsigned link_position, + unsigned start, unsigned end) + + { + unsigned coverage_size = c.graph.vertices_[coverage_id].table_size (); + auto& coverage_v = c.graph.vertices_[coverage_id]; + Coverage* coverage_table = (Coverage*) coverage_v.obj.head; + if (!coverage_table || !coverage_table->sanitize (coverage_v)) + return nullptr; + + auto new_coverage = + + hb_zip (coverage_table->iter (), hb_range ()) + | hb_filter ([&] (hb_pair_t<unsigned, unsigned> p) { + return p.second >= start && p.second < end; + }) + | hb_map_retains_sorting (hb_first) + ; + + return add_coverage (c, new_parent_id, link_position, new_coverage, coverage_size); + } + + template<typename It> + static Coverage* add_coverage (gsubgpos_graph_context_t& c, + unsigned parent_id, + unsigned link_position, + It glyphs, + unsigned max_size) + { + unsigned coverage_prime_id = c.graph.new_node (nullptr, nullptr); + auto& coverage_prime_vertex = c.graph.vertices_[coverage_prime_id]; + if (!make_coverage (c, glyphs, coverage_prime_id, max_size)) + return nullptr; + + auto* coverage_link = c.graph.vertices_[parent_id].obj.real_links.push (); + coverage_link->width = SmallTypes::size; + coverage_link->objidx = coverage_prime_id; + coverage_link->position = link_position; + coverage_prime_vertex.parents.push (parent_id); + + return (Coverage*) coverage_prime_vertex.obj.head; + } + + template<typename It> + static bool make_coverage (gsubgpos_graph_context_t& c, + It glyphs, + unsigned dest_obj, + unsigned max_size) + { + char* buffer = (char*) hb_calloc (1, max_size); + hb_serialize_context_t serializer (buffer, max_size); + OT::Layout::Common::Coverage_serialize (&serializer, glyphs); + serializer.end_serialize (); + if (serializer.in_error ()) + { + hb_free (buffer); + return false; + } + + hb_bytes_t coverage_copy = serializer.copy_bytes (); + c.add_buffer ((char *) coverage_copy.arrayZ); // Give ownership to the context, it will cleanup the buffer. + + auto& obj = c.graph.vertices_[dest_obj].obj; + obj.head = (char *) coverage_copy.arrayZ; + obj.tail = obj.head + coverage_copy.length; + + hb_free (buffer); + return true; + } + bool sanitize (graph_t::vertex_t& vertex) const { int64_t vertex_len = vertex.obj.tail - vertex.obj.head; diff --git a/thirdparty/harfbuzz/src/graph/graph.hh b/thirdparty/harfbuzz/src/graph/graph.hh index b3aef558a2..64878a84a4 100644 --- a/thirdparty/harfbuzz/src/graph/graph.hh +++ b/thirdparty/harfbuzz/src/graph/graph.hh @@ -49,6 +49,51 @@ struct graph_t unsigned end = 0; unsigned priority = 0; + void normalize () + { + obj.real_links.qsort (); + for (auto& l : obj.real_links) + { + for (unsigned i = 0; i < l.width; i++) + { + obj.head[l.position + i] = 0; + } + } + } + + bool equals (const vertex_t& other, + const graph_t& graph, + const graph_t& other_graph, + unsigned depth) const + { + if (!(as_bytes () == other.as_bytes ())) + { + DEBUG_MSG (SUBSET_REPACK, nullptr, + "vertex [%lu] bytes != [%lu] bytes, depth = %u", + table_size (), + other.table_size (), + depth); + + auto a = as_bytes (); + auto b = other.as_bytes (); + while (a || b) + { + DEBUG_MSG (SUBSET_REPACK, nullptr, + " 0x%x %s 0x%x", *a, (*a == *b) ? "==" : "!=", *b); + a++; + b++; + } + return false; + } + + return links_equal (obj.real_links, other.obj.real_links, graph, other_graph, depth); + } + + hb_bytes_t as_bytes () const + { + return hb_bytes_t (obj.head, table_size ()); + } + friend void swap (vertex_t& a, vertex_t& b) { hb_swap (a.obj, b.obj); @@ -60,6 +105,18 @@ struct graph_t hb_swap (a.priority, b.priority); } + hb_hashmap_t<unsigned, unsigned> + position_to_index_map () const + { + hb_hashmap_t<unsigned, unsigned> result; + + for (const auto& l : obj.real_links) { + result.set (l.position, l.objidx); + } + + return result; + } + bool is_shared () const { return parents.length > 1; @@ -84,7 +141,7 @@ struct graph_t { for (unsigned i = 0; i < obj.real_links.length; i++) { - auto& link = obj.real_links[i]; + auto& link = obj.real_links.arrayZ[i]; if (link.objidx != child_index) continue; @@ -155,6 +212,57 @@ struct graph_t return -table_size; } + + private: + bool links_equal (const hb_vector_t<hb_serialize_context_t::object_t::link_t>& this_links, + const hb_vector_t<hb_serialize_context_t::object_t::link_t>& other_links, + const graph_t& graph, + const graph_t& other_graph, + unsigned depth) const + { + auto a = this_links.iter (); + auto b = other_links.iter (); + + while (a && b) + { + const auto& link_a = *a; + const auto& link_b = *b; + + if (link_a.width != link_b.width || + link_a.is_signed != link_b.is_signed || + link_a.whence != link_b.whence || + link_a.position != link_b.position || + link_a.bias != link_b.bias) + return false; + + if (!graph.vertices_[link_a.objidx].equals ( + other_graph.vertices_[link_b.objidx], graph, other_graph, depth + 1)) + return false; + + a++; + b++; + } + + if (bool (a) != bool (b)) + return false; + + return true; + } + }; + + template <typename T> + struct vertex_and_table_t + { + vertex_and_table_t () : index (0), vertex (nullptr), table (nullptr) + {} + + unsigned index; + vertex_t* vertex; + T* table; + + operator bool () { + return table && vertex; + } }; /* @@ -169,7 +277,8 @@ struct graph_t : parents_invalid (true), distance_invalid (true), positions_invalid (true), - successful (true) + successful (true), + buffers () { num_roots_for_space_.push (1); bool removed_nil = false; @@ -201,6 +310,20 @@ struct graph_t ~graph_t () { vertices_.fini (); + for (char* b : buffers) + hb_free (b); + } + + bool operator== (const graph_t& other) const + { + return root ().equals (other.root (), *this, other, 0); + } + + // Sorts links of all objects in a consistent manner and zeroes all offsets. + void normalize () + { + for (auto& v : vertices_.writer ()) + v.normalize (); } bool in_error () const @@ -228,6 +351,27 @@ struct graph_t return vertices_[i].obj; } + void add_buffer (char* buffer) + { + buffers.push (buffer); + } + + /* + * Adds a 16 bit link from parent_id to child_id + */ + template<typename T> + void add_link (T* offset, + unsigned parent_id, + unsigned child_id) + { + auto& v = vertices_[parent_id]; + auto* link = v.obj.real_links.push (); + link->width = 2; + link->objidx = child_id; + link->position = (char*) offset - (char*) v.obj.head; + vertices_[child_id].parents.push (parent_id); + } + /* * Generates a new topological sorting of graph ordered by the shortest * distance to each node if positions are marked as invalid. @@ -345,13 +489,43 @@ struct graph_t } } - unsigned index_for_offset(unsigned node_idx, const void* offset) const + template <typename T, typename ...Ts> + vertex_and_table_t<T> as_table (unsigned parent, const void* offset, Ts... ds) + { + return as_table_from_index<T> (index_for_offset (parent, offset), std::forward<Ts>(ds)...); + } + + template <typename T, typename ...Ts> + vertex_and_table_t<T> as_table_from_index (unsigned index, Ts... ds) + { + if (index >= vertices_.length) + return vertex_and_table_t<T> (); + + vertex_and_table_t<T> r; + r.vertex = &vertices_[index]; + r.table = (T*) r.vertex->obj.head; + r.index = index; + if (!r.table) + return vertex_and_table_t<T> (); + + if (!r.table->sanitize (*(r.vertex), std::forward<Ts>(ds)...)) + return vertex_and_table_t<T> (); + + return r; + } + + // Finds the object id of the object pointed to by the offset at 'offset' + // within object[node_idx]. + unsigned index_for_offset (unsigned node_idx, const void* offset) const { const auto& node = object (node_idx); if (offset < node.head || offset >= node.tail) return -1; - for (const auto& link : node.real_links) + unsigned length = node.real_links.length; + for (unsigned i = 0; i < length; i++) { + // Use direct access for increased performance, this is a hot method. + const auto& link = node.real_links.arrayZ[i]; if (offset != node.head + link.position) continue; return link.objidx; @@ -360,6 +534,24 @@ struct graph_t return -1; } + // Finds the object id of the object pointed to by the offset at 'offset' + // within object[node_idx]. Ensures that the returned object is safe to mutate. + // That is, if the original child object is shared by parents other than node_idx + // it will be duplicated and the duplicate will be returned instead. + unsigned mutable_index_for_offset (unsigned node_idx, const void* offset) + { + unsigned child_idx = index_for_offset (node_idx, offset); + auto& child = vertices_[child_idx]; + for (unsigned p : child.parents) + { + if (p != node_idx) { + return duplicate (node_idx, child_idx); + } + } + + return child_idx; + } + /* * Assign unique space numbers to each connected subgraph of 24 bit and/or 32 bit offset(s). @@ -1039,6 +1231,7 @@ struct graph_t bool positions_invalid; bool successful; hb_vector_t<unsigned> num_roots_for_space_; + hb_vector_t<char*> buffers; }; } diff --git a/thirdparty/harfbuzz/src/graph/gsubgpos-context.cc b/thirdparty/harfbuzz/src/graph/gsubgpos-context.cc index e0ff6ff85f..b2044426d4 100644 --- a/thirdparty/harfbuzz/src/graph/gsubgpos-context.cc +++ b/thirdparty/harfbuzz/src/graph/gsubgpos-context.cc @@ -33,8 +33,7 @@ gsubgpos_graph_context_t::gsubgpos_graph_context_t (hb_tag_t table_tag_, : table_tag (table_tag_), graph (graph_), lookup_list_index (0), - lookups (), - buffers () + lookups () { if (table_tag_ != HB_OT_TAG_GPOS && table_tag_ != HB_OT_TAG_GSUB) @@ -53,7 +52,7 @@ unsigned gsubgpos_graph_context_t::create_node (unsigned size) if (!buffer) return -1; - buffers.push (buffer); + add_buffer (buffer); return graph.new_node (buffer, buffer + size); } diff --git a/thirdparty/harfbuzz/src/graph/gsubgpos-context.hh b/thirdparty/harfbuzz/src/graph/gsubgpos-context.hh index 49b24198ff..9fe9662e64 100644 --- a/thirdparty/harfbuzz/src/graph/gsubgpos-context.hh +++ b/thirdparty/harfbuzz/src/graph/gsubgpos-context.hh @@ -40,22 +40,16 @@ struct gsubgpos_graph_context_t graph_t& graph; unsigned lookup_list_index; hb_hashmap_t<unsigned, graph::Lookup*> lookups; - hb_vector_t<char*> buffers; + HB_INTERNAL gsubgpos_graph_context_t (hb_tag_t table_tag_, graph_t& graph_); - ~gsubgpos_graph_context_t () - { - for (char* b : buffers) - hb_free (b); - } - HB_INTERNAL unsigned create_node (unsigned size); void add_buffer (char* buffer) { - buffers.push (buffer); + graph.add_buffer (buffer); } private: diff --git a/thirdparty/harfbuzz/src/graph/gsubgpos-graph.hh b/thirdparty/harfbuzz/src/graph/gsubgpos-graph.hh index afa1152c44..a93e7d1c73 100644 --- a/thirdparty/harfbuzz/src/graph/gsubgpos-graph.hh +++ b/thirdparty/harfbuzz/src/graph/gsubgpos-graph.hh @@ -29,6 +29,7 @@ #include "../OT/Layout/GSUB/ExtensionSubst.hh" #include "gsubgpos-context.hh" #include "pairpos-graph.hh" +#include "markbasepos-graph.hh" #ifndef GRAPH_GSUBGPOS_GRAPH_HH #define GRAPH_GSUBGPOS_GRAPH_HH @@ -121,10 +122,12 @@ struct Lookup : public OT::Lookup if (c.table_tag != HB_OT_TAG_GPOS) return true; - if (!is_ext && type != OT::Layout::GPOS_impl::PosLookupSubTable::Type::Pair) + if (!is_ext && + type != OT::Layout::GPOS_impl::PosLookupSubTable::Type::Pair && + type != OT::Layout::GPOS_impl::PosLookupSubTable::Type::MarkBase) return true; - hb_vector_t<unsigned> all_new_subtables; + hb_vector_t<hb_pair_t<unsigned, hb_vector_t<unsigned>>> all_new_subtables; for (unsigned i = 0; i < subTable.len; i++) { unsigned subtable_index = c.graph.index_for_offset (this_index, &subTable[i]); @@ -133,39 +136,66 @@ struct Lookup : public OT::Lookup ExtensionFormat1<OT::Layout::GSUB_impl::ExtensionSubst>* extension = (ExtensionFormat1<OT::Layout::GSUB_impl::ExtensionSubst>*) c.graph.object (ext_subtable_index).head; - if (!extension->sanitize (c.graph.vertices_[ext_subtable_index])) + if (!extension || !extension->sanitize (c.graph.vertices_[ext_subtable_index])) continue; subtable_index = extension->get_subtable_index (c.graph, ext_subtable_index); type = extension->get_lookup_type (); - if (type != OT::Layout::GPOS_impl::PosLookupSubTable::Type::Pair) + if (type != OT::Layout::GPOS_impl::PosLookupSubTable::Type::Pair + && type != OT::Layout::GPOS_impl::PosLookupSubTable::Type::MarkBase) continue; } - PairPos* pairPos = (PairPos*) c.graph.object (subtable_index).head; - if (!pairPos->sanitize (c.graph.vertices_[subtable_index])) continue; - - hb_vector_t<unsigned> new_sub_tables = pairPos->split_subtables (c, subtable_index); + hb_vector_t<unsigned> new_sub_tables; + switch (type) + { + case 2: + new_sub_tables = split_subtable<PairPos> (c, subtable_index); break; + case 4: + new_sub_tables = split_subtable<MarkBasePos> (c, subtable_index); break; + default: + break; + } if (new_sub_tables.in_error ()) return false; - + new_sub_tables.iter() | hb_sink (all_new_subtables); + if (!new_sub_tables) continue; + hb_pair_t<unsigned, hb_vector_t<unsigned>>* entry = all_new_subtables.push (); + entry->first = i; + entry->second = std::move (new_sub_tables); } - if (all_new_subtables) + if (all_new_subtables) { add_sub_tables (c, this_index, type, all_new_subtables); + } return true; } + template<typename T> + hb_vector_t<unsigned> split_subtable (gsubgpos_graph_context_t& c, + unsigned objidx) + { + T* sub_table = (T*) c.graph.object (objidx).head; + if (!sub_table || !sub_table->sanitize (c.graph.vertices_[objidx])) + return hb_vector_t<unsigned> (); + + return sub_table->split_subtables (c, objidx); + } + void add_sub_tables (gsubgpos_graph_context_t& c, unsigned this_index, unsigned type, - hb_vector_t<unsigned>& subtable_indices) + hb_vector_t<hb_pair_t<unsigned, hb_vector_t<unsigned>>>& subtable_ids) { bool is_ext = is_extension (c.table_tag); auto& v = c.graph.vertices_[this_index]; + fix_existing_subtable_links (c, this_index, subtable_ids); + + unsigned new_subtable_count = 0; + for (const auto& p : subtable_ids) + new_subtable_count += p.second.length; size_t new_size = v.table_size () - + subtable_indices.length * OT::Offset16::static_size; + + new_subtable_count * OT::Offset16::static_size; char* buffer = (char*) hb_calloc (1, new_size); c.add_buffer (buffer); memcpy (buffer, v.obj.head, v.table_size()); @@ -175,30 +205,61 @@ struct Lookup : public OT::Lookup Lookup* new_lookup = (Lookup*) buffer; - new_lookup->subTable.len = subTable.len + subtable_indices.length; - unsigned offset_index = subTable.len; - for (unsigned subtable_id : subtable_indices) + unsigned shift = 0; + new_lookup->subTable.len = subTable.len + new_subtable_count; + for (const auto& p : subtable_ids) { - if (is_ext) + unsigned offset_index = p.first + shift + 1; + shift += p.second.length; + + for (unsigned subtable_id : p.second) { - unsigned ext_id = create_extension_subtable (c, subtable_id, type); - c.graph.vertices_[subtable_id].parents.push (ext_id); - subtable_id = ext_id; + if (is_ext) + { + unsigned ext_id = create_extension_subtable (c, subtable_id, type); + c.graph.vertices_[subtable_id].parents.push (ext_id); + subtable_id = ext_id; + } + + auto* link = v.obj.real_links.push (); + link->width = 2; + link->objidx = subtable_id; + link->position = (char*) &new_lookup->subTable[offset_index++] - + (char*) new_lookup; + c.graph.vertices_[subtable_id].parents.push (this_index); } - - auto* link = v.obj.real_links.push (); - link->width = 2; - link->objidx = subtable_id; - link->position = (char*) &new_lookup->subTable[offset_index++] - - (char*) new_lookup; - c.graph.vertices_[subtable_id].parents.push (this_index); } + // Repacker sort order depends on link order, which we've messed up so resort it. + v.obj.real_links.qsort (); + // The head location of the lookup has changed, invalidating the lookups map entry // in the context. Update the map. c.lookups.set (this_index, new_lookup); } + void fix_existing_subtable_links (gsubgpos_graph_context_t& c, + unsigned this_index, + hb_vector_t<hb_pair_t<unsigned, hb_vector_t<unsigned>>>& subtable_ids) + { + auto& v = c.graph.vertices_[this_index]; + Lookup* lookup = (Lookup*) v.obj.head; + + unsigned shift = 0; + for (const auto& p : subtable_ids) + { + unsigned insert_index = p.first + shift; + unsigned pos_offset = p.second.length * OT::Offset16::static_size; + unsigned insert_offset = (char*) &lookup->subTable[insert_index] - (char*) lookup; + shift += p.second.length; + + for (auto& l : v.obj.all_links_writer ()) + { + if (l.position > insert_offset) l.position += pos_offset; + } + } + } + unsigned create_extension_subtable (gsubgpos_graph_context_t& c, unsigned subtable_index, unsigned type) @@ -281,7 +342,7 @@ struct GSTAR : public OT::GSUBGPOS const auto& r = graph.root (); GSTAR* gstar = (GSTAR*) r.obj.head; - if (!gstar->sanitize (r)) + if (!gstar || !gstar->sanitize (r)) return nullptr; return gstar; @@ -327,17 +388,16 @@ struct GSTAR : public OT::GSUBGPOS hb_hashmap_t<unsigned, Lookup*>& lookups /* OUT */) { unsigned lookup_list_idx = get_lookup_list_index (graph); - const LookupList<Types>* lookupList = (const LookupList<Types>*) graph.object (lookup_list_idx).head; - if (!lookupList->sanitize (graph.vertices_[lookup_list_idx])) + if (!lookupList || !lookupList->sanitize (graph.vertices_[lookup_list_idx])) return; for (unsigned i = 0; i < lookupList->len; i++) { unsigned lookup_idx = graph.index_for_offset (lookup_list_idx, &(lookupList->arrayZ[i])); Lookup* lookup = (Lookup*) graph.object (lookup_idx).head; - if (!lookup->sanitize (graph.vertices_[lookup_idx])) continue; + if (!lookup || !lookup->sanitize (graph.vertices_[lookup_idx])) continue; lookups.set (lookup_idx, lookup); } } diff --git a/thirdparty/harfbuzz/src/graph/markbasepos-graph.hh b/thirdparty/harfbuzz/src/graph/markbasepos-graph.hh new file mode 100644 index 0000000000..56fa812406 --- /dev/null +++ b/thirdparty/harfbuzz/src/graph/markbasepos-graph.hh @@ -0,0 +1,507 @@ +/* + * Copyright © 2022 Google, Inc. + * + * This is part of HarfBuzz, a text shaping library. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and its documentation for any purpose, provided that the + * above copyright notice and the following two paragraphs appear in + * all copies of this software. + * + * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN + * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH + * DAMAGE. + * + * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, + * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * Google Author(s): Garret Rieger + */ + +#ifndef GRAPH_MARKBASEPOS_GRAPH_HH +#define GRAPH_MARKBASEPOS_GRAPH_HH + +#include "split-helpers.hh" +#include "coverage-graph.hh" +#include "../OT/Layout/GPOS/MarkBasePos.hh" +#include "../OT/Layout/GPOS/PosLookupSubTable.hh" + +namespace graph { + +struct AnchorMatrix : public OT::Layout::GPOS_impl::AnchorMatrix +{ + bool sanitize (graph_t::vertex_t& vertex, unsigned class_count) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + if (vertex_len < AnchorMatrix::min_size) return false; + + return vertex_len >= AnchorMatrix::min_size + + OT::Offset16::static_size * class_count * this->rows; + } + + bool shrink (gsubgpos_graph_context_t& c, + unsigned this_index, + unsigned old_class_count, + unsigned new_class_count) + { + if (new_class_count >= old_class_count) return false; + auto& o = c.graph.vertices_[this_index].obj; + unsigned base_count = rows; + o.tail = o.head + + AnchorMatrix::min_size + + OT::Offset16::static_size * base_count * new_class_count; + + // Reposition links into the new indexing scheme. + for (auto& link : o.real_links.writer ()) + { + unsigned index = (link.position - 2) / 2; + unsigned base = index / old_class_count; + unsigned klass = index % old_class_count; + if (klass >= new_class_count) + // should have already been removed + return false; + + unsigned new_index = base * new_class_count + klass; + + link.position = (char*) &(this->matrixZ[new_index]) - (char*) this; + } + + return true; + } + + unsigned clone (gsubgpos_graph_context_t& c, + unsigned this_index, + unsigned start, + unsigned end, + unsigned class_count) + { + unsigned base_count = rows; + unsigned new_class_count = end - start; + unsigned size = AnchorMatrix::min_size + + OT::Offset16::static_size * new_class_count * rows; + unsigned prime_id = c.create_node (size); + if (prime_id == (unsigned) -1) return -1; + AnchorMatrix* prime = (AnchorMatrix*) c.graph.object (prime_id).head; + prime->rows = base_count; + + auto& o = c.graph.vertices_[this_index].obj; + int num_links = o.real_links.length; + for (int i = 0; i < num_links; i++) + { + const auto& link = o.real_links[i]; + unsigned old_index = (link.position - 2) / OT::Offset16::static_size; + unsigned klass = old_index % class_count; + if (klass < start || klass >= end) continue; + + unsigned base = old_index / class_count; + unsigned new_klass = klass - start; + unsigned new_index = base * new_class_count + new_klass; + + + unsigned child_idx = link.objidx; + c.graph.add_link (&(prime->matrixZ[new_index]), + prime_id, + child_idx); + + auto& child = c.graph.vertices_[child_idx]; + child.remove_parent (this_index); + + o.real_links.remove (i); + num_links--; + i--; + } + + return prime_id; + } +}; + +struct MarkArray : public OT::Layout::GPOS_impl::MarkArray +{ + bool sanitize (graph_t::vertex_t& vertex) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + unsigned min_size = MarkArray::min_size; + if (vertex_len < min_size) return false; + + return vertex_len >= get_size (); + } + + bool shrink (gsubgpos_graph_context_t& c, + const hb_hashmap_t<unsigned, unsigned>& mark_array_links, + unsigned this_index, + unsigned new_class_count) + { + auto& o = c.graph.vertices_[this_index].obj; + for (const auto& link : o.real_links) + c.graph.vertices_[link.objidx].remove_parent (this_index); + o.real_links.reset (); + + unsigned new_index = 0; + for (const auto& record : this->iter ()) + { + unsigned klass = record.klass; + if (klass >= new_class_count) continue; + + (*this)[new_index].klass = klass; + unsigned position = (char*) &record.markAnchor - (char*) this; + unsigned* objidx; + if (!mark_array_links.has (position, &objidx)) + { + new_index++; + continue; + } + + c.graph.add_link (&(*this)[new_index].markAnchor, this_index, *objidx); + new_index++; + } + + this->len = new_index; + o.tail = o.head + MarkArray::min_size + + OT::Layout::GPOS_impl::MarkRecord::static_size * new_index; + return true; + } + + unsigned clone (gsubgpos_graph_context_t& c, + unsigned this_index, + const hb_hashmap_t<unsigned, unsigned>& pos_to_index, + hb_set_t& marks, + unsigned start_class) + { + unsigned size = MarkArray::min_size + + OT::Layout::GPOS_impl::MarkRecord::static_size * + marks.get_population (); + unsigned prime_id = c.create_node (size); + if (prime_id == (unsigned) -1) return -1; + MarkArray* prime = (MarkArray*) c.graph.object (prime_id).head; + prime->len = marks.get_population (); + + + unsigned i = 0; + for (hb_codepoint_t mark : marks) + { + (*prime)[i].klass = (*this)[mark].klass - start_class; + unsigned offset_pos = (char*) &((*this)[mark].markAnchor) - (char*) this; + unsigned* anchor_index; + if (pos_to_index.has (offset_pos, &anchor_index)) + c.graph.move_child (this_index, + &((*this)[mark].markAnchor), + prime_id, + &((*prime)[i].markAnchor)); + + i++; + } + + return prime_id; + } +}; + +struct MarkBasePosFormat1 : public OT::Layout::GPOS_impl::MarkBasePosFormat1_2<SmallTypes> +{ + bool sanitize (graph_t::vertex_t& vertex) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + return vertex_len >= MarkBasePosFormat1::static_size; + } + + hb_vector_t<unsigned> split_subtables (gsubgpos_graph_context_t& c, unsigned this_index) + { + hb_set_t visited; + + const unsigned base_coverage_id = c.graph.index_for_offset (this_index, &baseCoverage); + const unsigned base_size = + OT::Layout::GPOS_impl::PairPosFormat1_3<SmallTypes>::min_size + + MarkArray::min_size + + AnchorMatrix::min_size + + c.graph.vertices_[base_coverage_id].table_size (); + + hb_vector_t<class_info_t> class_to_info = get_class_info (c, this_index); + + unsigned class_count = classCount; + auto base_array = c.graph.as_table<AnchorMatrix> (this_index, + &baseArray, + class_count); + if (!base_array) return hb_vector_t<unsigned> (); + unsigned base_count = base_array.table->rows; + + unsigned partial_coverage_size = 4; + unsigned accumulated = base_size; + hb_vector_t<unsigned> split_points; + + for (unsigned klass = 0; klass < class_count; klass++) + { + class_info_t& info = class_to_info[klass]; + partial_coverage_size += OT::HBUINT16::static_size * info.marks.get_population (); + unsigned accumulated_delta = + OT::Layout::GPOS_impl::MarkRecord::static_size * info.marks.get_population () + + OT::Offset16::static_size * base_count; + + for (unsigned objidx : info.child_indices) + accumulated_delta += c.graph.find_subgraph_size (objidx, visited); + + accumulated += accumulated_delta; + unsigned total = accumulated + partial_coverage_size; + + if (total >= (1 << 16)) + { + split_points.push (klass); + accumulated = base_size + accumulated_delta; + partial_coverage_size = 4 + OT::HBUINT16::static_size * info.marks.get_population (); + visited.clear (); // node sharing isn't allowed between splits. + } + } + + + const unsigned mark_array_id = c.graph.index_for_offset (this_index, &markArray); + split_context_t split_context { + c, + this, + this_index, + std::move (class_to_info), + c.graph.vertices_[mark_array_id].position_to_index_map (), + }; + + return actuate_subtable_split<split_context_t> (split_context, split_points); + } + + private: + + struct class_info_t { + hb_set_t marks; + hb_vector_t<unsigned> child_indices; + }; + + struct split_context_t { + gsubgpos_graph_context_t& c; + MarkBasePosFormat1* thiz; + unsigned this_index; + hb_vector_t<class_info_t> class_to_info; + hb_hashmap_t<unsigned, unsigned> mark_array_links; + + hb_set_t marks_for (unsigned start, unsigned end) + { + hb_set_t marks; + for (unsigned klass = start; klass < end; klass++) + { + + class_to_info[klass].marks.iter () + | hb_sink (marks) + ; + } + return marks; + } + + unsigned original_count () + { + return thiz->classCount; + } + + unsigned clone_range (unsigned start, unsigned end) + { + return thiz->clone_range (*this, this->this_index, start, end); + } + + bool shrink (unsigned count) + { + return thiz->shrink (*this, this->this_index, count); + } + }; + + hb_vector_t<class_info_t> get_class_info (gsubgpos_graph_context_t& c, + unsigned this_index) + { + hb_vector_t<class_info_t> class_to_info; + + unsigned class_count= classCount; + class_to_info.resize (class_count); + + auto mark_array = c.graph.as_table<MarkArray> (this_index, &markArray); + if (!mark_array) return hb_vector_t<class_info_t> (); + unsigned mark_count = mark_array.table->len; + for (unsigned mark = 0; mark < mark_count; mark++) + { + unsigned klass = (*mark_array.table)[mark].get_class (); + class_to_info[klass].marks.add (mark); + } + + for (const auto& link : mark_array.vertex->obj.real_links) + { + unsigned mark = (link.position - 2) / + OT::Layout::GPOS_impl::MarkRecord::static_size; + unsigned klass = (*mark_array.table)[mark].get_class (); + class_to_info[klass].child_indices.push (link.objidx); + } + + unsigned base_array_id = + c.graph.index_for_offset (this_index, &baseArray); + auto& base_array_v = c.graph.vertices_[base_array_id]; + + for (const auto& link : base_array_v.obj.real_links) + { + unsigned index = (link.position - 2) / OT::Offset16::static_size; + unsigned klass = index % class_count; + class_to_info[klass].child_indices.push (link.objidx); + } + + return class_to_info; + } + + bool shrink (split_context_t& sc, + unsigned this_index, + unsigned count) + { + DEBUG_MSG (SUBSET_REPACK, nullptr, + " Shrinking MarkBasePosFormat1 (%u) to [0, %u).", + this_index, + count); + + unsigned old_count = classCount; + if (count >= old_count) + return true; + + classCount = count; + + auto mark_coverage = sc.c.graph.as_table<Coverage> (this_index, + &markCoverage); + if (!mark_coverage) return false; + hb_set_t marks = sc.marks_for (0, count); + auto new_coverage = + + hb_zip (hb_range (), mark_coverage.table->iter ()) + | hb_filter (marks, hb_first) + | hb_map_retains_sorting (hb_second) + ; + if (!Coverage::make_coverage (sc.c, + new_coverage, + mark_coverage.index, + 4 + 2 * marks.get_population ())) + return false; + + + auto base_array = sc.c.graph.as_table<AnchorMatrix> (this_index, + &baseArray, + old_count); + if (!base_array || !base_array.table->shrink (sc.c, + base_array.index, + old_count, + count)) + return false; + + auto mark_array = sc.c.graph.as_table<MarkArray> (this_index, + &markArray); + if (!mark_array || !mark_array.table->shrink (sc.c, + sc.mark_array_links, + mark_array.index, + count)) + return false; + + return true; + } + + // Create a new MarkBasePos that has all of the data for classes from [start, end). + unsigned clone_range (split_context_t& sc, + unsigned this_index, + unsigned start, unsigned end) const + { + DEBUG_MSG (SUBSET_REPACK, nullptr, + " Cloning MarkBasePosFormat1 (%u) range [%u, %u).", this_index, start, end); + + graph_t& graph = sc.c.graph; + unsigned prime_size = OT::Layout::GPOS_impl::MarkBasePosFormat1_2<SmallTypes>::static_size; + + unsigned prime_id = sc.c.create_node (prime_size); + if (prime_id == (unsigned) -1) return -1; + + MarkBasePosFormat1* prime = (MarkBasePosFormat1*) graph.object (prime_id).head; + prime->format = this->format; + unsigned new_class_count = end - start; + prime->classCount = new_class_count; + + unsigned base_coverage_id = + graph.index_for_offset (sc.this_index, &baseCoverage); + graph.add_link (&(prime->baseCoverage), prime_id, base_coverage_id); + graph.duplicate (prime_id, base_coverage_id); + + auto mark_coverage = sc.c.graph.as_table<Coverage> (this_index, + &markCoverage); + if (!mark_coverage) return false; + hb_set_t marks = sc.marks_for (start, end); + auto new_coverage = + + hb_zip (hb_range (), mark_coverage.table->iter ()) + | hb_filter (marks, hb_first) + | hb_map_retains_sorting (hb_second) + ; + if (!Coverage::add_coverage (sc.c, + prime_id, + 2, + + new_coverage, + marks.get_population () * 2 + 4)) + return -1; + + auto mark_array = + graph.as_table <MarkArray> (sc.this_index, &markArray); + if (!mark_array) return -1; + unsigned new_mark_array = + mark_array.table->clone (sc.c, + mark_array.index, + sc.mark_array_links, + marks, + start); + graph.add_link (&(prime->markArray), prime_id, new_mark_array); + + unsigned class_count = classCount; + auto base_array = + graph.as_table<AnchorMatrix> (sc.this_index, &baseArray, class_count); + if (!base_array) return -1; + unsigned new_base_array = + base_array.table->clone (sc.c, + base_array.index, + start, end, this->classCount); + graph.add_link (&(prime->baseArray), prime_id, new_base_array); + + return prime_id; + } +}; + + +struct MarkBasePos : public OT::Layout::GPOS_impl::MarkBasePos +{ + hb_vector_t<unsigned> split_subtables (gsubgpos_graph_context_t& c, + unsigned this_index) + { + switch (u.format) { + case 1: + return ((MarkBasePosFormat1*)(&u.format1))->split_subtables (c, this_index); +#ifndef HB_NO_BORING_EXPANSION + case 2: HB_FALLTHROUGH; + // Don't split 24bit PairPos's. +#endif + default: + return hb_vector_t<unsigned> (); + } + } + + bool sanitize (graph_t::vertex_t& vertex) const + { + int64_t vertex_len = vertex.obj.tail - vertex.obj.head; + if (vertex_len < u.format.get_size ()) return false; + + switch (u.format) { + case 1: + return ((MarkBasePosFormat1*)(&u.format1))->sanitize (vertex); +#ifndef HB_NO_BORING_EXPANSION + case 2: HB_FALLTHROUGH; +#endif + default: + // We don't handle format 3 and 4 here. + return false; + } + } +}; + + +} + +#endif // GRAPH_MARKBASEPOS_GRAPH_HH diff --git a/thirdparty/harfbuzz/src/graph/pairpos-graph.hh b/thirdparty/harfbuzz/src/graph/pairpos-graph.hh index 3ca4fc701c..976b872329 100644 --- a/thirdparty/harfbuzz/src/graph/pairpos-graph.hh +++ b/thirdparty/harfbuzz/src/graph/pairpos-graph.hh @@ -27,7 +27,9 @@ #ifndef GRAPH_PAIRPOS_GRAPH_HH #define GRAPH_PAIRPOS_GRAPH_HH +#include "split-helpers.hh" #include "coverage-graph.hh" +#include "classdef-graph.hh" #include "../OT/Layout/GPOS/PairPos.hh" #include "../OT/Layout/GPOS/PosLookupSubTable.hh" @@ -51,68 +53,62 @@ struct PairPosFormat1 : public OT::Layout::GPOS_impl::PairPosFormat1_3<SmallType const unsigned coverage_id = c.graph.index_for_offset (this_index, &coverage); const unsigned coverage_size = c.graph.vertices_[coverage_id].table_size (); - const unsigned base_size = OT::Layout::GPOS_impl::PairPosFormat1_3<SmallTypes>::min_size - + coverage_size; + const unsigned base_size = OT::Layout::GPOS_impl::PairPosFormat1_3<SmallTypes>::min_size; + unsigned partial_coverage_size = 4; unsigned accumulated = base_size; hb_vector_t<unsigned> split_points; for (unsigned i = 0; i < pairSet.len; i++) { unsigned pair_set_index = pair_set_graph_index (c, this_index, i); - accumulated += c.graph.find_subgraph_size (pair_set_index, visited); - accumulated += SmallTypes::size; // for PairSet offset. + unsigned accumulated_delta = + c.graph.find_subgraph_size (pair_set_index, visited) + + SmallTypes::size; // for PairSet offset. + partial_coverage_size += OT::HBUINT16::static_size; - // TODO(garretrieger): don't count the size of the largest pairset against the limit, since - // it will be packed last in the order and does not contribute to - // the 64kb limit. + accumulated += accumulated_delta; + unsigned total = accumulated + hb_min (partial_coverage_size, coverage_size); - if (accumulated > (1 << 16)) + if (total >= (1 << 16)) { split_points.push (i); - accumulated = base_size; - visited.clear (); // Pretend node sharing isn't allowed between splits. + accumulated = base_size + accumulated_delta; + partial_coverage_size = 6; + visited.clear (); // node sharing isn't allowed between splits. } } - return do_split (c, this_index, split_points); + split_context_t split_context { + c, + this, + this_index, + }; + + return actuate_subtable_split<split_context_t> (split_context, split_points); } private: - // Split this PairPos into two or more PairPos's. split_points defines - // the indices (first index to include in the new table) to split at. - // Returns the object id's of the newly created PairPos subtables. - hb_vector_t<unsigned> do_split (gsubgpos_graph_context_t& c, - unsigned this_index, - const hb_vector_t<unsigned> split_points) - { - hb_vector_t<unsigned> new_objects; - if (!split_points) - return new_objects; + struct split_context_t { + gsubgpos_graph_context_t& c; + PairPosFormat1* thiz; + unsigned this_index; - for (unsigned i = 0; i < split_points.length; i++) + unsigned original_count () { - unsigned start = split_points[i]; - unsigned end = (i < split_points.length - 1) ? split_points[i + 1] : pairSet.len; - unsigned id = clone_range (c, this_index, start, end); - - if (id == (unsigned) -1) - { - new_objects.reset (); - new_objects.allocated = -1; // mark error - return new_objects; - } - new_objects.push (id); + return thiz->pairSet.len; } - if (!shrink (c, this_index, split_points[0])) + unsigned clone_range (unsigned start, unsigned end) { - new_objects.reset (); - new_objects.allocated = -1; // mark error + return thiz->clone_range (this->c, this->this_index, start, end); } - return new_objects; - } + bool shrink (unsigned count) + { + return thiz->shrink (this->c, this->this_index, count); + } + }; bool shrink (gsubgpos_graph_context_t& c, unsigned this_index, @@ -129,11 +125,12 @@ struct PairPosFormat1 : public OT::Layout::GPOS_impl::PairPosFormat1_3<SmallType pairSet.len = count; c.graph.vertices_[this_index].obj.tail -= (old_count - count) * SmallTypes::size; - unsigned coverage_id = c.graph.index_for_offset (this_index, &coverage); + unsigned coverage_id = c.graph.mutable_index_for_offset (this_index, &coverage); unsigned coverage_size = c.graph.vertices_[coverage_id].table_size (); auto& coverage_v = c.graph.vertices_[coverage_id]; + Coverage* coverage_table = (Coverage*) coverage_v.obj.head; - if (!coverage_table->sanitize (coverage_v)) + if (!coverage_table || !coverage_table->sanitize (coverage_v)) return false; auto new_coverage = @@ -144,7 +141,7 @@ struct PairPosFormat1 : public OT::Layout::GPOS_impl::PairPosFormat1_3<SmallType | hb_map_retains_sorting (hb_first) ; - return make_coverage (c, new_coverage, coverage_id, coverage_size); + return Coverage::make_coverage (c, new_coverage, coverage_id, coverage_size); } // Create a new PairPos including PairSet's from start (inclusive) to end (exclusive). @@ -178,79 +175,431 @@ struct PairPosFormat1 : public OT::Layout::GPOS_impl::PairPosFormat1_3<SmallType } unsigned coverage_id = c.graph.index_for_offset (this_index, &coverage); - unsigned coverage_size = c.graph.vertices_[coverage_id].table_size (); - auto& coverage_v = c.graph.vertices_[coverage_id]; - Coverage* coverage_table = (Coverage*) coverage_v.obj.head; - if (!coverage_table->sanitize (coverage_v)) - return false; + if (!Coverage::clone_coverage (c, + coverage_id, + pair_pos_prime_id, + 2, + start, end)) + return -1; - auto new_coverage = - + hb_zip (coverage_table->iter (), hb_range ()) - | hb_filter ([&] (hb_pair_t<unsigned, unsigned> p) { - return p.second >= start && p.second < end; + return pair_pos_prime_id; + } + + + + unsigned pair_set_graph_index (gsubgpos_graph_context_t& c, unsigned this_index, unsigned i) const + { + return c.graph.index_for_offset (this_index, &pairSet[i]); + } +}; + +struct PairPosFormat2 : public OT::Layout::GPOS_impl::PairPosFormat2_4<SmallTypes> +{ + bool sanitize (graph_t::vertex_t& vertex) const + { + size_t vertex_len = vertex.table_size (); + unsigned min_size = OT::Layout::GPOS_impl::PairPosFormat2_4<SmallTypes>::min_size; + if (vertex_len < min_size) return false; + + const unsigned class1_count = class1Count; + return vertex_len >= + min_size + class1_count * get_class1_record_size (); + } + + hb_vector_t<unsigned> split_subtables (gsubgpos_graph_context_t& c, unsigned this_index) + { + const unsigned base_size = OT::Layout::GPOS_impl::PairPosFormat2_4<SmallTypes>::min_size; + const unsigned class_def_2_size = size_of (c, this_index, &classDef2); + const Coverage* coverage = get_coverage (c, this_index); + const ClassDef* class_def_1 = get_class_def_1 (c, this_index); + auto gid_and_class = + + coverage->iter () + | hb_map_retains_sorting ([&] (hb_codepoint_t gid) { + return hb_pair_t<hb_codepoint_t, hb_codepoint_t> (gid, class_def_1->get_class (gid)); }) - | hb_map_retains_sorting (hb_first) ; + class_def_size_estimator_t estimator (gid_and_class); + + const unsigned class1_count = class1Count; + const unsigned class2_count = class2Count; + const unsigned class1_record_size = get_class1_record_size (); - unsigned coverage_prime_id = c.graph.new_node (nullptr, nullptr); - auto& coverage_prime_vertex = c.graph.vertices_[coverage_prime_id]; - if (!make_coverage (c, new_coverage, coverage_prime_id, coverage_size)) + const unsigned value_1_len = valueFormat1.get_len (); + const unsigned value_2_len = valueFormat2.get_len (); + const unsigned total_value_len = value_1_len + value_2_len; + + unsigned accumulated = base_size; + unsigned coverage_size = 4; + unsigned class_def_1_size = 4; + unsigned max_coverage_size = coverage_size; + unsigned max_class_def_1_size = class_def_1_size; + + hb_vector_t<unsigned> split_points; + + hb_hashmap_t<unsigned, unsigned> device_tables = get_all_device_tables (c, this_index); + hb_vector_t<unsigned> format1_device_table_indices = valueFormat1.get_device_table_indices (); + hb_vector_t<unsigned> format2_device_table_indices = valueFormat2.get_device_table_indices (); + bool has_device_tables = bool(format1_device_table_indices) || bool(format2_device_table_indices); + + hb_set_t visited; + for (unsigned i = 0; i < class1_count; i++) + { + unsigned accumulated_delta = class1_record_size; + coverage_size += estimator.incremental_coverage_size (i); + class_def_1_size += estimator.incremental_class_def_size (i); + max_coverage_size = hb_max (max_coverage_size, coverage_size); + max_class_def_1_size = hb_max (max_class_def_1_size, class_def_1_size); + + if (has_device_tables) { + for (unsigned j = 0; j < class2_count; j++) + { + unsigned value1_index = total_value_len * (class2_count * i + j); + unsigned value2_index = value1_index + value_1_len; + accumulated_delta += size_of_value_record_children (c, + device_tables, + format1_device_table_indices, + value1_index, + visited); + accumulated_delta += size_of_value_record_children (c, + device_tables, + format2_device_table_indices, + value2_index, + visited); + } + } + + accumulated += accumulated_delta; + unsigned total = accumulated + + coverage_size + class_def_1_size + class_def_2_size + // The largest object will pack last and can exceed the size limit. + - hb_max (hb_max (coverage_size, class_def_1_size), class_def_2_size); + if (total >= (1 << 16)) + { + split_points.push (i); + // split does not include i, so add the size for i when we reset the size counters. + accumulated = base_size + accumulated_delta; + coverage_size = 4 + estimator.incremental_coverage_size (i); + class_def_1_size = 4 + estimator.incremental_class_def_size (i); + visited.clear (); // node sharing isn't allowed between splits. + } + } + + split_context_t split_context { + c, + this, + this_index, + class1_record_size, + total_value_len, + value_1_len, + value_2_len, + max_coverage_size, + max_class_def_1_size, + device_tables, + format1_device_table_indices, + format2_device_table_indices + }; + + return actuate_subtable_split<split_context_t> (split_context, split_points); + } + private: + + struct split_context_t + { + gsubgpos_graph_context_t& c; + PairPosFormat2* thiz; + unsigned this_index; + unsigned class1_record_size; + unsigned value_record_len; + unsigned value1_record_len; + unsigned value2_record_len; + unsigned max_coverage_size; + unsigned max_class_def_size; + + const hb_hashmap_t<unsigned, unsigned>& device_tables; + const hb_vector_t<unsigned>& format1_device_table_indices; + const hb_vector_t<unsigned>& format2_device_table_indices; + + unsigned original_count () + { + return thiz->class1Count; + } + + unsigned clone_range (unsigned start, unsigned end) + { + return thiz->clone_range (*this, start, end); + } + + bool shrink (unsigned count) + { + return thiz->shrink (*this, count); + } + }; + + size_t get_class1_record_size () const + { + const size_t class2_count = class2Count; + return + class2_count * (valueFormat1.get_size () + valueFormat2.get_size ()); + } + + unsigned clone_range (split_context_t& split_context, + unsigned start, unsigned end) const + { + DEBUG_MSG (SUBSET_REPACK, nullptr, + " Cloning PairPosFormat2 (%u) range [%u, %u).", split_context.this_index, start, end); + + graph_t& graph = split_context.c.graph; + + unsigned num_records = end - start; + unsigned prime_size = OT::Layout::GPOS_impl::PairPosFormat2_4<SmallTypes>::min_size + + num_records * split_context.class1_record_size; + + unsigned pair_pos_prime_id = split_context.c.create_node (prime_size); + if (pair_pos_prime_id == (unsigned) -1) return -1; + + PairPosFormat2* pair_pos_prime = + (PairPosFormat2*) graph.object (pair_pos_prime_id).head; + pair_pos_prime->format = this->format; + pair_pos_prime->valueFormat1 = this->valueFormat1; + pair_pos_prime->valueFormat2 = this->valueFormat2; + pair_pos_prime->class1Count = num_records; + pair_pos_prime->class2Count = this->class2Count; + clone_class1_records (split_context, + pair_pos_prime_id, + start, + end); + + unsigned coverage_id = + graph.index_for_offset (split_context.this_index, &coverage); + unsigned class_def_1_id = + graph.index_for_offset (split_context.this_index, &classDef1); + auto& coverage_v = graph.vertices_[coverage_id]; + auto& class_def_1_v = graph.vertices_[class_def_1_id]; + Coverage* coverage_table = (Coverage*) coverage_v.obj.head; + ClassDef* class_def_1_table = (ClassDef*) class_def_1_v.obj.head; + if (!coverage_table + || !coverage_table->sanitize (coverage_v) + || !class_def_1_table + || !class_def_1_table->sanitize (class_def_1_v)) return -1; - auto* coverage_link = c.graph.vertices_[pair_pos_prime_id].obj.real_links.push (); - coverage_link->width = SmallTypes::size; - coverage_link->objidx = coverage_prime_id; - coverage_link->position = 2; - coverage_prime_vertex.parents.push (pair_pos_prime_id); + auto klass_map = + + coverage_table->iter () + | hb_map_retains_sorting ([&] (hb_codepoint_t gid) { + return hb_pair_t<hb_codepoint_t, hb_codepoint_t> (gid, class_def_1_table->get_class (gid)); + }) + | hb_filter ([&] (hb_codepoint_t klass) { + return klass >= start && klass < end; + }, hb_second) + | hb_map_retains_sorting ([&] (hb_pair_t<hb_codepoint_t, hb_codepoint_t> gid_and_class) { + // Classes must be from 0...N so subtract start + return hb_pair_t<hb_codepoint_t, hb_codepoint_t> (gid_and_class.first, gid_and_class.second - start); + }) + ; + + if (!Coverage::add_coverage (split_context.c, + pair_pos_prime_id, + 2, + + klass_map | hb_map_retains_sorting (hb_first), + split_context.max_coverage_size)) + return -1; + + // classDef1 + if (!ClassDef::add_class_def (split_context.c, + pair_pos_prime_id, + 8, + + klass_map, + split_context.max_class_def_size)) + return -1; + + // classDef2 + unsigned class_def_2_id = + graph.index_for_offset (split_context.this_index, &classDef2); + auto* class_def_link = graph.vertices_[pair_pos_prime_id].obj.real_links.push (); + class_def_link->width = SmallTypes::size; + class_def_link->objidx = class_def_2_id; + class_def_link->position = 10; + graph.vertices_[class_def_2_id].parents.push (pair_pos_prime_id); + graph.duplicate (pair_pos_prime_id, class_def_2_id); return pair_pos_prime_id; } - template<typename It> - bool make_coverage (gsubgpos_graph_context_t& c, - It glyphs, - unsigned dest_obj, - unsigned max_size) const + void clone_class1_records (split_context_t& split_context, + unsigned pair_pos_prime_id, + unsigned start, unsigned end) const { - char* buffer = (char*) hb_calloc (1, max_size); - hb_serialize_context_t serializer (buffer, max_size); - Coverage_serialize (&serializer, glyphs); - serializer.end_serialize (); - if (serializer.in_error ()) + PairPosFormat2* pair_pos_prime = + (PairPosFormat2*) split_context.c.graph.object (pair_pos_prime_id).head; + + char* start_addr = ((char*)&values[0]) + start * split_context.class1_record_size; + unsigned num_records = end - start; + memcpy (&pair_pos_prime->values[0], + start_addr, + num_records * split_context.class1_record_size); + + if (!split_context.format1_device_table_indices + && !split_context.format2_device_table_indices) + // No device tables to move over. + return; + + unsigned class2_count = class2Count; + for (unsigned i = start; i < end; i++) { - hb_free (buffer); - return false; + for (unsigned j = 0; j < class2_count; j++) + { + unsigned value1_index = split_context.value_record_len * (class2_count * i + j); + unsigned value2_index = value1_index + split_context.value1_record_len; + + unsigned new_value1_index = split_context.value_record_len * (class2_count * (i - start) + j); + unsigned new_value2_index = new_value1_index + split_context.value1_record_len; + + transfer_device_tables (split_context, + pair_pos_prime_id, + split_context.format1_device_table_indices, + value1_index, + new_value1_index); + + transfer_device_tables (split_context, + pair_pos_prime_id, + split_context.format2_device_table_indices, + value2_index, + new_value2_index); + } } + } - hb_bytes_t coverage_copy = serializer.copy_bytes (); - c.add_buffer ((char *) coverage_copy.arrayZ); // Give ownership to the context, it will cleanup the buffer. + void transfer_device_tables (split_context_t& split_context, + unsigned pair_pos_prime_id, + const hb_vector_t<unsigned>& device_table_indices, + unsigned old_value_record_index, + unsigned new_value_record_index) const + { + PairPosFormat2* pair_pos_prime = + (PairPosFormat2*) split_context.c.graph.object (pair_pos_prime_id).head; - auto& obj = c.graph.vertices_[dest_obj].obj; - obj.head = (char *) coverage_copy.arrayZ; - obj.tail = obj.head + coverage_copy.length; + for (unsigned i : device_table_indices) + { + OT::Offset16* record = (OT::Offset16*) &values[old_value_record_index + i]; + unsigned record_position = ((char*) record) - ((char*) this); + if (!split_context.device_tables.has (record_position)) continue; + + split_context.c.graph.move_child ( + split_context.this_index, + record, + pair_pos_prime_id, + (OT::Offset16*) &pair_pos_prime->values[new_value_record_index + i]); + } + } - hb_free (buffer); - return true; + bool shrink (split_context_t& split_context, + unsigned count) + { + DEBUG_MSG (SUBSET_REPACK, nullptr, + " Shrinking PairPosFormat2 (%u) to [0, %u).", + split_context.this_index, + count); + unsigned old_count = class1Count; + if (count >= old_count) + return true; + + graph_t& graph = split_context.c.graph; + class1Count = count; + graph.vertices_[split_context.this_index].obj.tail -= + (old_count - count) * split_context.class1_record_size; + + unsigned coverage_id = + graph.mutable_index_for_offset (split_context.this_index, &coverage); + unsigned class_def_1_id = + graph.mutable_index_for_offset (split_context.this_index, &classDef1); + auto& coverage_v = graph.vertices_[coverage_id]; + auto& class_def_1_v = graph.vertices_[class_def_1_id]; + Coverage* coverage_table = (Coverage*) coverage_v.obj.head; + ClassDef* class_def_1_table = (ClassDef*) class_def_1_v.obj.head; + if (!coverage_table + || !coverage_table->sanitize (coverage_v) + || !class_def_1_table + || !class_def_1_table->sanitize (class_def_1_v)) + return false; + + auto klass_map = + + coverage_table->iter () + | hb_map_retains_sorting ([&] (hb_codepoint_t gid) { + return hb_pair_t<hb_codepoint_t, hb_codepoint_t> (gid, class_def_1_table->get_class (gid)); + }) + | hb_filter ([&] (hb_codepoint_t klass) { + return klass < count; + }, hb_second) + ; + + if (!Coverage::make_coverage (split_context.c, + + klass_map | hb_map_retains_sorting (hb_first), + coverage_id, + coverage_v.table_size ())) + return false; + + return ClassDef::make_class_def (split_context.c, + + klass_map, + class_def_1_id, + class_def_1_v.table_size ()); } - unsigned pair_set_graph_index (gsubgpos_graph_context_t& c, unsigned this_index, unsigned i) const + hb_hashmap_t<unsigned, unsigned> + get_all_device_tables (gsubgpos_graph_context_t& c, + unsigned this_index) const { - return c.graph.index_for_offset (this_index, &pairSet[i]); + const auto& v = c.graph.vertices_[this_index]; + return v.position_to_index_map (); } -}; -struct PairPosFormat2 : public OT::Layout::GPOS_impl::PairPosFormat2_4<SmallTypes> -{ - bool sanitize (graph_t::vertex_t& vertex) const + const Coverage* get_coverage (gsubgpos_graph_context_t& c, + unsigned this_index) const { - // TODO(garretrieger): implement me! - return true; + unsigned coverage_id = c.graph.index_for_offset (this_index, &coverage); + auto& coverage_v = c.graph.vertices_[coverage_id]; + + Coverage* coverage_table = (Coverage*) coverage_v.obj.head; + if (!coverage_table || !coverage_table->sanitize (coverage_v)) + return &Null(Coverage); + return coverage_table; } - hb_vector_t<unsigned> split_subtables (gsubgpos_graph_context_t& c, unsigned this_index) + const ClassDef* get_class_def_1 (gsubgpos_graph_context_t& c, + unsigned this_index) const + { + unsigned class_def_1_id = c.graph.index_for_offset (this_index, &classDef1); + auto& class_def_1_v = c.graph.vertices_[class_def_1_id]; + + ClassDef* class_def_1_table = (ClassDef*) class_def_1_v.obj.head; + if (!class_def_1_table || !class_def_1_table->sanitize (class_def_1_v)) + return &Null(ClassDef); + return class_def_1_table; + } + + unsigned size_of_value_record_children (gsubgpos_graph_context_t& c, + const hb_hashmap_t<unsigned, unsigned>& device_tables, + const hb_vector_t<unsigned> device_table_indices, + unsigned value_record_index, + hb_set_t& visited) + { + unsigned size = 0; + for (unsigned i : device_table_indices) + { + OT::Layout::GPOS_impl::Value* record = &values[value_record_index + i]; + unsigned record_position = ((char*) record) - ((char*) this); + unsigned* obj_idx; + if (!device_tables.has (record_position, &obj_idx)) continue; + size += c.graph.find_subgraph_size (*obj_idx, visited); + } + return size; + } + + unsigned size_of (gsubgpos_graph_context_t& c, + unsigned this_index, + const void* offset) const { - // TODO(garretrieger): implement me! - return hb_vector_t<unsigned> (); + const unsigned id = c.graph.index_for_offset (this_index, offset); + return c.graph.vertices_[id].table_size (); } }; diff --git a/thirdparty/harfbuzz/src/graph/split-helpers.hh b/thirdparty/harfbuzz/src/graph/split-helpers.hh new file mode 100644 index 0000000000..61fd7c2d2f --- /dev/null +++ b/thirdparty/harfbuzz/src/graph/split-helpers.hh @@ -0,0 +1,69 @@ +/* + * Copyright © 2022 Google, Inc. + * + * This is part of HarfBuzz, a text shaping library. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and its documentation for any purpose, provided that the + * above copyright notice and the following two paragraphs appear in + * all copies of this software. + * + * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN + * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH + * DAMAGE. + * + * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, + * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * Google Author(s): Garret Rieger + */ + +#ifndef GRAPH_SPLIT_HELPERS_HH +#define GRAPH_SPLIT_HELPERS_HH + +namespace graph { + +template<typename Context> +HB_INTERNAL +hb_vector_t<unsigned> actuate_subtable_split (Context& split_context, + const hb_vector_t<unsigned>& split_points) +{ + hb_vector_t<unsigned> new_objects; + if (!split_points) + return new_objects; + + for (unsigned i = 0; i < split_points.length; i++) + { + unsigned start = split_points[i]; + unsigned end = (i < split_points.length - 1) + ? split_points[i + 1] + : split_context.original_count (); + unsigned id = split_context.clone_range (start, end); + + if (id == (unsigned) -1) + { + new_objects.reset (); + new_objects.allocated = -1; // mark error + return new_objects; + } + new_objects.push (id); + } + + if (!split_context.shrink (split_points[0])) + { + new_objects.reset (); + new_objects.allocated = -1; // mark error + } + + return new_objects; +} + +} + +#endif // GRAPH_SPLIT_HELPERS_HH diff --git a/thirdparty/harfbuzz/src/graph/test-classdef-graph.cc b/thirdparty/harfbuzz/src/graph/test-classdef-graph.cc new file mode 100644 index 0000000000..55854ff5c2 --- /dev/null +++ b/thirdparty/harfbuzz/src/graph/test-classdef-graph.cc @@ -0,0 +1,119 @@ +/* + * Copyright © 2022 Google, Inc. + * + * This is part of HarfBuzz, a text shaping library. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and its documentation for any purpose, provided that the + * above copyright notice and the following two paragraphs appear in + * all copies of this software. + * + * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN + * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH + * DAMAGE. + * + * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, + * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * Google Author(s): Garret Rieger + */ + +#include "gsubgpos-context.hh" +#include "classdef-graph.hh" + +typedef hb_pair_t<hb_codepoint_t, hb_codepoint_t> gid_and_class_t; +typedef hb_vector_t<gid_and_class_t> gid_and_class_list_t; + + +static bool incremental_size_is (const gid_and_class_list_t& list, unsigned klass, + unsigned cov_expected, unsigned class_def_expected) +{ + graph::class_def_size_estimator_t estimator (list.iter ()); + + unsigned result = estimator.incremental_coverage_size (klass); + if (result != cov_expected) + { + printf ("FAIL: coverage expected size %u but was %u\n", cov_expected, result); + return false; + } + + result = estimator.incremental_class_def_size (klass); + if (result != class_def_expected) + { + printf ("FAIL: class def expected size %u but was %u\n", class_def_expected, result); + return false; + } + + return true; +} + +static void test_class_and_coverage_size_estimates () +{ + gid_and_class_list_t empty = { + }; + assert (incremental_size_is (empty, 0, 0, 0)); + assert (incremental_size_is (empty, 1, 0, 0)); + + gid_and_class_list_t class_zero = { + {5, 0}, + }; + assert (incremental_size_is (class_zero, 0, 2, 0)); + + gid_and_class_list_t consecutive = { + {4, 0}, + {5, 0}, + {6, 1}, + {7, 1}, + {8, 2}, + {9, 2}, + {10, 2}, + {11, 2}, + }; + assert (incremental_size_is (consecutive, 0, 4, 0)); + assert (incremental_size_is (consecutive, 1, 4, 4)); + assert (incremental_size_is (consecutive, 2, 8, 6)); + + gid_and_class_list_t non_consecutive = { + {4, 0}, + {5, 0}, + + {6, 1}, + {7, 1}, + + {9, 2}, + {10, 2}, + {11, 2}, + {12, 2}, + }; + assert (incremental_size_is (non_consecutive, 0, 4, 0)); + assert (incremental_size_is (non_consecutive, 1, 4, 6)); + assert (incremental_size_is (non_consecutive, 2, 8, 6)); + + gid_and_class_list_t multiple_ranges = { + {4, 0}, + {5, 0}, + + {6, 1}, + {7, 1}, + + {9, 1}, + + {11, 1}, + {12, 1}, + {13, 1}, + }; + assert (incremental_size_is (multiple_ranges, 0, 4, 0)); + assert (incremental_size_is (multiple_ranges, 1, 2 * 6, 3 * 6)); +} + +int +main (int argc, char **argv) +{ + test_class_and_coverage_size_estimates (); +} diff --git a/thirdparty/harfbuzz/src/hb-array.hh b/thirdparty/harfbuzz/src/hb-array.hh index 826a901819..5884007c19 100644 --- a/thirdparty/harfbuzz/src/hb-array.hh +++ b/thirdparty/harfbuzz/src/hb-array.hh @@ -342,7 +342,7 @@ struct hb_sorted_array_t : unsigned int i; return bfind (x, &i) ? &this->arrayZ[i] : not_found; } - template <typename T, typename ...Ts> + template <typename T> const Type *bsearch (const T &x, const Type *not_found = nullptr) const { unsigned int i; @@ -389,7 +389,7 @@ struct hb_sorted_array_t : this->length, sizeof (Type), _hb_cmp_method<T, Type, Ts...>, - ds...); + std::forward<Ts> (ds)...); } }; template <typename T> inline hb_sorted_array_t<T> diff --git a/thirdparty/harfbuzz/src/hb-atomic.hh b/thirdparty/harfbuzz/src/hb-atomic.hh index d6dfb0f57a..14c6fb3264 100644 --- a/thirdparty/harfbuzz/src/hb-atomic.hh +++ b/thirdparty/harfbuzz/src/hb-atomic.hh @@ -159,10 +159,13 @@ struct hb_atomic_int_t hb_atomic_int_t () = default; constexpr hb_atomic_int_t (int v) : v (v) {} + hb_atomic_int_t& operator = (int v_) { set_relaxed (v_); return *this; } + operator int () const { return get_relaxed (); } + void set_relaxed (int v_) { hb_atomic_int_impl_set_relaxed (&v, v_); } - void set (int v_) { hb_atomic_int_impl_set (&v, v_); } + void set_release (int v_) { hb_atomic_int_impl_set (&v, v_); } int get_relaxed () const { return hb_atomic_int_impl_get_relaxed (&v); } - int get () const { return hb_atomic_int_impl_get (&v); } + int get_acquire () const { return hb_atomic_int_impl_get (&v); } int inc () { return hb_atomic_int_impl_add (&v, 1); } int dec () { return hb_atomic_int_impl_add (&v, -1); } @@ -180,11 +183,11 @@ struct hb_atomic_ptr_t void init (T* v_ = nullptr) { set_relaxed (v_); } void set_relaxed (T* v_) { hb_atomic_ptr_impl_set_relaxed (&v, v_); } T *get_relaxed () const { return (T *) hb_atomic_ptr_impl_get_relaxed (&v); } - T *get () const { return (T *) hb_atomic_ptr_impl_get ((void **) &v); } + T *get_acquire () const { return (T *) hb_atomic_ptr_impl_get ((void **) &v); } bool cmpexch (const T *old, T *new_) const { return hb_atomic_ptr_impl_cmpexch ((void **) &v, (void *) old, (void *) new_); } - T * operator -> () const { return get (); } - template <typename C> operator C * () const { return get (); } + T * operator -> () const { return get_acquire (); } + template <typename C> operator C * () const { return get_acquire (); } T *v = nullptr; }; diff --git a/thirdparty/harfbuzz/src/hb-bit-set.hh b/thirdparty/harfbuzz/src/hb-bit-set.hh index 4765af67ce..a63887efda 100644 --- a/thirdparty/harfbuzz/src/hb-bit-set.hh +++ b/thirdparty/harfbuzz/src/hb-bit-set.hh @@ -56,7 +56,7 @@ struct hb_bit_set_t { successful = true; population = 0; - last_page_lookup.set_relaxed (0); + last_page_lookup = 0; page_map.init (); pages.init (); } @@ -614,7 +614,7 @@ struct hb_bit_set_t const auto* page_map_array = page_map.arrayZ; unsigned int major = get_major (*codepoint); - unsigned int i = last_page_lookup.get_relaxed (); + unsigned int i = last_page_lookup; if (unlikely (i >= page_map.length || page_map_array[i].major != major)) { @@ -632,7 +632,7 @@ struct hb_bit_set_t if (pages_array[current.index].next (codepoint)) { *codepoint += current.major * page_t::PAGE_BITS; - last_page_lookup.set_relaxed (i); + last_page_lookup = i; return true; } i++; @@ -645,11 +645,11 @@ struct hb_bit_set_t if (m != INVALID) { *codepoint = current.major * page_t::PAGE_BITS + m; - last_page_lookup.set_relaxed (i); + last_page_lookup = i; return true; } } - last_page_lookup.set_relaxed (0); + last_page_lookup = 0; *codepoint = INVALID; return false; } @@ -732,7 +732,7 @@ struct hb_bit_set_t { const auto* page_map_array = page_map.arrayZ; unsigned int major = get_major (codepoint); - unsigned int i = last_page_lookup.get_relaxed (); + unsigned int i = last_page_lookup; if (unlikely (i >= page_map.length || page_map_array[i].major != major)) { page_map.bfind (major, &i, HB_NOT_FOUND_STORE_CLOSEST); @@ -773,7 +773,7 @@ struct hb_bit_set_t { const auto* page_map_array = page_map.arrayZ; unsigned int major = get_major (codepoint); - unsigned int i = last_page_lookup.get_relaxed (); + unsigned int i = last_page_lookup; if (unlikely (i >= page_map.length || page_map_array[i].major != major)) { page_map.bfind(major, &i, HB_NOT_FOUND_STORE_CLOSEST); @@ -900,7 +900,7 @@ struct hb_bit_set_t /* The extra page_map length is necessary; can't just rely on vector here, * since the next check would be tricked because a null page also has * major==0, which we can't distinguish from an actualy major==0 page... */ - unsigned i = last_page_lookup.get_relaxed (); + unsigned i = last_page_lookup; if (likely (i < page_map.length)) { auto &cached_page = page_map.arrayZ[i]; @@ -924,7 +924,7 @@ struct hb_bit_set_t page_map[i] = map; } - last_page_lookup.set_relaxed (i); + last_page_lookup = i; return &pages[page_map[i].index]; } const page_t *page_for (hb_codepoint_t g) const @@ -934,7 +934,7 @@ struct hb_bit_set_t /* The extra page_map length is necessary; can't just rely on vector here, * since the next check would be tricked because a null page also has * major==0, which we can't distinguish from an actualy major==0 page... */ - unsigned i = last_page_lookup.get_relaxed (); + unsigned i = last_page_lookup; if (likely (i < page_map.length)) { auto &cached_page = page_map.arrayZ[i]; @@ -946,7 +946,7 @@ struct hb_bit_set_t if (!page_map.bfind (key, &i)) return nullptr; - last_page_lookup.set_relaxed (i); + last_page_lookup = i; return &pages[page_map[i].index]; } page_t &page_at (unsigned int i) { return pages[page_map[i].index]; } diff --git a/thirdparty/harfbuzz/src/hb-buffer-deserialize-json.hh b/thirdparty/harfbuzz/src/hb-buffer-deserialize-json.hh index 44c802a00c..87095855d6 100644 --- a/thirdparty/harfbuzz/src/hb-buffer-deserialize-json.hh +++ b/thirdparty/harfbuzz/src/hb-buffer-deserialize-json.hh @@ -32,7 +32,7 @@ #include "hb.hh" -#line 33 "hb-buffer-deserialize-json.hh" +#line 36 "hb-buffer-deserialize-json.hh" static const unsigned char _deserialize_json_trans_keys[] = { 0u, 0u, 9u, 123u, 9u, 34u, 97u, 117u, 120u, 121u, 34u, 34u, 9u, 58u, 9u, 57u, 48u, 57u, 9u, 125u, 9u, 125u, 9u, 125u, 34u, 34u, 9u, 58u, 9u, 57u, 48u, 57u, @@ -557,12 +557,12 @@ _hb_buffer_deserialize_json (hb_buffer_t *buffer, hb_glyph_info_t info = {0}; hb_glyph_position_t pos = {0}; -#line 554 "hb-buffer-deserialize-json.hh" +#line 561 "hb-buffer-deserialize-json.hh" { cs = deserialize_json_start; } -#line 557 "hb-buffer-deserialize-json.hh" +#line 566 "hb-buffer-deserialize-json.hh" { int _slen; int _trans; @@ -774,7 +774,7 @@ _resume: *end_ptr = p; } break; -#line 735 "hb-buffer-deserialize-json.hh" +#line 778 "hb-buffer-deserialize-json.hh" } _again: diff --git a/thirdparty/harfbuzz/src/hb-buffer-deserialize-text.hh b/thirdparty/harfbuzz/src/hb-buffer-deserialize-text.hh index 8fbcdcc18c..9062610de2 100644 --- a/thirdparty/harfbuzz/src/hb-buffer-deserialize-text.hh +++ b/thirdparty/harfbuzz/src/hb-buffer-deserialize-text.hh @@ -32,7 +32,7 @@ #include "hb.hh" -#line 33 "hb-buffer-deserialize-text.hh" +#line 36 "hb-buffer-deserialize-text.hh" static const unsigned char _deserialize_text_trans_keys[] = { 0u, 0u, 9u, 91u, 85u, 85u, 43u, 43u, 48u, 102u, 9u, 85u, 48u, 57u, 45u, 57u, 48u, 57u, 48u, 57u, 48u, 57u, 45u, 57u, 48u, 57u, 44u, 44u, 45u, 57u, 48u, 57u, @@ -509,12 +509,12 @@ _hb_buffer_deserialize_text (hb_buffer_t *buffer, hb_glyph_info_t info = {0}; hb_glyph_position_t pos = {0}; -#line 506 "hb-buffer-deserialize-text.hh" +#line 513 "hb-buffer-deserialize-text.hh" { cs = deserialize_text_start; } -#line 509 "hb-buffer-deserialize-text.hh" +#line 518 "hb-buffer-deserialize-text.hh" { int _slen; int _trans; @@ -894,7 +894,7 @@ _resume: *end_ptr = p; } break; -#line 826 "hb-buffer-deserialize-text.hh" +#line 898 "hb-buffer-deserialize-text.hh" } _again: @@ -1043,7 +1043,7 @@ _again: *end_ptr = p; } break; -#line 953 "hb-buffer-deserialize-text.hh" +#line 1047 "hb-buffer-deserialize-text.hh" } } diff --git a/thirdparty/harfbuzz/src/hb-buffer.h b/thirdparty/harfbuzz/src/hb-buffer.h index c6af759fb9..8c17489835 100644 --- a/thirdparty/harfbuzz/src/hb-buffer.h +++ b/thirdparty/harfbuzz/src/hb-buffer.h @@ -145,7 +145,7 @@ typedef struct hb_glyph_info_t { * @HB_GLYPH_FLAG_SAFE_TO_INSERT_TATWEEL: In scripts that use elongation (Arabic, Mongolian, Syriac, etc.), this flag signifies that it is safe to insert a U+0640 TATWEEL - character *before* this cluster for elongation. + character before this cluster for elongation. This flag does not determine the script-specific elongation places, but only when it is safe to do the elongation without diff --git a/thirdparty/harfbuzz/src/hb-cache.hh b/thirdparty/harfbuzz/src/hb-cache.hh index d6b229ed65..897f313fbd 100644 --- a/thirdparty/harfbuzz/src/hb-cache.hh +++ b/thirdparty/harfbuzz/src/hb-cache.hh @@ -32,12 +32,21 @@ /* Implements a lockfree cache for int->int functions. */ -template <unsigned int key_bits=16, unsigned int value_bits=8 + 32 - key_bits, unsigned int cache_bits=8> +template <unsigned int key_bits=16, + unsigned int value_bits=8 + 32 - key_bits, + unsigned int cache_bits=8, + bool thread_safe=true> struct hb_cache_t { + using item_t = typename std::conditional<thread_safe, + hb_atomic_int_t, + typename std::conditional<key_bits + value_bits - cache_bits <= 16, + short, + int>::type + >::type; + static_assert ((key_bits >= cache_bits), ""); - static_assert ((key_bits + value_bits - cache_bits <= 8 * sizeof (hb_atomic_int_t)), ""); - static_assert (sizeof (hb_atomic_int_t) == sizeof (unsigned int), ""); + static_assert ((key_bits + value_bits - cache_bits <= 8 * sizeof (item_t)), ""); void init () { clear (); } void fini () {} @@ -45,14 +54,14 @@ struct hb_cache_t void clear () { for (unsigned i = 0; i < ARRAY_LENGTH (values); i++) - values[i].set_relaxed (-1); + values[i] = -1; } bool get (unsigned int key, unsigned int *value) const { unsigned int k = key & ((1u<<cache_bits)-1); - unsigned int v = values[k].get_relaxed (); - if ((key_bits + value_bits - cache_bits == 8 * sizeof (hb_atomic_int_t) && v == (unsigned int) -1) || + unsigned int v = values[k]; + if ((key_bits + value_bits - cache_bits == 8 * sizeof (item_t) && v == (unsigned int) -1) || (v >> value_bits) != (key >> cache_bits)) return false; *value = v & ((1u<<value_bits)-1); @@ -65,16 +74,13 @@ struct hb_cache_t return false; /* Overflows */ unsigned int k = key & ((1u<<cache_bits)-1); unsigned int v = ((key>>cache_bits)<<value_bits) | value; - values[k].set_relaxed (v); + values[k] = v; return true; } private: - hb_atomic_int_t values[1u<<cache_bits]; + item_t values[1u<<cache_bits]; }; -typedef hb_cache_t<21, 16, 8> hb_cmap_cache_t; -typedef hb_cache_t<16, 24, 8> hb_advance_cache_t; - #endif /* HB_CACHE_HH */ diff --git a/thirdparty/harfbuzz/src/hb-common.cc b/thirdparty/harfbuzz/src/hb-common.cc index e6512872e8..bbb6cd552b 100644 --- a/thirdparty/harfbuzz/src/hb-common.cc +++ b/thirdparty/harfbuzz/src/hb-common.cc @@ -99,7 +99,7 @@ _hb_options_init () } /* This is idempotent and threadsafe. */ - _hb_options.set_relaxed (u.i); + _hb_options = u.i; } diff --git a/thirdparty/harfbuzz/src/hb-common.h b/thirdparty/harfbuzz/src/hb-common.h index 7c7ad87c7c..e92feb9898 100644 --- a/thirdparty/harfbuzz/src/hb-common.h +++ b/thirdparty/harfbuzz/src/hb-common.h @@ -495,6 +495,8 @@ hb_language_matches (hb_language_t language, * @HB_SCRIPT_TOTO: `Toto`, Since: 3.0.0 * @HB_SCRIPT_VITHKUQI: `Vith`, Since: 3.0.0 * @HB_SCRIPT_MATH: `Zmth`, Since: 3.4.0 + * @HB_SCRIPT_KAWI: `Kawi`, Since: 5.2.0 + * @HB_SCRIPT_NAG_MUNDARI: `Nagm`, Since: 5.2.0 * @HB_SCRIPT_INVALID: No script set * * Data type for scripts. Each #hb_script_t's value is an #hb_tag_t corresponding @@ -716,6 +718,12 @@ typedef enum */ HB_SCRIPT_MATH = HB_TAG ('Z','m','t','h'), + /* + * Since 5.2.0 + */ + HB_SCRIPT_KAWI = HB_TAG ('K','a','w','i'), /*15.0*/ + HB_SCRIPT_NAG_MUNDARI = HB_TAG ('N','a','g','m'), /*15.0*/ + /* No script set. */ HB_SCRIPT_INVALID = HB_TAG_NONE, diff --git a/thirdparty/harfbuzz/src/hb-config.hh b/thirdparty/harfbuzz/src/hb-config.hh index db8ec0e908..5567ddaec3 100644 --- a/thirdparty/harfbuzz/src/hb-config.hh +++ b/thirdparty/harfbuzz/src/hb-config.hh @@ -35,6 +35,9 @@ #include "config.h" #endif +#ifndef HB_BORING_EXPANSION +#define HB_NO_BORING_EXPANSION +#endif #ifdef HB_TINY #define HB_LEAN diff --git a/thirdparty/harfbuzz/src/hb-debug.hh b/thirdparty/harfbuzz/src/hb-debug.hh index 905a46a087..cbe13e5214 100644 --- a/thirdparty/harfbuzz/src/hb-debug.hh +++ b/thirdparty/harfbuzz/src/hb-debug.hh @@ -67,12 +67,12 @@ hb_options () #endif /* Make a local copy, so we can access bitfield threadsafely. */ hb_options_union_t u; - u.i = _hb_options.get_relaxed (); + u.i = _hb_options; if (unlikely (!u.i)) { _hb_options_init (); - u.i = _hb_options.get_relaxed (); + u.i = _hb_options; } return u.opts; diff --git a/thirdparty/harfbuzz/src/hb-face.cc b/thirdparty/harfbuzz/src/hb-face.cc index 61adbdd503..2160d6a010 100644 --- a/thirdparty/harfbuzz/src/hb-face.cc +++ b/thirdparty/harfbuzz/src/hb-face.cc @@ -132,7 +132,7 @@ hb_face_create_for_tables (hb_reference_table_func_t reference_table_func, face->user_data = user_data; face->destroy = destroy; - face->num_glyphs.set_relaxed (-1); + face->num_glyphs = -1; face->data.init0 (face); face->table.init0 (face); @@ -479,7 +479,7 @@ hb_face_set_upem (hb_face_t *face, if (hb_object_is_immutable (face)) return; - face->upem.set_relaxed (upem); + face->upem = upem; } /** @@ -514,7 +514,7 @@ hb_face_set_glyph_count (hb_face_t *face, if (hb_object_is_immutable (face)) return; - face->num_glyphs.set_relaxed (glyph_count); + face->num_glyphs = glyph_count; } /** diff --git a/thirdparty/harfbuzz/src/hb-face.hh b/thirdparty/harfbuzz/src/hb-face.hh index 765f272858..12e10d01e0 100644 --- a/thirdparty/harfbuzz/src/hb-face.hh +++ b/thirdparty/harfbuzz/src/hb-face.hh @@ -83,7 +83,7 @@ struct hb_face_t unsigned int get_upem () const { - unsigned int ret = upem.get_relaxed (); + unsigned int ret = upem; if (unlikely (!ret)) { return load_upem (); @@ -93,7 +93,7 @@ struct hb_face_t unsigned int get_num_glyphs () const { - unsigned int ret = num_glyphs.get_relaxed (); + unsigned int ret = num_glyphs; if (unlikely (ret == UINT_MAX)) return load_num_glyphs (); return ret; diff --git a/thirdparty/harfbuzz/src/hb-ft.cc b/thirdparty/harfbuzz/src/hb-ft.cc index ef073475cb..bcc1dd080f 100644 --- a/thirdparty/harfbuzz/src/hb-ft.cc +++ b/thirdparty/harfbuzz/src/hb-ft.cc @@ -80,16 +80,19 @@ */ +using hb_ft_advance_cache_t = hb_cache_t<16, 24, 8, false>; + struct hb_ft_font_t { int load_flags; bool symbol; /* Whether selected cmap is symbol cmap. */ bool unref; /* Whether to destroy ft_face when done. */ + bool transform; /* Whether to apply FT_Face's transform. */ mutable hb_mutex_t lock; FT_Face ft_face; mutable unsigned cached_serial; - mutable hb_advance_cache_t advance_cache; + mutable hb_ft_advance_cache_t advance_cache; }; static hb_ft_font_t * @@ -136,6 +139,8 @@ _hb_ft_font_destroy (void *data) /* hb_font changed, update FT_Face. */ static void _hb_ft_hb_font_changed (hb_font_t *font, FT_Face ft_face) { + hb_ft_font_t *ft_font = (hb_ft_font_t *) font->user_data; + float x_mult = 1.f, y_mult = 1.f; if (font->x_scale < 0) x_mult = -x_mult; @@ -173,6 +178,7 @@ static void _hb_ft_hb_font_changed (hb_font_t *font, FT_Face ft_face) FT_Matrix matrix = { (int) roundf (x_mult * (1<<16)), 0, 0, (int) roundf (y_mult * (1<<16))}; FT_Set_Transform (ft_face, &matrix, nullptr); + ft_font->transform = true; } #if defined(HAVE_FT_GET_VAR_BLEND_COORDINATES) && !defined(HB_NO_VAR) @@ -428,13 +434,19 @@ hb_ft_get_glyph_h_advances (hb_font_t* font, void* font_data, hb_lock_t lock (ft_font->lock); FT_Face ft_face = ft_font->ft_face; int load_flags = ft_font->load_flags; + float x_mult; #ifdef HAVE_FT_GET_TRANSFORM - FT_Matrix matrix; - FT_Get_Transform (ft_face, &matrix, nullptr); - float mult = matrix.xx / 65536.f; -#else - float mult = font->x_scale < 0 ? -1 : +1; + if (ft_font->transform) + { + FT_Matrix matrix; + FT_Get_Transform (ft_face, &matrix, nullptr); + x_mult = sqrtf ((float)matrix.xx * matrix.xx + (float)matrix.xy * matrix.xy) / 65536.f; + } + else #endif + { + x_mult = font->x_scale < 0 ? -1 : +1; + } for (unsigned int i = 0; i < count; i++) { @@ -450,7 +462,7 @@ hb_ft_get_glyph_h_advances (hb_font_t* font, void* font_data, ft_font->advance_cache.set (glyph, v); } - *first_advance = (int) (v * mult + (1<<9)) >> 10; + *first_advance = (int) (v * x_mult + (1<<9)) >> 10; first_glyph = &StructAtOffsetUnaligned<hb_codepoint_t> (first_glyph, glyph_stride); first_advance = &StructAtOffsetUnaligned<hb_position_t> (first_advance, advance_stride); } @@ -466,13 +478,19 @@ hb_ft_get_glyph_v_advance (hb_font_t *font, const hb_ft_font_t *ft_font = (const hb_ft_font_t *) font_data; hb_lock_t lock (ft_font->lock); FT_Fixed v; + float y_mult; #ifdef HAVE_FT_GET_TRANSFORM - FT_Matrix matrix; - FT_Get_Transform (ft_font->ft_face, &matrix, nullptr); - float y_mult = matrix.yy / 65536.f; -#else - float y_mult = font->y_scale < 0 ? -1 : +1; + if (ft_font->transform) + { + FT_Matrix matrix; + FT_Get_Transform (ft_font->ft_face, &matrix, nullptr); + y_mult = sqrtf ((float)matrix.yx * matrix.yx + (float)matrix.yy * matrix.yy) / 65536.f; + } + else #endif + { + y_mult = font->y_scale < 0 ? -1 : +1; + } if (unlikely (FT_Get_Advance (ft_font->ft_face, glyph, ft_font->load_flags | FT_LOAD_VERTICAL_LAYOUT, &v))) return 0; @@ -498,15 +516,21 @@ hb_ft_get_glyph_v_origin (hb_font_t *font, const hb_ft_font_t *ft_font = (const hb_ft_font_t *) font_data; hb_lock_t lock (ft_font->lock); FT_Face ft_face = ft_font->ft_face; + float x_mult, y_mult; #ifdef HAVE_FT_GET_TRANSFORM - FT_Matrix matrix; - FT_Get_Transform (ft_face, &matrix, nullptr); - float x_mult = matrix.xx / 65536.f; - float y_mult = matrix.yy / 65536.f; -#else - float x_mult = font->x_scale < 0 ? -1 : +1; - float y_mult = font->y_scale < 0 ? -1 : +1; + if (ft_font->transform) + { + FT_Matrix matrix; + FT_Get_Transform (ft_face, &matrix, nullptr); + x_mult = sqrtf ((float)matrix.xx * matrix.xx + (float)matrix.xy * matrix.xy) / 65536.f; + y_mult = sqrtf ((float)matrix.yx * matrix.yx + (float)matrix.yy * matrix.yy) / 65536.f; + } + else #endif + { + x_mult = font->x_scale < 0 ? -1 : +1; + y_mult = font->y_scale < 0 ? -1 : +1; + } if (unlikely (FT_Load_Glyph (ft_face, glyph, ft_font->load_flags))) return false; @@ -553,15 +577,21 @@ hb_ft_get_glyph_extents (hb_font_t *font, const hb_ft_font_t *ft_font = (const hb_ft_font_t *) font_data; hb_lock_t lock (ft_font->lock); FT_Face ft_face = ft_font->ft_face; + float x_mult, y_mult; #ifdef HAVE_FT_GET_TRANSFORM - FT_Matrix matrix; - FT_Get_Transform (ft_face, &matrix, nullptr); - float x_mult = matrix.xx / 65536.f; - float y_mult = matrix.yy / 65536.f; -#else - float x_mult = font->x_scale < 0 ? -1 : +1; - float y_mult = font->y_scale < 0 ? -1 : +1; + if (ft_font->transform) + { + FT_Matrix matrix; + FT_Get_Transform (ft_face, &matrix, nullptr); + x_mult = sqrtf ((float)matrix.xx * matrix.xx + (float)matrix.xy * matrix.xy) / 65536.f; + y_mult = sqrtf ((float)matrix.yx * matrix.yx + (float)matrix.yy * matrix.yy) / 65536.f; + } + else #endif + { + x_mult = font->x_scale < 0 ? -1 : +1; + y_mult = font->y_scale < 0 ? -1 : +1; + } if (unlikely (FT_Load_Glyph (ft_face, glyph, ft_font->load_flags))) return false; @@ -663,13 +693,19 @@ hb_ft_get_font_h_extents (hb_font_t *font HB_UNUSED, const hb_ft_font_t *ft_font = (const hb_ft_font_t *) font_data; hb_lock_t lock (ft_font->lock); FT_Face ft_face = ft_font->ft_face; + float y_mult; #ifdef HAVE_FT_GET_TRANSFORM - FT_Matrix matrix; - FT_Get_Transform (ft_face, &matrix, nullptr); - float y_mult = matrix.yy / 65536.f; -#else - float y_mult = font->y_scale < 0 ? -1 : +1; + if (ft_font->transform) + { + FT_Matrix matrix; + FT_Get_Transform (ft_face, &matrix, nullptr); + y_mult = sqrtf ((float)matrix.yx * matrix.yx + (float)matrix.yy * matrix.yy) / 65536.f; + } + else #endif + { + y_mult = font->y_scale < 0 ? -1 : +1; + } if (ft_face->units_per_EM != 0) { @@ -1233,13 +1269,14 @@ hb_ft_font_set_funcs (hb_font_t *font) if (FT_Select_Charmap (ft_face, FT_ENCODING_MS_SYMBOL)) FT_Select_Charmap (ft_face, FT_ENCODING_UNICODE); - _hb_ft_hb_font_changed (font, ft_face); ft_face->generic.data = blob; ft_face->generic.finalizer = (FT_Generic_Finalizer) _release_blob; _hb_ft_font_set_funcs (font, ft_face, true); hb_ft_font_set_load_flags (font, FT_LOAD_DEFAULT | FT_LOAD_NO_HINTING); + + _hb_ft_hb_font_changed (font, ft_face); } diff --git a/thirdparty/harfbuzz/src/hb-machinery.hh b/thirdparty/harfbuzz/src/hb-machinery.hh index ff2a99f5ed..2571f22e15 100644 --- a/thirdparty/harfbuzz/src/hb-machinery.hh +++ b/thirdparty/harfbuzz/src/hb-machinery.hh @@ -176,12 +176,12 @@ struct hb_lazy_loader_t : hb_data_wrapper_t<Data, WheresData> void init0 () {} /* Init, when memory is already set to 0. No-op for us. */ void init () { instance.set_relaxed (nullptr); } - void fini () { do_destroy (instance.get ()); init (); } + void fini () { do_destroy (instance.get_acquire ()); init (); } void free_instance () { retry: - Stored *p = instance.get (); + Stored *p = instance.get_acquire (); if (unlikely (p && !cmpexch (p, nullptr))) goto retry; do_destroy (p); @@ -203,7 +203,7 @@ struct hb_lazy_loader_t : hb_data_wrapper_t<Data, WheresData> Stored * get_stored () const { retry: - Stored *p = this->instance.get (); + Stored *p = this->instance.get_acquire (); if (unlikely (!p)) { if (unlikely (this->is_inert ())) diff --git a/thirdparty/harfbuzz/src/hb-object.hh b/thirdparty/harfbuzz/src/hb-object.hh index f6c7a56991..9876c2923c 100644 --- a/thirdparty/harfbuzz/src/hb-object.hh +++ b/thirdparty/harfbuzz/src/hb-object.hh @@ -144,14 +144,14 @@ struct hb_reference_count_t { mutable hb_atomic_int_t ref_count; - void init (int v = 1) { ref_count.set_relaxed (v); } - int get_relaxed () const { return ref_count.get_relaxed (); } + void init (int v = 1) { ref_count = v; } + int get_relaxed () const { return ref_count; } int inc () const { return ref_count.inc (); } int dec () const { return ref_count.dec (); } - void fini () { ref_count.set_relaxed (-0x0000DEAD); } + void fini () { ref_count = -0x0000DEAD; } - bool is_inert () const { return !ref_count.get_relaxed (); } - bool is_valid () const { return ref_count.get_relaxed () > 0; } + bool is_inert () const { return !ref_count; } + bool is_valid () const { return ref_count > 0; } }; @@ -214,15 +214,15 @@ static inline void hb_object_trace (const Type *obj, const char *function) obj ? obj->header.ref_count.get_relaxed () : 0); } -template <typename Type> -static inline Type *hb_object_create () +template <typename Type, typename ...Ts> +static inline Type *hb_object_create (Ts... ds) { Type *obj = (Type *) hb_calloc (1, sizeof (Type)); if (unlikely (!obj)) return obj; - new (obj) Type; + new (obj) Type (std::forward<Ts> (ds)...); hb_object_init (obj); hb_object_trace (obj, HB_FUNC); @@ -233,7 +233,7 @@ template <typename Type> static inline void hb_object_init (Type *obj) { obj->header.ref_count.init (); - obj->header.writable.set_relaxed (true); + obj->header.writable = true; obj->header.user_data.init (); } template <typename Type> @@ -244,12 +244,12 @@ static inline bool hb_object_is_valid (const Type *obj) template <typename Type> static inline bool hb_object_is_immutable (const Type *obj) { - return !obj->header.writable.get_relaxed (); + return !obj->header.writable; } template <typename Type> static inline void hb_object_make_immutable (const Type *obj) { - obj->header.writable.set_relaxed (false); + obj->header.writable = false; } template <typename Type> static inline Type *hb_object_reference (Type *obj) @@ -273,7 +273,8 @@ static inline bool hb_object_destroy (Type *obj) hb_object_fini (obj); - obj->~Type (); + if (!std::is_trivially_destructible<Type>::value) + obj->~Type (); return true; } @@ -281,7 +282,7 @@ template <typename Type> static inline void hb_object_fini (Type *obj) { obj->header.ref_count.fini (); /* Do this before user_data */ - hb_user_data_array_t *user_data = obj->header.user_data.get (); + hb_user_data_array_t *user_data = obj->header.user_data.get_acquire (); if (user_data) { user_data->fini (); @@ -301,7 +302,7 @@ static inline bool hb_object_set_user_data (Type *obj, assert (hb_object_is_valid (obj)); retry: - hb_user_data_array_t *user_data = obj->header.user_data.get (); + hb_user_data_array_t *user_data = obj->header.user_data.get_acquire (); if (unlikely (!user_data)) { user_data = (hb_user_data_array_t *) hb_calloc (sizeof (hb_user_data_array_t), 1); @@ -326,7 +327,7 @@ static inline void *hb_object_get_user_data (Type *obj, if (unlikely (!obj || obj->header.is_inert ())) return nullptr; assert (hb_object_is_valid (obj)); - hb_user_data_array_t *user_data = obj->header.user_data.get (); + hb_user_data_array_t *user_data = obj->header.user_data.get_acquire (); if (!user_data) return nullptr; return user_data->get (key); diff --git a/thirdparty/harfbuzz/src/hb-ot-cff1-table.hh b/thirdparty/harfbuzz/src/hb-ot-cff1-table.hh index 4aa337f78b..17b0296616 100644 --- a/thirdparty/harfbuzz/src/hb-ot-cff1-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-cff1-table.hh @@ -1379,7 +1379,7 @@ struct cff1 if (unlikely (!len)) return false; retry: - hb_sorted_vector_t<gname_t> *names = glyph_names.get (); + hb_sorted_vector_t<gname_t> *names = glyph_names.get_acquire (); if (unlikely (!names)) { names = (hb_sorted_vector_t<gname_t> *) hb_calloc (sizeof (hb_sorted_vector_t<gname_t>), 1); diff --git a/thirdparty/harfbuzz/src/hb-ot-font.cc b/thirdparty/harfbuzz/src/hb-ot-font.cc index 3f13b9994a..c90a65665c 100644 --- a/thirdparty/harfbuzz/src/hb-ot-font.cc +++ b/thirdparty/harfbuzz/src/hb-ot-font.cc @@ -59,13 +59,15 @@ * never need to call these functions directly. **/ +using hb_ot_font_advance_cache_t = hb_cache_t<24, 16, 8, true>; + struct hb_ot_font_t { const hb_ot_face_t *ot_face; /* h_advance caching */ mutable hb_atomic_int_t cached_coords_serial; - mutable hb_atomic_ptr_t<hb_advance_cache_t> advance_cache; + mutable hb_atomic_ptr_t<hb_ot_font_advance_cache_t> advance_cache; }; static hb_ot_font_t * @@ -161,14 +163,14 @@ hb_ot_get_glyph_h_advances (hb_font_t* font, void* font_data, bool use_cache = false; #endif - hb_advance_cache_t *cache = nullptr; + hb_ot_font_advance_cache_t *cache = nullptr; if (use_cache) { retry: - cache = ot_font->advance_cache.get (); + cache = ot_font->advance_cache.get_acquire (); if (unlikely (!cache)) { - cache = (hb_advance_cache_t *) hb_malloc (sizeof (hb_advance_cache_t)); + cache = (hb_ot_font_advance_cache_t *) hb_malloc (sizeof (hb_ot_font_advance_cache_t)); if (unlikely (!cache)) { use_cache = false; @@ -181,7 +183,7 @@ hb_ot_get_glyph_h_advances (hb_font_t* font, void* font_data, hb_free (cache); goto retry; } - ot_font->cached_coords_serial.set (font->serial_coords); + ot_font->cached_coords_serial.set_release (font->serial_coords); } } out: @@ -197,10 +199,10 @@ hb_ot_get_glyph_h_advances (hb_font_t* font, void* font_data, } else { /* Use cache. */ - if (ot_font->cached_coords_serial.get () != (int) font->serial_coords) + if (ot_font->cached_coords_serial.get_acquire () != (int) font->serial_coords) { ot_font->advance_cache->init (); - ot_font->cached_coords_serial.set (font->serial_coords); + ot_font->cached_coords_serial.set_release (font->serial_coords); } for (unsigned int i = 0; i < count; i++) diff --git a/thirdparty/harfbuzz/src/hb-ot-hmtx-table.hh b/thirdparty/harfbuzz/src/hb-ot-hmtx-table.hh index 50e4b54fde..96a394ba42 100644 --- a/thirdparty/harfbuzz/src/hb-ot-hmtx-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-hmtx-table.hh @@ -73,6 +73,8 @@ struct hmtxvmtx return_trace (true); } + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>>* get_mtx_map (const hb_subset_plan_t *plan) const + { return T::is_horizontal ? plan->hmtx_map : plan->vmtx_map; } bool subset_update_header (hb_subset_plan_t *plan, unsigned int num_hmetrics) const @@ -130,14 +132,15 @@ struct hmtxvmtx accelerator_t _mtx (c->plan->source); unsigned num_long_metrics; + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *mtx_map = get_mtx_map (c->plan); { /* Determine num_long_metrics to encode. */ auto& plan = c->plan; + num_long_metrics = plan->num_output_glyphs (); - hb_codepoint_t old_gid = 0; - unsigned int last_advance = plan->old_gid_for_new_gid (num_long_metrics - 1, &old_gid) ? _mtx.get_advance_without_var_unscaled (old_gid) : 0; + unsigned int last_advance = get_new_gid_advance_unscaled (plan, mtx_map, num_long_metrics - 1, _mtx); while (num_long_metrics > 1 && - last_advance == (plan->old_gid_for_new_gid (num_long_metrics - 2, &old_gid) ? _mtx.get_advance_without_var_unscaled (old_gid) : 0)) + last_advance == get_new_gid_advance_unscaled (plan, mtx_map, num_long_metrics - 2, _mtx)) { num_long_metrics--; } @@ -145,14 +148,18 @@ struct hmtxvmtx auto it = + hb_range (c->plan->num_output_glyphs ()) - | hb_map ([c, &_mtx] (unsigned _) + | hb_map ([c, &_mtx, mtx_map] (unsigned _) { - hb_codepoint_t old_gid; - if (!c->plan->old_gid_for_new_gid (_, &old_gid)) - return hb_pair (0u, 0); - int lsb = 0; - (void) _mtx.get_leading_bearing_without_var_unscaled (old_gid, &lsb); - return hb_pair (_mtx.get_advance_without_var_unscaled (old_gid), +lsb); + if (!mtx_map->has (_)) + { + hb_codepoint_t old_gid; + if (!c->plan->old_gid_for_new_gid (_, &old_gid)) + return hb_pair (0u, 0); + int lsb = 0; + (void) _mtx.get_leading_bearing_without_var_unscaled (old_gid, &lsb); + return hb_pair (_mtx.get_advance_without_var_unscaled (old_gid), +lsb); + } + return mtx_map->get (_); }) ; @@ -330,6 +337,24 @@ struct hmtxvmtx hb_blob_ptr_t<V> var_table; }; + /* get advance: when no variations, call get_advance_without_var_unscaled. + * when there're variations, get advance value from mtx_map in subset_plan*/ + unsigned get_new_gid_advance_unscaled (const hb_subset_plan_t *plan, + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *mtx_map, + unsigned new_gid, + const accelerator_t &_mtx) const + { + if (mtx_map->is_empty () || + (new_gid == 0 && !mtx_map->has (new_gid))) + { + hb_codepoint_t old_gid = 0; + return plan->old_gid_for_new_gid (new_gid, &old_gid) ? + _mtx.get_advance_without_var_unscaled (old_gid) : 0; + } + else + { return mtx_map->get (new_gid).first; } + } + protected: UnsizedArrayOf<LongMetric> longMetricZ; /* Paired advance width and leading diff --git a/thirdparty/harfbuzz/src/hb-ot-layout-common.hh b/thirdparty/harfbuzz/src/hb-ot-layout-common.hh index 0532039aad..05916a252c 100644 --- a/thirdparty/harfbuzz/src/hb-ot-layout-common.hh +++ b/thirdparty/harfbuzz/src/hb-ot-layout-common.hh @@ -84,10 +84,10 @@ using OT::Layout::MediumTypes; namespace OT { template<typename Iterator> -static inline void ClassDef_serialize (hb_serialize_context_t *c, +static inline bool ClassDef_serialize (hb_serialize_context_t *c, Iterator it); -static void ClassDef_remap_and_serialize ( +static bool ClassDef_remap_and_serialize ( hb_serialize_context_t *c, const hb_set_t &klasses, bool use_class_zero, @@ -186,6 +186,7 @@ struct hb_subset_layout_context_t : unsigned lookup_index_count; }; +struct VariationStore; struct hb_collect_variation_indices_context_t : hb_dispatch_context_t<hb_collect_variation_indices_context_t> { @@ -194,15 +195,27 @@ struct hb_collect_variation_indices_context_t : static return_t default_return_value () { return hb_empty_t (); } hb_set_t *layout_variation_indices; + hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *varidx_delta_map; + hb_font_t *font; + const VariationStore *var_store; const hb_set_t *glyph_set; const hb_map_t *gpos_lookups; + float *store_cache; hb_collect_variation_indices_context_t (hb_set_t *layout_variation_indices_, + hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *varidx_delta_map_, + hb_font_t *font_, + const VariationStore *var_store_, const hb_set_t *glyph_set_, - const hb_map_t *gpos_lookups_) : + const hb_map_t *gpos_lookups_, + float *store_cache_) : layout_variation_indices (layout_variation_indices_), + varidx_delta_map (varidx_delta_map_), + font (font_), + var_store (var_store_), glyph_set (glyph_set_), - gpos_lookups (gpos_lookups_) {} + gpos_lookups (gpos_lookups_), + store_cache (store_cache_) {} }; template<typename OutputArray> @@ -1380,17 +1393,14 @@ struct LookupOffsetList : List16OfOffsetTo<TLookup, OffsetType> */ -static void ClassDef_remap_and_serialize (hb_serialize_context_t *c, +static bool ClassDef_remap_and_serialize (hb_serialize_context_t *c, const hb_set_t &klasses, bool use_class_zero, hb_sorted_vector_t<hb_pair_t<hb_codepoint_t, hb_codepoint_t>> &glyph_and_klass, /* IN/OUT */ hb_map_t *klass_map /*IN/OUT*/) { if (!klass_map) - { - ClassDef_serialize (c, glyph_and_klass.iter ()); - return; - } + return ClassDef_serialize (c, glyph_and_klass.iter ()); /* any glyph not assigned a class value falls into Class zero (0), * if any glyph assigned to class 0, remapping must start with 0->0*/ @@ -1413,7 +1423,7 @@ static void ClassDef_remap_and_serialize (hb_serialize_context_t *c, } c->propagate_error (glyph_and_klass, klasses); - ClassDef_serialize (c, glyph_and_klass.iter ()); + return ClassDef_serialize (c, glyph_and_klass.iter ()); } /* @@ -1495,11 +1505,12 @@ struct ClassDefFormat1_3 ? hb_len (hb_iter (glyph_map.keys()) | hb_filter (glyph_filter)) : glyph_map.get_population (); use_class_zero = use_class_zero && glyph_count <= glyph_and_klass.length; - ClassDef_remap_and_serialize (c->serializer, - orig_klasses, - use_class_zero, - glyph_and_klass, - klass_map); + if (!ClassDef_remap_and_serialize (c->serializer, + orig_klasses, + use_class_zero, + glyph_and_klass, + klass_map)) + return_trace (false); return_trace (keep_empty_table || (bool) glyph_and_klass); } @@ -1736,11 +1747,12 @@ struct ClassDefFormat2_4 ? hb_len (hb_iter (glyphset) | hb_filter (glyph_filter)) : glyph_map.get_population (); use_class_zero = use_class_zero && glyph_count <= glyph_and_klass.length; - ClassDef_remap_and_serialize (c->serializer, - orig_klasses, - use_class_zero, - glyph_and_klass, - klass_map); + if (!ClassDef_remap_and_serialize (c->serializer, + orig_klasses, + use_class_zero, + glyph_and_klass, + klass_map)) + return_trace (false); return_trace (keep_empty_table || (bool) glyph_and_klass); } @@ -2124,9 +2136,9 @@ struct ClassDef }; template<typename Iterator> -static inline void ClassDef_serialize (hb_serialize_context_t *c, +static inline bool ClassDef_serialize (hb_serialize_context_t *c, Iterator it) -{ c->start_embed<ClassDef> ()->serialize (c, it); } +{ return (c->start_embed<ClassDef> ()->serialize (c, it)); } /* @@ -2280,16 +2292,16 @@ struct VarData unsigned int count = regionIndices.len; bool is_long = longWords (); unsigned word_count = wordCount (); - unsigned int scount = is_long ? count - word_count : word_count; + unsigned int scount = is_long ? count : word_count; unsigned int lcount = is_long ? word_count : 0; const HBUINT8 *bytes = get_delta_bytes (); - const HBUINT8 *row = bytes + inner * (scount + count); + const HBUINT8 *row = bytes + inner * get_row_size (); float delta = 0.; unsigned int i = 0; - const HBINT16 *lcursor = reinterpret_cast<const HBINT16 *> (row); + const HBINT32 *lcursor = reinterpret_cast<const HBINT32 *> (row); for (; i < lcount; i++) { float scalar = regions.evaluate (regionIndices.arrayZ[i], coords, coord_count, cache); @@ -2563,7 +2575,7 @@ struct VariationStore bool serialize (hb_serialize_context_t *c, const VariationStore *src, - const hb_array_t <hb_inc_bimap_t> &inner_maps) + const hb_array_t <const hb_inc_bimap_t> &inner_maps) { TRACE_SERIALIZE (this); #ifdef HB_NO_VAR @@ -2618,7 +2630,7 @@ struct VariationStore return_trace (true); } - bool subset (hb_subset_context_t *c) const + bool subset (hb_subset_context_t *c, const hb_array_t<const hb_inc_bimap_t> &inner_maps) const { TRACE_SUBSET (this); #ifdef HB_NO_VAR @@ -2628,22 +2640,7 @@ struct VariationStore VariationStore *varstore_prime = c->serializer->start_embed<VariationStore> (); if (unlikely (!varstore_prime)) return_trace (false); - const hb_set_t *variation_indices = c->plan->layout_variation_indices; - if (variation_indices->is_empty ()) return_trace (false); - - hb_vector_t<hb_inc_bimap_t> inner_maps; - inner_maps.resize ((unsigned) dataSets.len); - - for (unsigned idx : c->plan->layout_variation_indices->iter ()) - { - uint16_t major = idx >> 16; - uint16_t minor = idx & 0xFFFF; - - if (major >= inner_maps.length) - return_trace (false); - inner_maps[major].add (minor); - } - varstore_prime->serialize (c->serializer, this, inner_maps.as_array ()); + varstore_prime->serialize (c->serializer, this, inner_maps); return_trace ( !c->serializer->in_error() @@ -3169,28 +3166,36 @@ struct VariationDevice VariationStore::cache_t *store_cache = nullptr) const { return font->em_scalef_y (get_delta (font, store, store_cache)); } - VariationDevice* copy (hb_serialize_context_t *c, const hb_map_t *layout_variation_idx_map) const + VariationDevice* copy (hb_serialize_context_t *c, + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map) const { TRACE_SERIALIZE (this); + if (!layout_variation_idx_delta_map) return_trace (nullptr); auto snap = c->snapshot (); auto *out = c->embed (this); if (unlikely (!out)) return_trace (nullptr); - if (!layout_variation_idx_map || layout_variation_idx_map->is_empty ()) return_trace (out); /* TODO Just get() and bail if NO_VARIATION. Needs to setup the map to return that. */ - if (!layout_variation_idx_map->has (varIdx)) + if (!layout_variation_idx_delta_map->has (varIdx)) { c->revert (snap); return_trace (nullptr); } - unsigned new_idx = layout_variation_idx_map->get (varIdx); + unsigned new_idx = hb_first (layout_variation_idx_delta_map->get (varIdx)); out->varIdx = new_idx; return_trace (out); } - void record_variation_index (hb_set_t *layout_variation_indices) const + void collect_variation_index (hb_collect_variation_indices_context_t *c) const { - layout_variation_indices->add (varIdx); + c->layout_variation_indices->add (varIdx); + int delta = 0; + if (c->font && c->var_store) + delta = roundf (get_delta (c->font, *c->var_store, c->store_cache)); + + /* set new varidx to HB_OT_LAYOUT_NO_VARIATIONS_INDEX here, will remap + * varidx later*/ + c->varidx_delta_map->set (varIdx, hb_pair_t<unsigned, int> (HB_OT_LAYOUT_NO_VARIATIONS_INDEX, delta)); } bool sanitize (hb_sanitize_context_t *c) const @@ -3283,7 +3288,8 @@ struct Device } } - Device* copy (hb_serialize_context_t *c, const hb_map_t *layout_variation_idx_map=nullptr) const + Device* copy (hb_serialize_context_t *c, + const hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map=nullptr) const { TRACE_SERIALIZE (this); switch (u.b.format) { @@ -3295,14 +3301,14 @@ struct Device #endif #ifndef HB_NO_VAR case 0x8000: - return_trace (reinterpret_cast<Device *> (u.variation.copy (c, layout_variation_idx_map))); + return_trace (reinterpret_cast<Device *> (u.variation.copy (c, layout_variation_idx_delta_map))); #endif default: return_trace (nullptr); } } - void collect_variation_indices (hb_set_t *layout_variation_indices) const + void collect_variation_indices (hb_collect_variation_indices_context_t *c) const { switch (u.b.format) { #ifndef HB_NO_HINTING @@ -3313,7 +3319,7 @@ struct Device #endif #ifndef HB_NO_VAR case 0x8000: - u.variation.record_variation_index (layout_variation_indices); + u.variation.collect_variation_index (c); return; #endif default: @@ -3321,6 +3327,18 @@ struct Device } } + unsigned get_variation_index () const + { + switch (u.b.format) { +#ifndef HB_NO_VAR + case 0x8000: + return u.variation.varIdx; +#endif + default: + return HB_OT_LAYOUT_NO_VARIATIONS_INDEX; + } + } + protected: union { DeviceHeader b; diff --git a/thirdparty/harfbuzz/src/hb-ot-layout-gdef-table.hh b/thirdparty/harfbuzz/src/hb-ot-layout-gdef-table.hh index 5bc26d9182..22925fdfa9 100644 --- a/thirdparty/harfbuzz/src/hb-ot-layout-gdef-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-layout-gdef-table.hh @@ -200,15 +200,34 @@ struct CaretValueFormat3 bool subset (hb_subset_context_t *c) const { TRACE_SUBSET (this); - auto *out = c->serializer->embed (this); + auto *out = c->serializer->start_embed (*this); if (unlikely (!out)) return_trace (false); + if (!c->serializer->embed (caretValueFormat)) return_trace (false); + if (!c->serializer->embed (coordinate)) return_trace (false); + + unsigned varidx = (this+deviceTable).get_variation_index (); + if (c->plan->layout_variation_idx_delta_map->has (varidx)) + { + int delta = hb_second (c->plan->layout_variation_idx_delta_map->get (varidx)); + if (delta != 0) + { + if (!c->serializer->check_assign (out->coordinate, coordinate + delta, HB_SERIALIZE_ERROR_INT_OVERFLOW)) + return_trace (false); + } + } + + if (c->plan->all_axes_pinned) + return_trace (c->serializer->check_assign (out->caretValueFormat, 1, HB_SERIALIZE_ERROR_INT_OVERFLOW)); + + if (!c->serializer->embed (deviceTable)) + return_trace (false); return_trace (out->deviceTable.serialize_copy (c->serializer, deviceTable, this, c->serializer->to_bias (out), - hb_serialize_context_t::Head, c->plan->layout_variation_idx_map)); + hb_serialize_context_t::Head, c->plan->layout_variation_idx_delta_map)); } - void collect_variation_indices (hb_set_t *layout_variation_indices) const - { (this+deviceTable).collect_variation_indices (layout_variation_indices); } + void collect_variation_indices (hb_collect_variation_indices_context_t *c) const + { (this+deviceTable).collect_variation_indices (c); } bool sanitize (hb_sanitize_context_t *c) const { @@ -255,14 +274,14 @@ struct CaretValue } } - void collect_variation_indices (hb_set_t *layout_variation_indices) const + void collect_variation_indices (hb_collect_variation_indices_context_t *c) const { switch (u.format) { case 1: case 2: return; case 3: - u.format3.collect_variation_indices (layout_variation_indices); + u.format3.collect_variation_indices (c); return; default: return; } @@ -329,7 +348,7 @@ struct LigGlyph void collect_variation_indices (hb_collect_variation_indices_context_t *c) const { for (const Offset16To<CaretValue>& offset : carets.iter ()) - (this+offset).collect_variation_indices (c->layout_variation_indices); + (this+offset).collect_variation_indices (c); } bool sanitize (hb_sanitize_context_t *c) const @@ -586,7 +605,10 @@ struct GDEFVersion1_2 bool subset_varstore = false; if (version.to_int () >= 0x00010003u) { - subset_varstore = out->varStore.serialize_subset (c, varStore, this); + if (c->plan->all_axes_pinned) + out->varStore = 0; + else + subset_varstore = out->varStore.serialize_subset (c, varStore, this, c->plan->gdef_varstore_inner_maps.as_array ()); } if (subset_varstore) @@ -846,7 +868,7 @@ struct GDEF { get_lig_caret_list ().collect_variation_indices (c); } void remap_layout_variation_indices (const hb_set_t *layout_variation_indices, - hb_map_t *layout_variation_idx_map /* OUT */) const + hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map /* OUT */) const { if (!has_var_store ()) return; if (layout_variation_indices->is_empty ()) return; @@ -864,7 +886,11 @@ struct GDEF } unsigned new_idx = (new_major << 16) + new_minor; - layout_variation_idx_map->set (idx, new_idx); + if (!layout_variation_idx_delta_map->has (idx)) + continue; + int delta = hb_second (layout_variation_idx_delta_map->get (idx)); + + layout_variation_idx_delta_map->set (idx, hb_pair_t<unsigned, int> (new_idx, delta)); ++new_minor; last_major = major; } diff --git a/thirdparty/harfbuzz/src/hb-ot-layout-gsubgpos.hh b/thirdparty/harfbuzz/src/hb-ot-layout-gsubgpos.hh index c77ec12fbe..c15a42b0f1 100644 --- a/thirdparty/harfbuzz/src/hb-ot-layout-gsubgpos.hh +++ b/thirdparty/harfbuzz/src/hb-ot-layout-gsubgpos.hh @@ -4261,6 +4261,7 @@ struct GSUBGPOS } void prune_langsys (const hb_map_t *duplicate_feature_map, + const hb_set_t *layout_scripts, hb_hashmap_t<unsigned, hb::unique_ptr<hb_set_t>> *script_langsys_map, hb_set_t *new_feature_indexes /* OUT */) const { @@ -4269,6 +4270,8 @@ struct GSUBGPOS unsigned count = get_script_count (); for (unsigned script_index = 0; script_index < count; script_index++) { + const Tag& tag = get_script_tag (script_index); + if (!layout_scripts->has (tag)) continue; const Script& s = get_script (script_index); s.prune_langsys (&c, script_index); } diff --git a/thirdparty/harfbuzz/src/hb-ot-layout.cc b/thirdparty/harfbuzz/src/hb-ot-layout.cc index f9c0daa486..44e57987b7 100644 --- a/thirdparty/harfbuzz/src/hb-ot-layout.cc +++ b/thirdparty/harfbuzz/src/hb-ot-layout.cc @@ -601,9 +601,13 @@ hb_ot_layout_table_select_script (hb_face_t *face, * @feature_tags: (out) (array length=feature_count): Array of feature tags found in the table * * Fetches a list of all feature tags in the given face's GSUB or GPOS table. + * Note that there might be duplicate feature tags, belonging to different + * script/language-system pairs of the table. * * Return value: Total number of feature tags. * + * Since: 0.6.0 + * **/ unsigned int hb_ot_layout_table_get_feature_tags (hb_face_t *face, @@ -629,6 +633,9 @@ hb_ot_layout_table_get_feature_tags (hb_face_t *face, * or GPOS table. * * Return value: `true` if the feature is found, `false` otherwise + * + * Since: 0.6.0 + * **/ bool hb_ot_layout_table_find_feature (hb_face_t *face, @@ -668,6 +675,8 @@ hb_ot_layout_table_find_feature (hb_face_t *face, * * Return value: Total number of language tags. * + * Since: 0.6.0 + * **/ unsigned int hb_ot_layout_script_get_language_tags (hb_face_t *face, @@ -778,6 +787,8 @@ hb_ot_layout_script_select_language (hb_face_t *face, * * Return value: `true` if the feature is found, `false` otherwise * + * Since: 0.6.0 + * **/ hb_bool_t hb_ot_layout_language_get_required_feature_index (hb_face_t *face, @@ -846,6 +857,9 @@ hb_ot_layout_language_get_required_feature (hb_face_t *face, * returned will begin at the offset provided. * * Return value: Total number of features. + * + * Since: 0.6.0 + * **/ unsigned int hb_ot_layout_language_get_feature_indexes (hb_face_t *face, @@ -879,6 +893,9 @@ hb_ot_layout_language_get_feature_indexes (hb_face_t *face, * returned will begin at the offset provided. * * Return value: Total number of feature tags. + * + * Since: 0.6.0 + * **/ unsigned int hb_ot_layout_language_get_feature_tags (hb_face_t *face, @@ -919,6 +936,8 @@ hb_ot_layout_language_get_feature_tags (hb_face_t *face, * * Return value: `true` if the feature is found, `false` otherwise * + * Since: 0.6.0 + * **/ hb_bool_t hb_ot_layout_language_find_feature (hb_face_t *face, @@ -1167,9 +1186,12 @@ script_collect_features (hb_collect_features_context_t *c, * hb_ot_layout_collect_features: * @face: #hb_face_t to work upon * @table_tag: #HB_OT_TAG_GSUB or #HB_OT_TAG_GPOS - * @scripts: The array of scripts to collect features for - * @languages: The array of languages to collect features for - * @features: The array of features to collect + * @scripts: (nullable) (array zero-terminated=1): The array of scripts to collect features for, + * terminated by %HB_TAG_NONE + * @languages: (nullable) (array zero-terminated=1): The array of languages to collect features for, + * terminated by %HB_TAG_NONE + * @features: (nullable) (array zero-terminated=1): The array of features to collect, + * terminated by %HB_TAG_NONE * @feature_indexes: (out): The array of feature indexes found for the query * * Fetches a list of all feature indexes in the specified face's GSUB table @@ -1216,9 +1238,12 @@ hb_ot_layout_collect_features (hb_face_t *face, * hb_ot_layout_collect_lookups: * @face: #hb_face_t to work upon * @table_tag: #HB_OT_TAG_GSUB or #HB_OT_TAG_GPOS - * @scripts: The array of scripts to collect lookups for - * @languages: The array of languages to collect lookups for - * @features: The array of features to collect lookups for + * @scripts: (nullable) (array zero-terminated=1): The array of scripts to collect lookups for, + * terminated by %HB_TAG_NONE + * @languages: (nullable) (array zero-terminated=1): The array of languages to collect lookups for, + * terminated by %HB_TAG_NONE + * @features: (nullable) (array zero-terminated=1): The array of features to collect lookups for, + * terminated by %HB_TAG_NONE * @lookup_indexes: (out): The array of lookup indexes found for the query * * Fetches a list of all feature-lookup indexes in the specified face's GSUB @@ -1316,6 +1341,8 @@ hb_ot_layout_lookup_collect_glyphs (hb_face_t *face, * * Return value: `true` if feature variations were found, `false` otherwise. * + * Since: 1.4.0 + * **/ hb_bool_t hb_ot_layout_table_find_feature_variations (hb_face_t *face, @@ -1347,6 +1374,8 @@ hb_ot_layout_table_find_feature_variations (hb_face_t *face, * * Return value: Total number of lookups. * + * Since: 1.4.0 + * **/ unsigned int hb_ot_layout_feature_with_variations_get_lookups (hb_face_t *face, @@ -1379,6 +1408,8 @@ hb_ot_layout_feature_with_variations_get_lookups (hb_face_t *face, * * Return value: `true` if data found, `false` otherwise * + * Since: 0.6.0 + * **/ hb_bool_t hb_ot_layout_has_substitution (hb_face_t *face) @@ -2297,11 +2328,6 @@ struct hb_get_glyph_alternates_dispatch_t : static return_t default_return_value () { return 0; } bool stop_sublookup_iteration (return_t r) const { return r; } - hb_face_t *face; - - hb_get_glyph_alternates_dispatch_t (hb_face_t *face) : - face (face) {} - private: template <typename T, typename ...Ts> auto _dispatch (const T &obj, hb_priority<1>, Ts&&... ds) HB_AUTO_RETURN @@ -2340,7 +2366,7 @@ hb_ot_layout_lookup_get_glyph_alternates (hb_face_t *face, unsigned *alternate_count /* IN/OUT. May be NULL. */, hb_codepoint_t *alternate_glyphs /* OUT. May be NULL. */) { - hb_get_glyph_alternates_dispatch_t c (face); + hb_get_glyph_alternates_dispatch_t c; const OT::SubstLookup &lookup = face->table.GSUB->table->get_lookup (lookup_index); auto ret = lookup.dispatch (&c, glyph, start_offset, alternate_count, alternate_glyphs); if (!ret && alternate_count) *alternate_count = 0; diff --git a/thirdparty/harfbuzz/src/hb-ot-os2-table.hh b/thirdparty/harfbuzz/src/hb-ot-os2-table.hh index 3473afef54..c6e8fad6fc 100644 --- a/thirdparty/harfbuzz/src/hb-ot-os2-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-os2-table.hh @@ -166,6 +166,47 @@ struct OS2 } } + float map_wdth_to_widthclass(float width) const + { + if (width < 50) return 1.0f; + if (width > 200) return 9.0f; + + float ratio = (width - 50) / 12.5f; + int a = (int) floorf (ratio); + int b = (int) ceilf (ratio); + + /* follow this maping: + * https://docs.microsoft.com/en-us/typography/opentype/spec/os2#uswidthclass + */ + if (b <= 6) // 50-125 + { + if (a == b) return a + 1.0f; + } + else if (b == 7) // no mapping for 137.5 + { + a = 6; + b = 8; + } + else if (b == 8) + { + if (a == b) return 8.0f; // 150 + a = 6; + } + else + { + if (a == b && a == 12) return 9.0f; //200 + b = 12; + a = 8; + } + + float va = 50 + a * 12.5f; + float vb = 50 + b * 12.5f; + + float ret = a + (width - va) / (vb - va); + if (a <= 6) ret += 1.0f; + return ret; + } + bool subset (hb_subset_context_t *c) const { TRACE_SUBSET (this); @@ -183,6 +224,26 @@ struct OS2 _update_unicode_ranges (c->plan->unicodes, os2_prime->ulUnicodeRange); + if (c->plan->user_axes_location->has (HB_TAG ('w','g','h','t')) && + !c->plan->pinned_at_default) + { + float weight_class = c->plan->user_axes_location->get (HB_TAG ('w','g','h','t')); + if (!c->serializer->check_assign (os2_prime->usWeightClass, + roundf (hb_clamp (weight_class, 1.0f, 1000.0f)), + HB_SERIALIZE_ERROR_INT_OVERFLOW)) + return_trace (false); + } + + if (c->plan->user_axes_location->has (HB_TAG ('w','d','t','h')) && + !c->plan->pinned_at_default) + { + float width = c->plan->user_axes_location->get (HB_TAG ('w','d','t','h')); + if (!c->serializer->check_assign (os2_prime->usWidthClass, + roundf (map_wdth_to_widthclass (width)), + HB_SERIALIZE_ERROR_INT_OVERFLOW)) + return_trace (false); + } + return_trace (true); } diff --git a/thirdparty/harfbuzz/src/hb-ot-post-table.hh b/thirdparty/harfbuzz/src/hb-ot-post-table.hh index a4c0c4aa17..80d02ffba7 100644 --- a/thirdparty/harfbuzz/src/hb-ot-post-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-post-table.hh @@ -102,6 +102,14 @@ struct post if (!serialize (c->serializer, glyph_names)) return_trace (false); + if (c->plan->user_axes_location->has (HB_TAG ('s','l','n','t')) && + !c->plan->pinned_at_default) + { + float italic_angle = c->plan->user_axes_location->get (HB_TAG ('s','l','n','t')); + italic_angle = hb_max (-90.f, hb_min (italic_angle, 90.f)); + post_prime->italicAngle.set_float (italic_angle); + } + if (glyph_names && version.major == 2) return_trace (v2X.subset (c)); @@ -133,7 +141,7 @@ struct post } ~accelerator_t () { - hb_free (gids_sorted_by_name.get ()); + hb_free (gids_sorted_by_name.get_acquire ()); table.destroy (); } @@ -160,7 +168,7 @@ struct post if (unlikely (!len)) return false; retry: - uint16_t *gids = gids_sorted_by_name.get (); + uint16_t *gids = gids_sorted_by_name.get_acquire (); if (unlikely (!gids)) { diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-joining-list.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-joining-list.hh index a5ce3a6c93..c7b57820af 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-joining-list.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-joining-list.hh @@ -6,10 +6,10 @@ * * on files with these headers: * - * # ArabicShaping-14.0.0.txt - * # Date: 2021-05-21, 01:54:00 GMT [KW, RP] - * # Scripts-14.0.0.txt - * # Date: 2021-07-10, 00:35:31 GMT + * # ArabicShaping-15.0.0.txt + * # Date: 2022-02-14, 18:50:00 GMT [KW, RP] + * # Scripts-15.0.0.txt + * # Date: 2022-04-26, 23:15:02 GMT */ #ifndef HB_OT_SHAPER_ARABIC_JOINING_LIST_HH diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-table.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-table.hh index fd3d8645d1..d7670f2f95 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-arabic-table.hh @@ -6,10 +6,10 @@ * * on files with these headers: * - * # ArabicShaping-14.0.0.txt - * # Date: 2021-05-21, 01:54:00 GMT [KW, RP] - * # Blocks-14.0.0.txt - * # Date: 2021-01-22, 23:29:00 GMT [KW] + * # ArabicShaping-15.0.0.txt + * # Date: 2022-02-14, 18:50:00 GMT [KW, RP] + * # Blocks-15.0.0.txt + * # Date: 2022-01-28, 20:58:00 GMT [KW] * UnicodeData.txt does not have a header. */ diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-indic-machine.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-indic-machine.hh index d3a7cce3de..d52b13f616 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-indic-machine.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-indic-machine.hh @@ -53,7 +53,7 @@ enum indic_syllable_type_t { }; -#line 54 "hb-ot-shaper-indic-machine.hh" +#line 57 "hb-ot-shaper-indic-machine.hh" #define indic_syllable_machine_ex_A 9u #define indic_syllable_machine_ex_C 1u #define indic_syllable_machine_ex_CM 16u @@ -75,7 +75,7 @@ enum indic_syllable_type_t { #define indic_syllable_machine_ex_ZWNJ 5u -#line 74 "hb-ot-shaper-indic-machine.hh" +#line 79 "hb-ot-shaper-indic-machine.hh" static const unsigned char _indic_syllable_machine_trans_keys[] = { 8u, 8u, 4u, 8u, 5u, 7u, 5u, 8u, 4u, 8u, 4u, 12u, 4u, 8u, 8u, 8u, 5u, 7u, 5u, 8u, 4u, 8u, 4u, 12u, 4u, 12u, 4u, 12u, 8u, 8u, 5u, 7u, @@ -422,7 +422,7 @@ find_syllables_indic (hb_buffer_t *buffer) int cs; hb_glyph_info_t *info = buffer->info; -#line 415 "hb-ot-shaper-indic-machine.hh" +#line 426 "hb-ot-shaper-indic-machine.hh" { cs = indic_syllable_machine_start; ts = 0; @@ -438,7 +438,7 @@ find_syllables_indic (hb_buffer_t *buffer) unsigned int syllable_serial = 1; -#line 427 "hb-ot-shaper-indic-machine.hh" +#line 442 "hb-ot-shaper-indic-machine.hh" { int _slen; int _trans; @@ -452,7 +452,7 @@ _resume: #line 1 "NONE" {ts = p;} break; -#line 439 "hb-ot-shaper-indic-machine.hh" +#line 456 "hb-ot-shaper-indic-machine.hh" } _keys = _indic_syllable_machine_trans_keys + (cs<<1); @@ -555,7 +555,7 @@ _eof_trans: #line 113 "hb-ot-shaper-indic-machine.rl" {act = 6;} break; -#line 521 "hb-ot-shaper-indic-machine.hh" +#line 559 "hb-ot-shaper-indic-machine.hh" } _again: @@ -564,7 +564,7 @@ _again: #line 1 "NONE" {ts = 0;} break; -#line 528 "hb-ot-shaper-indic-machine.hh" +#line 568 "hb-ot-shaper-indic-machine.hh" } if ( ++p != pe ) diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-indic-table.cc b/thirdparty/harfbuzz/src/hb-ot-shaper-indic-table.cc index 8994f3ca59..bf6a2757bb 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-indic-table.cc +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-indic-table.cc @@ -6,12 +6,12 @@ * * on files with these headers: * - * # IndicSyllabicCategory-14.0.0.txt - * # Date: 2021-05-22, 01:01:00 GMT [KW, RP] - * # IndicPositionalCategory-14.0.0.txt - * # Date: 2021-05-22, 01:01:00 GMT [KW, RP] - * # Blocks-14.0.0.txt - * # Date: 2021-01-22, 23:29:00 GMT [KW] + * # IndicSyllabicCategory-15.0.0.txt + * # Date: 2022-05-26, 02:18:00 GMT [KW, RP] + * # IndicPositionalCategory-15.0.0.txt + * # Date: 2022-05-26, 02:18:00 GMT [KW, RP] + * # Blocks-15.0.0.txt + * # Date: 2022-01-28, 20:58:00 GMT [KW] */ #include "hb.hh" @@ -92,7 +92,7 @@ static_assert (OT_VPst == M_Cat(VPst), ""); #define _OT_R OT_Ra /* 14 chars; Ra */ #define _OT_Rf OT_Repha /* 1 chars; Repha */ #define _OT_Rt OT_Robatic /* 3 chars; Robatic */ -#define _OT_SM OT_SM /* 55 chars; SM */ +#define _OT_SM OT_SM /* 56 chars; SM */ #define _OT_S OT_Symbol /* 22 chars; Symbol */ #define _OT_V OT_V /* 172 chars; V */ #define _OT_VA OT_VAbv /* 18 chars; VAbv */ @@ -117,7 +117,7 @@ static_assert (OT_VPst == M_Cat(VPst), ""); #define _POS_R POS_POST_C /* 13 chars; POST_C */ #define _POS_L POS_PRE_C /* 5 chars; PRE_C */ #define _POS_LM POS_PRE_M /* 14 chars; PRE_M */ -#define _POS_SM POS_SMVD /* 129 chars; SMVD */ +#define _POS_SM POS_SMVD /* 130 chars; SMVD */ #pragma GCC diagnostic pop @@ -301,7 +301,7 @@ static const uint16_t indic_table[] = { /* 0CD8 */ _(X,X), _(X,X), _(X,X), _(X,X), _(X,X), _(C,C), _(C,C), _(X,X), /* 0CE0 */ _(V,C), _(V,C), _(M,BS), _(M,BS), _(X,X), _(X,X), _(GB,C), _(GB,C), /* 0CE8 */ _(GB,C), _(GB,C), _(GB,C), _(GB,C), _(GB,C), _(GB,C), _(GB,C), _(GB,C), - /* 0CF0 */ _(X,X), _(CS,C), _(CS,C), _(X,X), _(X,X), _(X,X), _(X,X), _(X,X), + /* 0CF0 */ _(X,X), _(CS,C), _(CS,C),_(SM,SM), _(X,X), _(X,X), _(X,X), _(X,X), /* 0CF8 */ _(X,X), _(X,X), _(X,X), _(X,X), _(X,X), _(X,X), _(X,X), _(X,X), /* Malayalam */ diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-indic.cc b/thirdparty/harfbuzz/src/hb-ot-shaper-indic.cc index 6eb400ab16..55509c1101 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-indic.cc +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-indic.cc @@ -276,7 +276,7 @@ struct indic_shape_plan_t { bool load_virama_glyph (hb_font_t *font, hb_codepoint_t *pglyph) const { - hb_codepoint_t glyph = virama_glyph.get_relaxed (); + hb_codepoint_t glyph = virama_glyph; if (unlikely (glyph == (hb_codepoint_t) -1)) { if (!config->virama || !font->get_nominal_glyph (config->virama, &glyph)) @@ -286,7 +286,7 @@ struct indic_shape_plan_t /* Our get_nominal_glyph() function needs a font, so we can't get the virama glyph * during shape planning... Instead, overwrite it here. */ - virama_glyph.set_relaxed ((int) glyph); + virama_glyph = (int) glyph; } *pglyph = glyph; @@ -330,7 +330,7 @@ data_create_indic (const hb_ot_shape_plan_t *plan) #ifndef HB_NO_UNISCRIBE_BUG_COMPATIBLE indic_plan->uniscribe_bug_compatible = hb_options ().uniscribe_bug_compatible; #endif - indic_plan->virama_glyph.set_relaxed (-1); + indic_plan->virama_glyph = -1; /* Use zero-context would_substitute() matching for new-spec of the main * Indic scripts, and scripts with one spec only, but not for old-specs. @@ -992,7 +992,7 @@ final_reordering_syllable_indic (const hb_ot_shape_plan_t *plan, * class of I_Cat(H) is desired but has been lost. */ /* We don't call load_virama_glyph(), since we know it's already * loaded. */ - hb_codepoint_t virama_glyph = indic_plan->virama_glyph.get_relaxed (); + hb_codepoint_t virama_glyph = indic_plan->virama_glyph; if (virama_glyph) { for (unsigned int i = start; i < end; i++) diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-khmer-machine.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-khmer-machine.hh index 2c40663bdd..e18bd75ef1 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-khmer-machine.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-khmer-machine.hh @@ -48,7 +48,7 @@ enum khmer_syllable_type_t { }; -#line 49 "hb-ot-shaper-khmer-machine.hh" +#line 52 "hb-ot-shaper-khmer-machine.hh" #define khmer_syllable_machine_ex_C 1u #define khmer_syllable_machine_ex_DOTTEDCIRCLE 11u #define khmer_syllable_machine_ex_H 4u @@ -66,7 +66,7 @@ enum khmer_syllable_type_t { #define khmer_syllable_machine_ex_ZWNJ 5u -#line 65 "hb-ot-shaper-khmer-machine.hh" +#line 70 "hb-ot-shaper-khmer-machine.hh" static const unsigned char _khmer_syllable_machine_trans_keys[] = { 5u, 26u, 5u, 26u, 1u, 15u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 5u, 26u, 1u, 15u, 5u, 26u, 5u, 26u, @@ -294,7 +294,7 @@ find_syllables_khmer (hb_buffer_t *buffer) int cs; hb_glyph_info_t *info = buffer->info; -#line 287 "hb-ot-shaper-khmer-machine.hh" +#line 298 "hb-ot-shaper-khmer-machine.hh" { cs = khmer_syllable_machine_start; ts = 0; @@ -310,7 +310,7 @@ find_syllables_khmer (hb_buffer_t *buffer) unsigned int syllable_serial = 1; -#line 299 "hb-ot-shaper-khmer-machine.hh" +#line 314 "hb-ot-shaper-khmer-machine.hh" { int _slen; int _trans; @@ -324,7 +324,7 @@ _resume: #line 1 "NONE" {ts = p;} break; -#line 311 "hb-ot-shaper-khmer-machine.hh" +#line 328 "hb-ot-shaper-khmer-machine.hh" } _keys = _khmer_syllable_machine_trans_keys + (cs<<1); @@ -394,7 +394,7 @@ _eof_trans: #line 98 "hb-ot-shaper-khmer-machine.rl" {act = 3;} break; -#line 368 "hb-ot-shaper-khmer-machine.hh" +#line 398 "hb-ot-shaper-khmer-machine.hh" } _again: @@ -403,7 +403,7 @@ _again: #line 1 "NONE" {ts = 0;} break; -#line 375 "hb-ot-shaper-khmer-machine.hh" +#line 407 "hb-ot-shaper-khmer-machine.hh" } if ( ++p != pe ) diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-myanmar-machine.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-myanmar-machine.hh index 464cf796d4..b109708937 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-myanmar-machine.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-myanmar-machine.hh @@ -50,7 +50,7 @@ enum myanmar_syllable_type_t { }; -#line 51 "hb-ot-shaper-myanmar-machine.hh" +#line 54 "hb-ot-shaper-myanmar-machine.hh" #define myanmar_syllable_machine_ex_A 9u #define myanmar_syllable_machine_ex_As 32u #define myanmar_syllable_machine_ex_C 1u @@ -77,7 +77,7 @@ enum myanmar_syllable_type_t { #define myanmar_syllable_machine_ex_ZWNJ 5u -#line 76 "hb-ot-shaper-myanmar-machine.hh" +#line 81 "hb-ot-shaper-myanmar-machine.hh" static const unsigned char _myanmar_syllable_machine_trans_keys[] = { 1u, 41u, 3u, 41u, 5u, 39u, 5u, 8u, 3u, 41u, 3u, 39u, 3u, 39u, 5u, 39u, 5u, 39u, 3u, 39u, 3u, 39u, 3u, 41u, 5u, 39u, 1u, 15u, 3u, 39u, 3u, 39u, @@ -443,7 +443,7 @@ find_syllables_myanmar (hb_buffer_t *buffer) int cs; hb_glyph_info_t *info = buffer->info; -#line 436 "hb-ot-shaper-myanmar-machine.hh" +#line 447 "hb-ot-shaper-myanmar-machine.hh" { cs = myanmar_syllable_machine_start; ts = 0; @@ -459,7 +459,7 @@ find_syllables_myanmar (hb_buffer_t *buffer) unsigned int syllable_serial = 1; -#line 448 "hb-ot-shaper-myanmar-machine.hh" +#line 463 "hb-ot-shaper-myanmar-machine.hh" { int _slen; int _trans; @@ -473,7 +473,7 @@ _resume: #line 1 "NONE" {ts = p;} break; -#line 460 "hb-ot-shaper-myanmar-machine.hh" +#line 477 "hb-ot-shaper-myanmar-machine.hh" } _keys = _myanmar_syllable_machine_trans_keys + (cs<<1); @@ -519,7 +519,7 @@ _eof_trans: #line 113 "hb-ot-shaper-myanmar-machine.rl" {te = p;p--;{ found_syllable (myanmar_non_myanmar_cluster); }} break; -#line 498 "hb-ot-shaper-myanmar-machine.hh" +#line 523 "hb-ot-shaper-myanmar-machine.hh" } _again: @@ -528,7 +528,7 @@ _again: #line 1 "NONE" {ts = 0;} break; -#line 505 "hb-ot-shaper-myanmar-machine.hh" +#line 532 "hb-ot-shaper-myanmar-machine.hh" } if ( ++p != pe ) diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-use-machine.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-use-machine.hh index 5b3ec05616..41e8a34f3b 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-use-machine.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-use-machine.hh @@ -53,7 +53,7 @@ enum use_syllable_type_t { }; -#line 54 "hb-ot-shaper-use-machine.hh" +#line 57 "hb-ot-shaper-use-machine.hh" #define use_syllable_machine_ex_B 1u #define use_syllable_machine_ex_CGJ 6u #define use_syllable_machine_ex_CMAbv 31u @@ -97,523 +97,669 @@ enum use_syllable_type_t { #define use_syllable_machine_ex_ZWNJ 14u -#line 96 "hb-ot-shaper-use-machine.hh" +#line 101 "hb-ot-shaper-use-machine.hh" static const unsigned char _use_syllable_machine_trans_keys[] = { - 0u, 53u, 11u, 53u, 11u, 53u, 1u, 53u, 23u, 48u, 24u, 47u, 25u, 47u, 26u, 47u, - 45u, 46u, 46u, 46u, 24u, 48u, 24u, 48u, 24u, 48u, 1u, 1u, 24u, 48u, 22u, 53u, - 23u, 53u, 23u, 53u, 23u, 53u, 12u, 53u, 23u, 53u, 12u, 53u, 12u, 53u, 12u, 53u, - 11u, 53u, 1u, 1u, 1u, 48u, 11u, 53u, 41u, 42u, 42u, 42u, 11u, 53u, 11u, 53u, - 1u, 53u, 23u, 48u, 24u, 47u, 25u, 47u, 26u, 47u, 45u, 46u, 46u, 46u, 24u, 48u, - 24u, 48u, 24u, 48u, 1u, 1u, 24u, 48u, 22u, 53u, 23u, 53u, 23u, 53u, 23u, 53u, - 12u, 53u, 23u, 53u, 12u, 53u, 12u, 53u, 12u, 53u, 11u, 53u, 1u, 1u, 1u, 48u, - 13u, 13u, 4u, 4u, 11u, 53u, 11u, 53u, 1u, 53u, 23u, 48u, 24u, 47u, 25u, 47u, - 26u, 47u, 45u, 46u, 46u, 46u, 24u, 48u, 24u, 48u, 24u, 48u, 1u, 1u, 24u, 48u, - 22u, 53u, 23u, 53u, 23u, 53u, 23u, 53u, 12u, 53u, 23u, 53u, 12u, 53u, 12u, 53u, - 12u, 53u, 11u, 53u, 1u, 1u, 1u, 48u, 11u, 53u, 11u, 53u, 1u, 53u, 23u, 48u, - 24u, 47u, 25u, 47u, 26u, 47u, 45u, 46u, 46u, 46u, 24u, 48u, 24u, 48u, 24u, 48u, - 1u, 1u, 24u, 48u, 22u, 53u, 23u, 53u, 23u, 53u, 23u, 53u, 12u, 53u, 23u, 53u, - 12u, 53u, 12u, 53u, 12u, 53u, 11u, 53u, 1u, 1u, 1u, 48u, 4u, 4u, 13u, 13u, - 1u, 53u, 11u, 53u, 41u, 42u, 42u, 42u, 1u, 5u, 50u, 52u, 49u, 52u, 49u, 51u, - 0 + 0u, 53u, 11u, 53u, 11u, 53u, 1u, 53u, 14u, 48u, 14u, 47u, 14u, 47u, 14u, 47u, + 14u, 46u, 14u, 46u, 14u, 14u, 14u, 48u, 14u, 48u, 14u, 48u, 1u, 14u, 14u, 48u, + 14u, 53u, 14u, 53u, 14u, 53u, 14u, 53u, 12u, 53u, 14u, 53u, 12u, 53u, 12u, 53u, + 12u, 53u, 11u, 53u, 1u, 14u, 1u, 48u, 11u, 53u, 14u, 42u, 14u, 42u, 11u, 53u, + 11u, 53u, 1u, 53u, 14u, 48u, 14u, 47u, 14u, 47u, 14u, 47u, 14u, 46u, 14u, 46u, + 14u, 14u, 14u, 48u, 14u, 48u, 14u, 48u, 1u, 14u, 14u, 48u, 14u, 53u, 14u, 53u, + 14u, 53u, 14u, 53u, 12u, 53u, 14u, 53u, 12u, 53u, 12u, 53u, 12u, 53u, 11u, 53u, + 1u, 14u, 1u, 14u, 1u, 48u, 13u, 14u, 4u, 14u, 11u, 53u, 11u, 53u, 1u, 53u, + 14u, 48u, 14u, 47u, 14u, 47u, 14u, 47u, 14u, 46u, 14u, 46u, 14u, 14u, 14u, 48u, + 14u, 48u, 14u, 48u, 1u, 14u, 14u, 48u, 14u, 53u, 14u, 53u, 14u, 53u, 14u, 53u, + 12u, 53u, 14u, 53u, 12u, 53u, 12u, 53u, 12u, 53u, 11u, 53u, 1u, 14u, 1u, 14u, + 1u, 48u, 11u, 53u, 11u, 53u, 1u, 53u, 14u, 48u, 14u, 47u, 14u, 47u, 14u, 47u, + 14u, 46u, 14u, 46u, 14u, 14u, 14u, 48u, 14u, 48u, 14u, 48u, 1u, 14u, 14u, 48u, + 14u, 53u, 14u, 53u, 14u, 53u, 14u, 53u, 12u, 53u, 14u, 53u, 12u, 53u, 12u, 53u, + 12u, 53u, 11u, 53u, 1u, 14u, 1u, 48u, 4u, 14u, 13u, 14u, 1u, 53u, 11u, 53u, + 14u, 42u, 14u, 42u, 1u, 5u, 14u, 52u, 14u, 52u, 14u, 51u, 0 }; static const char _use_syllable_machine_key_spans[] = { - 54, 43, 43, 53, 26, 24, 23, 22, - 2, 1, 25, 25, 25, 1, 25, 32, - 31, 31, 31, 42, 31, 42, 42, 42, - 43, 1, 48, 43, 2, 1, 43, 43, - 53, 26, 24, 23, 22, 2, 1, 25, - 25, 25, 1, 25, 32, 31, 31, 31, - 42, 31, 42, 42, 42, 43, 1, 48, - 1, 1, 43, 43, 53, 26, 24, 23, - 22, 2, 1, 25, 25, 25, 1, 25, - 32, 31, 31, 31, 42, 31, 42, 42, - 42, 43, 1, 48, 43, 43, 53, 26, - 24, 23, 22, 2, 1, 25, 25, 25, - 1, 25, 32, 31, 31, 31, 42, 31, - 42, 42, 42, 43, 1, 48, 1, 1, - 53, 43, 2, 1, 5, 3, 4, 3 + 54, 43, 43, 53, 35, 34, 34, 34, + 33, 33, 1, 35, 35, 35, 14, 35, + 40, 40, 40, 40, 42, 40, 42, 42, + 42, 43, 14, 48, 43, 29, 29, 43, + 43, 53, 35, 34, 34, 34, 33, 33, + 1, 35, 35, 35, 14, 35, 40, 40, + 40, 40, 42, 40, 42, 42, 42, 43, + 14, 14, 48, 2, 11, 43, 43, 53, + 35, 34, 34, 34, 33, 33, 1, 35, + 35, 35, 14, 35, 40, 40, 40, 40, + 42, 40, 42, 42, 42, 43, 14, 14, + 48, 43, 43, 53, 35, 34, 34, 34, + 33, 33, 1, 35, 35, 35, 14, 35, + 40, 40, 40, 40, 42, 40, 42, 42, + 42, 43, 14, 48, 11, 2, 53, 43, + 29, 29, 5, 39, 39, 38 }; static const short _use_syllable_machine_index_offsets[] = { - 0, 55, 99, 143, 197, 224, 249, 273, - 296, 299, 301, 327, 353, 379, 381, 407, - 440, 472, 504, 536, 579, 611, 654, 697, - 740, 784, 786, 835, 879, 882, 884, 928, - 972, 1026, 1053, 1078, 1102, 1125, 1128, 1130, - 1156, 1182, 1208, 1210, 1236, 1269, 1301, 1333, - 1365, 1408, 1440, 1483, 1526, 1569, 1613, 1615, - 1664, 1666, 1668, 1712, 1756, 1810, 1837, 1862, - 1886, 1909, 1912, 1914, 1940, 1966, 1992, 1994, - 2020, 2053, 2085, 2117, 2149, 2192, 2224, 2267, - 2310, 2353, 2397, 2399, 2448, 2492, 2536, 2590, - 2617, 2642, 2666, 2689, 2692, 2694, 2720, 2746, - 2772, 2774, 2800, 2833, 2865, 2897, 2929, 2972, - 3004, 3047, 3090, 3133, 3177, 3179, 3228, 3230, - 3232, 3286, 3330, 3333, 3335, 3341, 3345, 3350 + 0, 55, 99, 143, 197, 233, 268, 303, + 338, 372, 406, 408, 444, 480, 516, 531, + 567, 608, 649, 690, 731, 774, 815, 858, + 901, 944, 988, 1003, 1052, 1096, 1126, 1156, + 1200, 1244, 1298, 1334, 1369, 1404, 1439, 1473, + 1507, 1509, 1545, 1581, 1617, 1632, 1668, 1709, + 1750, 1791, 1832, 1875, 1916, 1959, 2002, 2045, + 2089, 2104, 2119, 2168, 2171, 2183, 2227, 2271, + 2325, 2361, 2396, 2431, 2466, 2500, 2534, 2536, + 2572, 2608, 2644, 2659, 2695, 2736, 2777, 2818, + 2859, 2902, 2943, 2986, 3029, 3072, 3116, 3131, + 3146, 3195, 3239, 3283, 3337, 3373, 3408, 3443, + 3478, 3512, 3546, 3548, 3584, 3620, 3656, 3671, + 3707, 3748, 3789, 3830, 3871, 3914, 3955, 3998, + 4041, 4084, 4128, 4143, 4192, 4204, 4207, 4261, + 4305, 4335, 4365, 4371, 4411, 4451 }; static const unsigned char _use_syllable_machine_indicies[] = { 0, 1, 2, 2, 3, 4, 2, 2, - 2, 2, 2, 5, 6, 7, 2, 2, - 2, 2, 8, 2, 2, 2, 9, 10, + 2, 2, 2, 5, 6, 7, 8, 2, + 2, 2, 9, 2, 2, 2, 10, 11, + 12, 13, 14, 15, 16, 17, 18, 19, + 20, 21, 22, 23, 2, 24, 25, 26, + 2, 27, 28, 29, 30, 31, 32, 33, + 30, 34, 2, 35, 2, 36, 2, 38, + 39, 37, 40, 37, 37, 37, 37, 37, + 37, 37, 41, 42, 43, 44, 45, 46, + 47, 48, 49, 50, 51, 52, 53, 54, + 37, 55, 56, 57, 37, 58, 59, 37, + 60, 61, 62, 63, 60, 37, 37, 37, + 37, 64, 37, 38, 39, 37, 40, 37, + 37, 37, 37, 37, 37, 37, 41, 42, + 43, 44, 45, 46, 47, 48, 49, 51, + 51, 52, 53, 54, 37, 55, 56, 57, + 37, 37, 37, 37, 60, 61, 62, 63, + 60, 37, 37, 37, 37, 64, 37, 38, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 40, 37, 37, 37, + 37, 37, 37, 37, 37, 42, 43, 44, + 45, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 55, 56, 57, 37, 37, + 37, 37, 37, 61, 62, 63, 65, 37, + 37, 37, 37, 42, 37, 40, 37, 37, + 37, 37, 37, 37, 37, 37, 42, 43, + 44, 45, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 55, 56, 57, 37, + 37, 37, 37, 37, 61, 62, 63, 65, + 37, 40, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 43, 44, 45, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 61, 62, 63, 37, 40, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 44, + 45, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 61, 62, 63, 37, 40, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 45, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 61, 62, + 63, 37, 40, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 61, 62, 37, 40, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 62, 37, 40, 37, + 40, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 43, 44, 45, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 55, + 56, 57, 37, 37, 37, 37, 37, 61, + 62, 63, 65, 37, 40, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 43, 44, + 45, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 56, 57, 37, 37, + 37, 37, 37, 61, 62, 63, 65, 37, + 40, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 43, 44, 45, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 57, 37, 37, 37, 37, 37, 61, + 62, 63, 65, 37, 66, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 40, 37, 40, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 43, 44, 45, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 61, 62, 63, 65, 37, 40, + 37, 37, 37, 37, 37, 37, 37, 41, + 42, 43, 44, 45, 37, 37, 37, 37, + 37, 37, 52, 53, 54, 37, 55, 56, + 57, 37, 37, 37, 37, 37, 61, 62, + 63, 65, 37, 37, 37, 37, 42, 37, + 40, 37, 37, 37, 37, 37, 37, 37, + 37, 42, 43, 44, 45, 37, 37, 37, + 37, 37, 37, 52, 53, 54, 37, 55, + 56, 57, 37, 37, 37, 37, 37, 61, + 62, 63, 65, 37, 37, 37, 37, 42, + 37, 40, 37, 37, 37, 37, 37, 37, + 37, 37, 42, 43, 44, 45, 37, 37, + 37, 37, 37, 37, 37, 53, 54, 37, + 55, 56, 57, 37, 37, 37, 37, 37, + 61, 62, 63, 65, 37, 37, 37, 37, + 42, 37, 40, 37, 37, 37, 37, 37, + 37, 37, 37, 42, 43, 44, 45, 37, + 37, 37, 37, 37, 37, 37, 37, 54, + 37, 55, 56, 57, 37, 37, 37, 37, + 37, 61, 62, 63, 65, 37, 37, 37, + 37, 42, 37, 67, 37, 40, 37, 37, + 37, 37, 37, 37, 37, 41, 42, 43, + 44, 45, 37, 47, 48, 37, 37, 37, + 52, 53, 54, 37, 55, 56, 57, 37, + 37, 37, 37, 37, 61, 62, 63, 65, + 37, 37, 37, 37, 42, 37, 40, 37, + 37, 37, 37, 37, 37, 37, 37, 42, + 43, 44, 45, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 55, 56, 57, + 37, 37, 37, 37, 37, 61, 62, 63, + 65, 37, 37, 37, 37, 42, 37, 67, + 37, 40, 37, 37, 37, 37, 37, 37, + 37, 41, 42, 43, 44, 45, 37, 37, + 48, 37, 37, 37, 52, 53, 54, 37, + 55, 56, 57, 37, 37, 37, 37, 37, + 61, 62, 63, 65, 37, 37, 37, 37, + 42, 37, 67, 37, 40, 37, 37, 37, + 37, 37, 37, 37, 41, 42, 43, 44, + 45, 37, 37, 37, 37, 37, 37, 52, + 53, 54, 37, 55, 56, 57, 37, 37, + 37, 37, 37, 61, 62, 63, 65, 37, + 37, 37, 37, 42, 37, 67, 37, 40, + 37, 37, 37, 37, 37, 37, 37, 41, + 42, 43, 44, 45, 46, 47, 48, 37, + 37, 37, 52, 53, 54, 37, 55, 56, + 57, 37, 37, 37, 37, 37, 61, 62, + 63, 65, 37, 37, 37, 37, 42, 37, + 38, 39, 37, 40, 37, 37, 37, 37, + 37, 37, 37, 41, 42, 43, 44, 45, + 46, 47, 48, 49, 37, 51, 52, 53, + 54, 37, 55, 56, 57, 37, 37, 37, + 37, 60, 61, 62, 63, 60, 37, 37, + 37, 37, 64, 37, 38, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 40, 37, 38, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 40, 37, 37, 37, 37, 37, 37, 37, + 37, 42, 43, 44, 45, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 55, + 56, 57, 37, 37, 37, 37, 37, 61, + 62, 63, 65, 37, 38, 39, 37, 40, + 37, 37, 37, 37, 37, 37, 37, 41, + 42, 43, 44, 45, 46, 47, 48, 49, + 50, 51, 52, 53, 54, 37, 55, 56, + 57, 37, 37, 37, 37, 60, 61, 62, + 63, 60, 37, 37, 37, 37, 64, 37, + 40, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 58, 59, 37, 40, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 59, 37, 69, 70, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 72, + 73, 74, 75, 76, 77, 78, 79, 80, + 1, 81, 82, 83, 84, 68, 85, 86, + 87, 68, 68, 68, 68, 88, 89, 90, + 91, 92, 68, 68, 68, 68, 93, 68, + 69, 70, 68, 71, 68, 68, 68, 68, + 68, 68, 68, 72, 73, 74, 75, 76, + 77, 78, 79, 80, 81, 81, 82, 83, + 84, 68, 85, 86, 87, 68, 68, 68, + 68, 88, 89, 90, 91, 92, 68, 68, + 68, 68, 93, 68, 69, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 68, 73, 74, 75, 76, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 85, 86, 87, 68, 68, 68, 68, 68, + 89, 90, 91, 94, 68, 68, 68, 68, + 73, 68, 71, 68, 68, 68, 68, 68, + 68, 68, 68, 73, 74, 75, 76, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 85, 86, 87, 68, 68, 68, 68, + 68, 89, 90, 91, 94, 68, 71, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 74, 75, 76, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 89, 90, 91, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 75, 76, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 89, 90, 91, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 76, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 89, 90, 91, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 89, 90, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 90, 68, 71, 68, 71, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 74, + 75, 76, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 85, 86, 87, 68, + 68, 68, 68, 68, 89, 90, 91, 94, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 74, 75, 76, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 86, 87, 68, 68, 68, 68, 68, + 89, 90, 91, 94, 68, 71, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 74, + 75, 76, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 87, 68, + 68, 68, 68, 68, 89, 90, 91, 94, + 68, 96, 95, 95, 95, 95, 95, 95, + 95, 95, 95, 95, 95, 95, 97, 95, + 71, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 74, 75, 76, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 89, + 90, 91, 94, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 72, 73, 74, 75, + 76, 68, 68, 68, 68, 68, 68, 82, + 83, 84, 68, 85, 86, 87, 68, 68, + 68, 68, 68, 89, 90, 91, 94, 68, + 68, 68, 68, 73, 68, 71, 68, 68, + 68, 68, 68, 68, 68, 68, 73, 74, + 75, 76, 68, 68, 68, 68, 68, 68, + 82, 83, 84, 68, 85, 86, 87, 68, + 68, 68, 68, 68, 89, 90, 91, 94, + 68, 68, 68, 68, 73, 68, 71, 68, + 68, 68, 68, 68, 68, 68, 68, 73, + 74, 75, 76, 68, 68, 68, 68, 68, + 68, 68, 83, 84, 68, 85, 86, 87, + 68, 68, 68, 68, 68, 89, 90, 91, + 94, 68, 68, 68, 68, 73, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 68, + 73, 74, 75, 76, 68, 68, 68, 68, + 68, 68, 68, 68, 84, 68, 85, 86, + 87, 68, 68, 68, 68, 68, 89, 90, + 91, 94, 68, 68, 68, 68, 73, 68, + 98, 68, 71, 68, 68, 68, 68, 68, + 68, 68, 72, 73, 74, 75, 76, 68, + 78, 79, 68, 68, 68, 82, 83, 84, + 68, 85, 86, 87, 68, 68, 68, 68, + 68, 89, 90, 91, 94, 68, 68, 68, + 68, 73, 68, 71, 68, 68, 68, 68, + 68, 68, 68, 68, 73, 74, 75, 76, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 85, 86, 87, 68, 68, 68, + 68, 68, 89, 90, 91, 94, 68, 68, + 68, 68, 73, 68, 98, 68, 71, 68, + 68, 68, 68, 68, 68, 68, 72, 73, + 74, 75, 76, 68, 68, 79, 68, 68, + 68, 82, 83, 84, 68, 85, 86, 87, + 68, 68, 68, 68, 68, 89, 90, 91, + 94, 68, 68, 68, 68, 73, 68, 98, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 72, 73, 74, 75, 76, 68, 68, + 68, 68, 68, 68, 82, 83, 84, 68, + 85, 86, 87, 68, 68, 68, 68, 68, + 89, 90, 91, 94, 68, 68, 68, 68, + 73, 68, 98, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 72, 73, 74, 75, + 76, 77, 78, 79, 68, 68, 68, 82, + 83, 84, 68, 85, 86, 87, 68, 68, + 68, 68, 68, 89, 90, 91, 94, 68, + 68, 68, 68, 73, 68, 69, 70, 68, + 71, 68, 68, 68, 68, 68, 68, 68, + 72, 73, 74, 75, 76, 77, 78, 79, + 80, 68, 81, 82, 83, 84, 68, 85, + 86, 87, 68, 68, 68, 68, 88, 89, + 90, 91, 92, 68, 68, 68, 68, 93, + 68, 69, 99, 99, 99, 99, 99, 99, + 99, 99, 99, 99, 99, 99, 100, 99, + 69, 95, 95, 95, 95, 95, 95, 95, + 95, 95, 95, 95, 95, 97, 95, 69, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 68, 73, 74, 75, + 76, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 85, 86, 87, 68, 68, + 68, 68, 68, 89, 90, 91, 94, 68, + 102, 103, 101, 3, 104, 104, 104, 104, + 104, 104, 104, 104, 104, 105, 104, 106, + 107, 68, 71, 68, 68, 68, 68, 68, + 68, 68, 108, 109, 110, 111, 112, 113, + 114, 115, 116, 117, 118, 119, 120, 121, + 68, 122, 123, 124, 68, 58, 59, 68, + 125, 126, 127, 128, 129, 68, 68, 68, + 68, 130, 68, 106, 107, 68, 71, 68, + 68, 68, 68, 68, 68, 68, 108, 109, + 110, 111, 112, 113, 114, 115, 116, 118, + 118, 119, 120, 121, 68, 122, 123, 124, + 68, 68, 68, 68, 125, 126, 127, 128, + 129, 68, 68, 68, 68, 130, 68, 106, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 68, 109, 110, 111, + 112, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 122, 123, 124, 68, 68, + 68, 68, 68, 126, 127, 128, 131, 68, + 68, 68, 68, 109, 68, 71, 68, 68, + 68, 68, 68, 68, 68, 68, 109, 110, + 111, 112, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 122, 123, 124, 68, + 68, 68, 68, 68, 126, 127, 128, 131, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 110, 111, 112, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 126, 127, 128, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 111, + 112, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 126, 127, 128, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 112, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 126, 127, + 128, 68, 71, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 126, 127, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 127, 68, 71, 68, + 71, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 110, 111, 112, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 122, + 123, 124, 68, 68, 68, 68, 68, 126, + 127, 128, 131, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 110, 111, + 112, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 123, 124, 68, 68, + 68, 68, 68, 126, 127, 128, 131, 68, + 71, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 110, 111, 112, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 124, 68, 68, 68, 68, 68, 126, + 127, 128, 131, 68, 132, 95, 95, 95, + 95, 95, 95, 95, 95, 95, 95, 95, + 95, 97, 95, 71, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 110, 111, 112, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 126, 127, 128, 131, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 108, + 109, 110, 111, 112, 68, 68, 68, 68, + 68, 68, 119, 120, 121, 68, 122, 123, + 124, 68, 68, 68, 68, 68, 126, 127, + 128, 131, 68, 68, 68, 68, 109, 68, + 71, 68, 68, 68, 68, 68, 68, 68, + 68, 109, 110, 111, 112, 68, 68, 68, + 68, 68, 68, 119, 120, 121, 68, 122, + 123, 124, 68, 68, 68, 68, 68, 126, + 127, 128, 131, 68, 68, 68, 68, 109, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 68, 109, 110, 111, 112, 68, 68, + 68, 68, 68, 68, 68, 120, 121, 68, + 122, 123, 124, 68, 68, 68, 68, 68, + 126, 127, 128, 131, 68, 68, 68, 68, + 109, 68, 71, 68, 68, 68, 68, 68, + 68, 68, 68, 109, 110, 111, 112, 68, + 68, 68, 68, 68, 68, 68, 68, 121, + 68, 122, 123, 124, 68, 68, 68, 68, + 68, 126, 127, 128, 131, 68, 68, 68, + 68, 109, 68, 133, 68, 71, 68, 68, + 68, 68, 68, 68, 68, 108, 109, 110, + 111, 112, 68, 114, 115, 68, 68, 68, + 119, 120, 121, 68, 122, 123, 124, 68, + 68, 68, 68, 68, 126, 127, 128, 131, + 68, 68, 68, 68, 109, 68, 71, 68, + 68, 68, 68, 68, 68, 68, 68, 109, + 110, 111, 112, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 122, 123, 124, + 68, 68, 68, 68, 68, 126, 127, 128, + 131, 68, 68, 68, 68, 109, 68, 133, + 68, 71, 68, 68, 68, 68, 68, 68, + 68, 108, 109, 110, 111, 112, 68, 68, + 115, 68, 68, 68, 119, 120, 121, 68, + 122, 123, 124, 68, 68, 68, 68, 68, + 126, 127, 128, 131, 68, 68, 68, 68, + 109, 68, 133, 68, 71, 68, 68, 68, + 68, 68, 68, 68, 108, 109, 110, 111, + 112, 68, 68, 68, 68, 68, 68, 119, + 120, 121, 68, 122, 123, 124, 68, 68, + 68, 68, 68, 126, 127, 128, 131, 68, + 68, 68, 68, 109, 68, 133, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 108, + 109, 110, 111, 112, 113, 114, 115, 68, + 68, 68, 119, 120, 121, 68, 122, 123, + 124, 68, 68, 68, 68, 68, 126, 127, + 128, 131, 68, 68, 68, 68, 109, 68, + 106, 107, 68, 71, 68, 68, 68, 68, + 68, 68, 68, 108, 109, 110, 111, 112, + 113, 114, 115, 116, 68, 118, 119, 120, + 121, 68, 122, 123, 124, 68, 68, 68, + 68, 125, 126, 127, 128, 129, 68, 68, + 68, 68, 130, 68, 106, 99, 99, 99, + 99, 99, 99, 99, 99, 99, 99, 99, + 99, 100, 99, 106, 95, 95, 95, 95, + 95, 95, 95, 95, 95, 95, 95, 95, + 97, 95, 106, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 71, + 68, 68, 68, 68, 68, 68, 68, 68, + 109, 110, 111, 112, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 122, 123, + 124, 68, 68, 68, 68, 68, 126, 127, + 128, 131, 68, 106, 107, 68, 71, 68, + 68, 68, 68, 68, 68, 68, 108, 109, + 110, 111, 112, 113, 114, 115, 116, 117, + 118, 119, 120, 121, 68, 122, 123, 124, + 68, 68, 68, 68, 125, 126, 127, 128, + 129, 68, 68, 68, 68, 130, 68, 5, + 6, 134, 8, 134, 134, 134, 134, 134, + 134, 134, 10, 11, 12, 13, 14, 15, + 16, 17, 18, 20, 20, 21, 22, 23, + 134, 24, 25, 26, 134, 134, 134, 134, + 30, 31, 32, 33, 30, 134, 134, 134, + 134, 36, 134, 5, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 8, 134, 134, 134, 134, 134, 134, 134, + 134, 11, 12, 13, 14, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 24, + 25, 26, 134, 134, 134, 134, 134, 31, + 32, 33, 135, 134, 134, 134, 134, 11, + 134, 8, 134, 134, 134, 134, 134, 134, + 134, 134, 11, 12, 13, 14, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 24, 25, 26, 134, 134, 134, 134, 134, + 31, 32, 33, 135, 134, 8, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 12, + 13, 14, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 31, 32, 33, 134, + 8, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 13, 14, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 31, + 32, 33, 134, 8, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 14, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 31, 32, 33, 134, 8, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 31, 32, 134, + 8, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 32, 134, 8, 134, 8, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 12, 13, + 14, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 24, 25, 26, 134, 134, + 134, 134, 134, 31, 32, 33, 135, 134, + 8, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 12, 13, 14, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 25, 26, 134, 134, 134, 134, 134, 31, + 32, 33, 135, 134, 8, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 12, 13, + 14, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 26, 134, 134, + 134, 134, 134, 31, 32, 33, 135, 134, + 136, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 8, 134, 8, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 12, 13, 14, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 31, 32, + 33, 135, 134, 8, 134, 134, 134, 134, + 134, 134, 134, 10, 11, 12, 13, 14, + 134, 134, 134, 134, 134, 134, 21, 22, + 23, 134, 24, 25, 26, 134, 134, 134, + 134, 134, 31, 32, 33, 135, 134, 134, + 134, 134, 11, 134, 8, 134, 134, 134, + 134, 134, 134, 134, 134, 11, 12, 13, + 14, 134, 134, 134, 134, 134, 134, 21, + 22, 23, 134, 24, 25, 26, 134, 134, + 134, 134, 134, 31, 32, 33, 135, 134, + 134, 134, 134, 11, 134, 8, 134, 134, + 134, 134, 134, 134, 134, 134, 11, 12, + 13, 14, 134, 134, 134, 134, 134, 134, + 134, 22, 23, 134, 24, 25, 26, 134, + 134, 134, 134, 134, 31, 32, 33, 135, + 134, 134, 134, 134, 11, 134, 8, 134, + 134, 134, 134, 134, 134, 134, 134, 11, + 12, 13, 14, 134, 134, 134, 134, 134, + 134, 134, 134, 23, 134, 24, 25, 26, + 134, 134, 134, 134, 134, 31, 32, 33, + 135, 134, 134, 134, 134, 11, 134, 137, + 134, 8, 134, 134, 134, 134, 134, 134, + 134, 10, 11, 12, 13, 14, 134, 16, + 17, 134, 134, 134, 21, 22, 23, 134, + 24, 25, 26, 134, 134, 134, 134, 134, + 31, 32, 33, 135, 134, 134, 134, 134, + 11, 134, 8, 134, 134, 134, 134, 134, + 134, 134, 134, 11, 12, 13, 14, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 24, 25, 26, 134, 134, 134, 134, + 134, 31, 32, 33, 135, 134, 134, 134, + 134, 11, 134, 137, 134, 8, 134, 134, + 134, 134, 134, 134, 134, 10, 11, 12, + 13, 14, 134, 134, 17, 134, 134, 134, + 21, 22, 23, 134, 24, 25, 26, 134, + 134, 134, 134, 134, 31, 32, 33, 135, + 134, 134, 134, 134, 11, 134, 137, 134, + 8, 134, 134, 134, 134, 134, 134, 134, + 10, 11, 12, 13, 14, 134, 134, 134, + 134, 134, 134, 21, 22, 23, 134, 24, + 25, 26, 134, 134, 134, 134, 134, 31, + 32, 33, 135, 134, 134, 134, 134, 11, + 134, 137, 134, 8, 134, 134, 134, 134, + 134, 134, 134, 10, 11, 12, 13, 14, + 15, 16, 17, 134, 134, 134, 21, 22, + 23, 134, 24, 25, 26, 134, 134, 134, + 134, 134, 31, 32, 33, 135, 134, 134, + 134, 134, 11, 134, 5, 6, 134, 8, + 134, 134, 134, 134, 134, 134, 134, 10, 11, 12, 13, 14, 15, 16, 17, 18, - 19, 20, 21, 22, 2, 23, 24, 25, - 2, 26, 27, 28, 29, 30, 31, 32, - 29, 33, 2, 34, 2, 35, 2, 37, - 38, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 39, 40, 41, 42, 43, 44, - 45, 46, 47, 48, 49, 50, 51, 52, - 36, 53, 54, 55, 36, 56, 57, 36, - 58, 59, 60, 61, 58, 36, 36, 36, - 36, 62, 36, 37, 38, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 39, 40, - 41, 42, 43, 44, 45, 46, 47, 49, - 49, 50, 51, 52, 36, 53, 54, 55, - 36, 36, 36, 36, 58, 59, 60, 61, - 58, 36, 36, 36, 36, 62, 36, 37, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 40, 41, 42, - 43, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 53, 54, 55, 36, 36, - 36, 36, 36, 59, 60, 61, 63, 36, - 36, 36, 36, 40, 36, 40, 41, 42, - 43, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 53, 54, 55, 36, 36, - 36, 36, 36, 59, 60, 61, 63, 36, - 41, 42, 43, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 59, 60, 61, - 36, 42, 43, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 59, 60, 61, - 36, 43, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 59, 60, 61, 36, - 59, 60, 36, 60, 36, 41, 42, 43, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 53, 54, 55, 36, 36, 36, - 36, 36, 59, 60, 61, 63, 36, 41, - 42, 43, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 54, 55, 36, - 36, 36, 36, 36, 59, 60, 61, 63, - 36, 41, 42, 43, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 55, 36, 36, 36, 36, 36, 59, 60, - 61, 63, 36, 64, 36, 41, 42, 43, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 59, 60, 61, 63, 36, 39, - 40, 41, 42, 43, 36, 36, 36, 36, - 36, 36, 50, 51, 52, 36, 53, 54, - 55, 36, 36, 36, 36, 36, 59, 60, - 61, 63, 36, 36, 36, 36, 40, 36, - 40, 41, 42, 43, 36, 36, 36, 36, - 36, 36, 50, 51, 52, 36, 53, 54, - 55, 36, 36, 36, 36, 36, 59, 60, - 61, 63, 36, 36, 36, 36, 40, 36, - 40, 41, 42, 43, 36, 36, 36, 36, - 36, 36, 36, 51, 52, 36, 53, 54, - 55, 36, 36, 36, 36, 36, 59, 60, - 61, 63, 36, 36, 36, 36, 40, 36, - 40, 41, 42, 43, 36, 36, 36, 36, - 36, 36, 36, 36, 52, 36, 53, 54, - 55, 36, 36, 36, 36, 36, 59, 60, - 61, 63, 36, 36, 36, 36, 40, 36, - 65, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 39, 40, 41, 42, 43, 36, - 45, 46, 36, 36, 36, 50, 51, 52, - 36, 53, 54, 55, 36, 36, 36, 36, - 36, 59, 60, 61, 63, 36, 36, 36, - 36, 40, 36, 40, 41, 42, 43, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 53, 54, 55, 36, 36, 36, 36, - 36, 59, 60, 61, 63, 36, 36, 36, - 36, 40, 36, 65, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 39, 40, 41, - 42, 43, 36, 36, 46, 36, 36, 36, - 50, 51, 52, 36, 53, 54, 55, 36, - 36, 36, 36, 36, 59, 60, 61, 63, - 36, 36, 36, 36, 40, 36, 65, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 39, 40, 41, 42, 43, 36, 36, 36, - 36, 36, 36, 50, 51, 52, 36, 53, - 54, 55, 36, 36, 36, 36, 36, 59, - 60, 61, 63, 36, 36, 36, 36, 40, - 36, 65, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 39, 40, 41, 42, 43, - 44, 45, 46, 36, 36, 36, 50, 51, - 52, 36, 53, 54, 55, 36, 36, 36, - 36, 36, 59, 60, 61, 63, 36, 36, - 36, 36, 40, 36, 37, 38, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 39, - 40, 41, 42, 43, 44, 45, 46, 47, - 36, 49, 50, 51, 52, 36, 53, 54, - 55, 36, 36, 36, 36, 58, 59, 60, - 61, 58, 36, 36, 36, 36, 62, 36, - 37, 36, 37, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, - 40, 41, 42, 43, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 53, 54, - 55, 36, 36, 36, 36, 36, 59, 60, - 61, 63, 36, 37, 38, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 39, 40, - 41, 42, 43, 44, 45, 46, 47, 48, - 49, 50, 51, 52, 36, 53, 54, 55, - 36, 36, 36, 36, 58, 59, 60, 61, - 58, 36, 36, 36, 36, 62, 36, 56, - 57, 36, 57, 36, 67, 68, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 69, - 70, 71, 72, 73, 74, 75, 76, 77, - 1, 78, 79, 80, 81, 66, 82, 83, - 84, 66, 66, 66, 66, 85, 86, 87, - 88, 89, 66, 66, 66, 66, 90, 66, - 67, 68, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 69, 70, 71, 72, 73, - 74, 75, 76, 77, 78, 78, 79, 80, - 81, 66, 82, 83, 84, 66, 66, 66, - 66, 85, 86, 87, 88, 89, 66, 66, - 66, 66, 90, 66, 67, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 70, 71, 72, 73, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 82, 83, 84, 66, 66, 66, 66, 66, - 86, 87, 88, 91, 66, 66, 66, 66, - 70, 66, 70, 71, 72, 73, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 82, 83, 84, 66, 66, 66, 66, 66, - 86, 87, 88, 91, 66, 71, 72, 73, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 86, 87, 88, 66, 72, 73, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 86, 87, 88, 66, 73, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 86, 87, 88, 66, 86, 87, 66, - 87, 66, 71, 72, 73, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 82, - 83, 84, 66, 66, 66, 66, 66, 86, - 87, 88, 91, 66, 71, 72, 73, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 83, 84, 66, 66, 66, 66, - 66, 86, 87, 88, 91, 66, 71, 72, - 73, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 84, 66, 66, - 66, 66, 66, 86, 87, 88, 91, 66, - 93, 92, 71, 72, 73, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 86, - 87, 88, 91, 66, 69, 70, 71, 72, - 73, 66, 66, 66, 66, 66, 66, 79, - 80, 81, 66, 82, 83, 84, 66, 66, - 66, 66, 66, 86, 87, 88, 91, 66, - 66, 66, 66, 70, 66, 70, 71, 72, - 73, 66, 66, 66, 66, 66, 66, 79, - 80, 81, 66, 82, 83, 84, 66, 66, - 66, 66, 66, 86, 87, 88, 91, 66, - 66, 66, 66, 70, 66, 70, 71, 72, - 73, 66, 66, 66, 66, 66, 66, 66, - 80, 81, 66, 82, 83, 84, 66, 66, - 66, 66, 66, 86, 87, 88, 91, 66, - 66, 66, 66, 70, 66, 70, 71, 72, - 73, 66, 66, 66, 66, 66, 66, 66, - 66, 81, 66, 82, 83, 84, 66, 66, - 66, 66, 66, 86, 87, 88, 91, 66, - 66, 66, 66, 70, 66, 94, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 69, - 70, 71, 72, 73, 66, 75, 76, 66, - 66, 66, 79, 80, 81, 66, 82, 83, - 84, 66, 66, 66, 66, 66, 86, 87, - 88, 91, 66, 66, 66, 66, 70, 66, - 70, 71, 72, 73, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 82, 83, - 84, 66, 66, 66, 66, 66, 86, 87, - 88, 91, 66, 66, 66, 66, 70, 66, - 94, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 69, 70, 71, 72, 73, 66, - 66, 76, 66, 66, 66, 79, 80, 81, - 66, 82, 83, 84, 66, 66, 66, 66, - 66, 86, 87, 88, 91, 66, 66, 66, - 66, 70, 66, 94, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 69, 70, 71, - 72, 73, 66, 66, 66, 66, 66, 66, - 79, 80, 81, 66, 82, 83, 84, 66, - 66, 66, 66, 66, 86, 87, 88, 91, - 66, 66, 66, 66, 70, 66, 94, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 69, 70, 71, 72, 73, 74, 75, 76, - 66, 66, 66, 79, 80, 81, 66, 82, - 83, 84, 66, 66, 66, 66, 66, 86, - 87, 88, 91, 66, 66, 66, 66, 70, - 66, 67, 68, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 69, 70, 71, 72, - 73, 74, 75, 76, 77, 66, 78, 79, - 80, 81, 66, 82, 83, 84, 66, 66, - 66, 66, 85, 86, 87, 88, 89, 66, - 66, 66, 66, 90, 66, 67, 95, 67, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 70, 71, 72, - 73, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 82, 83, 84, 66, 66, - 66, 66, 66, 86, 87, 88, 91, 66, - 97, 96, 3, 98, 99, 100, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 101, - 102, 103, 104, 105, 106, 107, 108, 109, - 110, 111, 112, 113, 114, 66, 115, 116, - 117, 66, 56, 57, 66, 118, 119, 120, - 88, 121, 66, 66, 66, 66, 122, 66, - 99, 100, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 101, 102, 103, 104, 105, - 106, 107, 108, 109, 111, 111, 112, 113, - 114, 66, 115, 116, 117, 66, 66, 66, - 66, 118, 119, 120, 88, 121, 66, 66, - 66, 66, 122, 66, 99, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 102, 103, 104, 105, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 115, 116, 117, 66, 66, 66, 66, 66, - 119, 120, 88, 123, 66, 66, 66, 66, - 102, 66, 102, 103, 104, 105, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 115, 116, 117, 66, 66, 66, 66, 66, - 119, 120, 88, 123, 66, 103, 104, 105, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 119, 120, 88, 66, 104, 105, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 119, 120, 88, 66, 105, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 119, 120, 88, 66, 119, 120, 66, - 120, 66, 103, 104, 105, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 115, - 116, 117, 66, 66, 66, 66, 66, 119, - 120, 88, 123, 66, 103, 104, 105, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 116, 117, 66, 66, 66, 66, - 66, 119, 120, 88, 123, 66, 103, 104, - 105, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 117, 66, 66, - 66, 66, 66, 119, 120, 88, 123, 66, - 124, 92, 103, 104, 105, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 119, - 120, 88, 123, 66, 101, 102, 103, 104, - 105, 66, 66, 66, 66, 66, 66, 112, - 113, 114, 66, 115, 116, 117, 66, 66, - 66, 66, 66, 119, 120, 88, 123, 66, - 66, 66, 66, 102, 66, 102, 103, 104, - 105, 66, 66, 66, 66, 66, 66, 112, - 113, 114, 66, 115, 116, 117, 66, 66, - 66, 66, 66, 119, 120, 88, 123, 66, - 66, 66, 66, 102, 66, 102, 103, 104, - 105, 66, 66, 66, 66, 66, 66, 66, - 113, 114, 66, 115, 116, 117, 66, 66, - 66, 66, 66, 119, 120, 88, 123, 66, - 66, 66, 66, 102, 66, 102, 103, 104, - 105, 66, 66, 66, 66, 66, 66, 66, - 66, 114, 66, 115, 116, 117, 66, 66, - 66, 66, 66, 119, 120, 88, 123, 66, - 66, 66, 66, 102, 66, 125, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 101, - 102, 103, 104, 105, 66, 107, 108, 66, - 66, 66, 112, 113, 114, 66, 115, 116, - 117, 66, 66, 66, 66, 66, 119, 120, - 88, 123, 66, 66, 66, 66, 102, 66, - 102, 103, 104, 105, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 115, 116, - 117, 66, 66, 66, 66, 66, 119, 120, - 88, 123, 66, 66, 66, 66, 102, 66, - 125, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 101, 102, 103, 104, 105, 66, - 66, 108, 66, 66, 66, 112, 113, 114, - 66, 115, 116, 117, 66, 66, 66, 66, - 66, 119, 120, 88, 123, 66, 66, 66, - 66, 102, 66, 125, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 101, 102, 103, - 104, 105, 66, 66, 66, 66, 66, 66, - 112, 113, 114, 66, 115, 116, 117, 66, - 66, 66, 66, 66, 119, 120, 88, 123, - 66, 66, 66, 66, 102, 66, 125, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 101, 102, 103, 104, 105, 106, 107, 108, - 66, 66, 66, 112, 113, 114, 66, 115, - 116, 117, 66, 66, 66, 66, 66, 119, - 120, 88, 123, 66, 66, 66, 66, 102, - 66, 99, 100, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 101, 102, 103, 104, - 105, 106, 107, 108, 109, 66, 111, 112, - 113, 114, 66, 115, 116, 117, 66, 66, - 66, 66, 118, 119, 120, 88, 121, 66, - 66, 66, 66, 122, 66, 99, 95, 99, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 102, 103, 104, - 105, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 115, 116, 117, 66, 66, - 66, 66, 66, 119, 120, 88, 123, 66, - 99, 100, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 101, 102, 103, 104, 105, - 106, 107, 108, 109, 110, 111, 112, 113, - 114, 66, 115, 116, 117, 66, 66, 66, - 66, 118, 119, 120, 88, 121, 66, 66, - 66, 66, 122, 66, 5, 6, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 9, + 134, 20, 21, 22, 23, 134, 24, 25, + 26, 134, 134, 134, 134, 30, 31, 32, + 33, 30, 134, 134, 134, 134, 36, 134, + 5, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 8, 134, 5, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 8, 134, 134, 134, + 134, 134, 134, 134, 134, 11, 12, 13, + 14, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 24, 25, 26, 134, 134, + 134, 134, 134, 31, 32, 33, 135, 134, + 138, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 8, 134, 7, 8, 134, 1, + 134, 134, 134, 1, 134, 134, 134, 134, + 134, 5, 6, 7, 8, 134, 134, 134, + 134, 134, 134, 134, 10, 11, 12, 13, + 14, 15, 16, 17, 18, 19, 20, 21, + 22, 23, 134, 24, 25, 26, 134, 27, + 28, 134, 30, 31, 32, 33, 30, 134, + 134, 134, 134, 36, 134, 5, 6, 134, + 8, 134, 134, 134, 134, 134, 134, 134, 10, 11, 12, 13, 14, 15, 16, 17, - 19, 19, 20, 21, 22, 126, 23, 24, - 25, 126, 126, 126, 126, 29, 30, 31, - 32, 29, 126, 126, 126, 126, 35, 126, - 5, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 10, 11, - 12, 13, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 23, 24, 25, 126, - 126, 126, 126, 126, 30, 31, 32, 127, - 126, 126, 126, 126, 10, 126, 10, 11, - 12, 13, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 23, 24, 25, 126, - 126, 126, 126, 126, 30, 31, 32, 127, - 126, 11, 12, 13, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 30, 31, - 32, 126, 12, 13, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 30, 31, - 32, 126, 13, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 30, 31, 32, - 126, 30, 31, 126, 31, 126, 11, 12, - 13, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 23, 24, 25, 126, 126, - 126, 126, 126, 30, 31, 32, 127, 126, - 11, 12, 13, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 24, 25, - 126, 126, 126, 126, 126, 30, 31, 32, - 127, 126, 11, 12, 13, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 25, 126, 126, 126, 126, 126, 30, - 31, 32, 127, 126, 128, 126, 11, 12, - 13, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 30, 31, 32, 127, 126, - 9, 10, 11, 12, 13, 126, 126, 126, - 126, 126, 126, 20, 21, 22, 126, 23, - 24, 25, 126, 126, 126, 126, 126, 30, - 31, 32, 127, 126, 126, 126, 126, 10, - 126, 10, 11, 12, 13, 126, 126, 126, - 126, 126, 126, 20, 21, 22, 126, 23, - 24, 25, 126, 126, 126, 126, 126, 30, - 31, 32, 127, 126, 126, 126, 126, 10, - 126, 10, 11, 12, 13, 126, 126, 126, - 126, 126, 126, 126, 21, 22, 126, 23, - 24, 25, 126, 126, 126, 126, 126, 30, - 31, 32, 127, 126, 126, 126, 126, 10, - 126, 10, 11, 12, 13, 126, 126, 126, - 126, 126, 126, 126, 126, 22, 126, 23, - 24, 25, 126, 126, 126, 126, 126, 30, - 31, 32, 127, 126, 126, 126, 126, 10, - 126, 129, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 9, 10, 11, 12, 13, - 126, 15, 16, 126, 126, 126, 20, 21, - 22, 126, 23, 24, 25, 126, 126, 126, - 126, 126, 30, 31, 32, 127, 126, 126, - 126, 126, 10, 126, 10, 11, 12, 13, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 23, 24, 25, 126, 126, 126, - 126, 126, 30, 31, 32, 127, 126, 126, - 126, 126, 10, 126, 129, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 9, 10, - 11, 12, 13, 126, 126, 16, 126, 126, - 126, 20, 21, 22, 126, 23, 24, 25, - 126, 126, 126, 126, 126, 30, 31, 32, - 127, 126, 126, 126, 126, 10, 126, 129, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 9, 10, 11, 12, 13, 126, 126, - 126, 126, 126, 126, 20, 21, 22, 126, - 23, 24, 25, 126, 126, 126, 126, 126, - 30, 31, 32, 127, 126, 126, 126, 126, - 10, 126, 129, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 9, 10, 11, 12, - 13, 14, 15, 16, 126, 126, 126, 20, - 21, 22, 126, 23, 24, 25, 126, 126, - 126, 126, 126, 30, 31, 32, 127, 126, - 126, 126, 126, 10, 126, 5, 6, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 9, 10, 11, 12, 13, 14, 15, 16, - 17, 126, 19, 20, 21, 22, 126, 23, - 24, 25, 126, 126, 126, 126, 29, 30, - 31, 32, 29, 126, 126, 126, 126, 35, - 126, 5, 126, 5, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 10, 11, 12, 13, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 23, - 24, 25, 126, 126, 126, 126, 126, 30, - 31, 32, 127, 126, 130, 126, 7, 126, - 1, 126, 126, 126, 1, 126, 126, 126, - 126, 126, 5, 6, 7, 126, 126, 126, - 126, 126, 126, 126, 126, 9, 10, 11, - 12, 13, 14, 15, 16, 17, 18, 19, - 20, 21, 22, 126, 23, 24, 25, 126, - 26, 27, 126, 29, 30, 31, 32, 29, - 126, 126, 126, 126, 35, 126, 5, 6, - 126, 126, 126, 126, 126, 126, 126, 126, - 126, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 126, - 23, 24, 25, 126, 126, 126, 126, 29, - 30, 31, 32, 29, 126, 126, 126, 126, - 35, 126, 26, 27, 126, 27, 126, 1, - 131, 131, 131, 1, 131, 133, 132, 33, - 132, 33, 133, 132, 133, 132, 33, 132, - 34, 132, 0 + 18, 19, 20, 21, 22, 23, 134, 24, + 25, 26, 134, 134, 134, 134, 30, 31, + 32, 33, 30, 134, 134, 134, 134, 36, + 134, 8, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 27, 28, 134, 8, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 134, 134, 134, 134, 134, + 134, 134, 134, 28, 134, 1, 139, 139, + 139, 1, 139, 141, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 142, + 140, 34, 140, 141, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 34, 142, + 140, 142, 140, 141, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 140, 140, 34, 140, + 35, 140, 0 }; static const char _use_syllable_machine_trans_targs[] = { - 1, 30, 0, 56, 58, 85, 86, 110, - 112, 98, 87, 88, 89, 90, 102, 104, - 105, 106, 113, 107, 99, 100, 101, 93, - 94, 95, 114, 115, 116, 108, 91, 92, - 0, 117, 119, 109, 0, 2, 3, 15, - 4, 5, 6, 7, 19, 21, 22, 23, - 27, 24, 16, 17, 18, 10, 11, 12, - 28, 29, 25, 8, 9, 0, 26, 13, - 14, 20, 0, 31, 32, 44, 33, 34, - 35, 36, 48, 50, 51, 52, 53, 45, - 46, 47, 39, 40, 41, 54, 37, 38, - 0, 54, 55, 42, 0, 43, 49, 0, - 0, 57, 0, 59, 60, 72, 61, 62, - 63, 64, 76, 78, 79, 80, 84, 81, - 73, 74, 75, 67, 68, 69, 82, 65, - 66, 82, 83, 70, 71, 77, 0, 96, - 97, 103, 111, 0, 0, 118 + 1, 31, 0, 59, 61, 90, 91, 116, + 0, 118, 104, 92, 93, 94, 95, 108, + 110, 111, 112, 119, 113, 105, 106, 107, + 99, 100, 101, 120, 121, 122, 114, 96, + 97, 98, 123, 125, 115, 0, 2, 3, + 0, 16, 4, 5, 6, 7, 20, 22, + 23, 24, 28, 25, 17, 18, 19, 11, + 12, 13, 29, 30, 26, 8, 9, 10, + 27, 14, 15, 21, 0, 32, 33, 0, + 46, 34, 35, 36, 37, 50, 52, 53, + 54, 55, 47, 48, 49, 41, 42, 43, + 56, 38, 39, 40, 57, 58, 44, 0, + 45, 0, 51, 0, 0, 0, 60, 0, + 0, 0, 62, 63, 76, 64, 65, 66, + 67, 80, 82, 83, 84, 89, 85, 77, + 78, 79, 71, 72, 73, 86, 68, 69, + 70, 87, 88, 74, 75, 81, 0, 102, + 103, 109, 117, 0, 0, 0, 124 }; static const char _use_syllable_machine_trans_actions[] = { 0, 0, 3, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 5, 0, 0, + 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 7, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 6, 0, 0, - 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 8, 0, 0, - 9, 10, 0, 0, 11, 0, 0, 12, - 13, 0, 14, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 9, + 0, 10, 0, 11, 12, 13, 0, 14, + 15, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 8, 0, - 0, 10, 0, 0, 0, 0, 15, 0, - 0, 0, 0, 16, 17, 0 + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 17, 0, + 0, 0, 0, 18, 19, 20, 0 }; static const char _use_syllable_machine_to_state_actions[] = { @@ -631,7 +777,8 @@ static const char _use_syllable_machine_to_state_actions[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0 + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0 }; static const char _use_syllable_machine_from_state_actions[] = { @@ -649,25 +796,27 @@ static const char _use_syllable_machine_from_state_actions[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0 + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0 }; static const short _use_syllable_machine_eof_trans[] = { - 0, 37, 37, 37, 37, 37, 37, 37, - 37, 37, 37, 37, 37, 37, 37, 37, - 37, 37, 37, 37, 37, 37, 37, 37, - 37, 37, 37, 37, 37, 37, 67, 67, - 67, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 93, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 67, 67, 96, 67, - 97, 99, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 67, 67, 93, 67, - 67, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 96, 67, 67, 127, 127, 127, - 127, 127, 127, 127, 127, 127, 127, 127, - 127, 127, 127, 127, 127, 127, 127, 127, - 127, 127, 127, 127, 127, 127, 127, 127, - 127, 127, 127, 127, 132, 133, 133, 133 + 0, 38, 38, 38, 38, 38, 38, 38, + 38, 38, 38, 38, 38, 38, 38, 38, + 38, 38, 38, 38, 38, 38, 38, 38, + 38, 38, 38, 38, 38, 38, 38, 69, + 69, 69, 69, 69, 69, 69, 69, 69, + 69, 69, 69, 69, 96, 69, 69, 69, + 69, 69, 69, 69, 69, 69, 69, 69, + 100, 96, 69, 102, 105, 69, 69, 69, + 69, 69, 69, 69, 69, 69, 69, 69, + 69, 69, 96, 69, 69, 69, 69, 69, + 69, 69, 69, 69, 69, 69, 100, 96, + 69, 69, 135, 135, 135, 135, 135, 135, + 135, 135, 135, 135, 135, 135, 135, 135, + 135, 135, 135, 135, 135, 135, 135, 135, + 135, 135, 135, 135, 135, 135, 135, 135, + 135, 135, 140, 141, 141, 141 }; static const int use_syllable_machine_start = 0; @@ -780,7 +929,7 @@ find_syllables_use (hb_buffer_t *buffer) unsigned int act HB_UNUSED; int cs; -#line 773 "hb-ot-shaper-use-machine.hh" +#line 933 "hb-ot-shaper-use-machine.hh" { cs = use_syllable_machine_start; ts = 0; @@ -793,7 +942,7 @@ find_syllables_use (hb_buffer_t *buffer) unsigned int syllable_serial = 1; -#line 782 "hb-ot-shaper-use-machine.hh" +#line 946 "hb-ot-shaper-use-machine.hh" { int _slen; int _trans; @@ -807,7 +956,7 @@ _resume: #line 1 "NONE" {ts = p;} break; -#line 794 "hb-ot-shaper-use-machine.hh" +#line 960 "hb-ot-shaper-use-machine.hh" } _keys = _use_syllable_machine_trans_keys + (cs<<1); @@ -825,14 +974,34 @@ _eof_trans: goto _again; switch ( _use_syllable_machine_trans_actions[_trans] ) { - case 9: + case 12: +#line 170 "hb-ot-shaper-use-machine.rl" + {te = p+1;{ found_syllable (use_virama_terminated_cluster); }} + break; + case 10: +#line 171 "hb-ot-shaper-use-machine.rl" + {te = p+1;{ found_syllable (use_sakot_terminated_cluster); }} + break; + case 8: #line 172 "hb-ot-shaper-use-machine.rl" {te = p+1;{ found_syllable (use_standard_cluster); }} break; + case 16: +#line 173 "hb-ot-shaper-use-machine.rl" + {te = p+1;{ found_syllable (use_number_joiner_terminated_cluster); }} + break; + case 14: +#line 174 "hb-ot-shaper-use-machine.rl" + {te = p+1;{ found_syllable (use_numeral_cluster); }} + break; case 6: #line 175 "hb-ot-shaper-use-machine.rl" {te = p+1;{ found_syllable (use_symbol_cluster); }} break; + case 20: +#line 176 "hb-ot-shaper-use-machine.rl" + {te = p+1;{ found_syllable (use_hieroglyph_cluster); }} + break; case 4: #line 177 "hb-ot-shaper-use-machine.rl" {te = p+1;{ found_syllable (use_broken_cluster); buffer->scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_BROKEN_SYLLABLE; }} @@ -842,6 +1011,10 @@ _eof_trans: {te = p+1;{ found_syllable (use_non_cluster); }} break; case 11: +#line 170 "hb-ot-shaper-use-machine.rl" + {te = p;p--;{ found_syllable (use_virama_terminated_cluster); }} + break; + case 9: #line 171 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_sakot_terminated_cluster); }} break; @@ -849,7 +1022,7 @@ _eof_trans: #line 172 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_standard_cluster); }} break; - case 14: + case 15: #line 173 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_number_joiner_terminated_cluster); }} break; @@ -861,43 +1034,19 @@ _eof_trans: #line 175 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_symbol_cluster); }} break; - case 17: + case 19: #line 176 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_hieroglyph_cluster); }} break; - case 15: + case 17: #line 177 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_broken_cluster); buffer->scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_BROKEN_SYLLABLE; }} break; - case 16: + case 18: #line 178 "hb-ot-shaper-use-machine.rl" {te = p;p--;{ found_syllable (use_non_cluster); }} break; - case 12: -#line 1 "NONE" - { switch( act ) { - case 1: - {{p = ((te))-1;} found_syllable (use_virama_terminated_cluster); } - break; - case 2: - {{p = ((te))-1;} found_syllable (use_sakot_terminated_cluster); } - break; - } - } - break; - case 8: -#line 1 "NONE" - {te = p+1;} -#line 170 "hb-ot-shaper-use-machine.rl" - {act = 1;} - break; - case 10: -#line 1 "NONE" - {te = p+1;} -#line 171 "hb-ot-shaper-use-machine.rl" - {act = 2;} - break; -#line 866 "hb-ot-shaper-use-machine.hh" +#line 1050 "hb-ot-shaper-use-machine.hh" } _again: @@ -906,7 +1055,7 @@ _again: #line 1 "NONE" {ts = 0;} break; -#line 873 "hb-ot-shaper-use-machine.hh" +#line 1059 "hb-ot-shaper-use-machine.hh" } if ( ++p != pe ) diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-use-table.hh b/thirdparty/harfbuzz/src/hb-ot-shaper-use-table.hh index e45ea30e60..6395d689ae 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-use-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-use-table.hh @@ -6,18 +6,18 @@ * * on files with these headers: * - * # IndicSyllabicCategory-14.0.0.txt - * # Date: 2021-05-22, 01:01:00 GMT [KW, RP] - * # IndicPositionalCategory-14.0.0.txt - * # Date: 2021-05-22, 01:01:00 GMT [KW, RP] - * # ArabicShaping-14.0.0.txt - * # Date: 2021-05-21, 01:54:00 GMT [KW, RP] - * # DerivedCoreProperties-14.0.0.txt - * # Date: 2021-08-12, 23:12:53 GMT - * # Blocks-14.0.0.txt - * # Date: 2021-01-22, 23:29:00 GMT [KW] - * # Scripts-14.0.0.txt - * # Date: 2021-07-10, 00:35:31 GMT + * # IndicSyllabicCategory-15.0.0.txt + * # Date: 2022-05-26, 02:18:00 GMT [KW, RP] + * # IndicPositionalCategory-15.0.0.txt + * # Date: 2022-05-26, 02:18:00 GMT [KW, RP] + * # ArabicShaping-15.0.0.txt + * # Date: 2022-02-14, 18:50:00 GMT [KW, RP] + * # DerivedCoreProperties-15.0.0.txt + * # Date: 2022-08-05, 22:17:05 GMT + * # Blocks-15.0.0.txt + * # Date: 2022-01-28, 20:58:00 GMT [KW] + * # Scripts-15.0.0.txt + * # Date: 2022-04-26, 23:15:02 GMT * # Override values For Indic_Syllabic_Category * # Not derivable * # Initial version based on Unicode 7.0 by Andrew Glass 2014-03-17 @@ -90,7 +90,7 @@ #pragma GCC diagnostic pop static const uint8_t -hb_use_u8[3083] = +hb_use_u8[3115] = { 16, 50, 51, 51, 51, 52, 51, 83, 118, 131, 51, 57, 58, 179, 195, 61, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, @@ -114,22 +114,22 @@ hb_use_u8[3083] = 47, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 48, 49, 2, 2, 2, 2, 2, 2, 2, 2, 50, 51, 2, 52, 2, 2, 53, 2, 2, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 2, 64, 65, 2, 66, 67, 68, 69, - 2, 70, 2, 71, 72, 73, 74, 2, 2, 75, 76, 77, 78, 2, 79, 2, - 2, 80, 80, 80, 80, 80, 80, 80, 80, 81, 2, 2, 2, 2, 2, 2, + 2, 70, 2, 71, 72, 73, 74, 2, 2, 75, 76, 77, 78, 2, 79, 80, + 2, 81, 81, 81, 81, 81, 81, 81, 81, 82, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 82, 83, 2, 2, 2, 2, 2, 2, 2, 84, - 85, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 80, 80, 80, 86, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 83, 84, 2, 2, 2, 2, 2, 2, 2, 85, + 86, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 81, 81, 81, 87, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 87, 88, 2, 2, 2, 2, 2, - 2, 2, 2, 89, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 88, 89, 2, 2, 2, 2, 2, + 2, 2, 2, 90, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 90, 2, 2, 91, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 92, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 93, 93, 94, 95, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, - 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, - 93, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, + 2, 2, 2, 91, 2, 2, 92, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 93, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 94, 94, 95, 96, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, + 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, + 94, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 2, 2, 2, 2, 2, 0, 0, 0, 3, 0, 0, 0, 0, 0, 4, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 7, 0, 0, 0, 0, 0, 0, @@ -147,7 +147,7 @@ hb_use_u8[3083] = 7, 0, 0, 0, 2, 2, 2, 2, 2, 39, 40, 41, 0, 0, 0, 0, 0, 10, 13, 28, 2, 2, 2, 2, 28, 2, 28, 2, 2, 2, 2, 2, 2, 7, 2, 28, 2, 2, 0, 15, 16, 17, 18, 19, 25, 20, 33, 22, - 0, 0, 0, 0, 0, 28, 9, 39, 42, 10, 27, 28, 2, 2, 2, 7, + 0, 0, 0, 0, 0, 28, 39, 39, 42, 10, 27, 28, 2, 2, 2, 7, 28, 7, 2, 28, 2, 2, 0, 15, 43, 0, 0, 25, 20, 0, 0, 2, 28, 28, 0, 0, 0, 0, 0, 0, 0, 0, 44, 28, 2, 2, 7, 0, 2, 7, 2, 2, 0, 28, 7, 7, 2, 0, 28, 7, 0, 2, 7, 0, @@ -191,75 +191,77 @@ hb_use_u8[3083] = 43, 100, 12, 0, 0, 0, 0, 0, 0, 2, 2, 59, 16, 46, 21, 111, 100, 100, 100, 112, 113, 0, 0, 0, 0, 2, 2, 2, 2, 2, 0, 28, 2, 9, 44, 114, 114, 114, 9, 114, 114, 13, 114, 114, 114, 24, 0, 38, - 0, 0, 0, 115, 116, 9, 3, 0, 0, 0, 0, 0, 0, 0, 117, 0, - 0, 0, 0, 0, 0, 0, 4, 118, 119, 40, 40, 3, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 119, 119, 120, 119, 119, 119, 119, 119, 119, 119, - 119, 0, 0, 121, 0, 0, 0, 0, 0, 0, 5, 121, 0, 0, 0, 0, + 0, 0, 0, 115, 49, 9, 3, 0, 0, 0, 0, 0, 0, 0, 116, 0, + 0, 0, 0, 0, 0, 0, 4, 117, 118, 40, 40, 3, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 118, 118, 119, 118, 118, 118, 118, 118, 118, 118, + 118, 0, 0, 120, 0, 0, 0, 0, 0, 0, 5, 120, 0, 0, 0, 0, 0, 44, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 2, 2, 2, 2, 0, 0, 0, 28, 0, 0, 0, 0, 0, 0, 0, - 122, 2, 51, 2, 106, 2, 8, 2, 2, 2, 63, 17, 14, 0, 0, 29, + 121, 2, 51, 2, 106, 2, 8, 2, 2, 2, 63, 17, 14, 0, 0, 29, 0, 2, 2, 0, 0, 0, 0, 0, 0, 27, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 123, 21, 21, 21, 21, 21, 21, 21, 124, 0, 0, 0, 0, + 2, 2, 2, 122, 21, 21, 21, 21, 21, 21, 21, 123, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 2, 0, 0, 0, 0, 0, - 50, 2, 2, 2, 20, 20, 125, 114, 0, 2, 2, 2, 126, 18, 57, 18, - 111, 100, 127, 0, 0, 0, 0, 0, 0, 9, 128, 2, 2, 2, 2, 2, - 2, 2, 129, 21, 20, 18, 46, 130, 131, 132, 0, 0, 0, 0, 0, 0, + 50, 2, 2, 2, 20, 20, 124, 114, 0, 2, 2, 2, 125, 18, 57, 18, + 111, 100, 126, 0, 0, 0, 0, 0, 0, 9, 127, 2, 2, 2, 2, 2, + 2, 2, 128, 21, 20, 18, 46, 129, 130, 131, 0, 0, 0, 0, 0, 0, 0, 2, 2, 50, 28, 2, 2, 2, 2, 2, 2, 2, 2, 8, 20, 57, - 97, 74, 133, 134, 135, 0, 0, 0, 0, 2, 136, 2, 2, 2, 2, 137, - 0, 28, 2, 40, 3, 0, 77, 13, 2, 51, 20, 138, 50, 51, 2, 2, - 103, 8, 7, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 139, 19, - 23, 0, 0, 140, 141, 0, 0, 0, 0, 2, 63, 43, 21, 78, 45, 142, + 97, 74, 132, 133, 134, 0, 0, 0, 0, 2, 135, 2, 2, 2, 2, 136, + 0, 28, 2, 40, 3, 0, 77, 13, 2, 51, 20, 137, 50, 51, 2, 2, + 103, 8, 7, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 138, 19, + 23, 0, 0, 139, 140, 0, 0, 0, 0, 2, 63, 43, 21, 78, 45, 141, 0, 79, 79, 79, 79, 79, 79, 79, 79, 0, 0, 0, 0, 0, 0, 0, - 4, 119, 119, 119, 119, 120, 0, 0, 0, 2, 2, 2, 2, 2, 7, 2, + 4, 118, 118, 118, 118, 119, 0, 0, 0, 2, 2, 2, 2, 2, 7, 2, 2, 2, 7, 2, 28, 2, 2, 2, 2, 2, 28, 2, 2, 2, 28, 7, - 0, 126, 18, 25, 29, 0, 0, 143, 144, 2, 2, 28, 2, 28, 2, 2, - 2, 2, 2, 2, 0, 12, 35, 0, 145, 2, 2, 11, 35, 0, 28, 2, + 0, 125, 18, 25, 29, 0, 0, 142, 143, 2, 2, 28, 2, 28, 2, 2, + 2, 2, 2, 2, 0, 12, 35, 0, 144, 2, 2, 11, 35, 0, 28, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 28, 2, 2, 7, 2, 2, 9, 39, 0, 0, 0, 0, 2, 2, 2, 2, 2, 25, 36, - 0, 2, 2, 2, 114, 114, 114, 114, 114, 146, 2, 7, 0, 0, 0, 0, + 0, 2, 2, 2, 114, 114, 114, 114, 114, 145, 2, 7, 0, 0, 0, 0, 0, 2, 12, 12, 0, 0, 0, 0, 0, 7, 2, 2, 7, 2, 2, 2, - 2, 28, 2, 7, 0, 28, 2, 0, 0, 147, 148, 149, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 20, 20, 18, 18, 18, 20, 20, 132, 0, 0, 0, - 0, 0, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, 2, 2, 2, 2, - 2, 51, 50, 51, 0, 0, 0, 0, 151, 9, 72, 2, 2, 2, 2, 2, + 2, 28, 2, 7, 0, 28, 2, 0, 0, 146, 147, 148, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 20, 20, 18, 18, 18, 20, 20, 131, 0, 0, 0, + 0, 0, 149, 149, 149, 149, 149, 149, 149, 149, 149, 149, 2, 2, 2, 2, + 2, 51, 50, 51, 0, 0, 0, 0, 150, 9, 72, 2, 2, 2, 2, 2, 2, 16, 17, 19, 14, 22, 35, 0, 0, 0, 29, 0, 0, 0, 0, 0, - 0, 9, 47, 2, 2, 2, 2, 2, 2, 2, 2, 2, 126, 18, 20, 152, - 20, 19, 153, 154, 2, 2, 2, 2, 2, 0, 0, 63, 155, 0, 0, 0, + 0, 9, 47, 2, 2, 2, 2, 2, 2, 2, 2, 2, 125, 18, 20, 151, + 20, 19, 152, 153, 2, 2, 2, 2, 2, 0, 0, 63, 154, 0, 0, 0, 0, 2, 11, 0, 0, 0, 0, 0, 0, 2, 63, 23, 18, 18, 18, 20, - 20, 106, 156, 0, 0, 157, 158, 29, 159, 28, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 21, 17, 20, 20, 160, 42, 0, 0, 0, - 44, 2, 2, 2, 7, 7, 2, 2, 28, 2, 2, 2, 2, 2, 2, 2, - 28, 2, 2, 2, 2, 2, 2, 2, 8, 16, 17, 19, 20, 161, 29, 0, - 0, 9, 9, 28, 2, 2, 2, 7, 28, 7, 2, 28, 2, 2, 56, 15, - 21, 14, 21, 45, 30, 31, 30, 32, 0, 0, 0, 0, 33, 0, 0, 0, - 2, 2, 21, 0, 9, 9, 9, 44, 0, 9, 9, 44, 0, 0, 0, 0, - 0, 2, 2, 63, 23, 18, 18, 18, 20, 21, 124, 13, 15, 0, 0, 0, - 0, 2, 2, 2, 2, 2, 0, 0, 162, 163, 0, 0, 0, 0, 0, 0, - 0, 16, 17, 18, 18, 64, 97, 23, 159, 9, 164, 7, 0, 0, 0, 0, - 0, 2, 2, 2, 2, 2, 2, 2, 63, 23, 18, 18, 0, 46, 46, 9, - 165, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 2, 18, - 0, 21, 17, 18, 18, 19, 14, 80, 165, 36, 0, 0, 0, 0, 0, 0, - 0, 2, 2, 2, 2, 2, 8, 166, 23, 18, 20, 20, 164, 7, 0, 0, - 0, 2, 2, 2, 2, 2, 7, 41, 134, 21, 20, 18, 74, 19, 20, 0, - 0, 2, 2, 2, 7, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 16, - 17, 18, 19, 20, 103, 165, 35, 0, 0, 2, 2, 2, 7, 28, 0, 2, - 2, 2, 2, 28, 7, 2, 2, 2, 2, 21, 21, 16, 30, 31, 10, 167, - 168, 169, 170, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 0, 2, 2, - 2, 63, 23, 18, 18, 0, 20, 21, 27, 106, 0, 31, 0, 0, 0, 0, - 0, 50, 18, 20, 20, 20, 138, 2, 2, 2, 171, 172, 9, 13, 173, 70, - 174, 0, 0, 1, 145, 0, 0, 0, 0, 50, 18, 20, 14, 17, 18, 2, - 2, 2, 2, 156, 156, 156, 175, 175, 175, 175, 175, 175, 13, 176, 0, 28, - 0, 20, 18, 18, 29, 20, 20, 9, 165, 0, 59, 59, 59, 59, 59, 59, - 59, 64, 19, 80, 44, 0, 0, 0, 0, 2, 2, 2, 7, 2, 28, 2, - 2, 50, 20, 20, 29, 0, 36, 20, 25, 9, 158, 177, 173, 0, 0, 0, - 0, 2, 2, 2, 28, 7, 2, 2, 2, 2, 2, 2, 2, 2, 21, 21, - 45, 20, 33, 80, 66, 0, 0, 0, 0, 2, 178, 64, 45, 0, 0, 0, + 20, 106, 155, 0, 0, 156, 157, 29, 158, 28, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 21, 17, 20, 20, 159, 42, 0, 0, 0, + 47, 125, 0, 0, 0, 0, 0, 0, 0, 2, 2, 2, 7, 7, 2, 2, + 28, 2, 2, 2, 2, 2, 2, 2, 28, 2, 2, 2, 2, 2, 2, 2, + 8, 16, 17, 19, 20, 160, 29, 0, 0, 9, 9, 28, 2, 2, 2, 7, + 28, 7, 2, 28, 2, 2, 56, 15, 21, 14, 21, 45, 30, 31, 30, 32, + 0, 0, 0, 0, 33, 0, 0, 0, 2, 2, 21, 0, 9, 9, 9, 44, + 0, 9, 9, 44, 0, 0, 0, 0, 0, 2, 2, 63, 23, 18, 18, 18, + 20, 21, 123, 13, 15, 0, 0, 0, 0, 2, 2, 2, 2, 2, 0, 0, + 161, 162, 0, 0, 0, 0, 0, 0, 0, 16, 17, 18, 18, 64, 97, 23, + 158, 9, 163, 7, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 2, + 63, 23, 18, 18, 0, 46, 46, 9, 164, 35, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 2, 2, 18, 0, 21, 17, 18, 18, 19, 14, 80, + 164, 36, 0, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 8, 165, + 23, 18, 20, 20, 163, 7, 0, 0, 0, 2, 2, 2, 2, 2, 7, 41, + 133, 21, 20, 18, 74, 19, 20, 0, 0, 2, 2, 2, 7, 0, 0, 0, + 0, 2, 2, 2, 2, 2, 2, 16, 17, 18, 19, 20, 103, 164, 35, 0, + 0, 2, 2, 2, 7, 28, 0, 2, 2, 2, 2, 28, 7, 2, 2, 2, + 2, 21, 21, 16, 30, 31, 10, 166, 167, 168, 169, 0, 0, 0, 0, 0, + 0, 2, 2, 2, 2, 0, 2, 2, 2, 63, 23, 18, 18, 0, 20, 21, + 27, 106, 0, 31, 0, 0, 0, 0, 0, 50, 18, 20, 20, 20, 137, 2, + 2, 2, 170, 171, 9, 13, 172, 70, 173, 0, 0, 1, 144, 0, 0, 0, + 0, 50, 18, 20, 14, 17, 18, 2, 2, 2, 2, 155, 155, 155, 174, 174, + 174, 174, 174, 174, 13, 175, 0, 28, 0, 20, 18, 18, 29, 20, 20, 9, + 164, 0, 59, 59, 59, 59, 59, 59, 59, 64, 19, 80, 44, 0, 0, 0, + 0, 2, 2, 2, 7, 2, 28, 2, 2, 50, 20, 20, 29, 0, 36, 20, + 25, 9, 157, 176, 172, 0, 0, 0, 0, 2, 2, 2, 28, 7, 2, 2, + 2, 2, 2, 2, 2, 2, 21, 21, 45, 20, 33, 80, 66, 0, 0, 0, + 0, 2, 177, 64, 45, 0, 0, 0, 0, 9, 178, 2, 2, 2, 2, 2, + 2, 2, 2, 21, 20, 18, 29, 0, 46, 14, 140, 0, 0, 0, 0, 0, 0, 179, 179, 179, 106, 7, 0, 0, 0, 9, 9, 9, 44, 0, 0, 0, 0, 2, 2, 2, 2, 2, 7, 0, 56, 180, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 38, 114, 24, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 2, 2, 2, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 0, 56, - 35, 0, 4, 119, 119, 119, 120, 0, 0, 9, 9, 9, 47, 2, 2, 2, + 35, 0, 4, 118, 118, 118, 119, 0, 0, 9, 9, 9, 47, 2, 2, 2, 0, 2, 2, 2, 2, 2, 0, 0, 2, 2, 2, 2, 2, 2, 2, 2, 44, 2, 2, 2, 2, 2, 2, 9, 9, 2, 2, 42, 42, 42, 90, 0, 0, O, O, O, GB, B, B, GB, O, O, WJ,FMPst,FMPst, O, CGJ, B, @@ -268,7 +270,7 @@ hb_use_u8[3083] = VPst,VMBlw, O, O, VAbv, GB,VMAbv,VMPst,VMPst, O, B, VBlw, O, O, VPre, VPre, O, VPre, H, O, VPst,FMAbv, O,CMBlw, O, VAbv, O, VAbv, H, O,VMBlw,VMAbv, CMAbv, GB, GB, O, MBlw,CMAbv,CMAbv, VPst, VAbv,VMAbv, O, VPst, O, VPre, VPre,VMAbv, - B, O, CS, CS, O, B, VAbv, VAbv, B, R, O, HVM, O, O, FBlw, O, + B, O, CS, CS,VMPst, B, VAbv, VAbv, B, R, O, HVM, O, O, FBlw, O, CMAbv, O,CMBlw, VAbv, VBlw, B, SUB, SUB, SUB, O, SUB, SUB, O, FBlw, O, B, VPst, VBlw, VPre,VMAbv,VMBlw,VMPst, IS, VAbv, MPst, MPre, MBlw, MBlw, B, MBlw, MBlw, VPst, VMPst,VMPst, B, MBlw, VPst, VPre, VAbv, VAbv,VMPst,VMPst,VMBlw, B,VMPst, VBlw, VPst, CGJ, @@ -276,18 +278,18 @@ hb_use_u8[3083] = CGJ, WJ, CGJ, GB,CMAbv,CMAbv, B, GB, B, VAbv, SUB, FPst, FPst,VMBlw, FPst, FPst, FBlw,VMAbv,FMBlw, VAbv, VPre, B, MPre, MBlw, SUB, FAbv, FAbv, MAbv, SUB, Sk, VPst, VAbv, VMAbv,VMAbv, FAbv,CMAbv, VPst, H, B, O,SMAbv,SMBlw,SMAbv,SMAbv,SMAbv, VPst, IS, VBlw, - FAbv,VMPre,VMPre,FMAbv,CMBlw,VMBlw,VMBlw,VMAbv, CS, CS,VMPst, O,FMAbv, ZWNJ, CGJ, WJ, - WJ, WJ, O,FMPst, O, O, H, MPst, VPst, H,VMAbv, VAbv,VMBlw, B, VBlw, FPst, - VPst, FAbv,VMPst, B,CMAbv, VAbv, MBlw, MPst, MBlw, H, O, VBlw, MPst, MPre, MAbv, MBlw, - O, B, FAbv, FAbv, FPst, VBlw, B, B, VPre, O,VMPst, IS, O,VMPst, VBlw, VPst, - VMBlw,VMBlw,VMAbv, O, IS,VMBlw, B,VMPst,VMAbv,VMPst, CS, CS, B, N, N, O, - HN, VPre, VBlw, VAbv, IS,CMAbv, O, VPst, B, R, R, O,FMBlw,CMBlw, VAbv, VPre, - VMAbv,VMAbv, H, VAbv,CMBlw,FMAbv, B, CS, CS, H,CMBlw,VMPst, H,VMPst, VAbv,VMAbv, - VPst, IS, R, MPst, R, MPst,CMBlw, B,FMBlw, VBlw,VMAbv, R, MBlw, MBlw, GB, FBlw, - FBlw,CMAbv, IS, VBlw, IS, GB, VAbv, H, H, O, VBlw, + FAbv,VMPre,VMPre,FMAbv,CMBlw,VMBlw,VMBlw,VMAbv, CS, O,FMAbv, ZWNJ, CGJ, WJ, WJ, WJ, + O,FMPst, O, O, H, MPst, VPst, H,VMAbv, VAbv,VMBlw, B, VBlw, FPst, VPst, FAbv, + VMPst, B,CMAbv, VAbv, MBlw, MPst, MBlw, H, O, VBlw, MPst, MPre, MAbv, MBlw, O, B, + FAbv, FAbv, FPst, VBlw, B, B, VPre, O,VMPst, IS, O,VMPst, VBlw, VPst,VMBlw,VMBlw, + VMAbv, O, IS,VMBlw, B,VMPst,VMAbv,VMPst, CS, CS, B, N, N, O, HN, VPre, + VBlw, VAbv, IS,CMAbv, O, VPst, B, R, R, O,FMBlw,CMBlw, VAbv, VPre,VMAbv,VMAbv, + H, VAbv,CMBlw,FMAbv, B, CS, CS, H,CMBlw,VMPst, H,VMPst, VAbv,VMAbv, VPst, IS, + R, MPst, R, MPst,CMBlw, B,FMBlw, VBlw,VMAbv, R, MBlw, MBlw, GB, FBlw, FBlw,CMAbv, + IS, VBlw, IS, GB, VAbv, R,VMPst, H, H, O, VBlw, }; static const uint16_t -hb_use_u16[768] = +hb_use_u16[776] = { 0, 0, 1, 2, 0, 0, 0, 0, 0, 0, 3, 4, 0, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 0, 0, 0, @@ -319,24 +321,25 @@ hb_use_u16[768] = 9, 9,173,170, 0, 0, 0, 0, 0, 0, 0, 9,174,175, 0, 9, 176, 0, 0,177,178, 0, 0, 0,179, 9, 9,180,181,182,183,184, 185, 9, 9,186,187, 0, 0, 0,188, 9,189,190,191, 9, 9,192, - 185, 9, 9,193,194,105,195,102, 9, 33,196,197, 0, 0, 0, 0, - 198,199, 94, 9, 9,200,201, 2,202, 20, 21,203,204,205,206,207, - 9, 9, 9,208,209,210,211, 0,195, 9, 9,212,213, 2, 0, 0, - 9, 9,214,215,216,217, 0, 0, 9, 9, 9,218,219, 2, 0, 0, - 9, 9,220,221, 2, 0, 0, 0, 9,222,223,103,224, 0, 0, 0, - 9, 9,225,226, 0, 0, 0, 0,227,228, 9,229,230, 2, 0, 0, - 0, 0,231, 9, 9,232,233, 0,234, 9, 9,235,236,237, 9, 9, - 238,239, 0, 0, 0, 0, 0, 0, 21, 9,214,240, 7, 9, 70, 18, - 9,241, 73,242, 0, 0, 0, 0,243, 9, 9,244,245, 2,246, 9, - 247,248, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9,249, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 98,250, 0, 0, 0, 0, - 0, 0, 0, 0, 2, 0, 0, 0, 9, 9, 9,251, 0, 0, 0, 0, - 9, 9, 9, 9,252,253,254,254,255,256, 0, 0, 0, 0,257, 0, - 9, 9, 9, 9, 9,258, 0, 0, 9, 9, 9, 9, 9, 9,105, 70, - 94,259, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,260, - 9, 9, 70,261,262, 0, 0, 0, 0, 9,263, 0, 9, 9,264, 2, - 9, 9, 9, 9,265, 2, 0, 0,129,129,129,129,129,129,129,129, - 160,160,160,160,160,160,160,160,160,160,160,160,160,160,160,129, + 185, 9, 9,193,194,105,195,102, 9, 33,196,197,198, 0, 0, 0, + 199,200, 94, 9, 9,201,202, 2,203, 20, 21,204,205,206,207,208, + 9, 9, 9,209,210,211,212, 0,195, 9, 9,213,214, 2, 0, 0, + 9, 9,215,216,217,218, 0, 0, 9, 9, 9,219,220, 2, 0, 0, + 9, 9,221,222, 2, 0, 0, 0, 9,223,224,103,225, 0, 0, 0, + 9, 9,226,227, 0, 0, 0, 0,228,229, 9,230,231, 2, 0, 0, + 0, 0,232, 9, 9,233,234, 0,235, 9, 9,236,237,238, 9, 9, + 239,240, 0, 0, 0, 0, 0, 0, 21, 9,215,241, 7, 9, 70, 18, + 9,242, 73,243, 0, 0, 0, 0,244, 9, 9,245,246, 2,247, 9, + 248,249, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9,250, + 251, 48, 9,252,253, 2, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 98,254, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, + 9, 9, 9,255, 0, 0, 0, 0, 9, 9, 9, 9,256,257,258,258, + 259,260, 0, 0, 0, 0,261, 0, 9, 9, 9, 9, 9,262, 0, 0, + 9, 9, 9, 9, 9, 9,105, 70, 94,263, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,264, 9, 9, 70,265,266, 0, 0, 0, + 0, 9,267, 0, 9, 9,268, 2, 9, 9, 9, 9,269, 2, 0, 0, + 129,129,129,129,129,129,129,129,160,160,160,160,160,160,160,160, + 160,160,160,160,160,160,160,129, }; static inline unsigned @@ -347,7 +350,7 @@ hb_use_b4 (const uint8_t* a, unsigned i) static inline uint_fast8_t hb_use_get_category (unsigned u) { - return u<921600u?hb_use_u8[2721+(((hb_use_u8[593+(((hb_use_u16[((hb_use_u8[113+(((hb_use_b4(hb_use_u8,u>>1>>3>>3>>5))<<5)+((u>>1>>3>>3)&31u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:O; + return u<921600u?hb_use_u8[2753+(((hb_use_u8[593+(((hb_use_u16[((hb_use_u8[113+(((hb_use_b4(hb_use_u8,u>>1>>3>>3>>5))<<5)+((u>>1>>3>>3)&31u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:O; } #undef B @@ -393,26 +396,5 @@ hb_use_get_category (unsigned u) #undef VMPre -#ifdef HB_USE_TABLE_MAIN -int main (int argc, char **argv) -{ - if (argc != 2) - { - for (unsigned u = 0; u < 0x10FFFFu; u++) - printf ("U+%04X %d\n", u, hb_use_get_category (u)); - return 0; - } - - hb_codepoint_t u; - sscanf (argv[1], "%x", &u); - - printf ("%d\n", hb_use_get_category (u)); - - return 0; -} - -#endif - - #endif /* HB_OT_SHAPER_USE_TABLE_HH */ /* == End of generated table == */ diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper-vowel-constraints.cc b/thirdparty/harfbuzz/src/hb-ot-shaper-vowel-constraints.cc index be4ac813b1..cb4db4a8b2 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper-vowel-constraints.cc +++ b/thirdparty/harfbuzz/src/hb-ot-shaper-vowel-constraints.cc @@ -10,8 +10,8 @@ * # Date: 2015-03-12, 21:17:00 GMT [AG] * # Date: 2019-11-08, 23:22:00 GMT [AG] * - * # Scripts-14.0.0.txt - * # Date: 2021-07-10, 00:35:31 GMT + * # Scripts-15.0.0.txt + * # Date: 2022-04-26, 23:15:02 GMT */ #include "hb.hh" diff --git a/thirdparty/harfbuzz/src/hb-ot-shaper.hh b/thirdparty/harfbuzz/src/hb-ot-shaper.hh index e160987f83..b2d1acb39b 100644 --- a/thirdparty/harfbuzz/src/hb-ot-shaper.hh +++ b/thirdparty/harfbuzz/src/hb-ot-shaper.hh @@ -380,6 +380,10 @@ hb_ot_shaper_categorize (const hb_ot_shape_planner_t *planner) case HB_SCRIPT_TOTO: case HB_SCRIPT_VITHKUQI: + /* Unicode-15.0 additions */ + case HB_SCRIPT_KAWI: + case HB_SCRIPT_NAG_MUNDARI: + /* If the designer designed the font for the 'DFLT' script, * (or we ended up arbitrarily pick 'latn'), use the default shaper. * Otherwise, use the specific shaper. diff --git a/thirdparty/harfbuzz/src/hb-ot-tag.cc b/thirdparty/harfbuzz/src/hb-ot-tag.cc index ceb3bf6df5..1b18270cca 100644 --- a/thirdparty/harfbuzz/src/hb-ot-tag.cc +++ b/thirdparty/harfbuzz/src/hb-ot-tag.cc @@ -307,12 +307,12 @@ hb_ot_tags_from_language (const char *lang_str, hb_tag_t lang_tag = hb_tag_from_string (lang_str, first_len); static hb_atomic_int_t last_tag_idx; /* Poor man's cache. */ - unsigned tag_idx = last_tag_idx.get_relaxed (); + unsigned tag_idx = last_tag_idx; if (likely (tag_idx < ot_languages_len && ot_languages[tag_idx].language == lang_tag) || hb_sorted_array (ot_languages, ot_languages_len).bfind (lang_tag, &tag_idx)) { - last_tag_idx.set_relaxed (tag_idx); + last_tag_idx = tag_idx; unsigned int i; while (tag_idx != 0 && ot_languages[tag_idx].language == ot_languages[tag_idx - 1].language) diff --git a/thirdparty/harfbuzz/src/hb-ot-var-avar-table.hh b/thirdparty/harfbuzz/src/hb-ot-var-avar-table.hh index 5946aef635..f60bc4a3ce 100644 --- a/thirdparty/harfbuzz/src/hb-ot-var-avar-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-var-avar-table.hh @@ -206,11 +206,10 @@ struct avar v = hb_clamp (v, -(1<<14), +(1<<14)); out.push (v); } - - OT::VariationStore::destroy_cache (var_store_cache); - for (unsigned i = 0; i < coords_length; i++) coords[i] = out[i]; + + OT::VariationStore::destroy_cache (var_store_cache); #endif } diff --git a/thirdparty/harfbuzz/src/hb-ot-var-mvar-table.hh b/thirdparty/harfbuzz/src/hb-ot-var-mvar-table.hh index 208db46741..420366fbb3 100644 --- a/thirdparty/harfbuzz/src/hb-ot-var-mvar-table.hh +++ b/thirdparty/harfbuzz/src/hb-ot-var-mvar-table.hh @@ -43,7 +43,7 @@ struct VariationValueRecord public: Tag valueTag; /* Four-byte tag identifying a font-wide measure. */ - HBUINT32 varIdx; /* Outer/inner index into VariationStore item. */ + VarIdx varIdx; /* Outer/inner index into VariationStore item. */ public: DEFINE_SIZE_STATIC (8); diff --git a/thirdparty/harfbuzz/src/hb-repacker.hh b/thirdparty/harfbuzz/src/hb-repacker.hh index 61b142238e..40a5326118 100644 --- a/thirdparty/harfbuzz/src/hb-repacker.hh +++ b/thirdparty/harfbuzz/src/hb-repacker.hh @@ -276,33 +276,17 @@ bool _process_overflows (const hb_vector_t<graph::overflow_record_t>& overflows, return resolution_attempted; } -/* - * Attempts to modify the topological sorting of the provided object graph to - * eliminate offset overflows in the links between objects of the graph. If a - * non-overflowing ordering is found the updated graph is serialized it into the - * provided serialization context. - * - * If necessary the structure of the graph may be modified in ways that do not - * affect the functionality of the graph. For example shared objects may be - * duplicated. - * - * For a detailed writeup describing how the algorithm operates see: - * docs/repacker.md - */ -template<typename T> -inline hb_blob_t* -hb_resolve_overflows (const T& packed, - hb_tag_t table_tag, - unsigned max_rounds = 20, - bool recalculate_extensions = false) { - graph_t sorted_graph (packed); +inline bool +hb_resolve_graph_overflows (hb_tag_t table_tag, + unsigned max_rounds , + bool recalculate_extensions, + graph_t& sorted_graph /* IN/OUT */) +{ sorted_graph.sort_shortest_distance (); bool will_overflow = graph::will_overflow (sorted_graph); if (!will_overflow) - { - return graph::serialize (sorted_graph); - } + return true; graph::gsubgpos_graph_context_t ext_context (table_tag, sorted_graph); if ((table_tag == HB_OT_TAG_GPOS @@ -314,13 +298,13 @@ hb_resolve_overflows (const T& packed, DEBUG_MSG (SUBSET_REPACK, nullptr, "Splitting subtables if needed."); if (!_presplit_subtables_if_needed (ext_context)) { DEBUG_MSG (SUBSET_REPACK, nullptr, "Subtable splitting failed."); - return nullptr; + return false; } DEBUG_MSG (SUBSET_REPACK, nullptr, "Promoting lookups to extensions if needed."); if (!_promote_extensions_if_needed (ext_context)) { DEBUG_MSG (SUBSET_REPACK, nullptr, "Extensions promotion failed."); - return nullptr; + return false; } } @@ -360,15 +344,41 @@ hb_resolve_overflows (const T& packed, if (sorted_graph.in_error ()) { DEBUG_MSG (SUBSET_REPACK, nullptr, "Sorted graph in error state."); - return nullptr; + return false; } if (graph::will_overflow (sorted_graph)) { DEBUG_MSG (SUBSET_REPACK, nullptr, "Offset overflow resolution failed."); - return nullptr; + return false; } + return true; +} + +/* + * Attempts to modify the topological sorting of the provided object graph to + * eliminate offset overflows in the links between objects of the graph. If a + * non-overflowing ordering is found the updated graph is serialized it into the + * provided serialization context. + * + * If necessary the structure of the graph may be modified in ways that do not + * affect the functionality of the graph. For example shared objects may be + * duplicated. + * + * For a detailed writeup describing how the algorithm operates see: + * docs/repacker.md + */ +template<typename T> +inline hb_blob_t* +hb_resolve_overflows (const T& packed, + hb_tag_t table_tag, + unsigned max_rounds = 20, + bool recalculate_extensions = false) { + graph_t sorted_graph (packed); + if (!hb_resolve_graph_overflows (table_tag, max_rounds, recalculate_extensions, sorted_graph)) + return nullptr; + return graph::serialize (sorted_graph); } diff --git a/thirdparty/harfbuzz/src/hb-serialize.hh b/thirdparty/harfbuzz/src/hb-serialize.hh index cecdcdeb74..f47cde5eb5 100644 --- a/thirdparty/harfbuzz/src/hb-serialize.hh +++ b/thirdparty/harfbuzz/src/hb-serialize.hh @@ -139,6 +139,14 @@ struct hb_serialize_context_t objidx = o.objidx; } #endif + + HB_INTERNAL static int cmp (const void* a, const void* b) + { + int cmp = ((const link_t*)a)->position - ((const link_t*)b)->position; + if (cmp) return cmp; + + return ((const link_t*)a)->objidx - ((const link_t*)b)->objidx; + } }; char *head; @@ -315,7 +323,7 @@ struct hb_serialize_context_t { object_t *obj = current; if (unlikely (!obj)) return; - if (unlikely (in_error())) return; + if (unlikely (in_error() && !only_overflow ())) return; current = current->next; revert (obj->head, obj->tail); diff --git a/thirdparty/harfbuzz/src/hb-static.cc b/thirdparty/harfbuzz/src/hb-static.cc index af95615c16..5d4c7cda1b 100644 --- a/thirdparty/harfbuzz/src/hb-static.cc +++ b/thirdparty/harfbuzz/src/hb-static.cc @@ -94,7 +94,7 @@ hb_face_t::load_num_glyphs () const ret = hb_max (ret, load_num_glyphs_from_maxp (this)); - num_glyphs.set_relaxed (ret); + num_glyphs = ret; return ret; } @@ -102,7 +102,7 @@ unsigned int hb_face_t::load_upem () const { unsigned int ret = table.head->get_upem (); - upem.set_relaxed (ret); + upem = ret; return ret; } diff --git a/thirdparty/harfbuzz/src/hb-subset-input.cc b/thirdparty/harfbuzz/src/hb-subset-input.cc index 7d19496275..14ae210d49 100644 --- a/thirdparty/harfbuzz/src/hb-subset-input.cc +++ b/thirdparty/harfbuzz/src/hb-subset-input.cc @@ -391,7 +391,7 @@ hb_subset_input_get_user_data (const hb_subset_input_t *input, * * Return value: `true` if success, `false` otherwise * - * Since: REPLACEME + * Since: EXPERIMENTAL **/ hb_bool_t hb_subset_input_pin_axis_to_default (hb_subset_input_t *input, @@ -415,7 +415,7 @@ hb_subset_input_pin_axis_to_default (hb_subset_input_t *input, * * Return value: `true` if success, `false` otherwise * - * Since: REPLACEME + * Since: EXPERIMENTAL **/ hb_bool_t hb_subset_input_pin_axis_location (hb_subset_input_t *input, diff --git a/thirdparty/harfbuzz/src/hb-subset-plan.cc b/thirdparty/harfbuzz/src/hb-subset-plan.cc index 7ff66333a8..079ab8bf99 100644 --- a/thirdparty/harfbuzz/src/hb-subset-plan.cc +++ b/thirdparty/harfbuzz/src/hb-subset-plan.cc @@ -89,8 +89,6 @@ _remap_indexes (const hb_set_t *indexes, } #ifndef HB_NO_SUBSET_LAYOUT -typedef void (*layout_collect_func_t) (hb_face_t *face, hb_tag_t table_tag, const hb_tag_t *scripts, const hb_tag_t *languages, const hb_tag_t *features, hb_set_t *lookup_indexes /* OUT */); - /* * Removes all tags from 'tags' that are not in filter. Additionally eliminates any duplicates. @@ -130,8 +128,8 @@ static bool _filter_tag_list(hb_vector_t<hb_tag_t>* tags, /* IN/OUT */ template <typename T> static void _collect_layout_indices (hb_subset_plan_t *plan, const T& table, - layout_collect_func_t layout_collect_func, - hb_set_t *indices /* OUT */) + hb_set_t *lookup_indices, /* OUT */ + hb_set_t *feature_indices /* OUT */) { unsigned num_features = table.get_feature_count (); hb_vector_t<hb_tag_t> features; @@ -149,12 +147,23 @@ static void _collect_layout_indices (hb_subset_plan_t *plan, || !plan->check_success (!scripts.in_error ()) || !scripts) return; - layout_collect_func (plan->source, - T::tableTag, - retain_all_scripts ? nullptr : scripts.arrayZ, - nullptr, - retain_all_features ? nullptr : features.arrayZ, - indices); + hb_ot_layout_collect_features (plan->source, + T::tableTag, + retain_all_scripts ? nullptr : scripts.arrayZ, + nullptr, + retain_all_features ? nullptr : features.arrayZ, + feature_indices); + + for (unsigned feature_index : *feature_indices) + { + //TODO: replace HB_OT_LAYOUT_NO_VARIATIONS_INDEX with variation_index for + //instancing + const OT::Feature &f = table.get_feature_variation (feature_index, HB_OT_LAYOUT_NO_VARIATIONS_INDEX); + f.add_lookup_indexes_to (lookup_indices); + } + + //TODO: update for instancing: only collect lookups from feature_indexes that have no variations + table.feature_variation_collect_lookups (feature_indices, lookup_indices); } @@ -232,11 +241,11 @@ _closure_glyphs_lookups_features (hb_subset_plan_t *plan, { hb_blob_ptr_t<T> table = plan->source_table<T> (); hb_tag_t table_tag = table->tableTag; - hb_set_t lookup_indices; + hb_set_t lookup_indices, feature_indices; _collect_layout_indices<T> (plan, *table, - hb_ot_layout_collect_lookups, - &lookup_indices); + &lookup_indices, + &feature_indices); if (table_tag == HB_OT_TAG_GSUB) hb_ot_layout_lookups_substitute_closure (plan->source, @@ -247,19 +256,13 @@ _closure_glyphs_lookups_features (hb_subset_plan_t *plan, &lookup_indices); _remap_indexes (&lookup_indices, lookups); - // Collect and prune features - hb_set_t feature_indices; - _collect_layout_indices<T> (plan, - *table, - hb_ot_layout_collect_features, - &feature_indices); - + // prune features table->prune_features (lookups, &feature_indices); hb_map_t duplicate_feature_map; _GSUBGPOS_find_duplicate_features (*table, lookups, &feature_indices, &duplicate_feature_map); feature_indices.clear (); - table->prune_langsys (&duplicate_feature_map, langsys_map, &feature_indices); + table->prune_langsys (&duplicate_feature_map, plan->layout_scripts, langsys_map, &feature_indices); _remap_indexes (&feature_indices, features); table.destroy (); @@ -269,11 +272,46 @@ _closure_glyphs_lookups_features (hb_subset_plan_t *plan, #ifndef HB_NO_VAR static inline void -_collect_layout_variation_indices (hb_subset_plan_t* plan, - const hb_set_t *glyphset, - const hb_map_t *gpos_lookups, - hb_set_t *layout_variation_indices, - hb_map_t *layout_variation_idx_map) +_generate_varstore_inner_maps (const hb_set_t& varidx_set, + unsigned subtable_count, + hb_vector_t<hb_inc_bimap_t> &inner_maps /* OUT */) +{ + if (varidx_set.is_empty () || subtable_count == 0) return; + + inner_maps.resize (subtable_count); + for (unsigned idx : varidx_set) + { + uint16_t major = idx >> 16; + uint16_t minor = idx & 0xFFFF; + + if (major >= subtable_count) + continue; + inner_maps[major].add (minor); + } +} + +static inline hb_font_t* +_get_hb_font_with_variations (const hb_subset_plan_t *plan) +{ + hb_font_t *font = hb_font_create (plan->source); + + hb_vector_t<hb_variation_t> vars; + vars.alloc (plan->user_axes_location->get_population ()); + + for (auto _ : *plan->user_axes_location) + { + hb_variation_t var; + var.tag = _.first; + var.value = _.second; + vars.push (var); + } + + hb_font_set_variations (font, vars.arrayZ, plan->user_axes_location->get_population ()); + return font; +} + +static inline void +_collect_layout_variation_indices (hb_subset_plan_t* plan) { hb_blob_ptr_t<OT::GDEF> gdef = plan->source_table<OT::GDEF> (); hb_blob_ptr_t<GPOS> gpos = plan->source_table<GPOS> (); @@ -284,13 +322,40 @@ _collect_layout_variation_indices (hb_subset_plan_t* plan, gpos.destroy (); return; } - OT::hb_collect_variation_indices_context_t c (layout_variation_indices, glyphset, gpos_lookups); + + const OT::VariationStore *var_store = nullptr; + hb_set_t varidx_set; + hb_font_t *font = nullptr; + float *store_cache = nullptr; + bool collect_delta = plan->pinned_at_default ? false : true; + if (collect_delta) + { + font = _get_hb_font_with_variations (plan); + if (gdef->has_var_store ()) + { + var_store = &(gdef->get_var_store ()); + store_cache = var_store->create_cache (); + } + } + + OT::hb_collect_variation_indices_context_t c (&varidx_set, + plan->layout_variation_idx_delta_map, + font, var_store, + plan->_glyphset_gsub, + plan->gpos_lookups, + store_cache); gdef->collect_variation_indices (&c); if (hb_ot_layout_has_positioning (plan->source)) gpos->collect_variation_indices (&c); - gdef->remap_layout_variation_indices (layout_variation_indices, layout_variation_idx_map); + hb_font_destroy (font); + var_store->destroy_cache (store_cache); + + gdef->remap_layout_variation_indices (&varidx_set, plan->layout_variation_idx_delta_map); + + unsigned subtable_count = gdef->has_var_store () ? gdef->get_var_store ().get_sub_table_count () : 0; + _generate_varstore_inner_maps (varidx_set, subtable_count, plan->gdef_varstore_inner_maps); gdef.destroy (); gpos.destroy (); @@ -506,11 +571,7 @@ _populate_gids_to_retain (hb_subset_plan_t* plan, #ifndef HB_NO_VAR if (close_over_gdef) - _collect_layout_variation_indices (plan, - plan->_glyphset_gsub, - plan->gpos_lookups, - plan->layout_variation_indices, - plan->layout_variation_idx_map); + _collect_layout_variation_indices (plan); #endif } @@ -585,12 +646,9 @@ _nameid_closure (hb_face_t *face, #ifndef HB_NO_VAR static void -_normalize_axes_location (hb_face_t *face, - const hb_hashmap_t<hb_tag_t, float> *user_axes_location, - hb_hashmap_t<hb_tag_t, int> *normalized_axes_location, /* OUT */ - bool &all_axes_pinned) +_normalize_axes_location (hb_face_t *face, hb_subset_plan_t *plan) { - if (user_axes_location->is_empty ()) + if (plan->user_axes_location->is_empty ()) return; hb_array_t<const OT::AxisRecord> axes = face->table.fvar->get_axes (); @@ -605,25 +663,27 @@ _normalize_axes_location (hb_face_t *face, for (const auto& axis : axes) { hb_tag_t axis_tag = axis.get_axis_tag (); - if (!user_axes_location->has (axis_tag)) + if (!plan->user_axes_location->has (axis_tag)) { axis_not_pinned = true; } else { - int normalized_v = axis.normalize_axis_value (user_axes_location->get (axis_tag)); + int normalized_v = axis.normalize_axis_value (plan->user_axes_location->get (axis_tag)); if (has_avar && axis_count < face->table.avar->get_axis_count ()) { normalized_v = seg_maps->map (normalized_v); } - normalized_axes_location->set (axis_tag, normalized_v); + plan->axes_location->set (axis_tag, normalized_v); + if (normalized_v != 0) + plan->pinned_at_default = false; } if (has_avar) seg_maps = &StructAfter<OT::SegmentMaps> (*seg_maps); - + axis_count++; } - all_axes_pinned = !axis_not_pinned; + plan->all_axes_pinned = !axis_not_pinned; } #endif /** @@ -683,8 +743,8 @@ hb_subset_plan_create_or_fail (hb_face_t *face, plan->gpos_features = hb_map_create (); plan->colrv1_layers = hb_map_create (); plan->colr_palettes = hb_map_create (); - plan->layout_variation_indices = hb_set_create (); - plan->layout_variation_idx_map = hb_map_create (); + plan->check_success (plan->layout_variation_idx_delta_map = hb_hashmap_create<unsigned, hb_pair_t<unsigned, int>> ()); + plan->gdef_varstore_inner_maps.init (); plan->check_success (plan->sanitized_table_cache = hb_hashmap_create<hb_tag_t, hb::unique_ptr<hb_blob_t>> ()); plan->check_success (plan->axes_location = hb_hashmap_create<hb_tag_t, int> ()); @@ -692,12 +752,20 @@ hb_subset_plan_create_or_fail (hb_face_t *face, if (plan->user_axes_location && input->axes_location) *plan->user_axes_location = *input->axes_location; plan->all_axes_pinned = false; + plan->pinned_at_default = true; + + plan->check_success (plan->vmtx_map = hb_hashmap_create<unsigned, hb_pair_t<unsigned, int>> ()); + plan->check_success (plan->hmtx_map = hb_hashmap_create<unsigned, hb_pair_t<unsigned, int>> ()); if (unlikely (plan->in_error ())) { hb_subset_plan_destroy (plan); return nullptr; } +#ifndef HB_NO_VAR + _normalize_axes_location (face, plan); +#endif + _populate_unicodes_to_retain (input->sets.unicodes, input->sets.glyphs, plan); _populate_gids_to_retain (plan, @@ -725,13 +793,6 @@ hb_subset_plan_create_or_fail (hb_face_t *face, plan->glyph_map->get(plan->unicode_to_new_gid_list.arrayZ[i].second); } -#ifndef HB_NO_VAR - _normalize_axes_location (face, - input->axes_location, - plan->axes_location, - plan->all_axes_pinned); -#endif - _nameid_closure (face, plan->name_ids, plan->all_axes_pinned, plan->user_axes_location); if (unlikely (plan->in_error ())) { hb_subset_plan_destroy (plan); @@ -754,44 +815,6 @@ hb_subset_plan_destroy (hb_subset_plan_t *plan) { if (!hb_object_destroy (plan)) return; - hb_set_destroy (plan->unicodes); - hb_set_destroy (plan->name_ids); - hb_set_destroy (plan->name_languages); - hb_set_destroy (plan->layout_features); - hb_set_destroy (plan->layout_scripts); - hb_set_destroy (plan->glyphs_requested); - hb_set_destroy (plan->drop_tables); - hb_set_destroy (plan->no_subset_tables); - hb_face_destroy (plan->source); - hb_face_destroy (plan->dest); - hb_map_destroy (plan->codepoint_to_glyph); - hb_map_destroy (plan->glyph_map); - hb_map_destroy (plan->reverse_glyph_map); - hb_map_destroy (plan->glyph_map_gsub); - hb_set_destroy (plan->_glyphset); - hb_set_destroy (plan->_glyphset_gsub); - hb_set_destroy (plan->_glyphset_mathed); - hb_set_destroy (plan->_glyphset_colred); - hb_map_destroy (plan->gsub_lookups); - hb_map_destroy (plan->gpos_lookups); - hb_map_destroy (plan->gsub_features); - hb_map_destroy (plan->gpos_features); - hb_map_destroy (plan->colrv1_layers); - hb_map_destroy (plan->colr_palettes); - hb_set_destroy (plan->layout_variation_indices); - hb_map_destroy (plan->layout_variation_idx_map); - - hb_hashmap_destroy (plan->gsub_langsys); - hb_hashmap_destroy (plan->gpos_langsys); - hb_hashmap_destroy (plan->axes_location); - hb_hashmap_destroy (plan->sanitized_table_cache); - - if (plan->user_axes_location) - { - hb_object_destroy (plan->user_axes_location); - hb_free (plan->user_axes_location); - } - hb_free (plan); } diff --git a/thirdparty/harfbuzz/src/hb-subset-plan.hh b/thirdparty/harfbuzz/src/hb-subset-plan.hh index 8912ae70d5..98a45e5f6d 100644 --- a/thirdparty/harfbuzz/src/hb-subset-plan.hh +++ b/thirdparty/harfbuzz/src/hb-subset-plan.hh @@ -33,10 +33,56 @@ #include "hb-subset-input.hh" #include "hb-map.hh" +#include "hb-bimap.hh" #include "hb-set.hh" struct hb_subset_plan_t { + hb_subset_plan_t () + {} + + ~hb_subset_plan_t() + { + hb_set_destroy (unicodes); + hb_set_destroy (name_ids); + hb_set_destroy (name_languages); + hb_set_destroy (layout_features); + hb_set_destroy (layout_scripts); + hb_set_destroy (glyphs_requested); + hb_set_destroy (drop_tables); + hb_set_destroy (no_subset_tables); + hb_face_destroy (source); + hb_face_destroy (dest); + hb_map_destroy (codepoint_to_glyph); + hb_map_destroy (glyph_map); + hb_map_destroy (reverse_glyph_map); + hb_map_destroy (glyph_map_gsub); + hb_set_destroy (_glyphset); + hb_set_destroy (_glyphset_gsub); + hb_set_destroy (_glyphset_mathed); + hb_set_destroy (_glyphset_colred); + hb_map_destroy (gsub_lookups); + hb_map_destroy (gpos_lookups); + hb_map_destroy (gsub_features); + hb_map_destroy (gpos_features); + hb_map_destroy (colrv1_layers); + hb_map_destroy (colr_palettes); + + hb_hashmap_destroy (gsub_langsys); + hb_hashmap_destroy (gpos_langsys); + hb_hashmap_destroy (axes_location); + hb_hashmap_destroy (sanitized_table_cache); + hb_hashmap_destroy (hmtx_map); + hb_hashmap_destroy (vmtx_map); + hb_hashmap_destroy (layout_variation_idx_delta_map); + + if (user_axes_location) + { + hb_object_destroy (user_axes_location); + hb_free (user_axes_location); + } + } + hb_object_header_t header; bool successful; @@ -101,10 +147,11 @@ struct hb_subset_plan_t hb_map_t *colrv1_layers; hb_map_t *colr_palettes; - //The set of layout item variation store delta set indices to be retained - hb_set_t *layout_variation_indices; - //Old -> New layout item variation store delta set index mapping - hb_map_t *layout_variation_idx_map; + //Old layout item variation index -> (New varidx, delta) mapping + hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *layout_variation_idx_delta_map; + + //gdef varstore retained varidx mapping + hb_vector_t<hb_inc_bimap_t> gdef_varstore_inner_maps; hb_hashmap_t<hb_tag_t, hb::unique_ptr<hb_blob_t>>* sanitized_table_cache; //normalized axes location map @@ -112,6 +159,12 @@ struct hb_subset_plan_t //user specified axes location map hb_hashmap_t<hb_tag_t, float> *user_axes_location; bool all_axes_pinned; + bool pinned_at_default; + + //hmtx metrics map: new gid->(advance, lsb) + hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *hmtx_map; + //vmtx metrics map: new gid->(advance, lsb) + hb_hashmap_t<unsigned, hb_pair_t<unsigned, int>> *vmtx_map; public: diff --git a/thirdparty/harfbuzz/src/hb-subset.cc b/thirdparty/harfbuzz/src/hb-subset.cc index f62e7e895b..1a0bcbd1fe 100644 --- a/thirdparty/harfbuzz/src/hb-subset.cc +++ b/thirdparty/harfbuzz/src/hb-subset.cc @@ -406,6 +406,27 @@ _passthrough (hb_subset_plan_t *plan, hb_tag_t tag) } static bool +_dependencies_satisfied (hb_subset_plan_t *plan, hb_tag_t tag, + hb_set_t &visited_set, hb_set_t &revisit_set) +{ + switch (tag) + { + case HB_OT_TAG_hmtx: + case HB_OT_TAG_vmtx: + if (!plan->pinned_at_default && + !visited_set.has (HB_OT_TAG_glyf)) + { + revisit_set.add (tag); + return false; + } + return true; + + default: + return true; + } +} + +static bool _subset_table (hb_subset_plan_t *plan, hb_vector_t<char> &buf, hb_tag_t tag) @@ -514,7 +535,7 @@ hb_subset_plan_execute_or_fail (hb_subset_plan_t *plan) return nullptr; } - hb_set_t tags_set; + hb_set_t tags_set, revisit_set; bool success = true; hb_tag_t table_tags[32]; unsigned offset = 0, num_tables = ARRAY_LENGTH (table_tags); @@ -527,10 +548,27 @@ hb_subset_plan_execute_or_fail (hb_subset_plan_t *plan) { hb_tag_t tag = table_tags[i]; if (_should_drop_table (plan, tag) && !tags_set.has (tag)) continue; + if (!_dependencies_satisfied (plan, tag, tags_set, revisit_set)) continue; tags_set.add (tag); success = _subset_table (plan, buf, tag); if (unlikely (!success)) goto end; } + + /*delayed subsetting for some tables since they might have dependency on other tables in some cases: + e.g: during instantiating glyf tables, hmetrics/vmetrics are updated and saved in subset plan, + hmtx/vmtx subsetting need to use these updated metrics values*/ + while (!revisit_set.is_empty ()) + { + hb_set_t revisit_temp; + for (hb_tag_t tag : revisit_set) + { + if (!_dependencies_satisfied (plan, tag, tags_set, revisit_temp)) continue; + tags_set.add (tag); + success = _subset_table (plan, buf, tag); + if (unlikely (!success)) goto end; + } + revisit_set = revisit_temp; + } offset += num_tables; } diff --git a/thirdparty/harfbuzz/src/hb-ucd-table.hh b/thirdparty/harfbuzz/src/hb-ucd-table.hh index 14734c91ea..a372a4afce 100644 --- a/thirdparty/harfbuzz/src/hb-ucd-table.hh +++ b/thirdparty/harfbuzz/src/hb-ucd-table.hh @@ -4,7 +4,7 @@ * * ./gen-ucd-table.py ucd.nounihan.grouped.xml * - * on file with this description: Unicode 14.0.0 + * on file with this description: Unicode 15.0.0 */ #ifndef HB_UCD_TABLE_HH @@ -13,7 +13,7 @@ #include "hb.hh" static const hb_script_t -_hb_ucd_sc_map[163] = +_hb_ucd_sc_map[165] = { HB_SCRIPT_COMMON, HB_SCRIPT_INHERITED, HB_SCRIPT_UNKNOWN, HB_SCRIPT_ARABIC, @@ -96,7 +96,8 @@ _hb_ucd_sc_map[163] = HB_SCRIPT_YEZIDI, HB_SCRIPT_CYPRO_MINOAN, HB_SCRIPT_OLD_UYGHUR, HB_SCRIPT_TANGSA, HB_SCRIPT_TOTO, HB_SCRIPT_VITHKUQI, - HB_SCRIPT_MATH, + HB_SCRIPT_MATH, HB_SCRIPT_KAWI, + HB_SCRIPT_NAG_MUNDARI, }; static const uint16_t _hb_ucd_dm1_p0_map[825] = @@ -1068,7 +1069,7 @@ _hb_ucd_dm2_u64_map[388] = #ifndef HB_OPTIMIZE_SIZE static const uint8_t -_hb_ucd_u8[17936] = +_hb_ucd_u8[18260] = { 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 9, 10, 7, 7, 7, 7, 11, 12, 13, 13, 13, 14, @@ -1076,7 +1077,7 @@ _hb_ucd_u8[17936] = 25, 26, 22, 22, 22, 27, 28, 29, 22, 30, 31, 32, 33, 34, 35, 36, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 37, 7, 38, 39, 7, 40, 7, 7, 7, 41, 22, 42, - 7, 7, 43, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, + 7, 7, 43, 7, 44, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, @@ -1098,12 +1099,12 @@ _hb_ucd_u8[17936] = 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, - 44, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, + 45, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 45, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 46, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 47, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 34, 35, 36, 37, 38, 39, 34, 34, 34, 40, 41, 42, 43, @@ -1122,35 +1123,36 @@ _hb_ucd_u8[17936] = 118,119,120,121,122,123,124,125,126,127,128,129, 34, 34,130,131, 132,133,134,135,136,137,138,139,140,141,142,122,143,144,145,146, 147,148,149,150,151,152,153,122,154,155,122,156,157,158,159,122, - 160,161,162,163,164,165,122,122,166,167,168,169,122,170,122,171, - 34, 34, 34, 34, 34, 34, 34,172,173, 34,174,122,122,122,122,122, - 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,175, - 34, 34, 34, 34, 34, 34, 34, 34,176,122,122,122,122,122,122,122, + 160,161,162,163,164,165,166,122,167,168,169,170,122,171,172,173, + 34, 34, 34, 34, 34, 34, 34,174,175, 34,176,122,122,122,122,122, + 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,177, + 34, 34, 34, 34, 34, 34, 34, 34,178,122,122,122,122,122,122,122, 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,122, - 122,122,122,122,122,122,122,122, 34, 34, 34, 34,177,122,122,122, - 34, 34, 34, 34,178,179,180,181,122,122,122,122,182,183,184,185, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,186, - 34, 34, 34, 34, 34, 34, 34, 34, 34,187,188,122,122,122,122,122, - 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,189, - 34, 34,190, 34, 34,191,122,122,122,122,122,122,122,122,122,122, - 122,122,122,122,122,122,122,122,192,193,122,122,122,122,122,122, - 122,122,122,122,122,122,122,122,122,122,122,122,122,122,194,195, - 69,196,197,198,199,200,201,122,202,203,204,205,206,207,208,209, - 69, 69, 69, 69,210,211,122,122,122,122,122,122,122,122,212,122, - 213,122,214,122,122,215,122,122,122,122,122,122,122,122,122,216, - 34,217,218,122,122,122,122,122,219,220,221,122,222,223,122,122, - 224,225,226,227,228,122, 69,229, 69, 69, 69, 69, 69,230,231,232, - 233,234, 69, 69,235,236, 69,237,122,122,122,122,122,122,122,122, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,238, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,239, 34, - 240, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,241, 34, 34, - 34, 34, 34, 34, 34, 34, 34,242,122,122,122,122,122,122,122,122, - 34, 34, 34, 34,243,122,122,122,122,122,122,122,122,122,122,122, - 34, 34, 34, 34, 34, 34,244,122,122,122,122,122,122,122,122,122, - 245,122,246,247,122,122,122,122,122,122,122,122,122,122,122,122, - 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,248, - 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,249, + 122,122,122,122,122,122,122,122, 34, 34, 34, 34,179,122,122,122, + 34, 34, 34, 34,180,181,182,183,122,122,122,122,184,185,186,187, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,188, + 34, 34, 34, 34, 34, 34, 34, 34, 34,189,190,122,122,122,122,122, + 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,191, + 34, 34,192, 34, 34,193,122,122,122,122,122,122,122,122,122,122, + 122,122,122,122,122,122,122,122,194,195,122,122,122,122,122,122, + 122,122,122,122,122,122,122,122,122,122,122,122,122,122,196,197, + 69,198,199,200,201,202,203,122,204,205,206,207,208,209,210,211, + 69, 69, 69, 69,212,213,122,122,122,122,122,122,122,122,214,122, + 215,216,217,122,122,218,122,122,122,219,122,122,122,122,122,220, + 34,221,222,122,122,122,122,122,223,224,225,122,226,227,122,122, + 228,229,230,231,232,122, 69,233, 69, 69, 69, 69, 69,234,235,236, + 237,238, 69, 69,239,240, 69,241,122,122,122,122,122,122,122,122, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,242, 34, 34, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,243, 34, + 244, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,245, 34, 34, + 34, 34, 34, 34, 34, 34, 34,246,122,122,122,122,122,122,122,122, + 34, 34, 34, 34,247,122,122,122,122,122,122,122,122,122,122,122, + 34, 34, 34, 34, 34, 34,248, 34, 34, 34, 34, 34, 34, 34, 34, 34, + 34, 34, 34, 34, 34, 34, 34,249,122,122,122,122,122,122,122,122, + 250,122,251,252,122,122,122,122,122,122,122,122,122,122,122,122, + 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,253, + 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,254, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 2, 4, 5, 6, 2, 7, 7, 7, 7, 7, 2, 8, 9, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 12, 13, 14, 15, 16, 16, 16, 16, 16, 16, 16, @@ -1213,7 +1215,7 @@ _hb_ucd_u8[17936] = 44, 44, 57, 80, 36, 61, 62, 44, 44, 44, 44, 93, 27, 27, 27, 91, 70, 86, 72, 36, 36, 36, 61, 36, 36, 36, 62, 36, 36, 44, 71, 87, 86, 86, 90, 85, 90, 86, 43, 44, 44, 44, 89, 90, 44, 44, 62, 61, - 62, 61, 44, 44, 44, 44, 44, 44, 43, 86, 36, 36, 36, 36, 61, 36, + 62, 94, 44, 44, 44, 44, 44, 44, 43, 86, 36, 36, 36, 36, 61, 36, 36, 36, 36, 36, 36, 70, 71, 86, 87, 43, 80, 86, 90, 86, 87, 77, 44, 44, 36, 94, 27, 27, 27, 95, 27, 27, 27, 27, 91, 36, 36, 36, 57, 86, 62, 36, 36, 36, 36, 36, 36, 36, 36, 61, 44, 36, 36, 36, @@ -1223,7 +1225,7 @@ _hb_ucd_u8[17936] = 36, 36, 36, 75, 43, 43, 43, 60, 7, 7, 7, 7, 7, 2, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 62, 61, 61, 36, 36, 61, 36, 36, 36, 36, 62, 62, 36, 36, 36, 36, 70, 36, 43, 43, 43, 43, 71, 44, - 36, 36, 61, 81, 43, 43, 43, 44, 7, 7, 7, 7, 7, 44, 36, 36, + 36, 36, 61, 81, 43, 43, 43, 80, 7, 7, 7, 7, 7, 44, 36, 36, 77, 67, 2, 2, 2, 2, 2, 2, 2, 97, 97, 67, 43, 67, 67, 67, 7, 7, 7, 7, 7, 27, 27, 27, 27, 27, 50, 50, 50, 4, 4, 86, 36, 36, 36, 36, 62, 36, 36, 36, 36, 36, 36, 36, 36, 36, 61, 44, @@ -1390,18 +1392,19 @@ _hb_ucd_u8[17936] = 44, 44, 44, 44,179, 27, 27, 27, 11, 47, 44, 44, 44, 44, 44, 44, 16,110, 44, 44, 44, 27, 27, 27, 36, 36, 43, 43, 44, 44, 44, 44, 27, 27, 27, 27, 27, 27, 27,100, 36, 36, 36, 36, 36, 57,184, 44, - 36, 44, 44, 44, 44, 44, 44, 44, 27, 27, 27, 95, 44, 44, 44, 44, - 180, 27, 30, 2, 2, 44, 44, 44, 36, 43, 43, 2, 2, 44, 44, 44, - 36, 36,183, 27, 27, 27, 44, 44, 87, 98, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 43, 43, 43, 43, 43, 43, 43, 60, 2, 2, 2, 44, - 27, 27, 27, 7, 7, 7, 7, 7, 71, 70, 71, 44, 44, 44, 44, 57, - 86, 87, 43, 85, 87, 60,185, 2, 2, 80, 44, 44, 44, 44, 79, 44, - 43, 71, 36, 36, 36, 36, 36, 36, 36, 36, 36, 70, 43, 43, 87, 43, - 43, 43, 80, 7, 7, 7, 7, 7, 2, 2, 94, 98, 44, 44, 44, 44, - 36, 70, 2, 61, 44, 44, 44, 44, 36, 94, 86, 43, 43, 43, 43, 85, - 98, 36, 63, 2, 59, 43, 60, 87, 7, 7, 7, 7, 7, 63, 63, 2, - 179, 27, 27, 27, 27, 27, 27, 27, 27, 27,100, 44, 44, 44, 44, 44, - 36, 36, 36, 36, 36, 36, 86, 87, 43, 86, 85, 43, 2, 2, 2, 80, + 36, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 57, 43, + 27, 27, 27, 95, 44, 44, 44, 44,180, 27, 30, 2, 2, 44, 44, 44, + 36, 43, 43, 2, 2, 44, 44, 44, 36, 36,183, 27, 27, 27, 44, 44, + 87, 98, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 43, 43, 43, 43, + 43, 43, 43, 60, 2, 2, 2, 44, 27, 27, 27, 7, 7, 7, 7, 7, + 71, 70, 71, 44, 44, 44, 44, 57, 86, 87, 43, 85, 87, 60,185, 2, + 2, 80, 44, 44, 44, 44, 79, 44, 43, 71, 36, 36, 36, 36, 36, 36, + 36, 36, 36, 70, 43, 43, 87, 43, 43, 43, 80, 7, 7, 7, 7, 7, + 2, 2, 94, 98, 44, 44, 44, 44, 36, 70, 2, 61, 44, 44, 44, 44, + 36, 94, 86, 43, 43, 43, 43, 85, 98, 36, 63, 2, 59, 43, 60, 87, + 7, 7, 7, 7, 7, 63, 63, 2,179, 27, 27, 27, 27, 27, 27, 27, + 27, 27,100, 44, 44, 44, 44, 44, 36, 36, 36, 36, 36, 36, 86, 87, + 43, 86, 85, 43, 2, 2, 2, 71, 70, 44, 44, 44, 44, 44, 44, 44, 36, 36, 36, 61, 61, 36, 36, 62, 36, 36, 36, 36, 36, 36, 36, 62, 36, 36, 36, 36, 63, 44, 44, 44, 36, 36, 36, 36, 36, 36, 36, 70, 86, 87, 43, 43, 43, 80, 44, 44, 43, 86, 62, 36, 36, 36, 61, 62, @@ -1423,17 +1426,20 @@ _hb_ucd_u8[17936] = 70, 43, 43, 43, 43, 71, 36, 36, 36, 70, 43, 43, 85, 70, 43, 60, 2, 2, 2, 59, 44, 44, 44, 44, 70, 43, 43, 85, 87, 43, 36, 36, 36, 36, 36, 36, 36, 43, 43, 43, 43, 43, 43, 85, 43, 2, 72, 2, - 2, 64, 44, 44, 44, 44, 44, 44, 43, 43, 43, 80, 43, 43, 43, 87, - 63, 2, 2, 44, 44, 44, 44, 44, 2, 36, 36, 36, 36, 36, 36, 36, - 44, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 89, 43, 43, 43, - 85, 43, 87, 80, 44, 44, 44, 44, 36, 36, 36, 61, 36, 62, 36, 36, - 70, 43, 43, 80, 44, 80, 43, 57, 43, 43, 43, 70, 44, 44, 44, 44, - 36, 36, 36, 62, 61, 36, 36, 36, 36, 36, 36, 36, 36, 86, 86, 90, - 43, 89, 87, 87, 61, 44, 44, 44, 36, 70, 85,107, 64, 44, 44, 44, + 2, 64, 44, 44, 44, 44, 44, 44, 2, 2, 2, 2, 2, 44, 44, 44, + 43, 43, 43, 80, 43, 43, 43, 87, 63, 2, 2, 44, 44, 44, 44, 44, + 2, 36, 36, 36, 36, 36, 36, 36, 44, 43, 43, 43, 43, 43, 43, 43, + 43, 43, 43, 43, 89, 43, 43, 43, 85, 43, 87, 80, 44, 44, 44, 44, + 36, 36, 36, 61, 36, 62, 36, 36, 70, 43, 43, 80, 44, 80, 43, 57, + 43, 43, 43, 70, 44, 44, 44, 44, 36, 36, 36, 62, 61, 36, 36, 36, + 36, 36, 36, 36, 36, 86, 86, 90, 43, 89, 87, 87, 61, 44, 44, 44, + 36, 70, 85,107, 64, 44, 44, 44, 43, 94, 36, 36, 36, 36, 36, 36, + 36, 36, 86, 43, 43, 80, 44, 86, 85, 60, 2, 2, 2, 2, 2, 2, 27, 27, 91, 67, 67, 67, 56, 20,168, 67, 67, 67, 67, 67, 67, 67, 67, 44, 44, 44, 44, 44, 44, 93,105,105,105,105,105,105,105,181, 2, 2, 64, 44, 44, 44, 44, 44, 63, 64, 44, 44, 44, 44, 44, 44, - 65, 65, 65, 65,132, 44, 44, 44, 43, 43, 60, 44, 44, 44, 44, 44, + 65, 65, 65, 65, 65, 65, 65, 65, 71, 36, 36, 70, 43, 43, 43, 43, + 43, 43, 43, 44, 44, 44, 44, 44, 43, 43, 60, 44, 44, 44, 44, 44, 43, 43, 43, 60, 2, 2, 67, 67, 40, 40, 97, 44, 44, 44, 44, 44, 7, 7, 7, 7, 7,179, 27, 27, 27, 62, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 44, 44, 62, 36, 27, 27, 27, 30, 2, 64, 44, 44, @@ -1441,7 +1447,8 @@ _hb_ucd_u8[17936] = 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 44, 44, 44, 57, 43, 74, 40, 40, 40, 40, 40, 40, 40, 88, 80, 44, 44, 44, 44, 44, 86, 44, 44, 44, 44, 44, 44, 44, 40, 40, 52, 40, 40, 40, 52, 81, - 36, 61, 44, 44, 44, 44, 44, 44, 44, 44, 36, 36, 44, 44, 44, 44, + 36, 61, 44, 44, 44, 44, 44, 44, 44, 61, 44, 44, 44, 44, 44, 44, + 36, 61, 62, 44, 44, 44, 44, 44, 44, 44, 36, 36, 44, 44, 44, 44, 36, 36, 36, 36, 36, 44, 50, 60, 65, 65, 44, 44, 44, 44, 44, 44, 43, 43, 43, 43, 43, 43, 43, 44, 43, 43, 43, 80, 44, 44, 44, 44, 67, 67, 67, 92, 55, 67, 67, 67, 67, 67,186, 87, 43, 67,186, 86, @@ -1466,10 +1473,12 @@ _hb_ucd_u8[17936] = 43, 43, 43, 43, 43, 43, 76, 67, 67, 67, 50, 67, 67, 67, 67, 67, 67, 67, 76, 21, 2, 2, 44, 44, 44, 44, 44, 44, 44, 57, 43, 43, 16, 16, 16, 16, 16, 39, 16, 16, 16, 16, 16, 16, 16, 16, 16,110, - 43, 43, 43, 80, 43, 43, 43, 43, 43, 43, 43, 43, 80, 57, 43, 43, - 43, 57, 80, 43, 43, 80, 44, 44, 43, 43, 43, 74, 40, 40, 40, 44, - 7, 7, 7, 7, 7, 44, 44, 77, 36, 36, 36, 36, 36, 36, 36, 80, - 36, 36, 36, 36, 36, 36, 43, 43, 7, 7, 7, 7, 7, 44, 44, 96, + 44, 44,150, 16, 16,110, 44, 44, 43, 43, 43, 80, 43, 43, 43, 43, + 43, 43, 43, 43, 80, 57, 43, 43, 43, 57, 80, 43, 43, 80, 44, 44, + 40, 40, 40, 40, 40, 40, 40, 44, 44, 44, 44, 44, 44, 44, 44, 57, + 43, 43, 43, 74, 40, 40, 40, 44, 7, 7, 7, 7, 7, 44, 44, 77, + 36, 36, 36, 36, 36, 36, 36, 80, 36, 36, 36, 36, 36, 36, 43, 43, + 7, 7, 7, 7, 7, 44, 44, 96, 36, 36, 36, 36, 36, 83, 43, 43, 36, 36, 36, 61, 36, 36, 62, 61, 36, 36, 61,179, 27, 27, 27, 27, 16, 16, 43, 43, 43, 74, 44, 44, 27, 27, 27, 27, 27, 27,163, 27, 188, 27,100, 44, 44, 44, 44, 44, 27, 27, 27, 27, 27, 27, 27,163, @@ -1482,138 +1491,141 @@ _hb_ucd_u8[17936] = 27, 27, 27, 27, 27, 27, 91, 67, 67, 67, 67, 67, 67, 67, 67, 44, 44, 44, 44, 67, 67, 67, 67, 67, 67, 92, 44, 44, 44, 44, 44, 44, 67, 67, 67, 67, 92, 44, 44, 44, 67, 44, 44, 44, 44, 44, 44, 44, - 67, 67, 67, 67, 67, 25, 41, 41, 67, 67, 67, 67, 44, 44, 55, 67, - 67, 67, 67, 67, 44, 44, 44, 44, 67, 67, 92, 44, 67, 67, 92, 44, + 67, 67, 67, 67, 67, 25, 41, 41, 67, 67, 67, 67, 44, 44, 67, 67, + 67, 67, 67, 92, 44, 55, 67, 67, 67, 67, 67, 67, 44, 44, 44, 44, + 67, 67, 67, 67, 67, 67, 67, 55, 67, 67, 67, 44, 44, 44, 44, 67, 67, 92, 67, 67, 67, 67, 67, 67, 79, 44, 44, 44, 44, 44, 44, 44, - 65, 65, 65, 65, 65, 65, 65, 65,171,171,171,171,171,171,171, 44, - 171,171,171,171,171,171,171, 0, 0, 0, 29, 21, 21, 21, 23, 21, - 22, 18, 21, 25, 21, 17, 13, 13, 25, 25, 25, 21, 21, 9, 9, 9, - 9, 22, 21, 18, 24, 16, 24, 5, 5, 5, 5, 22, 25, 18, 25, 0, - 23, 23, 26, 21, 24, 26, 7, 20, 25, 1, 26, 24, 26, 25, 15, 15, - 24, 15, 7, 19, 15, 21, 9, 25, 9, 5, 5, 25, 5, 9, 5, 7, - 7, 7, 9, 8, 8, 5, 7, 5, 6, 6, 24, 24, 6, 24, 12, 12, - 2, 2, 6, 5, 9, 21, 9, 2, 2, 9, 25, 9, 26, 12, 11, 11, - 2, 6, 5, 21, 17, 2, 2, 26, 26, 23, 2, 12, 17, 12, 21, 12, - 12, 21, 7, 2, 2, 7, 7, 21, 21, 2, 1, 1, 21, 23, 26, 26, - 1, 21, 6, 7, 7, 12, 12, 7, 21, 7, 12, 1, 12, 6, 6, 12, - 12, 26, 7, 26, 26, 7, 2, 1, 12, 2, 6, 2, 24, 7, 7, 6, - 1, 12, 12, 10, 10, 10, 10, 12, 21, 6, 2, 10, 10, 2, 15, 26, - 26, 2, 2, 21, 7, 10, 15, 7, 2, 23, 21, 26, 10, 7, 21, 15, - 15, 2, 17, 7, 29, 7, 7, 22, 18, 2, 14, 14, 14, 7, 10, 21, - 17, 21, 11, 12, 5, 2, 5, 6, 8, 8, 8, 24, 5, 24, 2, 24, - 9, 24, 24, 2, 29, 29, 29, 1, 17, 17, 20, 19, 22, 20, 27, 28, - 1, 29, 21, 20, 19, 21, 21, 16, 16, 21, 25, 22, 18, 21, 21, 29, - 1, 2, 15, 6, 18, 6, 23, 2, 12, 11, 9, 26, 26, 9, 26, 5, - 5, 26, 14, 9, 5, 14, 14, 15, 25, 26, 26, 22, 18, 26, 18, 25, - 18, 22, 5, 12, 2, 5, 22, 21, 21, 22, 18, 17, 26, 6, 7, 14, - 17, 22, 18, 18, 26, 14, 17, 6, 14, 6, 12, 24, 24, 6, 26, 15, - 6, 21, 11, 21, 24, 9, 6, 9, 23, 26, 6, 10, 4, 4, 3, 3, - 7, 25, 17, 16, 16, 22, 16, 16, 25, 17, 25, 2, 25, 24, 2, 15, - 12, 15, 14, 2, 21, 14, 7, 15, 12, 17, 21, 1, 26, 10, 10, 1, - 23, 15, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 10, 11, 12, - 13, 0, 14, 0, 0, 0, 0, 0, 15, 0, 16, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, - 0, 21, 22, 23, 0, 0, 0, 24, 25, 26, 27, 28, 29, 30, 31, 32, - 33, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 34, 0, 35, 0, 0, 0, 0, 0, 0, + 171,171,171,171,171,171,171, 44,171,171,171,171,171,171,171, 0, + 0, 0, 29, 21, 21, 21, 23, 21, 22, 18, 21, 25, 21, 17, 13, 13, + 25, 25, 25, 21, 21, 9, 9, 9, 9, 22, 21, 18, 24, 16, 24, 5, + 5, 5, 5, 22, 25, 18, 25, 0, 23, 23, 26, 21, 24, 26, 7, 20, + 25, 1, 26, 24, 26, 25, 15, 15, 24, 15, 7, 19, 15, 21, 9, 25, + 9, 5, 5, 25, 5, 9, 5, 7, 7, 7, 9, 8, 8, 5, 7, 5, + 6, 6, 24, 24, 6, 24, 12, 12, 2, 2, 6, 5, 9, 21, 9, 2, + 2, 9, 25, 9, 26, 12, 11, 11, 2, 6, 5, 21, 17, 2, 2, 26, + 26, 23, 2, 12, 17, 12, 21, 12, 12, 21, 7, 2, 2, 7, 7, 21, + 21, 2, 1, 1, 21, 23, 26, 26, 1, 21, 6, 7, 7, 12, 12, 7, + 21, 7, 12, 1, 12, 6, 6, 12, 12, 26, 7, 26, 26, 7, 2, 1, + 12, 2, 6, 2, 24, 7, 7, 6, 1, 12, 12, 10, 10, 10, 10, 12, + 21, 6, 2, 10, 10, 2, 15, 26, 26, 2, 2, 21, 7, 10, 15, 7, + 2, 23, 21, 26, 10, 7, 21, 15, 15, 2, 17, 7, 29, 7, 7, 22, + 18, 2, 14, 14, 14, 7, 10, 21, 17, 21, 11, 12, 5, 2, 5, 6, + 8, 8, 8, 24, 5, 24, 2, 24, 9, 24, 24, 2, 29, 29, 29, 1, + 17, 17, 20, 19, 22, 20, 27, 28, 1, 29, 21, 20, 19, 21, 21, 16, + 16, 21, 25, 22, 18, 21, 21, 29, 1, 2, 15, 6, 18, 6, 23, 2, + 12, 11, 9, 26, 26, 9, 26, 5, 5, 26, 14, 9, 5, 14, 14, 15, + 25, 26, 26, 22, 18, 26, 18, 25, 18, 22, 5, 12, 2, 5, 22, 21, + 21, 22, 18, 17, 26, 6, 7, 14, 17, 22, 18, 18, 26, 14, 17, 6, + 14, 6, 12, 24, 24, 6, 26, 15, 6, 21, 11, 21, 24, 9, 6, 9, + 23, 26, 6, 10, 4, 4, 3, 3, 7, 25, 17, 16, 16, 22, 16, 16, + 25, 17, 25, 2, 25, 24, 2, 15, 12, 15, 14, 2, 21, 14, 7, 15, + 12, 17, 21, 1, 26, 10, 10, 1, 23, 15, 0, 1, 2, 3, 4, 5, + 6, 7, 8, 9, 0, 10, 11, 12, 13, 0, 14, 0, 0, 0, 0, 0, + 15, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 37, 38, 0, 0, 0, 0, - 0, 0, 39, 40, 0, 0, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1, 2, 3, 4, 0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, - 0, 0, 0, 0, 6, 7, 8, 0, 9, 0, 10, 11, 0, 0, 12, 13, - 14, 15, 16, 0, 0, 0, 0, 17, 18, 19, 20, 0, 21, 0, 22, 23, - 0, 24, 25, 0, 0, 24, 26, 27, 0, 24, 26, 0, 0, 24, 26, 0, - 0, 24, 26, 0, 0, 0, 26, 0, 0, 24, 28, 0, 0, 24, 26, 0, - 0, 29, 26, 0, 0, 0, 30, 0, 0, 31, 32, 0, 0, 33, 34, 0, - 35, 36, 0, 37, 38, 0, 39, 0, 0, 40, 0, 0, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 43, 44, 0, 0, 0, 0, 45, 0, 0, 0, 0, 0, 0, 46, 0, 0, - 0, 47, 0, 0, 0, 0, 0, 0, 48, 0, 0, 49, 0, 50, 51, 0, - 0, 52, 53, 54, 0, 55, 0, 56, 0, 57, 0, 0, 0, 0, 58, 59, - 0, 0, 0, 0, 0, 0, 60, 61, 0, 0, 0, 0, 0, 0, 62, 63, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, - 0, 0, 0, 65, 0, 0, 0, 66, 0, 67, 0, 0, 68, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 69, 70, 0, 0, 71, - 0, 0, 0, 0, 0, 0, 0, 0, 72, 73, 0, 0, 0, 0, 53, 74, - 0, 75, 76, 0, 0, 77, 78, 0, 0, 0, 0, 0, 0, 79, 80, 81, - 0, 0, 0, 0, 0, 0, 0, 26, 0, 0, 0, 0, 0, 0, 0, 0, - 82, 0, 0, 0, 0, 0, 0, 0, 0, 83, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 20, 0, 21, 22, 23, 0, 0, 0, 24, + 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 84, 0, 0, 0, 0, 0, 0, 0, 85, - 0, 0, 0, 86, 0, 0, 0, 0, 87, 88, 0, 0, 0, 0, 0, 89, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 35, + 0, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 90, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 91, 0, 0, - 0, 0, 92, 0, 93, 0, 0, 0, 0, 0, 72, 94, 0, 95, 0, 0, - 96, 97, 0, 77, 0, 0, 98, 0, 0, 99, 0, 0, 0, 0, 0,100, - 0,101, 26,102, 0, 0, 0, 0, 0, 0,103, 0, 0, 0,104, 0, - 0, 0, 0, 0, 0, 65,105, 0, 0, 65, 0, 0, 0,106, 0, 0, - 0,107, 0, 0, 0, 0, 0, 0, 0, 95, 0, 0, 0, 0, 0, 0, - 0,108,109, 0, 0, 0, 0, 78, 0, 44,110, 0,111, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 65, 0, 0, 0, 0, 0, 0, - 0, 0,112, 0,113, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,114, - 0,115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0,116, 0, 0, 0, 0,117, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 37, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 38, 39, 0, 0, 0, 0, 0, 0, 40, 41, 42, 0, 43, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,118,119,120, 0, 0, 0, 0,121, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,122,123, 0, 0, 0, 0, 0, 0, - 0,115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,124, 0,125, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,126, 0, - 0, 0,127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1, 1, 1, 1, 1, 2, 3, 4, 5, 6, 7, 4, 4, 8, 9, 10, - 1, 11, 12, 13, 14, 15, 16, 17, 18, 1, 1, 1, 0, 0, 0, 0, - 19, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 21, 22, 1, - 23, 4, 21, 24, 25, 26, 27, 28, 29, 30, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 1, 1, 31, 0, 0, 0, 32, 33, 34, 35, 1, 36, - 0, 0, 0, 0, 37, 0, 0, 0, 0, 0, 0, 0, 0, 38, 1, 39, - 14, 39, 40, 41, 0, 0, 0, 0, 0, 0, 0, 0, 42, 0, 0, 0, - 0, 0, 0, 0, 43, 36, 44, 45, 21, 45, 46, 0, 0, 0, 0, 0, - 0, 0, 19, 1, 21, 0, 0, 47, 0, 0, 0, 0, 0, 38, 48, 1, - 1, 49, 49, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 51, 0, - 0, 0, 0, 0, 0, 0, 52, 1, 0, 0, 38, 14, 4, 1, 1, 1, - 53, 21, 43, 52, 54, 21, 35, 1, 0, 0, 0, 0, 0, 0, 0, 55, - 0, 0, 0, 56, 57, 58, 0, 0, 0, 0, 0, 56, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 59, 0, 0, 0, 56, 0, 60, 0, 0, - 0, 0, 0, 0, 0, 0, 61, 62, 0, 0, 63, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 65, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 66, 0, 0, 0, 67, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 68, 0, 0, 0, 0, 0, 0, 69, 70, 0, - 0, 0, 0, 0, 71, 72, 73, 74, 75, 76, 0, 0, 0, 0, 0, 0, - 0, 77, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 78, 79, 0, - 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 49, - 0, 0, 0, 0, 0, 80, 0, 0, 0, 0, 0, 0, 0, 62, 0, 0, - 0, 0, 0, 0, 63, 0, 0, 81, 0, 0, 82, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 83, 0, 0, 0, 0, 0, 0, 19, 84, 0, - 62, 0, 0, 0, 0, 49, 1, 85, 0, 0, 0, 0, 1, 52, 15, 86, - 36, 10, 21, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 55, 0, 0, - 0, 62, 0, 0, 0, 0, 0, 0, 0, 0, 19, 10, 1, 0, 0, 0, - 0, 0, 88, 0, 0, 0, 0, 0, 0, 89, 0, 0, 88, 0, 0, 0, - 0, 0, 0, 0, 0, 78, 0, 0, 0, 0, 0, 0, 87, 9, 12, 4, - 90, 8, 91, 47, 0, 58, 50, 0, 21, 1, 21, 92, 93, 1, 1, 1, - 1, 1, 1, 1, 1, 94, 95, 96, 0, 0, 0, 0, 97, 1, 98, 58, - 81, 99,100, 4, 58, 0, 0, 0, 0, 0, 0, 19, 50, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 61, 1, 1, 1, 1, 1, 1, 1, 1, - 0, 0,101,102, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,103, 0, - 0, 0, 0, 19, 0, 1, 1, 50, 0, 0, 0, 0, 0, 0, 0, 38, - 0, 0, 0, 0, 50, 0, 0, 0, 0, 63, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 62, 0, 0, 0, 0, 1, 1, 1, 1, 50, 0, 0, 0, - 0, 0,104, 68, 0, 0, 0, 0, 0, 0, 0, 0, 61, 0, 0, 0, - 0, 0, 0, 0, 78, 0, 0, 0, 62, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0,105,106, 58, 38, 81, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0,107, - 1, 14, 4, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 47, - 84, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 38, 87, 0, - 0, 0, 0,108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,109, 61, - 0,110, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, - 0, 0, 19, 58, 0, 0, 0, 0, 0,111, 14, 52, 84, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 0, 0, 0, 0, + 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, 6, 7, 8, 0, + 9, 0, 10, 11, 0, 0, 12, 13, 14, 15, 16, 0, 0, 0, 0, 17, + 18, 19, 20, 0, 21, 0, 22, 23, 0, 24, 25, 0, 0, 24, 26, 27, + 0, 24, 26, 0, 0, 24, 26, 0, 0, 24, 26, 0, 0, 0, 26, 0, + 0, 24, 28, 0, 0, 24, 26, 0, 0, 29, 26, 0, 0, 0, 30, 0, + 0, 31, 32, 0, 0, 33, 34, 0, 35, 36, 0, 37, 38, 0, 39, 0, + 0, 40, 0, 0, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 42, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 43, 44, 0, 0, 0, 0, 45, 0, + 0, 0, 0, 0, 0, 46, 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, + 48, 0, 0, 49, 0, 50, 51, 0, 0, 52, 53, 54, 0, 55, 0, 56, + 0, 57, 0, 0, 0, 0, 58, 59, 0, 0, 0, 0, 0, 0, 60, 61, + 0, 0, 0, 0, 0, 0, 62, 63, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 65, 0, 0, 0, 66, + 0, 67, 0, 0, 68, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 69, 70, 0, 0, 71, 0, 0, 0, 0, 0, 0, 0, 0, + 72, 73, 0, 0, 0, 0, 53, 74, 0, 75, 76, 0, 0, 77, 78, 0, + 0, 0, 0, 0, 0, 79, 80, 81, 0, 0, 0, 0, 0, 0, 0, 26, + 0, 0, 0, 0, 0, 0, 0, 0, 82, 0, 0, 0, 0, 0, 0, 0, + 0, 83, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 84, + 0, 0, 0, 0, 0, 0, 0, 85, 0, 0, 0, 86, 0, 0, 0, 0, + 87, 88, 0, 0, 0, 0, 0, 89, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 90, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 91, 0, 92, 0, 0, 93, 0, 94, 0, 0, 0, + 0, 0, 72, 95, 0, 96, 0, 0, 97, 98, 0, 77, 0, 0, 99, 0, + 0,100, 0, 0, 0, 0, 0,101, 0,102, 26,103, 0, 0, 0, 0, + 0, 0,104, 0, 0, 0,105, 0, 0, 0, 0, 0, 0, 65,106, 0, + 0, 65, 0, 0, 0,107, 0, 0, 0,108, 0, 0, 0, 0, 0, 0, + 0, 96, 0, 0, 0, 0, 0, 0, 0,109,110, 0, 0, 0, 0, 78, + 0, 44,111, 0,112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 65, 0, 0, 0, 0, 0, 0, 0, 0,113, 0,114, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,115, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,116, 0,117, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,118, + 0, 0, 0, 0,119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,120,121,122, 0, 0, + 0, 0,123, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 124,125, 0, 0,126, 0, 0, 0, 0,117, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,127, 0,128, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,129, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,130, 0, 0, 0,131, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 3, 4, + 5, 6, 7, 4, 4, 8, 9, 10, 1, 11, 12, 13, 14, 15, 16, 17, + 18, 1, 1, 1, 0, 0, 0, 0, 19, 1, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 20, 21, 22, 1, 23, 4, 21, 24, 25, 26, 27, 28, + 29, 30, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 31, 0, + 0, 0, 32, 33, 34, 35, 1, 36, 0, 0, 0, 0, 37, 0, 0, 0, + 0, 0, 0, 0, 0, 38, 1, 39, 14, 39, 40, 41, 0, 0, 0, 0, + 0, 0, 0, 0, 42, 0, 0, 0, 0, 0, 0, 0, 43, 36, 44, 45, + 21, 45, 46, 0, 0, 0, 0, 0, 0, 0, 19, 1, 21, 0, 0, 47, + 0, 0, 0, 0, 0, 38, 48, 1, 1, 49, 49, 50, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 51, 0, 0, 0, 0, 0, 0, 0, 52, 1, + 0, 0, 38, 14, 4, 1, 1, 1, 53, 21, 43, 52, 54, 21, 35, 1, + 0, 0, 0, 0, 0, 0, 0, 55, 0, 0, 0, 56, 57, 58, 0, 0, + 0, 0, 0, 56, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 59, + 0, 0, 0, 56, 0, 60, 0, 0, 0, 0, 0, 0, 0, 0, 61, 62, + 0, 0, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, + 0, 0, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 66, 0, + 0, 0, 67, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 68, 0, + 0, 0, 0, 0, 0, 69, 70, 0, 0, 0, 0, 0, 71, 72, 73, 74, + 75, 76, 0, 0, 0, 0, 0, 0, 0, 77, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 78, 79, 0, 0, 0, 0, 47, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 49, 0, 0, 0, 0, 0, 80, 0, 0, + 0, 0, 0, 0, 0, 62, 0, 0, 0, 0, 0, 0, 63, 0, 0, 81, + 0, 0, 82, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 83, 0, + 0, 0, 0, 0, 0, 19, 84, 0, 62, 0, 0, 0, 0, 49, 1, 85, + 0, 0, 0, 0, 1, 52, 15, 86, 36, 10, 21, 87, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 55, 0, 0, 0, 62, 0, 0, 0, 0, 0, 0, + 0, 0, 19, 10, 1, 0, 0, 0, 0, 0, 88, 0, 0, 0, 0, 0, + 0, 89, 0, 0, 88, 0, 0, 0, 0, 0, 0, 0, 0, 78, 0, 0, + 0, 0, 0, 0, 87, 9, 12, 4, 90, 8, 91, 47, 0, 58, 50, 0, + 21, 1, 21, 92, 93, 1, 1, 1, 1, 1, 1, 1, 1, 94, 95, 96, + 0, 0, 0, 0, 97, 1, 98, 58, 81, 99,100, 4, 58, 0, 0, 0, + 0, 0, 0, 19, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 61, + 1, 1, 1, 1, 1, 1, 1, 1, 0, 0,101,102, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,103, 0, 0, 0, 0, 19, 0, 1, 1, 50, + 0, 0, 0, 0, 0, 0, 0, 38, 0, 0, 0, 0, 50, 0, 0, 0, + 0, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 62, 0, 0, 0, 0, + 1, 1, 1, 1, 50, 0, 0, 0, 0, 0,104, 68, 0, 0, 0, 0, + 0, 0, 0, 0, 61, 0, 0, 0, 0, 0, 0, 0, 78, 0, 0, 0, + 62, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,105,106, 58, 38, + 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 63, 0, 0, + 0, 0, 0, 0, 0, 0, 0,107, 1, 14, 4, 12, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 47, 84, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 38, 87, 0, 0, 0, 0,108, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,109, 61, 0,110, 0, 0, 0, 0, 0, 0, + 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 19, 58, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 51, 0,111, 14, 52, 84, 0, 0, 0, 112, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 62, 0, 0, 61, 0, 0, 0, 0, 0, 0,113, 0, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 61, 62, 0, 0, 62, 0, 89, 0, 0, 0, 0, 0, @@ -1624,89 +1636,90 @@ _hb_ucd_u8[17936] = 0, 0, 61, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 79, 78, 0, 0, 0, 0, 0, 0, 0, 0, 61, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 56, 0, 89, 80, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 61, 0, 0, 0, 0, 0, 0, 8, 91, 0, 0, - 0, 0, 0, 0, 1, 87, 0, 0, 0, 0, 0, 0,116, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0,117, 0,118,119,120,121, 0,104, 4, - 122, 49, 23, 0, 0, 0, 0, 0, 0, 0, 38, 50, 0, 0, 0, 0, - 38, 58, 0, 0, 0, 0, 0, 0, 1, 87, 1, 1, 1, 1, 39, 1, - 48,105, 87, 0, 0, 0, 0, 0, 0, 0, 0, 59, 0, 0, 0, 0, - 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 4,122, 0, 0, - 0, 1,123, 0, 0, 0, 0, 0, 0, 0, 0, 0,230,230,230,230, - 230,232,220,220,220,220,232,216,220,220,220,220,220,202,202,220, - 220,220,220,202,202,220,220,220, 1, 1, 1, 1, 1,220,220,220, - 220,230,230,230,230,240,230,220,220,220,230,230,230,220,220, 0, - 230,230,230,220,220,220,220,230,232,220,220,230,233,234,234,233, - 234,234,233,230, 0, 0, 0,230, 0,220,230,230,230,230,220,230, - 230,230,222,220,230,230,220,220,230,222,228,230, 10, 11, 12, 13, - 14, 15, 16, 17, 18, 19, 19, 20, 21, 22, 0, 23, 0, 24, 25, 0, - 230,220, 0, 18, 30, 31, 32, 0, 0, 0, 0, 27, 28, 29, 30, 31, - 32, 33, 34,230,230,220,220,230,220,230,230,220, 35, 0, 0, 0, - 0, 0,230,230,230, 0, 0,230,230, 0,220,230,230,220, 0, 0, - 0, 36, 0, 0,230,220,230,230,220,220,230,220,220,230,220,230, - 220,230,230, 0, 0,220, 0, 0,230,230, 0,230, 0,230,230,230, - 230,230, 0, 0, 0,220,220,220,230,220,220,220,230,230, 0,220, - 27, 28, 29,230, 7, 0, 0, 0, 0, 9, 0, 0, 0,230,220,230, - 230, 0, 0, 0, 0, 0,230, 0, 0, 84, 91, 0, 0, 0, 0, 9, - 9, 0, 0, 0, 0, 0, 9, 0,103,103, 9, 0,107,107,107,107, - 118,118, 9, 0,122,122,122,122,220,220, 0, 0, 0,220, 0,220, - 0,216, 0, 0, 0,129,130, 0,132, 0, 0, 0, 0, 0,130,130, - 130,130, 0, 0,130, 0,230,230, 9, 0,230,230, 0, 0,220, 0, - 0, 0, 0, 7, 0, 9, 9, 0, 9, 9, 0, 0, 0,230, 0, 0, - 0,228, 0, 0, 0,222,230,220,220, 0, 0, 0,230, 0, 0,220, - 230,220, 0,220,230,230,230, 0, 0, 0, 9, 9, 0, 0, 7, 0, - 230, 0, 1, 1, 1, 0, 0, 0,230,234,214,220,202,230,230,230, - 230,230,232,228,228,220,218,230,233,220,230,220,230,230, 1, 1, - 1, 1, 1,230, 0, 1, 1,230,220,230, 1, 1, 0, 0,218,228, - 232,222,224,224, 0, 8, 8, 0, 0, 0, 0,220,230, 0,230,230, - 220, 0, 0,230, 0, 0, 26, 0, 0,220, 0,230,230, 1,220, 0, - 0,230,220, 0, 0, 0,220,220, 0, 0,230,220, 0, 9, 7, 0, - 0, 7, 9, 0, 0, 0, 9, 7, 6, 6, 0, 0, 0, 0, 1, 0, - 0,216,216, 1, 1, 1, 0, 0, 0,226,216,216,216,216,216, 0, - 220,220,220, 0,230,230, 7, 0, 16, 17, 17, 17, 17, 17, 17, 33, - 17, 17, 17, 19, 17, 17, 17, 17, 20,101, 17,113,129,169, 17, 27, - 28, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 0, 0, 0, 0, 0, 61, 0, 0, 79, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 8, 91, 0, 0, 0, 0, 0, 0, 1, 87, 0, 0, + 0, 0, 0, 0,116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,117, + 0,118,119,120,121, 0,104, 4,122, 49, 23, 0, 0, 0, 0, 0, + 0, 0, 38, 50, 0, 0, 0, 0, 38, 58, 0, 0, 0, 0, 0, 0, + 1, 87, 1, 1, 1, 1, 39, 1, 48,105, 87, 0, 0, 0, 0, 0, + 0, 0, 0, 19, 0, 0, 0, 0, 0, 0, 0, 59, 0, 0, 0, 0, + 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0,123, 0, 0, 0, 0, + 0, 0, 0, 0, 4,122, 0, 0, 0, 1,124, 0, 0, 0, 0, 0, + 0, 0, 0, 0,230,230,230,230,230,232,220,220,220,220,232,216, + 220,220,220,220,220,202,202,220,220,220,220,202,202,220,220,220, + 1, 1, 1, 1, 1,220,220,220,220,230,230,230,230,240,230,220, + 220,220,230,230,230,220,220, 0,230,230,230,220,220,220,220,230, + 232,220,220,230,233,234,234,233,234,234,233,230, 0, 0, 0,230, + 0,220,230,230,230,230,220,230,230,230,222,220,230,230,220,220, + 230,222,228,230, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 19, 20, + 21, 22, 0, 23, 0, 24, 25, 0,230,220, 0, 18, 30, 31, 32, 0, + 0, 0, 0, 27, 28, 29, 30, 31, 32, 33, 34,230,230,220,220,230, + 220,230,230,220, 35, 0, 0, 0, 0, 0,230,230,230, 0, 0,230, + 230, 0,220,230,230,220, 0, 0, 0, 36, 0, 0,230,220,230,230, + 220,220,230,220,220,230,220,230,220,230,230, 0, 0,220, 0, 0, + 230,230, 0,230, 0,230,230,230,230,230, 0, 0, 0,220,220,220, + 230,220,220,220,230,230, 0,220, 27, 28, 29,230, 7, 0, 0, 0, + 0, 9, 0, 0, 0,230,220,230,230, 0, 0, 0, 0, 0,230, 0, + 0, 84, 91, 0, 0, 0, 0, 9, 9, 0, 0, 0, 0, 0, 9, 0, + 103,103, 9, 0,107,107,107,107,118,118, 9, 0,122,122,122,122, + 220,220, 0, 0, 0,220, 0,220, 0,216, 0, 0, 0,129,130, 0, + 132, 0, 0, 0, 0, 0,130,130,130,130, 0, 0,130, 0,230,230, + 9, 0,230,230, 0, 0,220, 0, 0, 0, 0, 7, 0, 9, 9, 0, + 9, 9, 0, 0, 0,230, 0, 0, 0,228, 0, 0, 0,222,230,220, + 220, 0, 0, 0,230, 0, 0,220,230,220, 0,220,230,230,230, 0, + 0, 0, 9, 9, 0, 0, 7, 0,230, 0, 1, 1, 1, 0, 0, 0, + 230,234,214,220,202,230,230,230,230,230,232,228,228,220,218,230, + 233,220,230,220,230,230, 1, 1, 1, 1, 1,230, 0, 1, 1,230, + 220,230, 1, 1, 0, 0,218,228,232,222,224,224, 0, 8, 8, 0, + 0, 0, 0,220,230, 0,230,230,220, 0, 0,230, 0, 0, 26, 0, + 0,220, 0,230,230, 1,220, 0, 0,230,220, 0, 0, 0,220,220, + 0, 0,230,220, 0, 9, 7, 0, 0, 7, 9, 0, 0, 0, 9, 7, + 6, 6, 0, 0, 0, 0, 1, 0, 0,216,216, 1, 1, 1, 0, 0, + 0,226,216,216,216,216,216, 0,220,220,220, 0,232,232,220,230, + 230,230, 7, 0, 16, 17, 17, 17, 17, 17, 17, 33, 17, 17, 17, 19, + 17, 17, 17, 17, 20,101, 17,113,129,169, 17, 27, 28, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17,237, 0, 1, 2, 2, 0, 3, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 5, 0, 0, 0, 0, 6, 7, 8, 9, 0, 0, 0, - 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 20, 0, 0, 21, 22, 0, 0, 0, 0, 23, 24, 25, 26, - 0, 27, 0, 28, 29, 30, 31, 32, 0, 0, 0, 0, 0, 0, 0, 33, - 34, 35, 36, 0, 0, 0, 0, 0, 37, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 38, 39, 0, 0, 0, 0, 1, 2, 40, 41, 0, 1, 2, 2, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 2, - 0, 0, 0, 0, 0, 0, 3, 4, 0, 0, 5, 0, 0, 0, 6, 0, - 0, 0, 0, 0, 0, 0, 7, 1, 0, 0, 0, 0, 0, 0, 8, 9, - 0, 0, 0, 0, 0, 0, 10, 0, 0, 10, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 10, 0, 0, 0, 10, 0, 0, 0, 0, - 0, 0, 11, 12, 0, 13, 0, 14, 15, 16, 0, 0, 0, 0, 0, 1, - 17, 18, 0, 19, 7, 1, 0, 0, 0, 20, 20, 7, 20, 20, 20, 20, - 20, 20, 20, 8, 21, 0, 22, 0, 7, 23, 24, 0, 20, 20, 25, 0, - 0, 0, 26, 27, 1, 7, 20, 20, 20, 20, 20, 1, 28, 29, 30, 31, - 0, 0, 20, 0, 0, 0, 0, 0, 0, 0, 10, 0, 0, 0, 0, 0, - 0, 0, 20, 20, 20, 1, 0, 0, 8, 21, 32, 4, 0, 10, 0, 33, - 7, 20, 20, 20, 0, 0, 0, 0, 8, 34, 34, 35, 36, 34, 37, 0, - 38, 1, 20, 20, 0, 0, 39, 0, 1, 1, 0, 8, 21, 1, 20, 0, - 0, 0, 1, 0, 0, 40, 1, 1, 0, 0, 8, 21, 0, 1, 0, 1, - 0, 1, 0, 0, 0, 0, 26, 34, 34, 34, 34, 34, 34, 34, 34, 34, - 21, 7, 20, 41, 34, 34, 34, 34, 34, 34, 34, 34, 34, 21, 0, 42, - 43, 44, 0, 45, 0, 8, 21, 0, 0, 0, 0, 0, 0, 0, 0, 46, - 7, 1, 10, 1, 0, 0, 0, 1, 20, 20, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 26, 34, 9, 0, 0, 20, 20, 1, 20, 20, 0, - 0, 0, 0, 0, 0, 0, 26, 21, 0, 1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 3, 47, 48, 0, 0, 0, 0, 0, 0, 0, - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 9, 10, 11, 11, 11, 11, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 18, 19, 20, 21, 13, 22, 13, 13, 13, 13, 23, 24, 24, - 25, 26, 13, 13, 13, 27, 28, 29, 13, 30, 31, 32, 33, 34, 35, 36, + 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 17, 17, 17,237, 0, 1, 2, 2, 0, 3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 0, 6, 7, 8, 9, 0, 0, 0, 10, 11, 12, 13, + 14, 15, 16, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, + 0, 0, 21, 22, 0, 0, 0, 0, 23, 24, 25, 26, 0, 27, 0, 28, + 29, 30, 31, 32, 0, 0, 0, 0, 0, 0, 0, 33, 34, 35, 36, 0, + 0, 0, 0, 0, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 38, 39, + 0, 0, 0, 0, 1, 2, 40, 41, 0, 1, 2, 2, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 2, 0, 0, 0, 0, + 0, 0, 3, 4, 0, 0, 5, 0, 0, 0, 6, 0, 0, 0, 0, 0, + 0, 0, 7, 1, 0, 0, 0, 0, 0, 0, 8, 9, 0, 0, 0, 0, + 0, 0, 10, 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 10, 0, 0, 0, 10, 0, 0, 0, 0, 0, 0, 11, 12, + 0, 13, 0, 14, 15, 16, 0, 0, 0, 0, 0, 1, 17, 18, 0, 19, + 7, 1, 0, 0, 0, 20, 20, 7, 20, 20, 20, 20, 20, 20, 20, 8, + 21, 0, 22, 0, 7, 23, 24, 0, 20, 20, 25, 0, 0, 0, 26, 27, + 1, 7, 20, 20, 20, 20, 20, 1, 28, 29, 30, 31, 0, 0, 20, 0, + 0, 0, 0, 0, 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 20, 20, + 20, 1, 0, 0, 8, 21, 32, 4, 0, 10, 0, 33, 7, 20, 20, 20, + 0, 0, 0, 0, 8, 34, 34, 35, 36, 34, 37, 0, 38, 1, 20, 20, + 0, 0, 39, 0, 1, 1, 0, 8, 21, 1, 20, 0, 0, 0, 1, 0, + 0, 40, 1, 1, 0, 0, 8, 21, 0, 1, 0, 1, 0, 1, 0, 0, + 0, 0, 26, 34, 34, 34, 34, 34, 34, 34, 34, 34, 21, 7, 20, 41, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 21, 0, 42, 43, 44, 0, 45, + 0, 8, 21, 0, 0, 0, 0, 0, 0, 0, 0, 46, 7, 1, 10, 1, + 0, 0, 0, 1, 20, 20, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 26, 34, 9, 0, 0, 20, 20, 1, 20, 20, 0, 0, 0, 0, 0, + 0, 0, 26, 21, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 3, 47, 48, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, + 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, + 9, 10, 11, 11, 11, 11, 12, 13, 13, 13, 13, 14, 15, 16, 17, 18, + 19, 20, 21, 13, 22, 13, 13, 13, 13, 23, 24, 24, 25, 26, 13, 13, + 13, 27, 28, 29, 13, 30, 31, 32, 33, 34, 35, 36, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 37, 7, 38, 39, 7, 40, 7, 7, 7, 41, 13, 42, - 7, 7, 43, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 37, 7, 38, 39, 7, 40, 7, 7, 7, 41, 13, 42, 7, 7, 43, 7, + 44, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, @@ -1727,411 +1740,419 @@ _hb_ucd_u8[17936] = 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 44, 0, 0, 1, 2, 2, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, - 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, - 28, 29, 30, 31, 32, 32, 33, 34, 35, 36, 37, 37, 37, 37, 37, 38, - 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 2, 2, - 53, 54, 55, 56, 57, 58, 59, 59, 59, 59, 60, 59, 59, 59, 59, 59, - 59, 59, 61, 61, 59, 59, 59, 59, 62, 63, 64, 65, 66, 67, 68, 69, - 70, 71, 72, 73, 74, 75, 76, 77, 78, 59, 70, 70, 70, 70, 70, 70, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 45, 0, 0, 1, + 2, 2, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, + 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, + 32, 32, 33, 34, 35, 36, 37, 37, 37, 37, 37, 38, 39, 40, 41, 42, + 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 2, 2, 53, 54, 55, 56, + 57, 58, 59, 59, 59, 59, 60, 59, 59, 59, 59, 59, 59, 59, 61, 61, + 59, 59, 59, 59, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, + 74, 75, 76, 77, 78, 59, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, - 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 79, 70, 70, - 70, 70, 80, 80, 80, 80, 80, 80, 80, 80, 80, 81, 82, 82, 83, 84, - 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, + 70, 70, 70, 70, 70, 70, 70, 70, 70, 79, 70, 70, 70, 70, 80, 80, + 80, 80, 80, 80, 80, 80, 80, 81, 82, 82, 83, 84, 85, 86, 87, 88, + 89, 90, 91, 92, 93, 94, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, - 32, 95, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 70, 70, 97, 98, 99,100,101,101,102,103,104,105, - 106,107,108,109,110,111, 96,112,113,114,115,116,117,118,119,119, - 120,121,122,123,124,125,126,127,128,129,130,131,132, 96,133,134, - 135,136,137,138,139,140,141,142,143, 96,144,145, 96,146,147,148, - 149, 96,150,151,152,153,154,155, 96, 96,156,157,158,159, 96,160, - 96,161,162,162,162,162,162,162,162,163,164,162,165, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 96,166,167,167,167,167,167,167,167,167,168, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,169,169,169,169,170, 96, - 96, 96,171,171,171,171,172,173,174,175, 96, 96, 96, 96,176,177, - 178,179,180,180,180,180,180,180,180,180,180,180,180,180,180,180, - 180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180, - 180,181,180,180,180,180,180,180,182,182,182,183,184, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 96,185,186,187,188,189,189,190, 96, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,191,192, 96, 96, 96, 96, + 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 95, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 193,194, 59,195,196,197,198,199,200, 96,201,202,203, 59, 59,204, - 59,205,206,206,206,206,206,207, 96, 96, 96, 96, 96, 96, 96, 96, - 208, 96,209, 96,210, 96, 96,211, 96, 96, 96, 96, 96, 96, 96, 96, - 96,212,213,214,215, 96, 96, 96, 96, 96,216,217,218, 96,219,220, - 96, 96,221,222, 59,223,224, 96, 59, 59, 59, 59, 59, 59, 59,225, - 226,227,228,229, 59, 59,230,231, 59,232, 96, 96, 96, 96, 96, 96, - 96, 96, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,233, + 70, 70, 97, 98, 99,100,101,101,102,103,104,105,106,107,108,109, + 110,111, 96,112,113,114,115,116,117,118,119,119,120,121,122,123, + 124,125,126,127,128,129,130,131,132, 96,133,134,135,136,137,138, + 139,140,141,142,143, 96,144,145, 96,146,147,148,149, 96,150,151, + 152,153,154,155,156, 96,157,158,159,160, 96,161,162,163,164,164, + 164,164,164,164,164,165,166,164,167, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,168,169,169, + 169,169,169,169,169,169,170, 96, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96,171,171,171,171,172, 96, 96, 96,173,173, + 173,173,174,175,176,177, 96, 96, 96, 96,178,179,180,181,182,182, + 182,182,182,182,182,182,182,182,182,182,182,182,182,182,182,182, + 182,182,182,182,182,182,182,182,182,182,182,182,182,183,182,182, + 182,182,182,182,184,184,184,185,186, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,187,188,189, + 190,191,191,192, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96,193,194, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,195,196, 59,197, + 198,199,200,201,202, 96,203,204,205, 59, 59,206, 59,207,208,208, + 208,208,208,209, 96, 96, 96, 96, 96, 96, 96, 96,210, 96,211,212, + 213, 96, 96,214, 96, 96, 96,215, 96, 96, 96, 96, 96,216,217,218, + 219, 96, 96, 96, 96, 96,220,221,222, 96,223,224, 96, 96,225,226, + 59,227,228, 96, 59, 59, 59, 59, 59, 59, 59,229,230,231,232,233, + 59, 59,234,235, 59,236, 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, + 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,237, 70, 70, 70, 70, + 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,238, 70,239, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, - 234, 70,235, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, - 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,236, - 70, 70, 70, 70, 70, 70, 70, 70, 70,237, 96, 96, 96, 96, 96, 96, - 96, 96, 70, 70, 70, 70,238, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 70, 70, 70, 70, 70, 70,239, 96, 96, 96, 96, 96, 96, 96, - 96, 96,240, 96,241,242, 0, 1, 2, 2, 0, 1, 2, 2, 2, 3, - 4, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 0, 0, 0, - 0, 0, 0, 0, 19, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, - 19, 0, 19, 0, 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 0, - 0, 0, 0, 0, 26, 26, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, - 1, 1, 9, 9, 9, 9, 0, 9, 9, 9, 2, 2, 9, 9, 9, 9, - 0, 9, 2, 2, 2, 2, 9, 0, 9, 0, 9, 9, 9, 2, 9, 2, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, - 9, 9, 9, 9, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, - 55, 55, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 1, - 1, 6, 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 4, 4, 4, 2, 2, 4, - 4, 4, 2, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 2, 2, 2, 2, 2, 2, 2, 2, 14, 14, 14, 2, 2, 2, - 2, 14, 14, 14, 14, 14, 14, 2, 2, 2, 3, 3, 3, 3, 3, 0, - 3, 3, 3, 3, 3, 3, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 0, 3, 3, 3, 0, 0, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 3, 3, 1, 3, 3, 3, 3, 3, 3, 3, 37, 37, 37, 37, 37, 37, - 37, 37, 37, 37, 37, 37, 37, 37, 2, 37, 37, 37, 37, 2, 2, 37, - 37, 37, 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, 2, 2, 2, 2, - 2, 2, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 2, 2, 64, - 64, 64, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 2, 2, 90, 90, 90, 90, 90, 90, 90, 2, 95, 95, 95, 95, 95, 95, - 95, 95, 95, 95, 95, 95, 2, 2, 95, 2, 37, 37, 37, 2, 2, 2, - 2, 2, 3, 3, 3, 3, 3, 3, 3, 2, 3, 3, 2, 2, 2, 2, - 2, 2, 3, 3, 0, 3, 3, 3, 3, 3, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 1, 1, 1, 1, 7, 7, 7, 7, 7, 7, 7, 0, 0, - 7, 7, 5, 5, 5, 5, 2, 5, 5, 5, 5, 5, 5, 5, 5, 2, - 2, 5, 5, 2, 2, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 2, 5, 5, 5, 5, 5, 5, 5, 2, 5, 2, 2, 2, - 5, 5, 5, 5, 2, 2, 5, 5, 5, 5, 5, 2, 2, 5, 5, 5, - 5, 2, 2, 2, 2, 2, 2, 2, 2, 5, 2, 2, 2, 2, 5, 5, - 2, 5, 5, 5, 5, 5, 2, 2, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 2, 2, 11, 11, 11, 2, 11, 11, 11, 11, 11, 11, 2, 2, 2, - 2, 11, 11, 2, 2, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 2, 11, 11, 11, 11, 11, 11, 11, 2, 11, 11, 2, 11, - 11, 2, 11, 11, 2, 2, 11, 2, 11, 11, 11, 2, 2, 11, 11, 11, - 2, 2, 2, 11, 2, 2, 2, 2, 2, 2, 2, 11, 11, 11, 11, 2, - 11, 2, 2, 2, 2, 2, 2, 2, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 2, 2, 10, 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 2, 10, 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, 2, 10, 10, 2, 10, - 10, 10, 10, 10, 2, 2, 10, 10, 10, 10, 10, 10, 2, 10, 10, 10, - 2, 2, 10, 2, 2, 2, 2, 2, 2, 2, 10, 10, 10, 10, 2, 2, - 10, 10, 10, 10, 2, 2, 2, 2, 2, 2, 2, 10, 10, 10, 10, 10, - 10, 10, 2, 21, 21, 21, 2, 21, 21, 21, 21, 21, 21, 21, 21, 2, - 2, 21, 21, 2, 2, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 2, 21, 21, 21, 21, 21, 21, 21, 2, 21, 21, 2, 21, - 21, 21, 21, 21, 2, 2, 21, 21, 21, 21, 21, 2, 2, 21, 21, 21, - 2, 2, 2, 2, 2, 2, 2, 21, 21, 21, 2, 2, 2, 2, 21, 21, - 2, 21, 21, 21, 21, 21, 2, 2, 21, 21, 2, 2, 22, 22, 2, 22, - 22, 22, 22, 22, 22, 2, 2, 2, 22, 22, 22, 2, 22, 22, 22, 22, - 2, 2, 2, 22, 22, 2, 22, 2, 22, 22, 2, 2, 2, 22, 22, 2, - 2, 2, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 2, 2, 2, 2, - 22, 22, 22, 2, 2, 2, 2, 2, 2, 22, 2, 2, 2, 2, 2, 2, - 22, 22, 22, 22, 22, 2, 2, 2, 2, 2, 23, 23, 23, 23, 23, 23, - 23, 23, 23, 23, 23, 23, 23, 2, 23, 23, 23, 2, 23, 23, 23, 23, - 23, 23, 23, 23, 2, 2, 23, 23, 23, 23, 23, 2, 23, 23, 23, 23, - 2, 2, 2, 2, 2, 2, 2, 23, 23, 2, 23, 23, 23, 2, 2, 23, - 2, 2, 23, 23, 23, 23, 2, 2, 23, 23, 2, 2, 2, 2, 2, 2, - 2, 23, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 2, - 16, 16, 16, 2, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 2, 16, - 16, 16, 16, 16, 2, 2, 16, 16, 16, 16, 16, 2, 16, 16, 16, 16, - 2, 2, 2, 2, 2, 2, 2, 16, 16, 2, 16, 16, 16, 16, 2, 2, - 16, 16, 2, 16, 16, 2, 2, 2, 2, 2, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 2, 20, 20, 20, 2, 20, 20, 20, 20, - 20, 20, 2, 2, 2, 2, 20, 20, 20, 20, 20, 20, 20, 20, 2, 2, - 20, 20, 2, 36, 36, 36, 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, 36, 2, 2, 2, 36, 36, 36, 36, - 36, 36, 36, 36, 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, 2, 36, - 2, 2, 2, 2, 36, 2, 2, 2, 2, 36, 36, 36, 36, 36, 36, 2, - 36, 2, 2, 2, 2, 2, 2, 2, 36, 36, 2, 2, 36, 36, 36, 2, - 2, 2, 2, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, - 24, 24, 24, 24, 24, 2, 2, 2, 2, 0, 24, 24, 24, 24, 2, 2, - 2, 2, 2, 18, 18, 2, 18, 2, 18, 18, 18, 18, 18, 2, 18, 18, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 2, 18, - 2, 18, 18, 18, 18, 18, 18, 18, 2, 2, 18, 18, 18, 18, 18, 2, - 18, 2, 18, 18, 2, 2, 18, 18, 18, 18, 25, 25, 25, 25, 25, 25, - 25, 25, 2, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 2, - 2, 2, 25, 25, 25, 25, 25, 2, 25, 25, 25, 25, 25, 25, 25, 0, - 0, 0, 0, 25, 25, 2, 2, 2, 2, 2, 33, 33, 33, 33, 33, 33, - 33, 33, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, - 2, 8, 2, 2, 2, 2, 2, 8, 2, 2, 8, 8, 8, 0, 8, 8, - 8, 8, 12, 12, 12, 12, 12, 12, 12, 12, 30, 30, 30, 30, 30, 30, - 30, 30, 30, 2, 30, 30, 30, 30, 2, 2, 30, 30, 30, 30, 30, 30, - 30, 2, 30, 30, 30, 2, 2, 30, 30, 30, 30, 30, 30, 30, 30, 2, - 2, 2, 30, 30, 2, 2, 2, 2, 2, 2, 29, 29, 29, 29, 29, 29, - 29, 29, 29, 29, 29, 29, 29, 29, 2, 2, 28, 28, 28, 28, 28, 28, - 28, 28, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 2, - 2, 2, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 0, 0, 0, - 35, 35, 35, 2, 2, 2, 2, 2, 2, 2, 45, 45, 45, 45, 45, 45, - 45, 45, 45, 45, 45, 45, 45, 45, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 45, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 0, - 0, 2, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 2, 2, - 2, 2, 46, 46, 46, 46, 46, 46, 46, 46, 46, 46, 46, 46, 46, 2, - 46, 46, 46, 2, 46, 46, 2, 2, 2, 2, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 2, 2, 31, 31, 2, 2, 2, 2, - 2, 2, 32, 32, 0, 0, 32, 0, 32, 32, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 2, 2, 2, 2, 2, 2, 32, 2, 2, 2, 2, 2, - 2, 2, 32, 32, 32, 2, 2, 2, 2, 2, 28, 28, 28, 28, 28, 28, - 2, 2, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, - 48, 2, 48, 48, 48, 48, 2, 2, 2, 2, 48, 2, 2, 2, 48, 48, - 48, 48, 52, 52, 52, 52, 52, 52, 52, 52, 52, 52, 52, 52, 52, 52, - 2, 2, 52, 52, 52, 52, 52, 2, 2, 2, 58, 58, 58, 58, 58, 58, - 58, 58, 58, 58, 58, 58, 2, 2, 2, 2, 58, 58, 2, 2, 2, 2, - 2, 2, 58, 58, 58, 2, 2, 2, 58, 58, 54, 54, 54, 54, 54, 54, - 54, 54, 54, 54, 54, 54, 2, 2, 54, 54, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 2, 91, 91, 91, 91, 91, 2, - 2, 91, 91, 91, 2, 2, 2, 2, 2, 2, 91, 91, 91, 91, 91, 91, - 2, 2, 1, 1, 1, 1, 1, 1, 1, 2, 62, 62, 62, 62, 62, 62, - 62, 62, 62, 62, 62, 62, 62, 2, 2, 2, 62, 62, 62, 62, 62, 62, - 62, 2, 76, 76, 76, 76, 76, 76, 76, 76, 93, 93, 93, 93, 93, 93, - 93, 93, 93, 93, 93, 93, 2, 2, 2, 2, 2, 2, 2, 2, 93, 93, - 93, 93, 70, 70, 70, 70, 70, 70, 70, 70, 2, 2, 2, 70, 70, 70, - 70, 70, 70, 70, 2, 2, 2, 70, 70, 70, 73, 73, 73, 73, 73, 73, - 73, 73, 6, 2, 2, 2, 2, 2, 2, 2, 8, 8, 8, 2, 2, 8, - 8, 8, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, - 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 1, 1, 0, 2, 2, 2, 2, 2, 19, 19, 19, 19, 19, 19, - 9, 9, 9, 9, 9, 6, 19, 19, 19, 19, 19, 19, 19, 19, 19, 9, - 9, 9, 9, 9, 19, 19, 19, 19, 9, 9, 9, 9, 9, 19, 19, 19, - 19, 19, 6, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 9, 9, 9, 9, 9, 9, 9, 2, 2, 2, 9, 2, 9, 2, 9, - 2, 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, 9, 9, 9, 2, 2, - 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, 2, 2, 9, 9, 9, 2, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 2, 0, 0, 0, 0, 1, 1, - 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 19, 2, 2, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 0, 0, 0, 0, 0, 0, - 0, 2, 19, 19, 19, 19, 19, 2, 2, 2, 0, 2, 2, 2, 2, 2, - 2, 2, 1, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, - 9, 0, 0, 0, 19, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 19, 0, 19, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 2, 2, 2, - 2, 2, 27, 27, 27, 27, 27, 27, 27, 27, 0, 0, 0, 0, 2, 2, - 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 56, 56, 56, 56, 56, 56, - 56, 56, 55, 55, 55, 55, 2, 2, 2, 2, 2, 55, 55, 55, 55, 55, - 55, 55, 61, 61, 61, 61, 61, 61, 61, 61, 2, 2, 2, 2, 2, 2, - 2, 61, 61, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, - 2, 2, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 2, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 2, 2, 2, 2, 13, 13, 13, 13, 13, 13, - 2, 2, 0, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 0, 0, 13, - 0, 13, 0, 13, 13, 13, 13, 13, 13, 13, 13, 13, 1, 1, 1, 1, - 12, 12, 13, 13, 13, 13, 0, 0, 0, 0, 2, 15, 15, 15, 15, 15, + 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,240, 70, 70, 70, 70, + 70, 70, 70, 70, 70,241, 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, + 70, 70,242, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, + 70, 70, 70, 70,243, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, + 70, 70, 70, 70, 70,244, 96, 96, 96, 96, 96, 96, 96, 96,245, 96, + 246,247, 0, 1, 2, 2, 0, 1, 2, 2, 2, 3, 4, 5, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, 19, 19, + 19, 19, 19, 19, 19, 19, 19, 19, 19, 0, 0, 0, 0, 0, 0, 0, + 19, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, 0, 19, 0, + 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 0, 0, 0, 0, 0, + 26, 26, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 9, 9, + 9, 9, 0, 9, 9, 9, 2, 2, 9, 9, 9, 9, 0, 9, 2, 2, + 2, 2, 9, 0, 9, 0, 9, 9, 9, 2, 9, 2, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, 9, 9, 9, 9, + 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 6, 6, + 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 1, 1, 6, 2, 4, + 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, + 4, 4, 4, 4, 4, 2, 4, 4, 4, 2, 2, 4, 4, 4, 2, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 2, 2, + 2, 2, 2, 2, 2, 2, 14, 14, 14, 2, 2, 2, 2, 14, 14, 14, + 14, 14, 14, 2, 2, 2, 3, 3, 3, 3, 3, 0, 3, 3, 3, 3, + 3, 3, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 0, 3, 3, 3, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 1, 3, + 3, 3, 3, 3, 3, 3, 37, 37, 37, 37, 37, 37, 37, 37, 37, 37, + 37, 37, 37, 37, 2, 37, 37, 37, 37, 2, 2, 37, 37, 37, 38, 38, + 38, 38, 38, 38, 38, 38, 38, 38, 2, 2, 2, 2, 2, 2, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, 64, 2, 2, 64, 64, 64, 90, 90, + 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 2, 2, 90, 90, + 90, 90, 90, 90, 90, 2, 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, + 95, 95, 2, 2, 95, 2, 37, 37, 37, 2, 2, 2, 2, 2, 3, 3, + 3, 3, 3, 3, 3, 2, 3, 3, 2, 2, 2, 2, 2, 2, 3, 3, + 0, 3, 3, 3, 3, 3, 7, 7, 7, 7, 7, 7, 7, 7, 7, 1, + 1, 1, 1, 7, 7, 7, 7, 7, 7, 7, 0, 0, 7, 7, 5, 5, + 5, 5, 2, 5, 5, 5, 5, 5, 5, 5, 5, 2, 2, 5, 5, 2, + 2, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 2, + 5, 5, 5, 5, 5, 5, 5, 2, 5, 2, 2, 2, 5, 5, 5, 5, + 2, 2, 5, 5, 5, 5, 5, 2, 2, 5, 5, 5, 5, 2, 2, 2, + 2, 2, 2, 2, 2, 5, 2, 2, 2, 2, 5, 5, 2, 5, 5, 5, + 5, 5, 2, 2, 5, 5, 5, 5, 5, 5, 5, 5, 5, 2, 2, 11, + 11, 11, 2, 11, 11, 11, 11, 11, 11, 2, 2, 2, 2, 11, 11, 2, + 2, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 2, + 11, 11, 11, 11, 11, 11, 11, 2, 11, 11, 2, 11, 11, 2, 11, 11, + 2, 2, 11, 2, 11, 11, 11, 2, 2, 11, 11, 11, 2, 2, 2, 11, + 2, 2, 2, 2, 2, 2, 2, 11, 11, 11, 11, 2, 11, 2, 2, 2, + 2, 2, 2, 2, 11, 11, 11, 11, 11, 11, 11, 11, 11, 2, 2, 10, + 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, 10, 10, 2, 10, 10, 10, + 2, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 2, + 10, 10, 10, 10, 10, 10, 10, 2, 10, 10, 2, 10, 10, 10, 10, 10, + 2, 2, 10, 10, 10, 10, 10, 10, 2, 10, 10, 10, 2, 2, 10, 2, + 2, 2, 2, 2, 2, 2, 10, 10, 10, 10, 2, 2, 10, 10, 10, 10, + 2, 2, 2, 2, 2, 2, 2, 10, 10, 10, 10, 10, 10, 10, 2, 21, + 21, 21, 2, 21, 21, 21, 21, 21, 21, 21, 21, 2, 2, 21, 21, 2, + 2, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 2, + 21, 21, 21, 21, 21, 21, 21, 2, 21, 21, 2, 21, 21, 21, 21, 21, + 2, 2, 21, 21, 21, 21, 21, 2, 2, 21, 21, 21, 2, 2, 2, 2, + 2, 2, 2, 21, 21, 21, 2, 2, 2, 2, 21, 21, 2, 21, 21, 21, + 21, 21, 2, 2, 21, 21, 2, 2, 22, 22, 2, 22, 22, 22, 22, 22, + 22, 2, 2, 2, 22, 22, 22, 2, 22, 22, 22, 22, 2, 2, 2, 22, + 22, 2, 22, 2, 22, 22, 2, 2, 2, 22, 22, 2, 2, 2, 22, 22, + 22, 22, 22, 22, 22, 22, 22, 22, 2, 2, 2, 2, 22, 22, 22, 2, + 2, 2, 2, 2, 2, 22, 2, 2, 2, 2, 2, 2, 22, 22, 22, 22, + 22, 2, 2, 2, 2, 2, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, + 23, 23, 23, 2, 23, 23, 23, 2, 23, 23, 23, 23, 23, 23, 23, 23, + 2, 2, 23, 23, 23, 23, 23, 2, 23, 23, 23, 23, 2, 2, 2, 2, + 2, 2, 2, 23, 23, 2, 23, 23, 23, 2, 2, 23, 2, 2, 23, 23, + 23, 23, 2, 2, 23, 23, 2, 2, 2, 2, 2, 2, 2, 23, 16, 16, + 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 2, 16, 16, 16, 2, + 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 2, 16, 16, 16, 16, 16, + 2, 2, 16, 16, 16, 16, 16, 2, 16, 16, 16, 16, 2, 2, 2, 2, + 2, 2, 2, 16, 16, 2, 16, 16, 16, 16, 2, 2, 16, 16, 2, 16, + 16, 16, 2, 2, 2, 2, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, + 20, 20, 20, 2, 20, 20, 20, 2, 20, 20, 20, 20, 20, 20, 2, 2, + 2, 2, 20, 20, 20, 20, 20, 20, 20, 20, 2, 2, 20, 20, 2, 36, + 36, 36, 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, + 36, 36, 36, 36, 36, 2, 2, 2, 36, 36, 36, 36, 36, 36, 36, 36, + 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, 2, 36, 2, 2, 2, 2, + 36, 2, 2, 2, 2, 36, 36, 36, 36, 36, 36, 2, 36, 2, 2, 2, + 2, 2, 2, 2, 36, 36, 2, 2, 36, 36, 36, 2, 2, 2, 2, 24, + 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, + 24, 2, 2, 2, 2, 0, 24, 24, 24, 24, 2, 2, 2, 2, 2, 18, + 18, 2, 18, 2, 18, 18, 18, 18, 18, 2, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 2, 18, 2, 18, 18, 18, + 18, 18, 18, 18, 2, 2, 18, 18, 18, 18, 18, 2, 18, 2, 18, 18, + 18, 18, 18, 18, 18, 2, 18, 18, 2, 2, 18, 18, 18, 18, 25, 25, + 25, 25, 25, 25, 25, 25, 2, 25, 25, 25, 25, 25, 25, 25, 25, 25, + 25, 25, 25, 2, 2, 2, 25, 25, 25, 25, 25, 2, 25, 25, 25, 25, + 25, 25, 25, 0, 0, 0, 0, 25, 25, 2, 2, 2, 2, 2, 33, 33, + 33, 33, 33, 33, 33, 33, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, + 8, 8, 8, 8, 2, 8, 2, 2, 2, 2, 2, 8, 2, 2, 8, 8, + 8, 0, 8, 8, 8, 8, 12, 12, 12, 12, 12, 12, 12, 12, 30, 30, + 30, 30, 30, 30, 30, 30, 30, 2, 30, 30, 30, 30, 2, 2, 30, 30, + 30, 30, 30, 30, 30, 2, 30, 30, 30, 2, 2, 30, 30, 30, 30, 30, + 30, 30, 30, 2, 2, 2, 30, 30, 2, 2, 2, 2, 2, 2, 29, 29, + 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 2, 2, 28, 28, + 28, 28, 28, 28, 28, 28, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, + 34, 34, 34, 2, 2, 2, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, + 35, 0, 0, 0, 35, 35, 35, 2, 2, 2, 2, 2, 2, 2, 45, 45, + 45, 45, 45, 45, 45, 45, 45, 45, 45, 45, 45, 45, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 45, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, + 44, 44, 44, 0, 0, 2, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, + 43, 43, 2, 2, 2, 2, 46, 46, 46, 46, 46, 46, 46, 46, 46, 46, + 46, 46, 46, 2, 46, 46, 46, 2, 46, 46, 2, 2, 2, 2, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 2, 2, 31, 31, + 2, 2, 2, 2, 2, 2, 32, 32, 0, 0, 32, 0, 32, 32, 32, 32, + 32, 32, 32, 32, 32, 32, 32, 32, 2, 2, 2, 2, 2, 2, 32, 2, + 2, 2, 2, 2, 2, 2, 32, 32, 32, 2, 2, 2, 2, 2, 28, 28, + 28, 28, 28, 28, 2, 2, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, + 48, 48, 48, 48, 48, 2, 48, 48, 48, 48, 2, 2, 2, 2, 48, 2, + 2, 2, 48, 48, 48, 48, 52, 52, 52, 52, 52, 52, 52, 52, 52, 52, + 52, 52, 52, 52, 2, 2, 52, 52, 52, 52, 52, 2, 2, 2, 58, 58, + 58, 58, 58, 58, 58, 58, 58, 58, 58, 58, 2, 2, 2, 2, 58, 58, + 2, 2, 2, 2, 2, 2, 58, 58, 58, 2, 2, 2, 58, 58, 54, 54, + 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 2, 2, 54, 54, 91, 91, + 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 2, 91, 91, + 91, 91, 91, 2, 2, 91, 91, 91, 2, 2, 2, 2, 2, 2, 91, 91, + 91, 91, 91, 91, 2, 2, 1, 1, 1, 1, 1, 1, 1, 2, 62, 62, + 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 2, 2, 2, 62, 62, + 62, 62, 62, 62, 62, 2, 76, 76, 76, 76, 76, 76, 76, 76, 93, 93, + 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 2, 2, 2, 2, 2, 2, + 2, 2, 93, 93, 93, 93, 70, 70, 70, 70, 70, 70, 70, 70, 2, 2, + 2, 70, 70, 70, 70, 70, 70, 70, 2, 2, 2, 70, 70, 70, 73, 73, + 73, 73, 73, 73, 73, 73, 6, 2, 2, 2, 2, 2, 2, 2, 8, 8, + 8, 2, 2, 8, 8, 8, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, + 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, 1, 1, 0, 2, 2, 2, 2, 2, 19, 19, + 19, 19, 19, 19, 9, 9, 9, 9, 9, 6, 19, 19, 19, 19, 19, 19, + 19, 19, 19, 9, 9, 9, 9, 9, 19, 19, 19, 19, 9, 9, 9, 9, + 9, 19, 19, 19, 19, 19, 6, 19, 19, 19, 19, 19, 19, 19, 19, 19, + 19, 19, 19, 19, 19, 9, 9, 9, 9, 9, 9, 9, 2, 2, 2, 9, + 2, 9, 2, 9, 2, 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, 9, + 9, 9, 2, 2, 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, 2, 2, + 9, 9, 9, 2, 9, 9, 9, 9, 9, 9, 9, 9, 9, 2, 0, 0, + 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 19, + 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 0, 0, + 0, 0, 0, 0, 0, 2, 19, 19, 19, 19, 19, 2, 2, 2, 0, 2, + 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 2, 0, 0, + 0, 0, 0, 0, 9, 0, 0, 0, 19, 19, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 19, 0, 19, 0, 0, 0, 2, 2, 2, 2, 0, 0, + 0, 2, 2, 2, 2, 2, 27, 27, 27, 27, 27, 27, 27, 27, 0, 0, + 0, 0, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 56, 56, + 56, 56, 56, 56, 56, 56, 55, 55, 55, 55, 2, 2, 2, 2, 2, 55, + 55, 55, 55, 55, 55, 55, 61, 61, 61, 61, 61, 61, 61, 61, 2, 2, + 2, 2, 2, 2, 2, 61, 61, 2, 2, 2, 2, 2, 2, 2, 0, 0, + 0, 0, 0, 0, 2, 2, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 2, 13, 13, 13, 13, 13, 13, 13, 13, 13, 2, 2, 2, 2, 13, 13, + 13, 13, 13, 13, 2, 2, 0, 0, 0, 0, 2, 2, 2, 2, 0, 0, + 0, 0, 0, 13, 0, 13, 0, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 1, 1, 1, 1, 12, 12, 13, 13, 13, 13, 0, 0, 0, 0, 2, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 2, 2, 1, 1, 0, 0, 15, 15, 15, 0, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 0, 0, 17, - 17, 17, 2, 2, 2, 2, 2, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 2, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, - 12, 2, 12, 12, 12, 12, 12, 12, 12, 0, 17, 17, 17, 17, 17, 17, - 17, 0, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 2, - 2, 2, 39, 39, 39, 39, 39, 39, 39, 2, 86, 86, 86, 86, 86, 86, - 86, 86, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 2, 2, - 2, 2, 79, 79, 79, 79, 79, 79, 79, 79, 0, 0, 19, 19, 19, 19, - 19, 19, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, 19, 2, 2, 2, - 2, 2, 19, 19, 2, 19, 2, 19, 19, 19, 19, 19, 2, 2, 2, 2, - 2, 2, 2, 2, 19, 19, 19, 19, 19, 19, 60, 60, 60, 60, 60, 60, - 60, 60, 60, 60, 60, 60, 60, 2, 2, 2, 0, 0, 2, 2, 2, 2, - 2, 2, 65, 65, 65, 65, 65, 65, 65, 65, 75, 75, 75, 75, 75, 75, - 75, 75, 75, 75, 75, 75, 75, 75, 2, 2, 2, 2, 2, 2, 2, 2, - 75, 75, 75, 75, 2, 2, 2, 2, 2, 2, 69, 69, 69, 69, 69, 69, - 69, 69, 69, 69, 69, 69, 69, 69, 0, 69, 74, 74, 74, 74, 74, 74, - 74, 74, 74, 74, 74, 74, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 74, 12, 12, 12, 12, 12, 2, 2, 2, 84, 84, 84, 84, 84, 84, - 84, 84, 84, 84, 84, 84, 84, 84, 2, 0, 84, 84, 2, 2, 2, 2, - 84, 84, 33, 33, 33, 33, 33, 33, 33, 2, 68, 68, 68, 68, 68, 68, - 68, 68, 68, 68, 68, 68, 68, 68, 68, 2, 68, 68, 68, 68, 68, 68, - 2, 2, 68, 68, 2, 2, 68, 68, 68, 68, 92, 92, 92, 92, 92, 92, - 92, 92, 92, 92, 92, 2, 2, 2, 2, 2, 2, 2, 2, 92, 92, 92, - 92, 92, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, - 87, 2, 2, 30, 30, 30, 30, 30, 30, 2, 19, 19, 19, 0, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 9, 19, 19, 19, 19, 0, 0, 2, 2, - 2, 2, 87, 87, 87, 87, 87, 87, 2, 2, 87, 87, 2, 2, 2, 2, - 2, 2, 12, 12, 12, 12, 2, 2, 2, 2, 2, 2, 2, 12, 12, 12, - 12, 12, 13, 13, 2, 2, 2, 2, 2, 2, 19, 19, 19, 19, 19, 19, - 19, 2, 2, 2, 2, 4, 4, 4, 4, 4, 2, 2, 2, 2, 2, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 2, 14, 14, 14, 14, 14, 2, - 14, 2, 14, 14, 2, 14, 14, 2, 14, 14, 3, 3, 3, 2, 2, 2, - 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 0, 0, 2, 2, 3, 3, 3, 3, 3, 3, 2, 2, 2, 2, 2, 2, - 2, 3, 1, 1, 1, 1, 1, 1, 6, 6, 0, 0, 0, 2, 0, 0, - 0, 0, 3, 3, 3, 3, 3, 2, 3, 3, 3, 3, 3, 3, 3, 2, - 2, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 17, 17, 17, 17, 17, 17, 17, 17, 0, 0, 2, 2, 12, 12, 12, 12, - 12, 12, 2, 2, 12, 12, 12, 2, 2, 2, 2, 0, 0, 0, 0, 0, - 2, 2, 49, 49, 49, 49, 49, 49, 49, 49, 49, 49, 49, 49, 2, 49, - 49, 49, 49, 49, 49, 49, 49, 49, 49, 2, 49, 49, 49, 2, 49, 49, - 2, 49, 49, 49, 49, 49, 49, 49, 2, 2, 49, 49, 49, 2, 2, 2, - 2, 2, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 0, 0, 2, 2, - 2, 0, 0, 0, 0, 0, 0, 2, 2, 2, 9, 2, 2, 2, 2, 2, - 2, 2, 0, 0, 0, 0, 0, 1, 2, 2, 71, 71, 71, 71, 71, 71, - 71, 71, 71, 71, 71, 71, 71, 2, 2, 2, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 2, 2, 2, 2, 2, 2, 2, 1, 0, 0, 0, 0, 0, - 0, 0, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 42, 42, 42, 41, 41, 41, 41, 41, 41, - 41, 41, 41, 41, 41, 2, 2, 2, 2, 2,118,118,118,118,118,118, - 118,118,118,118,118, 2, 2, 2, 2, 2, 53, 53, 53, 53, 53, 53, - 53, 53, 53, 53, 53, 53, 53, 53, 2, 53, 59, 59, 59, 59, 59, 59, - 59, 59, 59, 59, 59, 59, 2, 2, 2, 2, 59, 59, 59, 59, 59, 59, - 2, 2, 40, 40, 40, 40, 40, 40, 40, 40, 51, 51, 51, 51, 51, 51, - 51, 51, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, - 2, 2, 50, 50, 2, 2, 2, 2, 2, 2,135,135,135,135,135,135, - 135,135,135,135,135,135, 2, 2, 2, 2,106,106,106,106,106,106, - 106,106,104,104,104,104,104,104,104,104,104,104,104,104, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2,104,161,161,161,161,161,161, - 161,161,161,161,161, 2,161,161,161,161,161,161,161, 2,161,161, - 2,161,161,161, 2,161,161,161,161,161,161,161, 2,161,161, 2, - 2, 2,110,110,110,110,110,110,110,110,110,110,110,110,110,110, - 110, 2,110,110,110,110,110,110, 2, 2, 19, 19, 19, 19, 19, 19, - 2, 19, 19, 2, 19, 19, 19, 19, 19, 19, 47, 47, 47, 47, 47, 47, - 2, 2, 47, 2, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, - 47, 47, 47, 47, 47, 47, 47, 47, 2, 47, 47, 2, 2, 2, 47, 2, - 2, 47, 81, 81, 81, 81, 81, 81, 81, 81, 81, 81, 81, 81, 81, 81, - 2, 81,120,120,120,120,120,120,120,120,116,116,116,116,116,116, - 116,116,116,116,116,116,116,116,116, 2, 2, 2, 2, 2, 2, 2, - 2,116,128,128,128,128,128,128,128,128,128,128,128, 2,128,128, - 2, 2, 2, 2, 2,128,128,128,128,128, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 2, 2, 2, 66, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 2, 2, 2, 2, 2, 72, 98, 98, 98, 98, 98, 98, - 98, 98, 97, 97, 97, 97, 97, 97, 97, 97, 2, 2, 2, 2, 97, 97, - 97, 97, 2, 2, 97, 97, 97, 97, 97, 97, 57, 57, 57, 57, 2, 57, - 57, 2, 2, 2, 2, 2, 57, 57, 57, 57, 57, 57, 57, 57, 2, 57, - 57, 57, 2, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 2, 2, 57, 57, 57, 2, 2, 2, - 2, 57, 57, 2, 2, 2, 2, 2, 2, 2, 88, 88, 88, 88, 88, 88, - 88, 88,117,117,117,117,117,117,117,117,112,112,112,112,112,112, - 112,112,112,112,112,112,112,112,112, 2, 2, 2, 2,112,112,112, - 112,112, 78, 78, 78, 78, 78, 78, 78, 78, 78, 78, 78, 78, 78, 78, - 2, 2, 2, 78, 78, 78, 78, 78, 78, 78, 83, 83, 83, 83, 83, 83, - 83, 83, 83, 83, 83, 83, 83, 83, 2, 2, 82, 82, 82, 82, 82, 82, - 82, 82, 82, 82, 82, 2, 2, 2, 2, 2,122,122,122,122,122,122, - 122,122,122,122, 2, 2, 2, 2, 2, 2, 2,122,122,122,122, 2, - 2, 2, 2,122,122,122,122,122,122,122, 89, 89, 89, 89, 89, 89, - 89, 89, 89, 2, 2, 2, 2, 2, 2, 2,130,130,130,130,130,130, - 130,130,130,130,130, 2, 2, 2, 2, 2, 2, 2,130,130,130,130, - 130,130,144,144,144,144,144,144,144,144,144,144, 2, 2, 2, 2, - 2, 2,156,156,156,156,156,156,156,156,156,156, 2,156,156,156, - 2, 2,156,156, 2, 2, 2, 2, 2, 2,147,147,147,147,147,147, - 147,147,148,148,148,148,148,148,148,148,148,148, 2, 2, 2, 2, - 2, 2,158,158,158,158,158,158,158,158,158,158, 2, 2, 2, 2, - 2, 2,153,153,153,153,153,153,153,153,153,153,153,153, 2, 2, - 2, 2,149,149,149,149,149,149,149,149,149,149,149,149,149,149, - 149, 2, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, - 2, 2, 2, 2, 94, 94, 94, 94, 94, 94, 2, 2, 2, 2, 2, 2, - 2, 94, 85, 85, 85, 85, 85, 85, 85, 85, 85, 85, 85, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 85, 2, 2,101,101,101,101,101,101, - 101,101,101, 2, 2, 2, 2, 2, 2, 2,101,101, 2, 2, 2, 2, - 2, 2, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 2, - 96, 96,111,111,111,111,111,111,111,111,111,111,111,111,111,111, - 111, 2,100,100,100,100,100,100,100,100, 2, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 2, 2, 2,108,108,108,108,108,108, - 108,108,108,108, 2,108,108,108,108,108,108,108,108,108,108,108, - 108, 2,129,129,129,129,129,129,129, 2,129, 2,129,129,129,129, - 2,129,129,129,129,129,129,129,129,129,129,129,129,129,129,129, - 2,129,129,129, 2, 2, 2, 2, 2, 2,109,109,109,109,109,109, - 109,109,109,109,109, 2, 2, 2, 2, 2,109,109, 2, 2, 2, 2, - 2, 2,107,107,107,107, 2,107,107,107,107,107,107,107,107, 2, - 2,107,107, 2, 2,107,107,107,107,107,107,107,107,107,107,107, - 107,107,107, 2,107,107,107,107,107,107,107, 2,107,107, 2,107, - 107,107,107,107, 2, 1,107,107,107,107,107, 2, 2,107,107,107, - 2, 2,107, 2, 2, 2, 2, 2, 2,107, 2, 2, 2, 2, 2,107, - 107,107,107,107,107,107, 2, 2,107,107,107,107,107,107,107, 2, - 2, 2,137,137,137,137,137,137,137,137,137,137,137,137, 2,137, - 137,137,137,137, 2, 2, 2, 2, 2, 2,124,124,124,124,124,124, - 124,124,124,124, 2, 2, 2, 2, 2, 2,123,123,123,123,123,123, - 123,123,123,123,123,123,123,123, 2, 2,114,114,114,114,114,114, - 114,114,114,114,114,114,114, 2, 2, 2,114,114, 2, 2, 2, 2, - 2, 2, 32, 32, 32, 32, 32, 2, 2, 2,102,102,102,102,102,102, - 102,102,102,102, 2, 2, 2, 2, 2, 2,126,126,126,126,126,126, - 126,126,126,126,126, 2, 2,126,126,126,126,126,126,126, 2, 2, - 2, 2,126,126,126,126,126,126,126, 2,142,142,142,142,142,142, - 142,142,142,142,142,142, 2, 2, 2, 2,125,125,125,125,125,125, - 125,125,125,125,125, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2,125,154,154,154,154,154,154,154, 2, 2,154, 2, 2,154,154, - 154,154,154,154,154,154, 2,154,154, 2,154,154,154,154,154,154, - 154,154,154,154,154,154,154,154, 2,154,154, 2, 2,154,154,154, - 154,154,154,154, 2, 2, 2, 2, 2, 2,150,150,150,150,150,150, - 150,150, 2, 2,150,150,150,150,150,150,150,150,150,150,150, 2, - 2, 2,141,141,141,141,141,141,141,141,140,140,140,140,140,140, - 140,140,140,140,140, 2, 2, 2, 2, 2,121,121,121,121,121,121, - 121,121,121, 2, 2, 2, 2, 2, 2, 2,133,133,133,133,133,133, - 133,133,133, 2,133,133,133,133,133,133,133,133,133,133,133,133, - 133, 2,133,133,133,133,133,133, 2, 2,133,133,133,133,133, 2, - 2, 2,134,134,134,134,134,134,134,134, 2, 2,134,134,134,134, - 134,134, 2,134,134,134,134,134,134,134,134,134,134,134,134,134, - 134, 2,138,138,138,138,138,138,138, 2,138,138, 2,138,138,138, - 138,138,138,138,138,138,138,138,138,138, 2, 2,138, 2,138,138, - 2,138,138,138, 2, 2, 2, 2, 2, 2,143,143,143,143,143,143, - 2,143,143, 2,143,143,143,143,143,143,143,143,143,143,143,143, - 143,143,143,143,143,143,143,143,143, 2,143,143, 2,143,143,143, - 143,143,143, 2, 2, 2, 2, 2, 2, 2,143,143, 2, 2, 2, 2, - 2, 2,145,145,145,145,145,145,145,145,145, 2, 2, 2, 2, 2, - 2, 2, 86, 2, 2, 2, 2, 2, 2, 2, 22, 22, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 22, 63, 63, 63, 63, 63, 63, - 63, 63, 63, 63, 2, 2, 2, 2, 2, 2, 63, 63, 63, 63, 63, 63, - 63, 2, 63, 63, 63, 63, 63, 2, 2, 2, 63, 63, 63, 63, 2, 2, - 2, 2,157,157,157,157,157,157,157,157,157,157,157, 2, 2, 2, - 2, 2, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, - 80, 2, 80, 2, 2, 2, 2, 2, 2, 2,127,127,127,127,127,127, - 127,127,127,127,127,127,127,127,127, 2, 79, 2, 2, 2, 2, 2, - 2, 2,115,115,115,115,115,115,115,115,115,115,115,115,115,115, - 115, 2,115,115, 2, 2, 2, 2,115,115,159,159,159,159,159,159, - 159,159,159,159,159,159,159,159,159, 2,159,159, 2, 2, 2, 2, - 2, 2,103,103,103,103,103,103,103,103,103,103,103,103,103,103, - 2, 2,119,119,119,119,119,119,119,119,119,119,119,119,119,119, - 2, 2,119,119, 2,119,119,119,119,119, 2, 2, 2, 2, 2,119, - 119,119,146,146,146,146,146,146,146,146,146,146,146, 2, 2, 2, - 2, 2, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 2, 2, 2, - 2, 99, 2, 2, 2, 2, 2, 2, 2, 99,136,139, 13, 13,155, 2, - 2, 2,136,136,136,136,136,136,136,136,155,155,155,155,155,155, - 155,155,155,155,155,155,155,155, 2, 2,136, 2, 2, 2, 2, 2, - 2, 2, 17, 17, 17, 17, 2, 17, 17, 17, 17, 17, 17, 17, 2, 17, - 17, 2, 17, 15, 15, 15, 15, 15, 15, 15, 17, 17, 17, 2, 2, 2, - 2, 2, 15, 15, 15, 2, 2, 2, 2, 2, 2, 2, 2, 2, 17, 17, - 17, 17,139,139,139,139,139,139,139,139,139,139,139,139, 2, 2, - 2, 2,105,105,105,105,105,105,105,105,105,105,105, 2, 2, 2, - 2, 2,105,105,105,105,105, 2, 2, 2,105, 2, 2, 2, 2, 2, - 2, 2,105,105, 2, 2,105,105,105,105, 1, 1, 1, 1, 1, 1, - 2, 2, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, - 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, - 0, 0, 2, 2, 0, 2, 2, 0, 0, 2, 2, 0, 0, 0, 0, 2, - 0, 0, 0, 0, 2, 0, 2, 0, 0, 0, 0, 0, 0, 0, 2, 0, - 0, 0, 0, 0, 0, 2, 2, 0, 0, 0, 0, 0, 2, 0, 0, 0, - 0, 2, 0, 0, 0, 0, 0, 2, 0, 2, 2, 2, 0, 0, 0, 0, - 0, 0, 0, 2, 0, 0, 0, 0, 0, 0,131,131,131,131,131,131, - 131,131,131,131,131,131, 2, 2, 2, 2, 2, 2, 2,131,131,131, - 131,131, 2,131,131,131,131,131,131,131, 56, 56, 56, 56, 56, 56, - 56, 2, 56, 2, 2, 56, 56, 56, 56, 56, 56, 56, 2, 56, 56, 2, - 56, 56, 56, 56, 56, 2, 2, 2, 2, 2,151,151,151,151,151,151, - 151,151,151,151,151,151,151, 2, 2, 2,151,151,151,151,151,151, - 2, 2,151,151, 2, 2, 2, 2,151,151,160,160,160,160,160,160, - 160,160,160,160,160,160,160,160,160, 2,152,152,152,152,152,152, - 152,152,152,152, 2, 2, 2, 2, 2,152, 30, 30, 30, 30, 2, 30, - 30, 2,113,113,113,113,113,113,113,113,113,113,113,113,113, 2, - 2,113,113,113,113,113,113,113,113, 2,132,132,132,132,132,132, - 132,132,132,132,132,132, 2, 2, 2, 2,132,132, 2, 2, 2, 2, - 132,132, 3, 3, 3, 3, 2, 3, 3, 3, 2, 3, 3, 2, 3, 2, - 2, 3, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 3, 3, - 3, 3, 2, 3, 2, 3, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, - 2, 3, 2, 3, 2, 3, 2, 3, 3, 3, 2, 3, 2, 3, 2, 3, - 2, 3, 2, 3, 3, 3, 3, 2, 3, 2, 3, 3, 2, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 2, 2, 2, 2, 2, 3, 3, 3, 2, 3, - 3, 3, 2, 2, 2, 2, 2, 2, 0, 0, 15, 0, 0, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 13, 2, 2, 2, 2, 2, - 2, 2, 13, 13, 13, 2, 2, 2, 2, 2, 2, 0, 2, 2, 2, 2, - 2, 2, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 9, 9, 9, 10, - 9, 11, 12, 13, 9, 9, 9, 14, 9, 9, 15, 9, 9, 9, 9, 9, + 15, 15, 15, 15, 15, 2, 2, 1, 1, 0, 0, 15, 15, 15, 0, 17, + 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 17, 0, 0, 17, 17, 17, 2, 2, 2, 2, 2, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 2, 12, 12, 12, 12, 12, 12, 12, 12, 12, + 12, 12, 12, 12, 12, 2, 12, 12, 12, 12, 12, 12, 12, 0, 17, 17, + 17, 17, 17, 17, 17, 0, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, + 39, 39, 39, 2, 2, 2, 39, 39, 39, 39, 39, 39, 39, 2, 86, 86, + 86, 86, 86, 86, 86, 86, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, + 77, 77, 2, 2, 2, 2, 79, 79, 79, 79, 79, 79, 79, 79, 0, 0, + 19, 19, 19, 19, 19, 19, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, + 19, 2, 2, 2, 2, 2, 19, 19, 2, 19, 2, 19, 19, 19, 19, 19, + 2, 2, 2, 2, 2, 2, 2, 2, 19, 19, 19, 19, 19, 19, 60, 60, + 60, 60, 60, 60, 60, 60, 60, 60, 60, 60, 60, 2, 2, 2, 0, 0, + 2, 2, 2, 2, 2, 2, 65, 65, 65, 65, 65, 65, 65, 65, 75, 75, + 75, 75, 75, 75, 75, 75, 75, 75, 75, 75, 75, 75, 2, 2, 2, 2, + 2, 2, 2, 2, 75, 75, 75, 75, 2, 2, 2, 2, 2, 2, 69, 69, + 69, 69, 69, 69, 69, 69, 69, 69, 69, 69, 69, 69, 0, 69, 74, 74, + 74, 74, 74, 74, 74, 74, 74, 74, 74, 74, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 74, 12, 12, 12, 12, 12, 2, 2, 2, 84, 84, + 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 2, 0, 84, 84, + 2, 2, 2, 2, 84, 84, 33, 33, 33, 33, 33, 33, 33, 2, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, 68, 68, 68, 68, 68, 2, 68, 68, + 68, 68, 68, 68, 2, 2, 68, 68, 2, 2, 68, 68, 68, 68, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 2, 2, 2, 2, 2, 2, 2, + 2, 92, 92, 92, 92, 92, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, + 87, 87, 87, 87, 87, 2, 2, 30, 30, 30, 30, 30, 30, 2, 19, 19, + 19, 0, 19, 19, 19, 19, 19, 19, 19, 19, 19, 9, 19, 19, 19, 19, + 0, 0, 2, 2, 2, 2, 87, 87, 87, 87, 87, 87, 2, 2, 87, 87, + 2, 2, 2, 2, 2, 2, 12, 12, 12, 12, 2, 2, 2, 2, 2, 2, + 2, 12, 12, 12, 12, 12, 13, 13, 2, 2, 2, 2, 2, 2, 19, 19, + 19, 19, 19, 19, 19, 2, 2, 2, 2, 4, 4, 4, 4, 4, 2, 2, + 2, 2, 2, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 2, 14, 14, + 14, 14, 14, 2, 14, 2, 14, 14, 2, 14, 14, 2, 14, 14, 3, 3, + 3, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 0, 0, 2, 2, 3, 3, 3, 3, 3, 3, 2, 2, + 2, 2, 2, 2, 2, 3, 1, 1, 1, 1, 1, 1, 6, 6, 0, 0, + 0, 2, 0, 0, 0, 0, 3, 3, 3, 3, 3, 2, 3, 3, 3, 3, + 3, 3, 3, 2, 2, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 17, 17, 17, 17, 17, 17, 17, 17, 0, 0, 2, 2, + 12, 12, 12, 12, 12, 12, 2, 2, 12, 12, 12, 2, 2, 2, 2, 0, + 0, 0, 0, 0, 2, 2, 49, 49, 49, 49, 49, 49, 49, 49, 49, 49, + 49, 49, 2, 49, 49, 49, 49, 49, 49, 49, 49, 49, 49, 2, 49, 49, + 49, 2, 49, 49, 2, 49, 49, 49, 49, 49, 49, 49, 2, 2, 49, 49, + 49, 2, 2, 2, 2, 2, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, + 0, 0, 2, 2, 2, 0, 0, 0, 0, 0, 0, 2, 2, 2, 9, 2, + 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 1, 2, 2, 71, 71, + 71, 71, 71, 71, 71, 71, 71, 71, 71, 71, 71, 2, 2, 2, 67, 67, + 67, 67, 67, 67, 67, 67, 67, 2, 2, 2, 2, 2, 2, 2, 1, 0, + 0, 0, 0, 0, 0, 0, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, + 42, 42, 2, 2, 2, 2, 2, 2, 2, 2, 2, 42, 42, 42, 41, 41, + 41, 41, 41, 41, 41, 41, 41, 41, 41, 2, 2, 2, 2, 2,118,118, + 118,118,118,118,118,118,118,118,118, 2, 2, 2, 2, 2, 53, 53, + 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 2, 53, 59, 59, + 59, 59, 59, 59, 59, 59, 59, 59, 59, 59, 2, 2, 2, 2, 59, 59, + 59, 59, 59, 59, 2, 2, 40, 40, 40, 40, 40, 40, 40, 40, 51, 51, + 51, 51, 51, 51, 51, 51, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, + 50, 50, 50, 50, 2, 2, 50, 50, 2, 2, 2, 2, 2, 2,135,135, + 135,135,135,135,135,135,135,135,135,135, 2, 2, 2, 2,106,106, + 106,106,106,106,106,106,104,104,104,104,104,104,104,104,104,104, + 104,104, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,104,161,161, + 161,161,161,161,161,161,161,161,161, 2,161,161,161,161,161,161, + 161, 2,161,161, 2,161,161,161, 2,161,161,161,161,161,161,161, + 2,161,161, 2, 2, 2,110,110,110,110,110,110,110,110,110,110, + 110,110,110,110,110, 2,110,110,110,110,110,110, 2, 2, 19, 19, + 19, 19, 19, 19, 2, 19, 19, 2, 19, 19, 19, 19, 19, 19, 47, 47, + 47, 47, 47, 47, 2, 2, 47, 2, 47, 47, 47, 47, 47, 47, 47, 47, + 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 2, 47, 47, 2, + 2, 2, 47, 2, 2, 47, 81, 81, 81, 81, 81, 81, 81, 81, 81, 81, + 81, 81, 81, 81, 2, 81,120,120,120,120,120,120,120,120,116,116, + 116,116,116,116,116,116,116,116,116,116,116,116,116, 2, 2, 2, + 2, 2, 2, 2, 2,116,128,128,128,128,128,128,128,128,128,128, + 128, 2,128,128, 2, 2, 2, 2, 2,128,128,128,128,128, 66, 66, + 66, 66, 66, 66, 66, 66, 66, 66, 66, 66, 2, 2, 2, 66, 72, 72, + 72, 72, 72, 72, 72, 72, 72, 72, 2, 2, 2, 2, 2, 72, 98, 98, + 98, 98, 98, 98, 98, 98, 97, 97, 97, 97, 97, 97, 97, 97, 2, 2, + 2, 2, 97, 97, 97, 97, 2, 2, 97, 97, 97, 97, 97, 97, 57, 57, + 57, 57, 2, 57, 57, 2, 2, 2, 2, 2, 57, 57, 57, 57, 57, 57, + 57, 57, 2, 57, 57, 57, 2, 57, 57, 57, 57, 57, 57, 57, 57, 57, + 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 2, 2, 57, 57, + 57, 2, 2, 2, 2, 57, 57, 2, 2, 2, 2, 2, 2, 2, 88, 88, + 88, 88, 88, 88, 88, 88,117,117,117,117,117,117,117,117,112,112, + 112,112,112,112,112,112,112,112,112,112,112,112,112, 2, 2, 2, + 2,112,112,112,112,112, 78, 78, 78, 78, 78, 78, 78, 78, 78, 78, + 78, 78, 78, 78, 2, 2, 2, 78, 78, 78, 78, 78, 78, 78, 83, 83, + 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 2, 2, 82, 82, + 82, 82, 82, 82, 82, 82, 82, 82, 82, 2, 2, 2, 2, 2,122,122, + 122,122,122,122,122,122,122,122, 2, 2, 2, 2, 2, 2, 2,122, + 122,122,122, 2, 2, 2, 2,122,122,122,122,122,122,122, 89, 89, + 89, 89, 89, 89, 89, 89, 89, 2, 2, 2, 2, 2, 2, 2,130,130, + 130,130,130,130,130,130,130,130,130, 2, 2, 2, 2, 2, 2, 2, + 130,130,130,130,130,130,144,144,144,144,144,144,144,144,144,144, + 2, 2, 2, 2, 2, 2,156,156,156,156,156,156,156,156,156,156, + 2,156,156,156, 2, 2,156,156, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 3, 3, 3,147,147,147,147,147,147,147,147,148,148, + 148,148,148,148,148,148,148,148, 2, 2, 2, 2, 2, 2,158,158, + 158,158,158,158,158,158,158,158, 2, 2, 2, 2, 2, 2,153,153, + 153,153,153,153,153,153,153,153,153,153, 2, 2, 2, 2,149,149, + 149,149,149,149,149,149,149,149,149,149,149,149,149, 2, 94, 94, + 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 2, 2, 2, 2, + 94, 94, 94, 94, 94, 94, 2, 2, 2, 2, 2, 2, 2, 94, 85, 85, + 85, 85, 85, 85, 85, 85, 85, 85, 85, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 85, 2, 2,101,101,101,101,101,101,101,101,101, 2, + 2, 2, 2, 2, 2, 2,101,101, 2, 2, 2, 2, 2, 2, 96, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 2, 96, 96,111,111, + 111,111,111,111,111,111,111,111,111,111,111,111,111, 2,100,100, + 100,100,100,100,100,100, 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, + 36, 36, 36, 2, 2, 2,108,108,108,108,108,108,108,108,108,108, + 2,108,108,108,108,108,108,108, 2, 2, 2, 2, 2, 2,129,129, + 129,129,129,129,129, 2,129, 2,129,129,129,129, 2,129,129,129, + 129,129,129,129,129,129,129,129,129,129,129,129, 2,129,129,129, + 2, 2, 2, 2, 2, 2,109,109,109,109,109,109,109,109,109,109, + 109, 2, 2, 2, 2, 2,109,109, 2, 2, 2, 2, 2, 2,107,107, + 107,107, 2,107,107,107,107,107,107,107,107, 2, 2,107,107, 2, + 2,107,107,107,107,107,107,107,107,107,107,107,107,107,107, 2, + 107,107,107,107,107,107,107, 2,107,107, 2,107,107,107,107,107, + 2, 1,107,107,107,107,107, 2, 2,107,107,107, 2, 2,107, 2, + 2, 2, 2, 2, 2,107, 2, 2, 2, 2, 2,107,107,107,107,107, + 107,107, 2, 2,107,107,107,107,107,107,107, 2, 2, 2,137,137, + 137,137,137,137,137,137,137,137,137,137, 2,137,137,137,137,137, + 2, 2, 2, 2, 2, 2,124,124,124,124,124,124,124,124,124,124, + 2, 2, 2, 2, 2, 2,123,123,123,123,123,123,123,123,123,123, + 123,123,123,123, 2, 2,114,114,114,114,114,114,114,114,114,114, + 114,114,114, 2, 2, 2,114,114, 2, 2, 2, 2, 2, 2, 32, 32, + 32, 32, 32, 2, 2, 2,102,102,102,102,102,102,102,102,102,102, + 2, 2, 2, 2, 2, 2,126,126,126,126,126,126,126,126,126,126, + 126, 2, 2,126,126,126,126,126,126,126, 2, 2, 2, 2,126,126, + 126,126,126,126,126, 2,142,142,142,142,142,142,142,142,142,142, + 142,142, 2, 2, 2, 2,125,125,125,125,125,125,125,125,125,125, + 125, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,125,154,154, + 154,154,154,154,154, 2, 2,154, 2, 2,154,154,154,154,154,154, + 154,154, 2,154,154, 2,154,154,154,154,154,154,154,154,154,154, + 154,154,154,154, 2,154,154, 2, 2,154,154,154,154,154,154,154, + 2, 2, 2, 2, 2, 2,150,150,150,150,150,150,150,150, 2, 2, + 150,150,150,150,150,150,150,150,150,150,150, 2, 2, 2,141,141, + 141,141,141,141,141,141,140,140,140,140,140,140,140,140,140,140, + 140, 2, 2, 2, 2, 2,121,121,121,121,121,121,121,121,121, 2, + 2, 2, 2, 2, 2, 2, 7, 7, 2, 2, 2, 2, 2, 2,133,133, + 133,133,133,133,133,133,133, 2,133,133,133,133,133,133,133,133, + 133,133,133,133,133, 2,133,133,133,133,133,133, 2, 2,133,133, + 133,133,133, 2, 2, 2,134,134,134,134,134,134,134,134, 2, 2, + 134,134,134,134,134,134, 2,134,134,134,134,134,134,134,134,134, + 134,134,134,134,134, 2,138,138,138,138,138,138,138, 2,138,138, + 2,138,138,138,138,138,138,138,138,138,138,138,138,138, 2, 2, + 138, 2,138,138, 2,138,138,138, 2, 2, 2, 2, 2, 2,143,143, + 143,143,143,143, 2,143,143, 2,143,143,143,143,143,143,143,143, + 143,143,143,143,143,143,143,143,143,143,143,143,143, 2,143,143, + 2,143,143,143,143,143,143, 2, 2, 2, 2, 2, 2, 2,143,143, + 2, 2, 2, 2, 2, 2,145,145,145,145,145,145,145,145,145, 2, + 2, 2, 2, 2, 2, 2,163,163,163,163,163,163,163,163,163, 2, + 163,163,163,163,163,163,163,163,163, 2, 2, 2,163,163,163,163, + 2, 2, 2, 2, 2, 2, 86, 2, 2, 2, 2, 2, 2, 2, 22, 22, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 22, 63, 63, + 63, 63, 63, 63, 63, 63, 63, 63, 2, 2, 2, 2, 2, 2, 63, 63, + 63, 63, 63, 63, 63, 2, 63, 63, 63, 63, 63, 2, 2, 2, 63, 63, + 63, 63, 2, 2, 2, 2,157,157,157,157,157,157,157,157,157,157, + 157, 2, 2, 2, 2, 2, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, + 80, 80, 80, 80, 2, 2,127,127,127,127,127,127,127,127,127,127, + 127,127,127,127,127, 2, 79, 2, 2, 2, 2, 2, 2, 2,115,115, + 115,115,115,115,115,115,115,115,115,115,115,115,115, 2,115,115, + 2, 2, 2, 2,115,115,159,159,159,159,159,159,159,159,159,159, + 159,159,159,159,159, 2,159,159, 2, 2, 2, 2, 2, 2,103,103, + 103,103,103,103,103,103,103,103,103,103,103,103, 2, 2,119,119, + 119,119,119,119,119,119,119,119,119,119,119,119, 2, 2,119,119, + 2,119,119,119,119,119, 2, 2, 2, 2, 2,119,119,119,146,146, + 146,146,146,146,146,146,146,146,146, 2, 2, 2, 2, 2, 99, 99, + 99, 99, 99, 99, 99, 99, 99, 99, 99, 2, 2, 2, 2, 99, 2, 2, + 2, 2, 2, 2, 2, 99,136,139, 13, 13,155, 2, 2, 2,136,136, + 136,136,136,136,136,136,155,155,155,155,155,155,155,155,155,155, + 155,155,155,155, 2, 2,136, 2, 2, 2, 2, 2, 2, 2, 17, 17, + 17, 17, 2, 17, 17, 17, 17, 17, 17, 17, 2, 17, 17, 2, 17, 15, + 15, 15, 15, 15, 15, 15, 17, 17, 17, 2, 2, 2, 2, 2, 2, 2, + 15, 2, 2, 2, 2, 2, 15, 15, 15, 2, 2, 17, 2, 2, 2, 2, + 2, 2, 17, 17, 17, 17,139,139,139,139,139,139,139,139,139,139, + 139,139, 2, 2, 2, 2,105,105,105,105,105,105,105,105,105,105, + 105, 2, 2, 2, 2, 2,105,105,105,105,105, 2, 2, 2,105, 2, + 2, 2, 2, 2, 2, 2,105,105, 2, 2,105,105,105,105, 1, 1, + 1, 1, 1, 1, 2, 2, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, + 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, + 1, 1, 1, 1, 0, 0, 2, 2, 0, 2, 2, 0, 0, 2, 2, 0, + 0, 0, 0, 2, 0, 0, 0, 0, 2, 0, 2, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, 0, 0, 0, 2, 2, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 2, 0, 2, 2, 2, + 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0,131,131, + 131,131,131,131,131,131,131,131,131,131, 2, 2, 2, 2, 2, 2, + 2,131,131,131,131,131, 2,131,131,131,131,131,131,131, 2, 2, + 2, 2, 2, 19, 19, 19, 56, 56, 56, 56, 56, 56, 56, 2, 56, 2, + 2, 56, 56, 56, 56, 56, 56, 56, 2, 56, 56, 2, 56, 56, 56, 56, + 56, 2, 2, 2, 2, 2, 6, 6, 6, 6, 6, 6, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 6,151,151,151,151,151,151,151,151,151,151, + 151,151,151, 2, 2, 2,151,151,151,151,151,151, 2, 2,151,151, + 2, 2, 2, 2,151,151,160,160,160,160,160,160,160,160,160,160, + 160,160,160,160,160, 2,152,152,152,152,152,152,152,152,152,152, + 2, 2, 2, 2, 2,152,164,164,164,164,164,164,164,164,164,164, + 2, 2, 2, 2, 2, 2, 30, 30, 30, 30, 2, 30, 30, 2,113,113, + 113,113,113,113,113,113,113,113,113,113,113, 2, 2,113,113,113, + 113,113,113,113,113, 2,132,132,132,132,132,132,132,132,132,132, + 132,132, 2, 2, 2, 2,132,132, 2, 2, 2, 2,132,132, 3, 3, + 3, 3, 2, 3, 3, 3, 2, 3, 3, 2, 3, 2, 2, 3, 2, 3, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 3, 3, 3, 3, 2, 3, + 2, 3, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, 3, 2, 3, + 2, 3, 2, 3, 3, 3, 2, 3, 2, 3, 2, 3, 2, 3, 2, 3, + 3, 3, 3, 2, 3, 2, 3, 3, 2, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 2, 2, 2, 2, 2, 3, 3, 3, 2, 3, 3, 3, 2, 2, + 2, 2, 2, 2, 0, 0, 15, 0, 0, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 0, 0, 0, 0, 2, 2, 2, 0, 0, 0, 0, 0, 13, 2, + 2, 2, 2, 2, 2, 2, 13, 13, 13, 2, 2, 2, 2, 2, 2, 0, + 2, 2, 2, 2, 2, 2, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, + 9, 9, 9, 10, 9, 11, 12, 13, 9, 9, 9, 14, 9, 9, 15, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 16, 17, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 19, 20, 9, 21, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 16, 17, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 19, + 20, 9, 21, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 22, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 22, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, @@ -2140,60 +2161,61 @@ _hb_ucd_u8[17936] = 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 23, 24, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, - 5, 6, 7, 8, 9, 10, 11, 12, 0, 0, 13, 14, 15, 16, 17, 18, - 19, 20, 21, 22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 23, 0, 0, 24, 25, 26, 27, 28, 29, 30, 0, 0, - 31, 32, 0, 33, 0, 34, 0, 35, 0, 0, 0, 0, 36, 37, 38, 39, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 41, 42, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 43, 44, 0, 45, 0, 0, 0, 0, 0, 0, 46, 47, 0, 0, - 0, 0, 0, 48, 0, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 50, 51, 0, 0, 0, 52, 0, 0, 53, 0, 0, 0, - 0, 0, 0, 0, 54, 0, 0, 0, 0, 0, 0, 0, 55, 0, 0, 0, - 0, 0, 0, 0, 56, 0, 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, + 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 23, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 0, 0, 13, 14, + 15, 16, 17, 18, 19, 20, 21, 22, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 23, 0, 0, 24, 25, 26, 27, 28, + 29, 30, 0, 0, 31, 32, 0, 33, 0, 34, 0, 35, 0, 0, 0, 0, + 36, 37, 38, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 41, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 58, 59, 60, 61, 62, 63, 64, 65, 0, 0, 0, 0, - 0, 0, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 43, 44, 0, 45, 0, 0, 0, 0, 0, 0, + 46, 47, 0, 0, 0, 0, 0, 48, 0, 49, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 50, 51, 0, 0, 0, 52, 0, 0, + 53, 0, 0, 0, 0, 0, 0, 0, 54, 0, 0, 0, 0, 0, 0, 0, + 55, 0, 0, 0, 0, 0, 0, 0, 56, 0, 0, 0, 0, 0, 0, 0, + 0, 57, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 58, 59, 60, 61, 62, 63, 64, 65, + 0, 0, 0, 0, 0, 0, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 67, 68, 0, 69, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, - 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99,100,101,102, - 103, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0,104, 0, 0, 0, 0, 0, 0,105,106, 0,107, 0, 0, 0, - 108, 0,109, 0,110, 0,111,112,113, 0,114, 0, 0, 0,115, 0, - 0, 0,116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,117, 0, 0, + 0, 0, 0, 0, 67, 68, 0, 69, 70, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, + 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, + 99,100,101,102,103, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,104, 0, 0, 0, 0, 0, 0,105,106, 0, + 107, 0, 0, 0,108, 0,109, 0,110, 0,111,112,113, 0,114, 0, + 0, 0,115, 0, 0, 0,116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0,118,119,120,121, 0,122,123,124,125,126, 0,127, + 0,117, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0,118,119,120,121, 0,122,123,124, + 125,126, 0,127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,128,129,130,131,132,133,134,135,136,137,138,139, + 140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155, + 156,157, 0, 0, 0,158,159,160,161, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,162,163, 0, + 0, 0, 0, 0, 0, 0,164, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143, - 144,145,146,147,148,149,150,151,152,153,154,155,156,157, 0, 0, - 0,158,159,160,161, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,162,163, 0, 0, 0, 0, 0, - 0, 0,164, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0,165, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,166, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,167, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0,165, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,166, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,167, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,168, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,168, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0,169,170, 0, 0, 0, 0,171, + 172, 0, 0, 0,173,174,175,176,177,178,179,180,181,182,183,184, + 185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200, + 201,202,203,204,205,206, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0,169,170, 0, 0, 0, 0,171,172, 0, 0, 0, - 173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188, - 189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204, - 205,206, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, + 1, 2, 3, 4, }; static const uint16_t -_hb_ucd_u16[9200] = +_hb_ucd_u16[9320] = { 0, 0, 1, 2, 3, 4, 5, 6, 0, 0, 7, 8, 9, 10, 11, 12, 13, 13, 13, 14, 15, 13, 13, 16, 17, 18, 19, 20, 21, 22, 13, 23, @@ -2267,509 +2289,517 @@ _hb_ucd_u16[9200] = 48, 48, 48, 468, 48, 469, 48, 470, 48, 471, 472, 140, 140, 140, 140, 140, 48, 48, 48, 48, 196, 140, 140, 140, 9, 9, 9, 473, 11, 11, 11, 474, 48, 48, 475, 192, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 271, 476, - 48, 48, 477, 478, 140, 140, 140, 140, 48, 464, 479, 48, 62, 480, 140, 48, - 481, 140, 140, 48, 482, 140, 48, 314, 483, 48, 48, 484, 485, 457, 486, 487, - 222, 48, 48, 488, 489, 48, 196, 192, 490, 48, 491, 492, 493, 48, 48, 494, - 222, 48, 48, 495, 496, 497, 498, 499, 48, 97, 500, 501, 140, 140, 140, 140, - 502, 503, 504, 48, 48, 505, 506, 192, 507, 83, 84, 508, 509, 510, 511, 512, - 48, 48, 48, 513, 514, 515, 478, 140, 48, 48, 48, 516, 517, 192, 140, 140, - 48, 48, 518, 519, 520, 521, 140, 140, 48, 48, 48, 522, 523, 192, 524, 140, - 48, 48, 525, 526, 192, 140, 140, 140, 48, 173, 527, 528, 314, 140, 140, 140, - 48, 48, 500, 529, 140, 140, 140, 140, 140, 140, 9, 9, 11, 11, 148, 530, - 531, 532, 48, 533, 534, 192, 140, 140, 140, 140, 535, 48, 48, 536, 537, 140, - 538, 48, 48, 539, 540, 541, 48, 48, 542, 543, 544, 48, 48, 48, 48, 196, - 84, 48, 518, 545, 546, 148, 175, 547, 48, 548, 549, 550, 140, 140, 140, 140, - 551, 48, 48, 552, 553, 192, 554, 48, 555, 556, 192, 140, 140, 140, 140, 140, - 140, 140, 140, 140, 140, 140, 48, 557, 140, 140, 140, 100, 271, 558, 559, 560, - 48, 207, 140, 140, 140, 140, 140, 140, 272, 272, 272, 272, 272, 272, 561, 562, - 48, 48, 48, 48, 388, 140, 140, 140, 140, 48, 48, 48, 48, 48, 48, 563, - 48, 48, 200, 564, 140, 140, 140, 140, 48, 48, 48, 48, 314, 140, 140, 140, - 48, 48, 48, 196, 48, 200, 370, 48, 48, 48, 48, 200, 192, 48, 204, 565, - 48, 48, 48, 566, 567, 568, 569, 570, 48, 140, 140, 140, 140, 140, 140, 140, - 140, 140, 140, 140, 9, 9, 11, 11, 271, 571, 140, 140, 140, 140, 140, 140, - 48, 48, 48, 48, 572, 573, 574, 574, 575, 576, 140, 140, 140, 140, 577, 578, + 48, 48, 477, 478, 140, 140, 140, 479, 48, 464, 480, 48, 62, 481, 140, 48, + 482, 140, 140, 48, 483, 140, 48, 314, 484, 48, 48, 485, 486, 457, 487, 488, + 222, 48, 48, 489, 490, 48, 196, 192, 491, 48, 492, 493, 494, 48, 48, 495, + 222, 48, 48, 496, 497, 498, 499, 500, 48, 97, 501, 502, 503, 140, 140, 140, + 504, 505, 506, 48, 48, 507, 508, 192, 509, 83, 84, 510, 511, 512, 513, 514, + 48, 48, 48, 515, 516, 517, 478, 140, 48, 48, 48, 518, 519, 192, 140, 140, + 48, 48, 520, 521, 522, 523, 140, 140, 48, 48, 48, 524, 525, 192, 526, 140, + 48, 48, 527, 528, 192, 140, 140, 140, 48, 173, 529, 530, 314, 140, 140, 140, + 48, 48, 501, 531, 140, 140, 140, 140, 140, 140, 9, 9, 11, 11, 148, 532, + 533, 534, 48, 535, 536, 192, 140, 140, 140, 140, 537, 48, 48, 538, 539, 140, + 540, 48, 48, 541, 542, 543, 48, 48, 544, 545, 546, 48, 48, 48, 48, 196, + 547, 140, 140, 140, 140, 140, 140, 140, 84, 48, 520, 548, 549, 148, 175, 550, + 48, 551, 552, 553, 140, 140, 140, 140, 554, 48, 48, 555, 556, 192, 557, 48, + 558, 559, 192, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 48, 560, + 561, 115, 48, 562, 563, 192, 140, 140, 140, 140, 140, 100, 271, 564, 565, 566, + 48, 207, 140, 140, 140, 140, 140, 140, 272, 272, 272, 272, 272, 272, 567, 568, + 48, 48, 48, 48, 388, 140, 140, 140, 140, 48, 48, 48, 48, 48, 48, 569, + 48, 48, 48, 570, 571, 572, 140, 140, 48, 48, 48, 48, 314, 140, 140, 140, + 48, 48, 48, 196, 48, 200, 370, 48, 48, 48, 48, 200, 192, 48, 204, 573, + 48, 48, 48, 574, 575, 576, 577, 578, 48, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 9, 9, 11, 11, 271, 579, 140, 140, 140, 140, 140, 140, + 48, 48, 48, 48, 580, 581, 582, 582, 583, 584, 140, 140, 140, 140, 585, 586, 48, 48, 48, 48, 48, 48, 48, 440, 48, 48, 48, 48, 48, 199, 140, 140, - 196, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 579, - 48, 48, 580, 140, 140, 580, 581, 48, 48, 48, 48, 48, 48, 48, 48, 206, - 48, 48, 48, 48, 48, 48, 71, 151, 196, 582, 583, 140, 140, 140, 140, 140, - 32, 32, 584, 32, 585, 209, 209, 209, 209, 209, 209, 209, 323, 140, 140, 140, - 209, 209, 209, 209, 209, 209, 209, 324, 209, 209, 586, 209, 209, 209, 587, 588, - 589, 209, 590, 209, 209, 209, 288, 140, 209, 209, 209, 209, 591, 140, 140, 140, - 140, 140, 140, 140, 140, 140, 271, 592, 209, 209, 209, 209, 209, 287, 271, 461, - 9, 593, 11, 594, 595, 596, 241, 9, 597, 598, 599, 600, 601, 9, 593, 11, - 602, 603, 11, 604, 605, 606, 607, 9, 608, 11, 9, 593, 11, 594, 595, 11, - 241, 9, 597, 607, 9, 608, 11, 9, 593, 11, 609, 9, 610, 611, 612, 613, - 11, 614, 9, 615, 616, 617, 618, 11, 619, 9, 620, 11, 621, 622, 622, 622, - 32, 32, 32, 623, 32, 32, 624, 625, 626, 627, 45, 140, 140, 140, 140, 140, - 628, 629, 140, 140, 140, 140, 140, 140, 630, 631, 632, 140, 140, 140, 140, 140, - 48, 48, 151, 633, 634, 140, 140, 140, 140, 48, 635, 140, 48, 48, 636, 637, - 140, 140, 140, 140, 140, 140, 638, 200, 48, 48, 48, 48, 639, 585, 140, 140, - 9, 9, 597, 11, 640, 370, 140, 140, 140, 140, 140, 140, 140, 140, 140, 498, - 271, 271, 641, 642, 140, 140, 140, 140, 498, 271, 643, 644, 140, 140, 140, 140, - 645, 48, 646, 647, 648, 649, 650, 651, 652, 206, 653, 206, 140, 140, 140, 654, - 209, 209, 325, 209, 209, 209, 209, 209, 209, 323, 334, 655, 655, 655, 209, 324, - 656, 209, 209, 209, 209, 209, 209, 209, 209, 209, 657, 140, 140, 140, 658, 209, - 659, 209, 209, 325, 660, 661, 324, 140, 209, 209, 209, 209, 209, 209, 209, 662, - 209, 209, 209, 209, 209, 663, 426, 426, 209, 209, 209, 209, 209, 209, 209, 323, - 209, 209, 209, 209, 209, 660, 325, 427, 325, 209, 209, 209, 664, 176, 209, 209, - 664, 209, 657, 661, 140, 140, 140, 140, 209, 209, 209, 209, 209, 323, 657, 665, - 287, 209, 426, 288, 324, 176, 664, 287, 209, 666, 209, 209, 288, 140, 140, 192, - 48, 48, 48, 48, 48, 48, 140, 140, 48, 48, 48, 196, 48, 48, 48, 48, + 196, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 587, + 48, 48, 588, 589, 140, 590, 591, 48, 48, 48, 48, 48, 48, 48, 48, 206, + 48, 48, 48, 48, 48, 48, 71, 151, 196, 592, 593, 140, 140, 140, 140, 140, + 32, 32, 594, 32, 595, 209, 209, 209, 209, 209, 209, 209, 323, 140, 140, 140, + 209, 209, 209, 209, 209, 209, 209, 324, 209, 209, 596, 209, 209, 209, 597, 598, + 599, 209, 600, 209, 209, 209, 288, 140, 209, 209, 209, 209, 601, 140, 140, 140, + 140, 140, 140, 140, 271, 602, 271, 602, 209, 209, 209, 209, 209, 287, 271, 461, + 9, 603, 11, 604, 605, 606, 241, 9, 607, 608, 609, 610, 611, 9, 603, 11, + 612, 613, 11, 614, 615, 616, 617, 9, 618, 11, 9, 603, 11, 604, 605, 11, + 241, 9, 607, 617, 9, 618, 11, 9, 603, 11, 619, 9, 620, 621, 622, 623, + 11, 624, 9, 625, 626, 627, 628, 11, 629, 9, 630, 11, 631, 632, 632, 632, + 32, 32, 32, 633, 32, 32, 634, 635, 636, 637, 45, 140, 140, 140, 140, 140, + 638, 639, 640, 140, 140, 140, 140, 140, 641, 642, 643, 27, 27, 27, 644, 140, + 645, 140, 140, 140, 140, 140, 140, 140, 48, 48, 151, 646, 647, 140, 140, 140, + 140, 48, 648, 140, 48, 48, 649, 650, 140, 140, 140, 140, 140, 48, 651, 192, + 140, 140, 140, 140, 140, 140, 652, 200, 48, 48, 48, 48, 653, 595, 140, 140, + 9, 9, 607, 11, 654, 370, 140, 140, 140, 140, 140, 140, 140, 140, 140, 499, + 271, 271, 655, 656, 140, 140, 140, 140, 499, 271, 657, 658, 140, 140, 140, 140, + 659, 48, 660, 661, 662, 663, 664, 665, 666, 206, 667, 206, 140, 140, 140, 668, + 209, 209, 325, 209, 209, 209, 209, 209, 209, 323, 334, 669, 669, 669, 209, 324, + 670, 209, 209, 209, 209, 209, 209, 209, 209, 209, 671, 140, 140, 140, 672, 209, + 673, 209, 209, 325, 674, 675, 324, 140, 209, 209, 209, 209, 209, 209, 209, 676, + 209, 209, 209, 209, 209, 677, 426, 426, 209, 209, 209, 209, 209, 209, 209, 678, + 209, 209, 209, 209, 209, 176, 325, 427, 325, 209, 209, 209, 679, 176, 209, 209, + 679, 209, 671, 675, 140, 140, 140, 140, 209, 209, 209, 209, 209, 323, 671, 426, + 674, 209, 209, 680, 681, 325, 674, 674, 209, 682, 209, 209, 288, 140, 140, 192, + 48, 48, 48, 48, 48, 48, 140, 140, 48, 48, 48, 207, 48, 48, 48, 48, 48, 204, 48, 48, 48, 48, 48, 48, 48, 48, 478, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 100, 140, 48, 204, 140, 140, 140, 140, 140, 140, - 48, 48, 48, 48, 71, 140, 140, 140, 667, 140, 668, 668, 668, 668, 668, 668, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 140, - 391, 391, 391, 391, 391, 391, 391, 669, 391, 391, 391, 391, 391, 391, 391, 670, - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 3, 1, 2, 2, 3, - 0, 0, 0, 0, 0, 4, 0, 4, 2, 2, 5, 2, 2, 2, 5, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 6, 0, 0, 0, 0, 7, 8, 0, 0, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 10, 11, - 12, 13, 14, 14, 15, 14, 14, 14, 14, 14, 14, 14, 16, 17, 14, 14, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 19, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 20, 21, 21, 21, 22, 20, 21, 21, 21, 21, - 21, 23, 24, 25, 25, 25, 25, 25, 25, 26, 25, 25, 25, 27, 28, 26, - 29, 30, 31, 32, 31, 31, 31, 31, 33, 34, 35, 31, 31, 31, 36, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 29, 31, 31, 31, 31, - 37, 38, 37, 37, 37, 37, 37, 37, 37, 39, 31, 31, 31, 31, 31, 31, - 40, 40, 40, 40, 40, 40, 41, 26, 42, 42, 42, 42, 42, 42, 42, 43, - 44, 44, 44, 44, 44, 45, 44, 46, 47, 47, 47, 48, 37, 49, 31, 31, - 31, 50, 51, 31, 31, 31, 31, 31, 31, 31, 31, 31, 52, 31, 31, 31, - 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 54, 53, 55, 53, 53, 53, - 56, 57, 58, 59, 59, 60, 61, 62, 57, 63, 64, 65, 66, 59, 59, 67, - 68, 69, 70, 71, 71, 72, 73, 74, 69, 75, 76, 77, 78, 71, 79, 26, - 80, 81, 82, 83, 83, 84, 85, 86, 81, 87, 88, 26, 89, 83, 90, 91, - 92, 93, 94, 95, 95, 96, 97, 98, 93, 99, 100, 101, 102, 95, 95, 26, - 103, 104, 105, 106, 107, 104, 108, 109, 104, 105, 110, 26, 111, 108, 108, 112, - 113, 114, 115, 113, 113, 115, 113, 116, 114, 117, 118, 119, 120, 113, 121, 113, - 122, 123, 124, 122, 122, 124, 125, 126, 123, 127, 128, 128, 129, 122, 130, 26, - 131, 132, 133, 131, 131, 131, 131, 131, 132, 133, 134, 131, 135, 131, 131, 131, - 136, 137, 138, 139, 137, 137, 140, 141, 138, 142, 143, 137, 144, 137, 145, 26, - 146, 147, 147, 147, 147, 147, 147, 148, 147, 147, 147, 149, 26, 26, 26, 26, - 150, 151, 152, 152, 153, 152, 152, 154, 155, 154, 152, 156, 26, 26, 26, 26, - 157, 157, 157, 157, 157, 157, 157, 157, 157, 158, 157, 157, 157, 159, 158, 157, - 157, 157, 157, 158, 157, 157, 157, 160, 157, 160, 161, 162, 26, 26, 26, 26, - 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, - 163, 163, 163, 163, 164, 164, 164, 164, 165, 166, 164, 164, 164, 164, 164, 167, - 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, - 169, 169, 169, 169, 169, 169, 169, 169, 169, 170, 171, 170, 169, 169, 169, 169, - 169, 170, 169, 169, 169, 169, 170, 171, 170, 169, 171, 169, 169, 169, 169, 169, - 169, 169, 170, 169, 169, 169, 169, 169, 169, 169, 169, 172, 169, 169, 169, 173, - 169, 169, 169, 174, 175, 175, 175, 175, 175, 175, 175, 175, 175, 175, 176, 176, - 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, - 178, 178, 178, 179, 180, 180, 180, 180, 180, 180, 180, 180, 180, 181, 180, 182, - 183, 183, 184, 185, 186, 186, 187, 26, 188, 188, 189, 26, 190, 191, 192, 26, - 193, 193, 193, 193, 193, 193, 193, 193, 193, 193, 193, 194, 193, 195, 193, 195, - 196, 197, 197, 198, 197, 197, 197, 197, 197, 197, 197, 197, 197, 197, 197, 199, - 197, 197, 197, 197, 197, 200, 177, 177, 177, 177, 177, 177, 177, 177, 201, 26, - 202, 202, 202, 203, 202, 204, 202, 204, 205, 202, 206, 206, 206, 207, 208, 26, - 209, 209, 209, 209, 209, 210, 209, 209, 209, 211, 209, 212, 193, 193, 193, 193, - 213, 213, 213, 214, 215, 215, 215, 215, 215, 215, 215, 216, 215, 215, 215, 217, - 215, 218, 215, 218, 215, 219, 9, 9, 9, 220, 26, 26, 26, 26, 26, 26, - 221, 221, 221, 221, 221, 221, 221, 221, 221, 222, 221, 221, 221, 221, 221, 223, - 224, 224, 224, 224, 224, 224, 224, 224, 225, 225, 225, 225, 225, 225, 226, 227, - 228, 228, 228, 228, 228, 228, 228, 229, 228, 230, 231, 231, 231, 231, 231, 231, - 18, 232, 164, 164, 164, 164, 164, 233, 224, 26, 234, 9, 235, 236, 237, 238, - 2, 2, 2, 2, 239, 240, 2, 2, 2, 2, 2, 241, 242, 243, 2, 244, - 2, 2, 2, 2, 2, 2, 2, 245, 9, 9, 9, 9, 9, 9, 9, 9, - 14, 14, 246, 246, 14, 14, 14, 14, 246, 246, 14, 247, 14, 14, 14, 246, - 14, 14, 14, 14, 14, 14, 248, 14, 248, 14, 249, 250, 14, 14, 251, 252, - 0, 253, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 254, 0, 255, 256, - 0, 257, 2, 258, 0, 0, 0, 0, 259, 26, 9, 9, 9, 9, 260, 26, - 0, 0, 0, 0, 261, 262, 4, 0, 0, 263, 0, 0, 2, 2, 2, 2, - 2, 264, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 48, 48, 48, 48, 71, 48, 48, 48, 48, 48, 48, 140, 140, 140, 140, 140, + 683, 140, 570, 570, 570, 570, 570, 570, 32, 32, 32, 32, 32, 32, 32, 32, + 32, 32, 32, 32, 32, 32, 32, 140, 391, 391, 391, 391, 391, 391, 391, 684, + 391, 391, 391, 391, 391, 391, 391, 685, 0, 0, 0, 0, 0, 0, 0, 0, + 1, 2, 2, 3, 1, 2, 2, 3, 0, 0, 0, 0, 0, 4, 0, 4, + 2, 2, 5, 2, 2, 2, 5, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 6, + 0, 0, 0, 0, 7, 8, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 10, 11, 12, 13, 14, 14, 15, 14, 14, 14, + 14, 14, 14, 14, 16, 17, 14, 14, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 19, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 20, 21, + 21, 21, 22, 20, 21, 21, 21, 21, 21, 23, 24, 25, 25, 25, 25, 25, + 25, 26, 25, 25, 25, 27, 28, 26, 29, 30, 31, 32, 31, 31, 31, 31, + 33, 34, 35, 31, 31, 31, 36, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 29, 31, 31, 31, 31, 37, 38, 37, 37, 37, 37, 37, 37, + 37, 39, 31, 31, 31, 31, 31, 31, 40, 40, 40, 40, 40, 40, 41, 26, + 42, 42, 42, 42, 42, 42, 42, 43, 44, 44, 44, 44, 44, 45, 44, 46, + 47, 47, 47, 48, 37, 49, 31, 31, 31, 50, 51, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 52, 31, 31, 31, 53, 53, 53, 53, 53, 53, 53, 53, + 53, 53, 54, 53, 55, 53, 53, 53, 56, 57, 58, 59, 59, 60, 61, 62, + 57, 63, 64, 65, 66, 59, 59, 67, 68, 69, 70, 71, 71, 72, 73, 74, + 69, 75, 76, 77, 78, 71, 79, 26, 80, 81, 82, 83, 83, 84, 85, 86, + 81, 87, 88, 26, 89, 83, 90, 91, 92, 93, 94, 95, 95, 96, 97, 98, + 93, 99, 100, 101, 102, 95, 95, 26, 103, 104, 105, 106, 107, 104, 108, 109, + 104, 105, 110, 26, 111, 108, 108, 112, 113, 114, 115, 113, 113, 115, 113, 116, + 114, 117, 118, 119, 120, 113, 121, 113, 122, 123, 124, 122, 122, 124, 125, 126, + 123, 127, 128, 128, 129, 122, 130, 26, 131, 132, 133, 131, 131, 131, 131, 131, + 132, 133, 134, 131, 135, 131, 131, 131, 136, 137, 138, 139, 137, 137, 140, 141, + 138, 142, 143, 137, 144, 137, 145, 26, 146, 147, 147, 147, 147, 147, 147, 148, + 147, 147, 147, 149, 26, 26, 26, 26, 150, 151, 152, 152, 153, 152, 152, 154, + 155, 156, 152, 157, 26, 26, 26, 26, 158, 158, 158, 158, 158, 158, 158, 158, + 158, 159, 158, 158, 158, 160, 159, 158, 158, 158, 158, 159, 158, 158, 158, 161, + 158, 161, 162, 163, 26, 26, 26, 26, 164, 164, 164, 164, 164, 164, 164, 164, + 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 165, 165, 165, 165, + 166, 167, 165, 165, 165, 165, 165, 168, 169, 169, 169, 169, 169, 169, 169, 169, + 169, 169, 169, 169, 169, 169, 169, 169, 170, 170, 170, 170, 170, 170, 170, 170, + 170, 171, 172, 171, 170, 170, 170, 170, 170, 171, 170, 170, 170, 170, 171, 172, + 171, 170, 172, 170, 170, 170, 170, 170, 170, 170, 171, 170, 170, 170, 170, 170, + 170, 170, 170, 173, 170, 170, 170, 174, 170, 170, 170, 175, 176, 176, 176, 176, + 176, 176, 176, 176, 176, 176, 177, 177, 178, 178, 178, 178, 178, 178, 178, 178, + 178, 178, 178, 178, 178, 178, 178, 178, 179, 179, 179, 180, 181, 181, 181, 181, + 181, 181, 181, 181, 181, 182, 181, 183, 184, 184, 185, 186, 187, 187, 188, 26, + 189, 189, 190, 26, 191, 192, 193, 26, 194, 194, 194, 194, 194, 194, 194, 194, + 194, 194, 194, 195, 194, 196, 194, 196, 197, 198, 198, 199, 198, 198, 198, 198, + 198, 198, 198, 198, 198, 198, 198, 200, 198, 198, 198, 198, 198, 201, 178, 178, + 178, 178, 178, 178, 178, 178, 202, 26, 203, 203, 203, 204, 203, 205, 203, 205, + 206, 203, 207, 207, 207, 208, 209, 26, 210, 210, 210, 210, 210, 211, 210, 210, + 210, 212, 210, 213, 194, 194, 194, 194, 214, 214, 214, 215, 216, 216, 216, 216, + 216, 216, 216, 217, 216, 216, 216, 218, 216, 219, 216, 219, 216, 220, 9, 9, + 9, 221, 26, 26, 26, 26, 26, 26, 222, 222, 222, 222, 222, 222, 222, 222, + 222, 223, 222, 222, 222, 222, 222, 224, 225, 225, 225, 225, 225, 225, 225, 225, + 226, 226, 226, 226, 226, 226, 227, 228, 229, 229, 229, 229, 229, 229, 229, 230, + 229, 231, 232, 232, 232, 232, 232, 232, 18, 233, 165, 165, 165, 165, 165, 234, + 225, 26, 235, 9, 236, 237, 238, 239, 2, 2, 2, 2, 240, 241, 2, 2, + 2, 2, 2, 242, 243, 244, 2, 245, 2, 2, 2, 2, 2, 2, 2, 246, + 9, 9, 9, 9, 9, 9, 9, 9, 14, 14, 247, 247, 14, 14, 14, 14, + 247, 247, 14, 248, 14, 14, 14, 247, 14, 14, 14, 14, 14, 14, 249, 14, + 249, 14, 250, 251, 14, 14, 252, 253, 0, 254, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 255, 0, 256, 257, 0, 258, 2, 259, 0, 0, 0, 0, + 260, 26, 9, 9, 9, 9, 261, 26, 0, 0, 0, 0, 262, 263, 4, 0, + 0, 264, 0, 0, 2, 2, 2, 2, 2, 265, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 257, 26, 26, 26, 0, 265, 26, 26, 0, 0, 0, 0, - 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 267, 0, - 0, 0, 268, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 269, 269, 269, 269, 269, 269, 269, 269, 269, 269, 269, 269, 2, 2, 2, 2, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 270, 271, - 164, 164, 164, 164, 165, 166, 272, 272, 272, 272, 272, 272, 272, 273, 274, 273, - 169, 169, 171, 26, 171, 171, 171, 171, 171, 171, 171, 171, 18, 18, 18, 18, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 275, 26, 26, 26, 26, - 276, 276, 276, 277, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 278, 26, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 279, 26, 26, 26, 0, 280, - 281, 0, 0, 0, 282, 283, 0, 284, 285, 286, 286, 286, 286, 286, 286, 286, - 286, 286, 287, 288, 289, 290, 290, 290, 290, 290, 290, 290, 290, 290, 290, 291, - 292, 293, 293, 293, 293, 293, 294, 168, 168, 168, 168, 168, 168, 168, 168, 168, - 168, 295, 0, 0, 293, 293, 293, 293, 0, 0, 0, 0, 280, 26, 290, 290, - 168, 168, 168, 295, 0, 0, 0, 0, 0, 0, 0, 0, 168, 168, 168, 296, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 290, 290, 290, 290, 290, 297, - 290, 290, 290, 290, 290, 290, 290, 290, 290, 290, 290, 0, 0, 0, 0, 0, - 276, 276, 276, 276, 276, 276, 276, 276, 0, 0, 0, 0, 0, 0, 0, 0, - 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, - 298, 299, 298, 298, 298, 298, 298, 298, 300, 26, 301, 301, 301, 301, 301, 301, - 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, - 302, 302, 302, 302, 302, 303, 26, 26, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 26, - 0, 0, 0, 0, 305, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 306, 2, 2, 2, 2, 2, 2, 2, 307, 308, 309, 26, 26, 310, 2, - 311, 311, 311, 311, 311, 312, 0, 313, 314, 314, 314, 314, 314, 314, 314, 26, - 315, 315, 315, 315, 315, 315, 315, 315, 316, 317, 315, 318, 53, 53, 53, 53, - 319, 319, 319, 319, 319, 320, 321, 321, 321, 321, 322, 323, 168, 168, 168, 324, - 325, 325, 325, 325, 325, 325, 325, 325, 325, 326, 325, 327, 163, 163, 163, 328, - 329, 329, 329, 329, 329, 329, 330, 26, 329, 331, 329, 332, 163, 163, 163, 163, - 333, 333, 333, 333, 333, 333, 333, 333, 334, 26, 26, 335, 336, 336, 337, 26, - 338, 338, 338, 26, 171, 171, 2, 2, 2, 2, 2, 339, 340, 341, 175, 175, - 175, 175, 175, 175, 175, 175, 175, 175, 336, 336, 336, 336, 336, 342, 336, 343, - 168, 168, 168, 168, 344, 26, 168, 168, 295, 345, 168, 168, 168, 168, 168, 344, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 258, 26, 26, 26, + 0, 266, 26, 26, 0, 0, 0, 0, 267, 267, 267, 267, 267, 267, 267, 267, + 267, 267, 267, 267, 267, 267, 267, 267, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 268, 0, 0, 0, 269, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 270, 270, 270, 270, 270, 270, 270, 270, + 270, 270, 270, 270, 2, 2, 2, 2, 17, 17, 17, 17, 17, 17, 17, 17, + 17, 17, 17, 17, 17, 17, 271, 272, 165, 165, 165, 165, 166, 167, 273, 273, + 273, 273, 273, 273, 273, 274, 275, 274, 170, 170, 172, 26, 172, 172, 172, 172, + 172, 172, 172, 172, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 276, 26, 26, 26, 26, 277, 277, 277, 278, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 277, 279, 26, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 280, 26, 26, 26, 0, 281, 282, 0, 0, 0, 283, 284, 0, 285, + 286, 287, 287, 287, 287, 287, 287, 287, 287, 287, 288, 289, 290, 291, 291, 291, + 291, 291, 291, 291, 291, 291, 291, 292, 293, 294, 294, 294, 294, 294, 295, 169, + 169, 169, 169, 169, 169, 169, 169, 169, 169, 296, 0, 0, 294, 294, 294, 294, + 0, 0, 0, 0, 281, 26, 291, 291, 169, 169, 169, 296, 0, 0, 0, 0, + 0, 0, 0, 0, 169, 169, 169, 297, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 291, 291, 291, 291, 291, 298, 291, 291, 291, 291, 291, 291, 291, 291, + 291, 291, 291, 0, 0, 0, 0, 0, 277, 277, 277, 277, 277, 277, 277, 277, + 0, 0, 0, 0, 0, 0, 0, 0, 299, 299, 299, 299, 299, 299, 299, 299, + 299, 299, 299, 299, 299, 299, 299, 299, 299, 300, 299, 299, 299, 299, 299, 299, + 301, 26, 302, 302, 302, 302, 302, 302, 303, 303, 303, 303, 303, 303, 303, 303, + 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 304, 26, 26, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 305, 305, 305, 305, + 305, 305, 305, 305, 305, 305, 305, 26, 0, 0, 0, 0, 306, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 307, 2, 2, 2, 2, 2, 2, + 2, 308, 309, 310, 26, 26, 311, 2, 312, 312, 312, 312, 312, 313, 0, 314, + 315, 315, 315, 315, 315, 315, 315, 26, 316, 316, 316, 316, 316, 316, 316, 316, + 317, 318, 316, 319, 53, 53, 53, 53, 320, 320, 320, 320, 320, 321, 322, 322, + 322, 322, 323, 324, 169, 169, 169, 325, 326, 326, 326, 326, 326, 326, 326, 326, + 326, 327, 326, 328, 164, 164, 164, 329, 330, 330, 330, 330, 330, 330, 331, 26, + 330, 332, 330, 333, 164, 164, 164, 164, 334, 334, 334, 334, 334, 334, 334, 334, + 335, 26, 26, 336, 337, 337, 338, 26, 339, 339, 339, 26, 172, 172, 2, 2, + 2, 2, 2, 340, 341, 342, 176, 176, 176, 176, 176, 176, 176, 176, 176, 176, + 337, 337, 337, 337, 337, 343, 337, 344, 169, 169, 169, 169, 345, 26, 169, 169, + 296, 346, 169, 169, 169, 169, 169, 345, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 280, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 347, 26, 26, 26, 26, 348, 26, 349, 350, 25, 25, 351, 352, + 353, 25, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 354, 26, 355, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 356, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 357, 31, 31, 31, 31, 31, + 31, 358, 26, 26, 26, 26, 31, 31, 9, 9, 0, 314, 9, 359, 0, 0, + 0, 0, 360, 0, 258, 281, 361, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 362, 363, 0, 0, 0, 1, 2, 2, 3, + 1, 2, 2, 3, 364, 291, 290, 291, 291, 291, 291, 365, 169, 169, 169, 296, + 366, 366, 366, 367, 258, 258, 26, 368, 369, 370, 369, 369, 371, 369, 369, 372, + 369, 373, 369, 373, 26, 26, 26, 26, 369, 369, 369, 369, 369, 369, 369, 369, + 369, 369, 369, 369, 369, 369, 369, 374, 375, 0, 0, 0, 0, 0, 376, 0, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 253, 0, 377, 378, 26, 26, 26, + 26, 26, 0, 0, 0, 0, 0, 379, 380, 380, 380, 381, 382, 382, 382, 382, + 382, 382, 383, 26, 384, 0, 0, 281, 385, 385, 385, 385, 386, 387, 388, 388, + 388, 389, 390, 390, 390, 390, 390, 391, 392, 392, 392, 393, 394, 394, 394, 394, + 395, 394, 396, 26, 26, 26, 26, 26, 397, 397, 397, 397, 397, 397, 397, 397, + 397, 397, 398, 398, 398, 398, 398, 398, 399, 399, 399, 400, 399, 401, 402, 402, + 402, 402, 403, 402, 402, 402, 402, 403, 404, 404, 404, 404, 404, 26, 405, 405, + 405, 405, 405, 405, 406, 407, 408, 409, 408, 409, 410, 408, 411, 408, 411, 412, + 26, 26, 26, 26, 26, 26, 26, 26, 413, 413, 413, 413, 413, 413, 413, 413, + 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 414, 26, + 413, 413, 415, 26, 413, 26, 26, 26, 416, 2, 2, 2, 2, 2, 417, 308, + 26, 26, 26, 26, 26, 26, 26, 26, 418, 419, 420, 420, 420, 420, 421, 422, + 423, 423, 424, 423, 425, 425, 425, 425, 426, 426, 426, 427, 428, 426, 26, 26, + 26, 26, 26, 26, 429, 429, 430, 431, 432, 432, 432, 433, 434, 434, 434, 435, + 26, 26, 26, 26, 26, 26, 26, 26, 436, 436, 436, 436, 437, 437, 437, 438, + 437, 437, 439, 437, 437, 437, 437, 437, 440, 441, 442, 443, 444, 444, 445, 446, + 444, 447, 444, 447, 448, 448, 448, 448, 449, 449, 449, 449, 26, 26, 26, 26, + 450, 450, 450, 450, 451, 452, 451, 26, 453, 453, 453, 453, 453, 453, 454, 455, + 456, 456, 457, 456, 458, 458, 459, 458, 460, 460, 461, 462, 26, 463, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 464, 464, 464, 464, 464, 464, 464, 464, + 464, 465, 26, 26, 26, 26, 26, 26, 466, 466, 466, 466, 466, 466, 467, 26, + 466, 466, 466, 466, 466, 466, 467, 468, 469, 469, 469, 469, 469, 26, 469, 470, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 31, 31, 31, 50, 471, 471, 471, 471, 471, 472, 473, 26, + 26, 26, 26, 26, 26, 26, 26, 474, 475, 475, 475, 475, 475, 26, 476, 476, + 476, 476, 476, 477, 26, 26, 478, 478, 478, 479, 26, 26, 26, 26, 480, 480, + 480, 481, 26, 26, 482, 482, 483, 26, 484, 484, 484, 484, 484, 484, 484, 484, + 484, 485, 486, 484, 484, 484, 485, 487, 488, 488, 488, 488, 488, 488, 488, 488, + 489, 490, 491, 491, 491, 492, 491, 493, 494, 494, 494, 494, 494, 494, 495, 494, + 494, 26, 496, 496, 496, 496, 497, 26, 498, 498, 498, 498, 498, 498, 498, 498, + 498, 498, 498, 498, 499, 137, 500, 26, 501, 501, 502, 501, 501, 501, 501, 501, + 503, 26, 26, 26, 26, 26, 26, 26, 504, 505, 506, 507, 506, 508, 509, 509, + 509, 509, 509, 509, 509, 510, 509, 511, 512, 513, 514, 515, 515, 516, 517, 518, + 513, 519, 520, 521, 522, 523, 523, 26, 524, 524, 524, 524, 524, 524, 524, 524, + 524, 524, 524, 525, 526, 26, 26, 26, 527, 527, 527, 527, 527, 527, 527, 527, + 527, 26, 527, 528, 26, 26, 26, 26, 529, 529, 529, 529, 529, 529, 530, 529, + 529, 529, 529, 530, 26, 26, 26, 26, 531, 531, 531, 531, 531, 531, 531, 531, + 532, 26, 531, 533, 198, 534, 26, 26, 535, 535, 535, 535, 535, 535, 535, 536, + 535, 536, 26, 26, 26, 26, 26, 26, 537, 537, 537, 538, 537, 539, 537, 537, + 540, 26, 26, 26, 26, 26, 26, 26, 541, 541, 541, 541, 541, 541, 541, 542, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 543, 543, 543, 543, + 543, 543, 543, 543, 543, 543, 544, 545, 546, 547, 548, 549, 549, 549, 550, 551, + 546, 26, 549, 552, 26, 26, 26, 26, 26, 26, 26, 26, 553, 554, 553, 553, + 553, 553, 553, 554, 555, 26, 26, 26, 556, 556, 556, 556, 556, 556, 556, 556, + 556, 26, 557, 557, 557, 557, 557, 557, 557, 557, 557, 557, 558, 26, 178, 178, + 559, 559, 559, 559, 559, 559, 559, 560, 53, 561, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 562, 563, 562, 562, 562, 562, 564, 562, + 565, 26, 562, 562, 562, 566, 567, 567, 567, 567, 568, 567, 567, 569, 570, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 571, 572, 573, 573, 573, 573, 571, 574, + 573, 26, 573, 575, 576, 577, 578, 578, 578, 579, 580, 581, 578, 582, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 583, 583, 583, 584, 585, 585, 586, 585, 585, 585, 585, 587, + 585, 585, 585, 588, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 589, 26, + 108, 108, 108, 108, 108, 108, 590, 591, 592, 592, 592, 592, 592, 592, 592, 592, + 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 593, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 592, 592, 592, 592, 592, 592, 592, 592, + 592, 592, 592, 592, 592, 594, 595, 26, 592, 592, 592, 592, 592, 592, 592, 592, + 596, 26, 26, 26, 26, 26, 26, 26, 26, 26, 597, 597, 597, 597, 597, 597, + 597, 597, 597, 597, 597, 597, 598, 26, 599, 599, 599, 599, 599, 599, 599, 599, + 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, + 599, 599, 600, 26, 26, 26, 26, 26, 601, 601, 601, 601, 601, 601, 601, 601, + 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, + 602, 26, 26, 26, 26, 26, 26, 26, 305, 305, 305, 305, 305, 305, 305, 305, + 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 603, + 604, 604, 604, 605, 604, 606, 607, 607, 607, 607, 607, 607, 607, 607, 607, 608, + 607, 609, 610, 610, 610, 611, 611, 26, 612, 612, 612, 612, 612, 612, 612, 612, + 613, 26, 612, 614, 614, 612, 612, 615, 612, 612, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 279, 276, 276, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 346, 26, 26, 26, 26, - 347, 26, 348, 349, 25, 25, 350, 351, 352, 25, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 353, 26, 354, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 355, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 356, 31, 31, 31, 31, 31, 31, 357, 26, 26, 26, 26, 31, 31, - 9, 9, 0, 313, 9, 358, 0, 0, 0, 0, 359, 0, 257, 280, 360, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 361, - 362, 0, 0, 0, 1, 2, 2, 3, 1, 2, 2, 3, 363, 290, 289, 290, - 290, 290, 290, 364, 168, 168, 168, 295, 365, 365, 365, 366, 257, 257, 26, 367, - 368, 369, 368, 368, 370, 368, 368, 371, 368, 372, 368, 372, 26, 26, 26, 26, - 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 373, - 374, 0, 0, 0, 0, 0, 375, 0, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 252, 0, 376, 377, 26, 26, 26, 26, 26, 0, 0, 0, 0, 0, 378, - 379, 379, 379, 380, 381, 381, 381, 381, 381, 381, 382, 26, 383, 0, 0, 280, - 384, 384, 384, 384, 385, 386, 387, 387, 387, 388, 389, 389, 389, 389, 389, 390, - 391, 391, 391, 392, 393, 393, 393, 393, 394, 393, 395, 26, 26, 26, 26, 26, - 396, 396, 396, 396, 396, 396, 396, 396, 396, 396, 397, 397, 397, 397, 397, 397, - 398, 398, 398, 399, 398, 400, 401, 401, 401, 401, 402, 401, 401, 401, 401, 402, - 403, 403, 403, 403, 403, 26, 404, 404, 404, 404, 404, 404, 405, 406, 407, 408, - 407, 408, 409, 407, 410, 407, 410, 411, 26, 26, 26, 26, 26, 26, 26, 26, - 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, - 412, 412, 412, 412, 412, 412, 413, 26, 412, 412, 414, 26, 412, 26, 26, 26, - 415, 2, 2, 2, 2, 2, 416, 307, 26, 26, 26, 26, 26, 26, 26, 26, - 417, 418, 419, 419, 419, 419, 420, 421, 422, 422, 423, 422, 424, 424, 424, 424, - 425, 425, 425, 426, 427, 425, 26, 26, 26, 26, 26, 26, 428, 428, 429, 430, - 431, 431, 431, 432, 433, 433, 433, 434, 26, 26, 26, 26, 26, 26, 26, 26, - 435, 435, 435, 435, 436, 436, 436, 437, 436, 436, 438, 436, 436, 436, 436, 436, - 439, 440, 441, 442, 443, 443, 444, 445, 443, 446, 443, 446, 447, 447, 447, 447, - 448, 448, 448, 448, 26, 26, 26, 26, 449, 449, 449, 449, 450, 451, 450, 26, - 452, 452, 452, 452, 452, 452, 453, 454, 455, 455, 456, 455, 457, 457, 458, 457, - 459, 459, 460, 461, 26, 462, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 463, 463, 463, 463, 463, 463, 463, 463, 463, 464, 26, 26, 26, 26, 26, 26, - 465, 465, 465, 465, 465, 465, 466, 26, 465, 465, 465, 465, 465, 465, 466, 467, - 468, 468, 468, 468, 468, 26, 468, 469, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 31, 31, 31, 50, - 470, 470, 470, 470, 470, 471, 472, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 473, 473, 473, 473, 473, 26, 474, 474, 474, 474, 474, 475, 26, 26, 476, 476, - 476, 477, 26, 26, 26, 26, 478, 478, 478, 479, 26, 26, 480, 480, 481, 26, - 482, 482, 482, 482, 482, 482, 482, 482, 482, 483, 484, 482, 482, 482, 483, 485, - 486, 486, 486, 486, 486, 486, 486, 486, 487, 488, 489, 489, 489, 490, 489, 491, - 492, 492, 492, 492, 492, 492, 493, 492, 492, 26, 494, 494, 494, 494, 495, 26, - 496, 496, 496, 496, 496, 496, 496, 496, 496, 496, 496, 496, 497, 137, 498, 26, - 499, 499, 500, 499, 499, 499, 499, 501, 26, 26, 26, 26, 26, 26, 26, 26, - 502, 503, 504, 505, 504, 506, 507, 507, 507, 507, 507, 507, 507, 508, 507, 509, - 510, 511, 512, 513, 513, 514, 515, 516, 511, 517, 518, 519, 520, 521, 521, 26, - 522, 522, 522, 522, 522, 522, 522, 522, 522, 522, 522, 523, 524, 26, 26, 26, - 525, 525, 525, 525, 525, 525, 525, 525, 525, 26, 525, 526, 26, 26, 26, 26, - 527, 527, 527, 527, 527, 527, 528, 527, 527, 527, 527, 528, 26, 26, 26, 26, - 529, 529, 529, 529, 529, 529, 529, 529, 530, 26, 529, 531, 197, 532, 26, 26, - 533, 533, 533, 533, 533, 533, 533, 534, 533, 534, 26, 26, 26, 26, 26, 26, - 535, 535, 535, 536, 535, 537, 535, 535, 538, 26, 26, 26, 26, 26, 26, 26, - 539, 539, 539, 539, 539, 539, 539, 540, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 541, 541, 541, 541, 541, 541, 541, 541, 541, 541, 542, 543, - 544, 545, 546, 547, 547, 547, 548, 549, 544, 26, 547, 550, 26, 26, 26, 26, - 26, 26, 26, 26, 551, 552, 551, 551, 551, 551, 551, 552, 553, 26, 26, 26, - 554, 554, 554, 554, 554, 554, 554, 554, 554, 26, 555, 555, 555, 555, 555, 555, - 555, 555, 555, 555, 556, 26, 177, 177, 557, 557, 557, 557, 557, 557, 557, 558, - 559, 560, 559, 559, 559, 559, 561, 559, 562, 26, 559, 559, 559, 563, 564, 564, - 564, 564, 565, 564, 564, 566, 567, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 568, 569, 570, 570, 570, 570, 568, 571, 570, 26, 570, 572, 573, 574, 575, 575, - 575, 576, 577, 578, 575, 579, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 580, 580, 580, 581, - 26, 26, 26, 26, 26, 26, 582, 26, 108, 108, 108, 108, 108, 108, 583, 584, - 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, - 585, 585, 585, 586, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 587, 588, 26, - 585, 585, 585, 585, 585, 585, 585, 585, 589, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 590, 590, 590, 590, 590, 590, 590, 590, 590, 590, 590, 590, 591, 26, - 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, - 592, 592, 592, 592, 592, 593, 592, 594, 26, 26, 26, 26, 26, 26, 26, 26, - 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, - 595, 595, 595, 595, 595, 595, 595, 595, 596, 26, 26, 26, 26, 26, 26, 26, - 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, - 304, 304, 304, 304, 304, 304, 304, 597, 598, 598, 598, 599, 598, 600, 601, 601, - 601, 601, 601, 601, 601, 601, 601, 602, 601, 603, 604, 604, 604, 605, 605, 26, - 606, 606, 606, 606, 606, 606, 606, 606, 607, 26, 606, 608, 608, 606, 606, 609, - 606, 606, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 610, 610, 610, 610, 610, 610, 610, 610, - 610, 610, 610, 611, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 612, 612, 612, 612, 612, 612, 612, 612, 612, 613, 612, 612, 612, 612, 612, 612, - 612, 614, 612, 612, 26, 26, 26, 26, 26, 26, 26, 26, 615, 26, 346, 26, - 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, - 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 26, - 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, - 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 618, 26, 26, 26, 26, 26, - 616, 619, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 620, 621, - 622, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, - 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, - 286, 286, 286, 286, 623, 26, 26, 26, 26, 26, 624, 26, 625, 26, 626, 626, - 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, - 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 627, - 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 629, 628, 630, - 628, 631, 628, 632, 280, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 9, 9, 9, 9, 9, 633, 9, 9, 220, 26, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 280, 26, 26, 26, 26, 26, 26, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 275, 26, - 0, 0, 0, 0, 257, 362, 0, 0, 0, 0, 0, 0, 634, 635, 0, 636, - 637, 638, 0, 0, 0, 639, 0, 0, 0, 0, 0, 0, 0, 265, 26, 26, - 14, 14, 14, 14, 14, 14, 14, 14, 246, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 0, 0, 280, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 257, 26, 0, 0, 0, 259, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 254, 0, 0, 0, 0, 0, - 0, 0, 0, 254, 640, 641, 0, 642, 643, 0, 0, 0, 0, 0, 0, 0, - 268, 644, 254, 254, 0, 0, 0, 645, 646, 647, 648, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 275, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 267, 0, 0, 0, 0, 0, 0, - 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, - 649, 650, 26, 651, 652, 649, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 2, 2, 2, 347, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 653, 269, 269, 654, 655, 656, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 657, 657, 657, 657, 657, 658, 657, 659, 657, 660, 26, 26, 26, 26, 26, 26, - 26, 26, 661, 661, 661, 662, 26, 26, 663, 663, 663, 663, 663, 663, 663, 664, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 171, 665, 169, 171, - 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, - 666, 666, 666, 666, 666, 666, 666, 666, 667, 666, 668, 26, 26, 26, 26, 26, - 669, 669, 669, 669, 669, 669, 669, 669, 669, 670, 669, 671, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 362, 0, - 0, 0, 0, 0, 0, 0, 376, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 362, 0, 0, 0, 0, 0, 0, 275, 26, 26, 26, 26, 26, 26, 26, 26, - 672, 31, 31, 31, 673, 674, 675, 676, 677, 678, 673, 679, 673, 675, 675, 680, - 31, 681, 31, 682, 683, 681, 31, 682, 26, 26, 26, 26, 26, 26, 51, 26, - 0, 0, 0, 0, 0, 280, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 280, 26, 0, 257, 362, 0, 362, 0, 362, 0, 0, 0, 275, 26, - 0, 0, 0, 0, 0, 275, 26, 26, 26, 26, 26, 26, 684, 0, 0, 0, - 685, 26, 0, 0, 0, 0, 0, 280, 0, 259, 313, 26, 275, 26, 26, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 686, 0, 376, 0, 376, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 280, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 259, 0, 280, 259, 26, - 0, 280, 0, 0, 0, 0, 0, 0, 0, 26, 0, 313, 0, 0, 0, 0, - 0, 26, 0, 0, 0, 275, 313, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 280, 26, 0, 275, 376, 376, - 257, 26, 0, 0, 0, 376, 0, 265, 275, 26, 0, 313, 0, 26, 257, 26, - 0, 0, 359, 0, 0, 0, 0, 0, 0, 265, 26, 26, 26, 26, 0, 313, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 26, 26, 26, 26, - 276, 276, 276, 276, 276, 276, 276, 687, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 279, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 276, 346, 26, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 687, 26, 26, 26, - 276, 276, 276, 279, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 688, 26, 26, 26, 26, 26, 26, - 689, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 617, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 618, 618, 618, 618, 618, 618, 618, 618, + 618, 619, 618, 618, 618, 618, 618, 618, 618, 620, 618, 618, 26, 26, 26, 26, + 26, 26, 26, 26, 621, 26, 347, 26, 622, 622, 622, 622, 622, 622, 622, 622, + 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, + 622, 622, 622, 622, 622, 622, 622, 26, 623, 623, 623, 623, 623, 623, 623, 623, + 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, + 623, 623, 624, 26, 26, 26, 26, 26, 622, 625, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 626, 627, 628, 287, 287, 287, 287, 287, 287, 287, + 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, + 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 629, 26, 630, 26, + 26, 26, 631, 26, 632, 26, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, + 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, + 633, 633, 633, 633, 633, 633, 633, 634, 635, 635, 635, 635, 635, 635, 635, 635, + 635, 635, 635, 635, 635, 636, 635, 637, 635, 638, 635, 639, 281, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 9, 9, 9, 9, 9, 640, 9, 9, + 221, 26, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 281, 26, 26, 26, 26, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 276, 26, 0, 0, 0, 0, 258, 363, 0, 0, + 0, 0, 0, 0, 641, 642, 0, 643, 644, 645, 0, 0, 0, 646, 0, 0, + 0, 0, 0, 0, 0, 266, 26, 26, 14, 14, 14, 14, 14, 14, 14, 14, + 247, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 0, 0, 281, 26, 0, 0, 281, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 258, 26, 0, 0, 0, 260, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 255, 0, 0, 0, 0, 0, 0, 0, 0, 255, 647, 648, 0, 649, + 650, 0, 0, 0, 0, 0, 0, 0, 269, 651, 255, 255, 0, 0, 0, 652, + 653, 654, 655, 0, 0, 0, 0, 0, 0, 0, 0, 0, 276, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 268, 0, 0, 0, 0, 0, 0, 656, 656, 656, 656, 656, 656, 656, 656, + 656, 656, 656, 656, 656, 656, 656, 656, 656, 657, 26, 658, 659, 656, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 2, 2, 2, 348, 660, 308, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 661, 270, 270, 662, 663, 664, 18, 18, + 18, 18, 18, 18, 18, 665, 26, 26, 26, 666, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 667, 667, 667, 667, 667, 668, 667, 669, + 667, 670, 26, 26, 26, 26, 26, 26, 26, 26, 671, 671, 671, 672, 26, 26, + 673, 673, 673, 673, 673, 673, 673, 674, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 675, 675, 675, 675, 675, 676, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 172, 677, 170, 172, 678, 678, 678, 678, 678, 678, 678, 678, + 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, + 679, 678, 680, 26, 26, 26, 26, 26, 681, 681, 681, 681, 681, 681, 681, 681, + 681, 682, 681, 683, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 363, 0, 0, 0, 0, 0, 0, 0, 377, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 363, 0, 0, 0, 0, 0, 0, 276, + 26, 26, 26, 26, 26, 26, 26, 26, 684, 31, 31, 31, 685, 686, 687, 688, + 689, 690, 685, 691, 685, 687, 687, 692, 31, 693, 31, 694, 695, 693, 31, 694, + 26, 26, 26, 26, 26, 26, 51, 26, 0, 0, 0, 0, 0, 281, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 281, 26, 0, 258, 363, 0, + 363, 0, 363, 0, 0, 0, 276, 26, 0, 0, 0, 0, 0, 276, 26, 26, + 26, 26, 26, 26, 696, 0, 0, 0, 697, 26, 0, 0, 0, 0, 0, 281, + 0, 260, 314, 26, 276, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 698, 0, 377, 0, 377, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 258, 699, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 314, 0, 281, 260, 26, 0, 281, 0, 0, 0, 0, 0, 0, + 0, 26, 0, 314, 0, 0, 0, 0, 0, 26, 0, 0, 0, 276, 314, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 281, 26, 0, 276, 0, 377, 0, 260, 0, 0, 0, 0, 0, 269, + 276, 696, 0, 281, 0, 260, 0, 260, 0, 0, 360, 0, 0, 0, 0, 0, + 0, 266, 26, 26, 26, 26, 0, 314, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 26, 26, 26, 26, 277, 277, 277, 277, 277, 277, 277, 347, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 280, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 347, 26, 277, 277, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 700, 26, 26, 26, 277, 277, 277, 280, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 701, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 702, 26, 26, 26, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, + 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 939, 940, 941, 942, 946, 948, 0, 962, + 969, 970, 971, 976,1001,1002,1003,1008, 0,1033,1040,1041,1042,1043,1047, 0, + 0,1080,1081,1082,1086,1110, 0, 0,1124,1125,1126,1127,1131,1133, 0,1147, + 1154,1155,1156,1161,1187,1188,1189,1193, 0,1219,1226,1227,1228,1229,1233, 0, + 0,1267,1268,1269,1273,1298, 0,1303, 943,1128, 944,1129, 954,1139, 958,1143, + 959,1144, 960,1145, 961,1146, 964,1149, 0, 0, 973,1158, 974,1159, 975,1160, + 983,1168, 978,1163, 988,1173, 990,1175, 991,1176, 993,1178, 994,1179, 0, 0, + 1004,1190,1005,1191,1006,1192,1014,1199,1007, 0, 0, 0,1016,1201,1020,1206, + 0,1022,1208,1025,1211,1023,1209, 0, 0, 0, 0,1032,1218,1037,1223,1035, + 1221, 0, 0, 0,1044,1230,1045,1231,1049,1235, 0, 0,1058,1244,1064,1250, + 1060,1246,1066,1252,1067,1253,1072,1258,1069,1255,1077,1264,1074,1261, 0, 0, + 1083,1270,1084,1271,1085,1272,1088,1275,1089,1276,1096,1283,1103,1290,1111,1299, + 1115,1118,1307,1120,1309,1121,1310, 0,1053,1239, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,1093,1280, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 949,1134,1010,1195,1050,1236,1090,1277,1341,1368,1340, + 1367,1342,1369,1339,1366, 0,1320,1347,1418,1419,1323,1350, 0, 0, 992,1177, + 1018,1204,1055,1241,1416,1417,1415,1424,1202, 0, 0, 0, 987,1172, 0, 0, + 1031,1217,1321,1348,1322,1349,1338,1365, 950,1135, 951,1136, 979,1164, 980,1165, + 1011,1196,1012,1197,1051,1237,1052,1238,1061,1247,1062,1248,1091,1278,1092,1279, + 1071,1257,1076,1263, 0, 0, 997,1182, 0, 0, 0, 0, 0, 0, 945,1130, + 982,1167,1337,1364,1335,1362,1046,1232,1422,1423,1113,1301, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 8, 9, 0, 10,1425, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0,1314,1427, 5, + 1434,1438,1443, 0,1450, 0,1455,1461,1514, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1446,1458,1468,1476,1480,1486,1517, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1489,1503,1494,1500,1508, 0, 0, 0, 0,1520,1521, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0,1526,1528, 0,1525, 0, 0, 0,1522, + 0, 0, 0, 0,1536,1532,1539, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1534, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1556, 0, 0, 0, 0, 0, 0,1548,1550, 0,1547, 0, 0, 0,1567, + 0, 0, 0, 0,1558,1554,1561, 0, 0, 0, 0, 0, 0, 0,1568,1569, + 0, 0, 0, 0, 0, 0, 0, 0, 0,1529,1551, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0,1523,1545,1524,1546, 0, 0,1527,1549, + 0, 0,1570,1571,1530,1552,1531,1553, 0, 0,1533,1555,1535,1557,1537,1559, + 0, 0,1572,1573,1544,1566,1538,1560,1540,1562,1541,1563,1542,1564, 0, 0, + 1543,1565, 0, 0, 0, 0, 0, 0, 0, 0,1606,1607,1609,1608,1610, 0, + 0, 0, 0, 0, 0, 0, 0, 0,1613, 0,1611, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1612, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1620, 0, 0, 0, 0, 0, 0, 0,1623, 0, 0,1624, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1614,1615,1616,1617,1618,1619,1621,1622, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1628,1629, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1625,1626, 0,1627, 0, 0, 0,1634, 0, 0,1635, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1630,1631,1632, 0, 0,1633, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1639, 0, 0,1638,1640, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1636,1637, 0, 0, 0, 0, 0, 0,1641, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1642,1644,1643, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1645, 0, 0, 0, 0, 0, 0, 0,1646, 0, 0, 0, 0, 0, 0,1648, + 1649, 0,1647,1650, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1651,1653,1652, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1654, 0,1655,1657,1656, 0, 0, 0, 0,1659, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1660, 0, 0, 0, 0,1661, 0, 0, 0, 0,1662, + 0, 0, 0, 0,1663, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1658, 0, 0, 0, 0, 0, 0, 0, 0, 0,1664, 0,1665,1673, 0, + 1674, 0, 0, 0, 0, 0, 0, 0, 0,1666, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1668, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1669, 0, 0, 0, 0,1670, 0, 0, 0, 0,1671, + 0, 0, 0, 0,1672, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1667, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1675, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1676, 0, + 1677, 0,1678, 0,1679, 0,1680, 0, 0, 0,1681, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1682, 0,1683, 0, 0,1684,1685, 0,1686, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 953,1138, 955,1140, 956,1141, 957,1142, + 1324,1351, 963,1148, 965,1150, 968,1153, 966,1151, 967,1152,1378,1380,1379,1381, + 984,1169, 985,1170,1420,1421, 986,1171, 989,1174, 995,1180, 998,1183, 996,1181, + 999,1184,1000,1185,1015,1200,1329,1356,1017,1203,1019,1205,1021,1207,1024,1210, + 1687,1688,1027,1213,1026,1212,1028,1214,1029,1215,1030,1216,1034,1220,1036,1222, + 1039,1225,1038,1224,1334,1361,1336,1363,1382,1384,1383,1385,1056,1242,1057,1243, + 1059,1245,1063,1249,1689,1690,1065,1251,1068,1254,1070,1256,1386,1387,1388,1389, + 1691,1692,1073,1259,1075,1262,1079,1266,1078,1265,1095,1282,1098,1285,1097,1284, + 1390,1391,1392,1393,1099,1286,1100,1287,1101,1288,1102,1289,1105,1292,1104,1291, + 1106,1294,1107,1295,1108,1296,1114,1302,1119,1308,1122,1311,1123,1312,1186,1260, + 1293,1305, 0,1394, 0, 0, 0, 0, 952,1137, 947,1132,1317,1344,1316,1343, + 1319,1346,1318,1345,1693,1695,1371,1375,1370,1374,1373,1377,1372,1376,1694,1696, + 981,1166, 977,1162, 972,1157,1326,1353,1325,1352,1328,1355,1327,1354,1697,1698, + 1009,1194,1013,1198,1054,1240,1048,1234,1331,1358,1330,1357,1333,1360,1332,1359, + 1699,1700,1396,1401,1395,1400,1398,1403,1397,1402,1399,1404,1094,1281,1087,1274, + 1406,1411,1405,1410,1408,1413,1407,1412,1409,1414,1109,1297,1117,1306,1116,1304, + 1112,1300, 0, 0, 0, 0, 0, 0,1471,1472,1701,1705,1702,1706,1703,1707, + 1430,1431,1715,1719,1716,1720,1717,1721,1477,1478,1729,1731,1730,1732, 0, 0, + 1435,1436,1733,1735,1734,1736, 0, 0,1481,1482,1737,1741,1738,1742,1739,1743, + 1439,1440,1751,1755,1752,1756,1753,1757,1490,1491,1765,1768,1766,1769,1767,1770, + 1447,1448,1771,1774,1772,1775,1773,1776,1495,1496,1777,1779,1778,1780, 0, 0, + 1451,1452,1781,1783,1782,1784, 0, 0,1504,1505,1785,1788,1786,1789,1787,1790, + 0,1459, 0,1791, 0,1792, 0,1793,1509,1510,1794,1798,1795,1799,1796,1800, + 1462,1463,1808,1812,1809,1813,1810,1814,1467, 21,1475, 22,1479, 23,1485, 24, + 1493, 27,1499, 28,1507, 29, 0, 0,1704,1708,1709,1710,1711,1712,1713,1714, + 1718,1722,1723,1724,1725,1726,1727,1728,1740,1744,1745,1746,1747,1748,1749,1750, + 1754,1758,1759,1760,1761,1762,1763,1764,1797,1801,1802,1803,1804,1805,1806,1807, + 1811,1815,1816,1817,1818,1819,1820,1821,1470,1469,1822,1474,1465, 0,1473,1825, + 1429,1428,1426, 12,1432, 0, 26, 0, 0,1315,1823,1484,1466, 0,1483,1829, + 1433, 13,1437, 14,1441,1826,1827,1828,1488,1487,1513, 19, 0, 0,1492,1515, + 1445,1444,1442, 15, 0,1831,1832,1833,1502,1501,1516, 25,1497,1498,1506,1518, + 1457,1456,1454, 17,1453,1313, 11, 3, 0, 0,1824,1512,1519, 0,1511,1830, + 1449, 16,1460, 18,1464, 4, 0, 0, 30, 31, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 0, + 0, 0, 2, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1834,1835, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1836, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1837,1839,1838, 0, 0, 0, 0,1840, 0, 0, 0, + 0,1841, 0, 0,1842, 0, 0, 0, 0, 0, 0, 0,1843, 0,1844, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0,1845, 0, 0,1846, 0, 0,1847, + 0,1848, 0, 0, 0, 0, 0, 0, 937, 0,1850, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1849, 936, 938,1851,1852, 0, 0,1853,1854, 0, 0, + 1855,1856, 0, 0, 0, 0, 0, 0,1857,1858, 0, 0,1861,1862, 0, 0, + 1863,1864, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1867,1868,1869,1870,1859,1860,1865,1866, 0, 0, 0, 0, + 0, 0,1871,1872,1873,1874, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 32, 33, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1875, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1877, 0,1878, 0,1879, 0,1880, 0,1881, 0,1882, 0, + 1883, 0,1884, 0,1885, 0,1886, 0,1887, 0,1888, 0, 0,1889, 0,1890, + 0,1891, 0, 0, 0, 0, 0, 0,1892,1893, 0,1894,1895, 0,1896,1897, + 0,1898,1899, 0,1900,1901, 0, 0, 0, 0, 0, 0,1876, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1902, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1904, 0,1905, 0,1906, 0,1907, 0,1908, 0,1909, 0, + 1910, 0,1911, 0,1912, 0,1913, 0,1914, 0,1915, 0, 0,1916, 0,1917, + 0,1918, 0, 0, 0, 0, 0, 0,1919,1920, 0,1921,1922, 0,1923,1924, + 0,1925,1926, 0,1927,1928, 0, 0, 0, 0, 0, 0,1903, 0, 0,1929, + 1930,1931,1932, 0, 0, 0,1933, 0, 710, 385, 724, 715, 455, 103, 186, 825, + 825, 242, 751, 205, 241, 336, 524, 601, 663, 676, 688, 738, 411, 434, 474, 500, + 649, 746, 799, 108, 180, 416, 482, 662, 810, 275, 462, 658, 692, 344, 618, 679, + 293, 388, 440, 492, 740, 116, 146, 168, 368, 414, 481, 527, 606, 660, 665, 722, + 781, 803, 809, 538, 553, 588, 642, 758, 811, 701, 233, 299, 573, 612, 487, 540, + 714, 779, 232, 267, 412, 445, 457, 585, 594, 766, 167, 613, 149, 148, 560, 589, + 648, 768, 708, 345, 411, 704, 105, 259, 313, 496, 518, 174, 542, 120, 307, 101, + 430, 372, 584, 183, 228, 529, 650, 697, 424, 732, 428, 349, 632, 355, 517, 110, + 135, 147, 403, 580, 624, 700, 750, 170, 193, 245, 297, 374, 463, 543, 763, 801, + 812, 815, 162, 384, 420, 730, 287, 330, 337, 366, 459, 476, 509, 558, 591, 610, + 726, 652, 734, 759, 154, 163, 198, 473, 683, 697, 292, 311, 353, 423, 572, 494, + 113, 217, 259, 280, 314, 499, 506, 603, 608, 752, 778, 782, 788, 117, 557, 748, + 774, 320, 109, 126, 260, 265, 373, 411, 479, 523, 655, 737, 823, 380, 765, 161, + 395, 398, 438, 451, 502, 516, 537, 583, 791, 136, 340, 769, 122, 273, 446, 727, + 305, 322, 400, 496, 771, 155, 190, 269, 377, 391, 406, 432, 501, 519, 599, 684, + 687, 749, 776, 175, 452, 191, 480, 510, 659, 772, 805, 813, 397, 444, 619, 566, + 568, 575, 491, 471, 707, 111, 636, 156, 153, 288, 346, 578, 256, 435, 383, 729, + 680, 767, 694, 295, 128, 210, 0, 0, 227, 0, 379, 0, 0, 150, 493, 525, + 544, 551, 552, 556, 783, 576, 604, 0, 661, 0, 703, 0, 0, 735, 743, 0, + 0, 0, 793, 794, 795, 808, 741, 773, 118, 127, 130, 166, 169, 177, 207, 213, + 215, 226, 229, 268, 270, 317, 327, 329, 335, 369, 375, 381, 404, 441, 448, 458, + 477, 484, 503, 539, 545, 547, 546, 548, 549, 550, 554, 555, 561, 564, 569, 591, + 593, 595, 598, 607, 620, 625, 625, 651, 690, 695, 705, 706, 716, 717, 733, 735, + 777, 786, 790, 315, 869, 623, 0, 0, 102, 145, 134, 115, 129, 138, 165, 171, + 207, 202, 206, 212, 227, 231, 240, 243, 250, 254, 294, 296, 303, 308, 319, 325, + 321, 329, 326, 335, 341, 357, 360, 362, 370, 379, 388, 389, 393, 421, 424, 438, + 456, 454, 458, 465, 477, 535, 485, 490, 493, 507, 512, 514, 521, 522, 525, 526, + 528, 533, 532, 541, 565, 569, 574, 586, 591, 597, 607, 637, 647, 674, 691, 693, + 695, 698, 703, 699, 705, 704, 702, 706, 709, 717, 728, 736, 747, 754, 770, 777, + 783, 784, 786, 787, 790, 802, 825, 848, 847, 857, 55, 65, 66, 883, 892, 916, + 822, 824, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1586, 0,1605, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1602,1603,1934,1935,1574,1575,1576,1577,1579,1580,1581,1583,1584, 0, + 1585,1587,1588,1589,1591, 0,1592, 0,1593,1594, 0,1595,1596, 0,1598,1599, + 1600,1601,1604,1582,1578,1590,1597, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1936, 0,1937, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1938, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1939,1940, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1941,1942, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1944,1943, 0,1945, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1946,1947, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1948, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1949,1950,1951,1952,1953,1954,1955, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 939, 940, 941, 942, 946, 948, 0, 962, 969, 970, 971, 976,1001,1002,1003,1008, - 0,1033,1040,1041,1042,1043,1047, 0, 0,1080,1081,1082,1086,1110, 0, 0, - 1124,1125,1126,1127,1131,1133, 0,1147,1154,1155,1156,1161,1187,1188,1189,1193, - 0,1219,1226,1227,1228,1229,1233, 0, 0,1267,1268,1269,1273,1298, 0,1303, - 943,1128, 944,1129, 954,1139, 958,1143, 959,1144, 960,1145, 961,1146, 964,1149, - 0, 0, 973,1158, 974,1159, 975,1160, 983,1168, 978,1163, 988,1173, 990,1175, - 991,1176, 993,1178, 994,1179, 0, 0,1004,1190,1005,1191,1006,1192,1014,1199, - 1007, 0, 0, 0,1016,1201,1020,1206, 0,1022,1208,1025,1211,1023,1209, 0, - 0, 0, 0,1032,1218,1037,1223,1035,1221, 0, 0, 0,1044,1230,1045,1231, - 1049,1235, 0, 0,1058,1244,1064,1250,1060,1246,1066,1252,1067,1253,1072,1258, - 1069,1255,1077,1264,1074,1261, 0, 0,1083,1270,1084,1271,1085,1272,1088,1275, - 1089,1276,1096,1283,1103,1290,1111,1299,1115,1118,1307,1120,1309,1121,1310, 0, - 1053,1239, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1093, - 1280, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 949,1134,1010, - 1195,1050,1236,1090,1277,1341,1368,1340,1367,1342,1369,1339,1366, 0,1320,1347, - 1418,1419,1323,1350, 0, 0, 992,1177,1018,1204,1055,1241,1416,1417,1415,1424, - 1202, 0, 0, 0, 987,1172, 0, 0,1031,1217,1321,1348,1322,1349,1338,1365, - 950,1135, 951,1136, 979,1164, 980,1165,1011,1196,1012,1197,1051,1237,1052,1238, - 1061,1247,1062,1248,1091,1278,1092,1279,1071,1257,1076,1263, 0, 0, 997,1182, - 0, 0, 0, 0, 0, 0, 945,1130, 982,1167,1337,1364,1335,1362,1046,1232, - 1422,1423,1113,1301, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 8, 9, 0, 10,1425, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 0, 0, 0,1314,1427, 5,1434,1438,1443, 0,1450, 0,1455,1461, - 1514, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1446,1458,1468,1476,1480,1486, - 1517, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1489,1503,1494,1500,1508, 0, - 0, 0, 0,1520,1521, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1526,1528, 0,1525, 0, 0, 0,1522, 0, 0, 0, 0,1536,1532,1539, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1534, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1556, 0, 0, 0, 0, 0, 0, - 1548,1550, 0,1547, 0, 0, 0,1567, 0, 0, 0, 0,1558,1554,1561, 0, - 0, 0, 0, 0, 0, 0,1568,1569, 0, 0, 0, 0, 0, 0, 0, 0, - 0,1529,1551, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1523,1545,1524,1546, 0, 0,1527,1549, 0, 0,1570,1571,1530,1552,1531,1553, - 0, 0,1533,1555,1535,1557,1537,1559, 0, 0,1572,1573,1544,1566,1538,1560, - 1540,1562,1541,1563,1542,1564, 0, 0,1543,1565, 0, 0, 0, 0, 0, 0, - 0, 0,1606,1607,1609,1608,1610, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1613, 0,1611, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,1612, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1620, 0, 0, 0, 0, 0, 0, - 0,1623, 0, 0,1624, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1614,1615,1616,1617,1618,1619,1621,1622, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1628,1629, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1625,1626, 0,1627, - 0, 0, 0,1634, 0, 0,1635, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1630,1631,1632, 0, 0,1633, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1639, 0, 0,1638,1640, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1636,1637, 0, 0, - 0, 0, 0, 0,1641, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1642,1644,1643, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1645, 0, 0, 0, 0, 0, 0, 0, - 1646, 0, 0, 0, 0, 0, 0,1648,1649, 0,1647,1650, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1651,1653,1652, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1654, 0,1655,1657,1656, 0, - 0, 0, 0,1659, 0, 0, 0, 0, 0, 0, 0, 0, 0,1660, 0, 0, - 0, 0,1661, 0, 0, 0, 0,1662, 0, 0, 0, 0,1663, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1658, 0, 0, 0, 0, 0, 0, - 0, 0, 0,1664, 0,1665,1673, 0,1674, 0, 0, 0, 0, 0, 0, 0, - 0,1666, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,1668, 0, 0, 0, 0, 0, 0, 0, 0, 0,1669, 0, 0, - 0, 0,1670, 0, 0, 0, 0,1671, 0, 0, 0, 0,1672, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1667, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0,1675, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0,1676, 0,1677, 0,1678, 0,1679, 0,1680, 0, - 0, 0,1681, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1682, 0,1683, 0, 0, - 1684,1685, 0,1686, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 953,1138, 955,1140, 956,1141, 957,1142,1324,1351, 963,1148, 965,1150, 968,1153, - 966,1151, 967,1152,1378,1380,1379,1381, 984,1169, 985,1170,1420,1421, 986,1171, - 989,1174, 995,1180, 998,1183, 996,1181, 999,1184,1000,1185,1015,1200,1329,1356, - 1017,1203,1019,1205,1021,1207,1024,1210,1687,1688,1027,1213,1026,1212,1028,1214, - 1029,1215,1030,1216,1034,1220,1036,1222,1039,1225,1038,1224,1334,1361,1336,1363, - 1382,1384,1383,1385,1056,1242,1057,1243,1059,1245,1063,1249,1689,1690,1065,1251, - 1068,1254,1070,1256,1386,1387,1388,1389,1691,1692,1073,1259,1075,1262,1079,1266, - 1078,1265,1095,1282,1098,1285,1097,1284,1390,1391,1392,1393,1099,1286,1100,1287, - 1101,1288,1102,1289,1105,1292,1104,1291,1106,1294,1107,1295,1108,1296,1114,1302, - 1119,1308,1122,1311,1123,1312,1186,1260,1293,1305, 0,1394, 0, 0, 0, 0, - 952,1137, 947,1132,1317,1344,1316,1343,1319,1346,1318,1345,1693,1695,1371,1375, - 1370,1374,1373,1377,1372,1376,1694,1696, 981,1166, 977,1162, 972,1157,1326,1353, - 1325,1352,1328,1355,1327,1354,1697,1698,1009,1194,1013,1198,1054,1240,1048,1234, - 1331,1358,1330,1357,1333,1360,1332,1359,1699,1700,1396,1401,1395,1400,1398,1403, - 1397,1402,1399,1404,1094,1281,1087,1274,1406,1411,1405,1410,1408,1413,1407,1412, - 1409,1414,1109,1297,1117,1306,1116,1304,1112,1300, 0, 0, 0, 0, 0, 0, - 1471,1472,1701,1705,1702,1706,1703,1707,1430,1431,1715,1719,1716,1720,1717,1721, - 1477,1478,1729,1731,1730,1732, 0, 0,1435,1436,1733,1735,1734,1736, 0, 0, - 1481,1482,1737,1741,1738,1742,1739,1743,1439,1440,1751,1755,1752,1756,1753,1757, - 1490,1491,1765,1768,1766,1769,1767,1770,1447,1448,1771,1774,1772,1775,1773,1776, - 1495,1496,1777,1779,1778,1780, 0, 0,1451,1452,1781,1783,1782,1784, 0, 0, - 1504,1505,1785,1788,1786,1789,1787,1790, 0,1459, 0,1791, 0,1792, 0,1793, - 1509,1510,1794,1798,1795,1799,1796,1800,1462,1463,1808,1812,1809,1813,1810,1814, - 1467, 21,1475, 22,1479, 23,1485, 24,1493, 27,1499, 28,1507, 29, 0, 0, - 1704,1708,1709,1710,1711,1712,1713,1714,1718,1722,1723,1724,1725,1726,1727,1728, - 1740,1744,1745,1746,1747,1748,1749,1750,1754,1758,1759,1760,1761,1762,1763,1764, - 1797,1801,1802,1803,1804,1805,1806,1807,1811,1815,1816,1817,1818,1819,1820,1821, - 1470,1469,1822,1474,1465, 0,1473,1825,1429,1428,1426, 12,1432, 0, 26, 0, - 0,1315,1823,1484,1466, 0,1483,1829,1433, 13,1437, 14,1441,1826,1827,1828, - 1488,1487,1513, 19, 0, 0,1492,1515,1445,1444,1442, 15, 0,1831,1832,1833, - 1502,1501,1516, 25,1497,1498,1506,1518,1457,1456,1454, 17,1453,1313, 11, 3, - 0, 0,1824,1512,1519, 0,1511,1830,1449, 16,1460, 18,1464, 4, 0, 0, - 30, 31, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 20, 0, 0, 0, 2, 6, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1834,1835, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1836, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1837,1839,1838, - 0, 0, 0, 0,1840, 0, 0, 0, 0,1841, 0, 0,1842, 0, 0, 0, - 0, 0, 0, 0,1843, 0,1844, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0,1845, 0, 0,1846, 0, 0,1847, 0,1848, 0, 0, 0, 0, 0, 0, - 937, 0,1850, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1849, 936, 938, - 1851,1852, 0, 0,1853,1854, 0, 0,1855,1856, 0, 0, 0, 0, 0, 0, - 1857,1858, 0, 0,1861,1862, 0, 0,1863,1864, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1867,1868,1869,1870, - 1859,1860,1865,1866, 0, 0, 0, 0, 0, 0,1871,1872,1873,1874, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 33, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1875, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1877, 0,1878, 0, - 1879, 0,1880, 0,1881, 0,1882, 0,1883, 0,1884, 0,1885, 0,1886, 0, - 1887, 0,1888, 0, 0,1889, 0,1890, 0,1891, 0, 0, 0, 0, 0, 0, - 1892,1893, 0,1894,1895, 0,1896,1897, 0,1898,1899, 0,1900,1901, 0, 0, - 0, 0, 0, 0,1876, 0, 0, 0, 0, 0, 0, 0, 0, 0,1902, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1904, 0,1905, 0, - 1906, 0,1907, 0,1908, 0,1909, 0,1910, 0,1911, 0,1912, 0,1913, 0, - 1914, 0,1915, 0, 0,1916, 0,1917, 0,1918, 0, 0, 0, 0, 0, 0, - 1919,1920, 0,1921,1922, 0,1923,1924, 0,1925,1926, 0,1927,1928, 0, 0, - 0, 0, 0, 0,1903, 0, 0,1929,1930,1931,1932, 0, 0, 0,1933, 0, - 710, 385, 724, 715, 455, 103, 186, 825, 825, 242, 751, 205, 241, 336, 524, 601, - 663, 676, 688, 738, 411, 434, 474, 500, 649, 746, 799, 108, 180, 416, 482, 662, - 810, 275, 462, 658, 692, 344, 618, 679, 293, 388, 440, 492, 740, 116, 146, 168, - 368, 414, 481, 527, 606, 660, 665, 722, 781, 803, 809, 538, 553, 588, 642, 758, - 811, 701, 233, 299, 573, 612, 487, 540, 714, 779, 232, 267, 412, 445, 457, 585, - 594, 766, 167, 613, 149, 148, 560, 589, 648, 768, 708, 345, 411, 704, 105, 259, - 313, 496, 518, 174, 542, 120, 307, 101, 430, 372, 584, 183, 228, 529, 650, 697, - 424, 732, 428, 349, 632, 355, 517, 110, 135, 147, 403, 580, 624, 700, 750, 170, - 193, 245, 297, 374, 463, 543, 763, 801, 812, 815, 162, 384, 420, 730, 287, 330, - 337, 366, 459, 476, 509, 558, 591, 610, 726, 652, 734, 759, 154, 163, 198, 473, - 683, 697, 292, 311, 353, 423, 572, 494, 113, 217, 259, 280, 314, 499, 506, 603, - 608, 752, 778, 782, 788, 117, 557, 748, 774, 320, 109, 126, 260, 265, 373, 411, - 479, 523, 655, 737, 823, 380, 765, 161, 395, 398, 438, 451, 502, 516, 537, 583, - 791, 136, 340, 769, 122, 273, 446, 727, 305, 322, 400, 496, 771, 155, 190, 269, - 377, 391, 406, 432, 501, 519, 599, 684, 687, 749, 776, 175, 452, 191, 480, 510, - 659, 772, 805, 813, 397, 444, 619, 566, 568, 575, 491, 471, 707, 111, 636, 156, - 153, 288, 346, 578, 256, 435, 383, 729, 680, 767, 694, 295, 128, 210, 0, 0, - 227, 0, 379, 0, 0, 150, 493, 525, 544, 551, 552, 556, 783, 576, 604, 0, - 661, 0, 703, 0, 0, 735, 743, 0, 0, 0, 793, 794, 795, 808, 741, 773, - 118, 127, 130, 166, 169, 177, 207, 213, 215, 226, 229, 268, 270, 317, 327, 329, - 335, 369, 375, 381, 404, 441, 448, 458, 477, 484, 503, 539, 545, 547, 546, 548, - 549, 550, 554, 555, 561, 564, 569, 591, 593, 595, 598, 607, 620, 625, 625, 651, - 690, 695, 705, 706, 716, 717, 733, 735, 777, 786, 790, 315, 869, 623, 0, 0, - 102, 145, 134, 115, 129, 138, 165, 171, 207, 202, 206, 212, 227, 231, 240, 243, - 250, 254, 294, 296, 303, 308, 319, 325, 321, 329, 326, 335, 341, 357, 360, 362, - 370, 379, 388, 389, 393, 421, 424, 438, 456, 454, 458, 465, 477, 535, 485, 490, - 493, 507, 512, 514, 521, 522, 525, 526, 528, 533, 532, 541, 565, 569, 574, 586, - 591, 597, 607, 637, 647, 674, 691, 693, 695, 698, 703, 699, 705, 704, 702, 706, - 709, 717, 728, 736, 747, 754, 770, 777, 783, 784, 786, 787, 790, 802, 825, 848, - 847, 857, 55, 65, 66, 883, 892, 916, 822, 824, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1586, 0,1605, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1602,1603,1934,1935,1574,1575, - 1576,1577,1579,1580,1581,1583,1584, 0,1585,1587,1588,1589,1591, 0,1592, 0, - 1593,1594, 0,1595,1596, 0,1598,1599,1600,1601,1604,1582,1578,1590,1597, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1936, 0,1937, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1938, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1939,1940, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1941,1942, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1944,1943, 0,1945, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1946,1947, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1948, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1949,1950, - 1951,1952,1953,1954,1955, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1956,1957,1958,1960,1959, - 1961, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 106, 104, 107, 826, 114, 118, 119, 121, 123, 124, 127, 125, 34, 830, 130, 131, - 132, 137, 827, 35, 133, 139, 829, 142, 143, 112, 144, 145, 924, 151, 152, 37, - 157, 158, 159, 160, 38, 165, 166, 169, 171, 172, 173, 174, 176, 177, 178, 179, - 181, 182, 182, 182, 833, 468, 184, 185, 834, 187, 188, 189, 196, 192, 194, 195, - 197, 199, 200, 201, 203, 204, 204, 206, 208, 209, 211, 218, 213, 219, 214, 216, - 153, 234, 221, 222, 223, 220, 225, 224, 230, 835, 235, 236, 237, 238, 239, 244, - 836, 837, 247, 248, 249, 246, 251, 39, 40, 253, 255, 255, 838, 257, 258, 259, - 261, 839, 262, 263, 301, 264, 41, 266, 270, 272, 271, 841, 274, 842, 277, 276, - 278, 281, 282, 42, 283, 284, 285, 286, 43, 843, 44, 289, 290, 291, 293, 934, - 298, 845, 845, 621, 300, 300, 45, 852, 894, 302, 304, 46, 306, 309, 310, 312, - 316, 48, 47, 317, 846, 318, 323, 324, 325, 324, 328, 329, 333, 331, 332, 334, - 335, 336, 338, 339, 342, 343, 347, 351, 849, 350, 348, 352, 354, 359, 850, 361, - 358, 356, 49, 363, 365, 367, 364, 50, 369, 371, 851, 376, 386, 378, 53, 381, - 52, 51, 140, 141, 387, 382, 614, 78, 388, 389, 390, 394, 392, 856, 54, 399, - 396, 402, 404, 858, 405, 401, 407, 55, 408, 409, 410, 413, 859, 415, 56, 417, - 860, 418, 57, 419, 422, 424, 425, 861, 840, 862, 426, 863, 429, 431, 427, 433, - 437, 441, 438, 439, 442, 443, 864, 436, 449, 450, 58, 454, 453, 865, 447, 460, - 866, 867, 461, 466, 465, 464, 59, 467, 470, 469, 472, 828, 475, 868, 478, 870, - 483, 485, 486, 871, 488, 489, 872, 873, 495, 497, 60, 498, 61, 61, 504, 505, - 507, 508, 511, 62, 513, 874, 515, 875, 518, 844, 520, 876, 877, 878, 63, 64, - 528, 880, 879, 881, 882, 530, 531, 531, 533, 66, 534, 67, 68, 884, 536, 538, - 541, 69, 885, 549, 886, 887, 556, 559, 70, 561, 562, 563, 888, 889, 889, 567, - 71, 890, 570, 571, 72, 891, 577, 73, 581, 579, 582, 893, 587, 74, 590, 592, - 596, 75, 895, 896, 76, 897, 600, 898, 602, 605, 607, 899, 900, 609, 901, 611, - 853, 77, 615, 616, 79, 617, 252, 902, 903, 854, 855, 621, 622, 731, 80, 627, - 626, 628, 164, 629, 630, 631, 633, 904, 632, 634, 639, 640, 635, 641, 646, 651, - 638, 643, 644, 645, 905, 907, 906, 81, 653, 654, 656, 911, 657, 908, 82, 83, - 909, 910, 84, 664, 665, 666, 667, 669, 668, 671, 670, 674, 672, 673, 675, 85, - 677, 678, 86, 681, 682, 912, 685, 686, 87, 689, 36, 913, 914, 88, 89, 696, - 702, 709, 711, 915, 712, 713, 718, 719, 917, 831, 721, 720, 723, 832, 725, 728, - 918, 919, 739, 742, 744, 920, 745, 753, 756, 757, 755, 760, 761, 921, 762, 90, - 764, 922, 91, 775, 279, 780, 923, 925, 92, 93, 785, 926, 94, 927, 787, 787, - 789, 928, 792, 95, 796, 797, 798, 800, 96, 929, 802, 804, 806, 97, 98, 807, - 930, 99, 931, 932, 933, 814, 100, 816, 817, 818, 819, 820, 821, 935, 0, 0, + 0, 0, 0,1956,1957,1958,1960,1959,1961, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 106, 104, 107, 826, 114, 118, 119, 121, + 123, 124, 127, 125, 34, 830, 130, 131, 132, 137, 827, 35, 133, 139, 829, 142, + 143, 112, 144, 145, 924, 151, 152, 37, 157, 158, 159, 160, 38, 165, 166, 169, + 171, 172, 173, 174, 176, 177, 178, 179, 181, 182, 182, 182, 833, 468, 184, 185, + 834, 187, 188, 189, 196, 192, 194, 195, 197, 199, 200, 201, 203, 204, 204, 206, + 208, 209, 211, 218, 213, 219, 214, 216, 153, 234, 221, 222, 223, 220, 225, 224, + 230, 835, 235, 236, 237, 238, 239, 244, 836, 837, 247, 248, 249, 246, 251, 39, + 40, 253, 255, 255, 838, 257, 258, 259, 261, 839, 262, 263, 301, 264, 41, 266, + 270, 272, 271, 841, 274, 842, 277, 276, 278, 281, 282, 42, 283, 284, 285, 286, + 43, 843, 44, 289, 290, 291, 293, 934, 298, 845, 845, 621, 300, 300, 45, 852, + 894, 302, 304, 46, 306, 309, 310, 312, 316, 48, 47, 317, 846, 318, 323, 324, + 325, 324, 328, 329, 333, 331, 332, 334, 335, 336, 338, 339, 342, 343, 347, 351, + 849, 350, 348, 352, 354, 359, 850, 361, 358, 356, 49, 363, 365, 367, 364, 50, + 369, 371, 851, 376, 386, 378, 53, 381, 52, 51, 140, 141, 387, 382, 614, 78, + 388, 389, 390, 394, 392, 856, 54, 399, 396, 402, 404, 858, 405, 401, 407, 55, + 408, 409, 410, 413, 859, 415, 56, 417, 860, 418, 57, 419, 422, 424, 425, 861, + 840, 862, 426, 863, 429, 431, 427, 433, 437, 441, 438, 439, 442, 443, 864, 436, + 449, 450, 58, 454, 453, 865, 447, 460, 866, 867, 461, 466, 465, 464, 59, 467, + 470, 469, 472, 828, 475, 868, 478, 870, 483, 485, 486, 871, 488, 489, 872, 873, + 495, 497, 60, 498, 61, 61, 504, 505, 507, 508, 511, 62, 513, 874, 515, 875, + 518, 844, 520, 876, 877, 878, 63, 64, 528, 880, 879, 881, 882, 530, 531, 531, + 533, 66, 534, 67, 68, 884, 536, 538, 541, 69, 885, 549, 886, 887, 556, 559, + 70, 561, 562, 563, 888, 889, 889, 567, 71, 890, 570, 571, 72, 891, 577, 73, + 581, 579, 582, 893, 587, 74, 590, 592, 596, 75, 895, 896, 76, 897, 600, 898, + 602, 605, 607, 899, 900, 609, 901, 611, 853, 77, 615, 616, 79, 617, 252, 902, + 903, 854, 855, 621, 622, 731, 80, 627, 626, 628, 164, 629, 630, 631, 633, 904, + 632, 634, 639, 640, 635, 641, 646, 651, 638, 643, 644, 645, 905, 907, 906, 81, + 653, 654, 656, 911, 657, 908, 82, 83, 909, 910, 84, 664, 665, 666, 667, 669, + 668, 671, 670, 674, 672, 673, 675, 85, 677, 678, 86, 681, 682, 912, 685, 686, + 87, 689, 36, 913, 914, 88, 89, 696, 702, 709, 711, 915, 712, 713, 718, 719, + 917, 831, 721, 720, 723, 832, 725, 728, 918, 919, 739, 742, 744, 920, 745, 753, + 756, 757, 755, 760, 761, 921, 762, 90, 764, 922, 91, 775, 279, 780, 923, 925, + 92, 93, 785, 926, 94, 927, 787, 787, 789, 928, 792, 95, 796, 797, 798, 800, + 96, 929, 802, 804, 806, 97, 98, 807, 930, 99, 931, 932, 933, 814, 100, 816, + 817, 818, 819, 820, 821, 935, 0, 0, }; static const int16_t _hb_ucd_i16[196] = @@ -2792,12 +2822,12 @@ _hb_ucd_i16[196] = static inline uint_fast8_t _hb_ucd_gc (unsigned u) { - return u<1114110u?_hb_ucd_u8[6664+(((_hb_ucd_u8[1296+(((_hb_ucd_u16[((_hb_ucd_u8[544+(((_hb_ucd_u8[u>>1>>3>>3>>4])<<4)+((u>>1>>3>>3)&15u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:2; + return u<1114110u?_hb_ucd_u8[6800+(((_hb_ucd_u8[1312+(((_hb_ucd_u16[((_hb_ucd_u8[544+(((_hb_ucd_u8[u>>1>>3>>3>>4])<<4)+((u>>1>>3>>3)&15u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:2; } static inline uint_fast8_t _hb_ucd_ccc (unsigned u) { - return u<125259u?_hb_ucd_u8[8984+(((_hb_ucd_u8[7960+(((_hb_ucd_u8[7288+(((_hb_ucd_u8[7042+(u>>2>>3>>4)])<<4)+((u>>2>>3)&15u))])<<3)+((u>>2)&7u))])<<2)+((u)&3u))]:0; + return u<125259u?_hb_ucd_u8[9184+(((_hb_ucd_u8[8128+(((_hb_ucd_u8[7424+(((_hb_ucd_u8[7178+(u>>2>>3>>4)])<<4)+((u>>2>>3)&15u))])<<3)+((u>>2)&7u))])<<2)+((u)&3u))]:0; } static inline unsigned _hb_ucd_b4 (const uint8_t* a, unsigned i) @@ -2807,24 +2837,24 @@ _hb_ucd_b4 (const uint8_t* a, unsigned i) static inline int_fast16_t _hb_ucd_bmg (unsigned u) { - return u<65380u?_hb_ucd_i16[((_hb_ucd_u8[9728+(((_hb_ucd_u8[9608+(((_hb_ucd_b4(9480+_hb_ucd_u8,u>>2>>3>>3))<<3)+((u>>2>>3)&7u))])<<3)+((u>>2)&7u))])<<2)+((u)&3u)]:0; + return u<65380u?_hb_ucd_i16[((_hb_ucd_u8[9932+(((_hb_ucd_u8[9812+(((_hb_ucd_b4(9684+_hb_ucd_u8,u>>2>>3>>3))<<3)+((u>>2>>3)&7u))])<<3)+((u>>2)&7u))])<<2)+((u)&3u)]:0; } static inline uint_fast8_t _hb_ucd_sc (unsigned u) { - return u<918000u?_hb_ucd_u8[11234+(((_hb_ucd_u16[2000+(((_hb_ucd_u8[10514+(((_hb_ucd_u8[10064+(u>>3>>4>>4)])<<4)+((u>>3>>4)&15u))])<<4)+((u>>3)&15u))])<<3)+((u)&7u))]:2; + return u<918000u?_hb_ucd_u8[11454+(((_hb_ucd_u16[2040+(((_hb_ucd_u8[10718+(((_hb_ucd_u8[10268+(u>>3>>4>>4)])<<4)+((u>>3>>4)&15u))])<<4)+((u>>3)&15u))])<<3)+((u)&7u))]:2; } static inline uint_fast16_t _hb_ucd_dm (unsigned u) { - return u<195102u?_hb_ucd_u16[5888+(((_hb_ucd_u8[17136+(((_hb_ucd_u8[16754+(u>>4>>5)])<<5)+((u>>4)&31u))])<<4)+((u)&15u))]:0; + return u<195102u?_hb_ucd_u16[6008+(((_hb_ucd_u8[17460+(((_hb_ucd_u8[17078+(u>>4>>5)])<<5)+((u>>4)&31u))])<<4)+((u)&15u))]:0; } #elif !defined(HB_NO_UCD_UNASSIGNED) static const uint8_t -_hb_ucd_u8[17564] = +_hb_ucd_u8[17868] = { 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 9, 10, 7, 7, 7, 7, 11, 12, 13, 13, 13, 14, @@ -2832,7 +2862,7 @@ _hb_ucd_u8[17564] = 25, 26, 22, 22, 22, 27, 28, 29, 22, 30, 31, 32, 33, 34, 35, 36, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 37, 7, 38, 39, 7, 40, 7, 7, 7, 41, 22, 42, - 7, 7, 43, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, + 7, 7, 43, 7, 44, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, @@ -2854,12 +2884,12 @@ _hb_ucd_u8[17564] = 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, - 44, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, + 45, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 45, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 46, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 47, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 34, 35, 36, 37, 38, 39, 34, 34, 34, 40, 41, 42, 43, @@ -2878,35 +2908,36 @@ _hb_ucd_u8[17564] = 118,119,120,121,122,123,124,125,126,127,128,129, 34, 34,130,131, 132,133,134,135,136,137,138,139,140,141,142,122,143,144,145,146, 147,148,149,150,151,152,153,122,154,155,122,156,157,158,159,122, - 160,161,162,163,164,165,122,122,166,167,168,169,122,170,122,171, - 34, 34, 34, 34, 34, 34, 34,172,173, 34,174,122,122,122,122,122, - 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,175, - 34, 34, 34, 34, 34, 34, 34, 34,176,122,122,122,122,122,122,122, + 160,161,162,163,164,165,166,122,167,168,169,170,122,171,172,173, + 34, 34, 34, 34, 34, 34, 34,174,175, 34,176,122,122,122,122,122, + 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,177, + 34, 34, 34, 34, 34, 34, 34, 34,178,122,122,122,122,122,122,122, 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,122, - 122,122,122,122,122,122,122,122, 34, 34, 34, 34,177,122,122,122, - 34, 34, 34, 34,178,179,180,181,122,122,122,122,182,183,184,185, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,186, - 34, 34, 34, 34, 34, 34, 34, 34, 34,187,188,122,122,122,122,122, - 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,189, - 34, 34,190, 34, 34,191,122,122,122,122,122,122,122,122,122,122, - 122,122,122,122,122,122,122,122,192,193,122,122,122,122,122,122, - 122,122,122,122,122,122,122,122,122,122,122,122,122,122,194,195, - 69,196,197,198,199,200,201,122,202,203,204,205,206,207,208,209, - 69, 69, 69, 69,210,211,122,122,122,122,122,122,122,122,212,122, - 213,122,214,122,122,215,122,122,122,122,122,122,122,122,122,216, - 34,217,218,122,122,122,122,122,219,220,221,122,222,223,122,122, - 224,225,226,227,228,122, 69,229, 69, 69, 69, 69, 69,230,231,232, - 233,234, 69, 69,235,236, 69,237,122,122,122,122,122,122,122,122, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,238, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,239, 34, - 240, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,241, 34, 34, - 34, 34, 34, 34, 34, 34, 34,242,122,122,122,122,122,122,122,122, - 34, 34, 34, 34,243,122,122,122,122,122,122,122,122,122,122,122, - 34, 34, 34, 34, 34, 34,244,122,122,122,122,122,122,122,122,122, - 245,122,246,247,122,122,122,122,122,122,122,122,122,122,122,122, - 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,248, - 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,249, + 122,122,122,122,122,122,122,122, 34, 34, 34, 34,179,122,122,122, + 34, 34, 34, 34,180,181,182,183,122,122,122,122,184,185,186,187, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,188, + 34, 34, 34, 34, 34, 34, 34, 34, 34,189,190,122,122,122,122,122, + 122,122,122,122,122,122,122,122,122,122,122,122,122,122,122,191, + 34, 34,192, 34, 34,193,122,122,122,122,122,122,122,122,122,122, + 122,122,122,122,122,122,122,122,194,195,122,122,122,122,122,122, + 122,122,122,122,122,122,122,122,122,122,122,122,122,122,196,197, + 69,198,199,200,201,202,203,122,204,205,206,207,208,209,210,211, + 69, 69, 69, 69,212,213,122,122,122,122,122,122,122,122,214,122, + 215,216,217,122,122,218,122,122,122,219,122,122,122,122,122,220, + 34,221,222,122,122,122,122,122,223,224,225,122,226,227,122,122, + 228,229,230,231,232,122, 69,233, 69, 69, 69, 69, 69,234,235,236, + 237,238, 69, 69,239,240, 69,241,122,122,122,122,122,122,122,122, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,242, 34, 34, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,243, 34, + 244, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, + 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,245, 34, 34, + 34, 34, 34, 34, 34, 34, 34,246,122,122,122,122,122,122,122,122, + 34, 34, 34, 34,247,122,122,122,122,122,122,122,122,122,122,122, + 34, 34, 34, 34, 34, 34,248, 34, 34, 34, 34, 34, 34, 34, 34, 34, + 34, 34, 34, 34, 34, 34, 34,249,122,122,122,122,122,122,122,122, + 250,122,251,252,122,122,122,122,122,122,122,122,122,122,122,122, + 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,253, + 107,107,107,107,107,107,107,107,107,107,107,107,107,107,107,254, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 2, 4, 5, 6, 2, 7, 7, 7, 7, 7, 2, 8, 9, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 12, 13, 14, 15, 16, 16, 16, 16, 16, 16, 16, @@ -2969,7 +3000,7 @@ _hb_ucd_u8[17564] = 44, 44, 57, 80, 36, 61, 62, 44, 44, 44, 44, 93, 27, 27, 27, 91, 70, 86, 72, 36, 36, 36, 61, 36, 36, 36, 62, 36, 36, 44, 71, 87, 86, 86, 90, 85, 90, 86, 43, 44, 44, 44, 89, 90, 44, 44, 62, 61, - 62, 61, 44, 44, 44, 44, 44, 44, 43, 86, 36, 36, 36, 36, 61, 36, + 62, 94, 44, 44, 44, 44, 44, 44, 43, 86, 36, 36, 36, 36, 61, 36, 36, 36, 36, 36, 36, 70, 71, 86, 87, 43, 80, 86, 90, 86, 87, 77, 44, 44, 36, 94, 27, 27, 27, 95, 27, 27, 27, 27, 91, 36, 36, 36, 57, 86, 62, 36, 36, 36, 36, 36, 36, 36, 36, 61, 44, 36, 36, 36, @@ -2979,7 +3010,7 @@ _hb_ucd_u8[17564] = 36, 36, 36, 75, 43, 43, 43, 60, 7, 7, 7, 7, 7, 2, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 62, 61, 61, 36, 36, 61, 36, 36, 36, 36, 62, 62, 36, 36, 36, 36, 70, 36, 43, 43, 43, 43, 71, 44, - 36, 36, 61, 81, 43, 43, 43, 44, 7, 7, 7, 7, 7, 44, 36, 36, + 36, 36, 61, 81, 43, 43, 43, 80, 7, 7, 7, 7, 7, 44, 36, 36, 77, 67, 2, 2, 2, 2, 2, 2, 2, 97, 97, 67, 43, 67, 67, 67, 7, 7, 7, 7, 7, 27, 27, 27, 27, 27, 50, 50, 50, 4, 4, 86, 36, 36, 36, 36, 62, 36, 36, 36, 36, 36, 36, 36, 36, 36, 61, 44, @@ -3146,18 +3177,19 @@ _hb_ucd_u8[17564] = 44, 44, 44, 44,179, 27, 27, 27, 11, 47, 44, 44, 44, 44, 44, 44, 16,110, 44, 44, 44, 27, 27, 27, 36, 36, 43, 43, 44, 44, 44, 44, 27, 27, 27, 27, 27, 27, 27,100, 36, 36, 36, 36, 36, 57,184, 44, - 36, 44, 44, 44, 44, 44, 44, 44, 27, 27, 27, 95, 44, 44, 44, 44, - 180, 27, 30, 2, 2, 44, 44, 44, 36, 43, 43, 2, 2, 44, 44, 44, - 36, 36,183, 27, 27, 27, 44, 44, 87, 98, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 43, 43, 43, 43, 43, 43, 43, 60, 2, 2, 2, 44, - 27, 27, 27, 7, 7, 7, 7, 7, 71, 70, 71, 44, 44, 44, 44, 57, - 86, 87, 43, 85, 87, 60,185, 2, 2, 80, 44, 44, 44, 44, 79, 44, - 43, 71, 36, 36, 36, 36, 36, 36, 36, 36, 36, 70, 43, 43, 87, 43, - 43, 43, 80, 7, 7, 7, 7, 7, 2, 2, 94, 98, 44, 44, 44, 44, - 36, 70, 2, 61, 44, 44, 44, 44, 36, 94, 86, 43, 43, 43, 43, 85, - 98, 36, 63, 2, 59, 43, 60, 87, 7, 7, 7, 7, 7, 63, 63, 2, - 179, 27, 27, 27, 27, 27, 27, 27, 27, 27,100, 44, 44, 44, 44, 44, - 36, 36, 36, 36, 36, 36, 86, 87, 43, 86, 85, 43, 2, 2, 2, 80, + 36, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 57, 43, + 27, 27, 27, 95, 44, 44, 44, 44,180, 27, 30, 2, 2, 44, 44, 44, + 36, 43, 43, 2, 2, 44, 44, 44, 36, 36,183, 27, 27, 27, 44, 44, + 87, 98, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 43, 43, 43, 43, + 43, 43, 43, 60, 2, 2, 2, 44, 27, 27, 27, 7, 7, 7, 7, 7, + 71, 70, 71, 44, 44, 44, 44, 57, 86, 87, 43, 85, 87, 60,185, 2, + 2, 80, 44, 44, 44, 44, 79, 44, 43, 71, 36, 36, 36, 36, 36, 36, + 36, 36, 36, 70, 43, 43, 87, 43, 43, 43, 80, 7, 7, 7, 7, 7, + 2, 2, 94, 98, 44, 44, 44, 44, 36, 70, 2, 61, 44, 44, 44, 44, + 36, 94, 86, 43, 43, 43, 43, 85, 98, 36, 63, 2, 59, 43, 60, 87, + 7, 7, 7, 7, 7, 63, 63, 2,179, 27, 27, 27, 27, 27, 27, 27, + 27, 27,100, 44, 44, 44, 44, 44, 36, 36, 36, 36, 36, 36, 86, 87, + 43, 86, 85, 43, 2, 2, 2, 71, 70, 44, 44, 44, 44, 44, 44, 44, 36, 36, 36, 61, 61, 36, 36, 62, 36, 36, 36, 36, 36, 36, 36, 62, 36, 36, 36, 36, 63, 44, 44, 44, 36, 36, 36, 36, 36, 36, 36, 70, 86, 87, 43, 43, 43, 80, 44, 44, 43, 86, 62, 36, 36, 36, 61, 62, @@ -3179,17 +3211,20 @@ _hb_ucd_u8[17564] = 70, 43, 43, 43, 43, 71, 36, 36, 36, 70, 43, 43, 85, 70, 43, 60, 2, 2, 2, 59, 44, 44, 44, 44, 70, 43, 43, 85, 87, 43, 36, 36, 36, 36, 36, 36, 36, 43, 43, 43, 43, 43, 43, 85, 43, 2, 72, 2, - 2, 64, 44, 44, 44, 44, 44, 44, 43, 43, 43, 80, 43, 43, 43, 87, - 63, 2, 2, 44, 44, 44, 44, 44, 2, 36, 36, 36, 36, 36, 36, 36, - 44, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 43, 89, 43, 43, 43, - 85, 43, 87, 80, 44, 44, 44, 44, 36, 36, 36, 61, 36, 62, 36, 36, - 70, 43, 43, 80, 44, 80, 43, 57, 43, 43, 43, 70, 44, 44, 44, 44, - 36, 36, 36, 62, 61, 36, 36, 36, 36, 36, 36, 36, 36, 86, 86, 90, - 43, 89, 87, 87, 61, 44, 44, 44, 36, 70, 85,107, 64, 44, 44, 44, + 2, 64, 44, 44, 44, 44, 44, 44, 2, 2, 2, 2, 2, 44, 44, 44, + 43, 43, 43, 80, 43, 43, 43, 87, 63, 2, 2, 44, 44, 44, 44, 44, + 2, 36, 36, 36, 36, 36, 36, 36, 44, 43, 43, 43, 43, 43, 43, 43, + 43, 43, 43, 43, 89, 43, 43, 43, 85, 43, 87, 80, 44, 44, 44, 44, + 36, 36, 36, 61, 36, 62, 36, 36, 70, 43, 43, 80, 44, 80, 43, 57, + 43, 43, 43, 70, 44, 44, 44, 44, 36, 36, 36, 62, 61, 36, 36, 36, + 36, 36, 36, 36, 36, 86, 86, 90, 43, 89, 87, 87, 61, 44, 44, 44, + 36, 70, 85,107, 64, 44, 44, 44, 43, 94, 36, 36, 36, 36, 36, 36, + 36, 36, 86, 43, 43, 80, 44, 86, 85, 60, 2, 2, 2, 2, 2, 2, 27, 27, 91, 67, 67, 67, 56, 20,168, 67, 67, 67, 67, 67, 67, 67, 67, 44, 44, 44, 44, 44, 44, 93,105,105,105,105,105,105,105,181, 2, 2, 64, 44, 44, 44, 44, 44, 63, 64, 44, 44, 44, 44, 44, 44, - 65, 65, 65, 65,132, 44, 44, 44, 43, 43, 60, 44, 44, 44, 44, 44, + 65, 65, 65, 65, 65, 65, 65, 65, 71, 36, 36, 70, 43, 43, 43, 43, + 43, 43, 43, 44, 44, 44, 44, 44, 43, 43, 60, 44, 44, 44, 44, 44, 43, 43, 43, 60, 2, 2, 67, 67, 40, 40, 97, 44, 44, 44, 44, 44, 7, 7, 7, 7, 7,179, 27, 27, 27, 62, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 44, 44, 62, 36, 27, 27, 27, 30, 2, 64, 44, 44, @@ -3197,7 +3232,8 @@ _hb_ucd_u8[17564] = 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 44, 44, 44, 57, 43, 74, 40, 40, 40, 40, 40, 40, 40, 88, 80, 44, 44, 44, 44, 44, 86, 44, 44, 44, 44, 44, 44, 44, 40, 40, 52, 40, 40, 40, 52, 81, - 36, 61, 44, 44, 44, 44, 44, 44, 44, 44, 36, 36, 44, 44, 44, 44, + 36, 61, 44, 44, 44, 44, 44, 44, 44, 61, 44, 44, 44, 44, 44, 44, + 36, 61, 62, 44, 44, 44, 44, 44, 44, 44, 36, 36, 44, 44, 44, 44, 36, 36, 36, 36, 36, 44, 50, 60, 65, 65, 44, 44, 44, 44, 44, 44, 43, 43, 43, 43, 43, 43, 43, 44, 43, 43, 43, 80, 44, 44, 44, 44, 67, 67, 67, 92, 55, 67, 67, 67, 67, 67,186, 87, 43, 67,186, 86, @@ -3222,10 +3258,12 @@ _hb_ucd_u8[17564] = 43, 43, 43, 43, 43, 43, 76, 67, 67, 67, 50, 67, 67, 67, 67, 67, 67, 67, 76, 21, 2, 2, 44, 44, 44, 44, 44, 44, 44, 57, 43, 43, 16, 16, 16, 16, 16, 39, 16, 16, 16, 16, 16, 16, 16, 16, 16,110, - 43, 43, 43, 80, 43, 43, 43, 43, 43, 43, 43, 43, 80, 57, 43, 43, - 43, 57, 80, 43, 43, 80, 44, 44, 43, 43, 43, 74, 40, 40, 40, 44, - 7, 7, 7, 7, 7, 44, 44, 77, 36, 36, 36, 36, 36, 36, 36, 80, - 36, 36, 36, 36, 36, 36, 43, 43, 7, 7, 7, 7, 7, 44, 44, 96, + 44, 44,150, 16, 16,110, 44, 44, 43, 43, 43, 80, 43, 43, 43, 43, + 43, 43, 43, 43, 80, 57, 43, 43, 43, 57, 80, 43, 43, 80, 44, 44, + 40, 40, 40, 40, 40, 40, 40, 44, 44, 44, 44, 44, 44, 44, 44, 57, + 43, 43, 43, 74, 40, 40, 40, 44, 7, 7, 7, 7, 7, 44, 44, 77, + 36, 36, 36, 36, 36, 36, 36, 80, 36, 36, 36, 36, 36, 36, 43, 43, + 7, 7, 7, 7, 7, 44, 44, 96, 36, 36, 36, 36, 36, 83, 43, 43, 36, 36, 36, 61, 36, 36, 62, 61, 36, 36, 61,179, 27, 27, 27, 27, 16, 16, 43, 43, 43, 74, 44, 44, 27, 27, 27, 27, 27, 27,163, 27, 188, 27,100, 44, 44, 44, 44, 44, 27, 27, 27, 27, 27, 27, 27,163, @@ -3238,206 +3276,210 @@ _hb_ucd_u8[17564] = 27, 27, 27, 27, 27, 27, 91, 67, 67, 67, 67, 67, 67, 67, 67, 44, 44, 44, 44, 67, 67, 67, 67, 67, 67, 92, 44, 44, 44, 44, 44, 44, 67, 67, 67, 67, 92, 44, 44, 44, 67, 44, 44, 44, 44, 44, 44, 44, - 67, 67, 67, 67, 67, 25, 41, 41, 67, 67, 67, 67, 44, 44, 55, 67, - 67, 67, 67, 67, 44, 44, 44, 44, 67, 67, 92, 44, 67, 67, 92, 44, + 67, 67, 67, 67, 67, 25, 41, 41, 67, 67, 67, 67, 44, 44, 67, 67, + 67, 67, 67, 92, 44, 55, 67, 67, 67, 67, 67, 67, 44, 44, 44, 44, + 67, 67, 67, 67, 67, 67, 67, 55, 67, 67, 67, 44, 44, 44, 44, 67, 67, 92, 67, 67, 67, 67, 67, 67, 79, 44, 44, 44, 44, 44, 44, 44, - 65, 65, 65, 65, 65, 65, 65, 65,171,171,171,171,171,171,171, 44, - 171,171,171,171,171,171,171, 0, 0, 0, 29, 21, 21, 21, 23, 21, - 22, 18, 21, 25, 21, 17, 13, 13, 25, 25, 25, 21, 21, 9, 9, 9, - 9, 22, 21, 18, 24, 16, 24, 5, 5, 5, 5, 22, 25, 18, 25, 0, - 23, 23, 26, 21, 24, 26, 7, 20, 25, 1, 26, 24, 26, 25, 15, 15, - 24, 15, 7, 19, 15, 21, 9, 25, 9, 5, 5, 25, 5, 9, 5, 7, - 7, 7, 9, 8, 8, 5, 7, 5, 6, 6, 24, 24, 6, 24, 12, 12, - 2, 2, 6, 5, 9, 21, 9, 2, 2, 9, 25, 9, 26, 12, 11, 11, - 2, 6, 5, 21, 17, 2, 2, 26, 26, 23, 2, 12, 17, 12, 21, 12, - 12, 21, 7, 2, 2, 7, 7, 21, 21, 2, 1, 1, 21, 23, 26, 26, - 1, 21, 6, 7, 7, 12, 12, 7, 21, 7, 12, 1, 12, 6, 6, 12, - 12, 26, 7, 26, 26, 7, 2, 1, 12, 2, 6, 2, 24, 7, 7, 6, - 1, 12, 12, 10, 10, 10, 10, 12, 21, 6, 2, 10, 10, 2, 15, 26, - 26, 2, 2, 21, 7, 10, 15, 7, 2, 23, 21, 26, 10, 7, 21, 15, - 15, 2, 17, 7, 29, 7, 7, 22, 18, 2, 14, 14, 14, 7, 10, 21, - 17, 21, 11, 12, 5, 2, 5, 6, 8, 8, 8, 24, 5, 24, 2, 24, - 9, 24, 24, 2, 29, 29, 29, 1, 17, 17, 20, 19, 22, 20, 27, 28, - 1, 29, 21, 20, 19, 21, 21, 16, 16, 21, 25, 22, 18, 21, 21, 29, - 1, 2, 15, 6, 18, 6, 23, 2, 12, 11, 9, 26, 26, 9, 26, 5, - 5, 26, 14, 9, 5, 14, 14, 15, 25, 26, 26, 22, 18, 26, 18, 25, - 18, 22, 5, 12, 2, 5, 22, 21, 21, 22, 18, 17, 26, 6, 7, 14, - 17, 22, 18, 18, 26, 14, 17, 6, 14, 6, 12, 24, 24, 6, 26, 15, - 6, 21, 11, 21, 24, 9, 6, 9, 23, 26, 6, 10, 4, 4, 3, 3, - 7, 25, 17, 16, 16, 22, 16, 16, 25, 17, 25, 2, 25, 24, 2, 15, - 12, 15, 14, 2, 21, 14, 7, 15, 12, 17, 21, 1, 26, 10, 10, 1, - 23, 15, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 10, 11, 12, - 13, 0, 14, 0, 0, 0, 0, 0, 15, 0, 16, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 171,171,171,171,171,171,171, 44,171,171,171,171,171,171,171, 0, + 0, 0, 29, 21, 21, 21, 23, 21, 22, 18, 21, 25, 21, 17, 13, 13, + 25, 25, 25, 21, 21, 9, 9, 9, 9, 22, 21, 18, 24, 16, 24, 5, + 5, 5, 5, 22, 25, 18, 25, 0, 23, 23, 26, 21, 24, 26, 7, 20, + 25, 1, 26, 24, 26, 25, 15, 15, 24, 15, 7, 19, 15, 21, 9, 25, + 9, 5, 5, 25, 5, 9, 5, 7, 7, 7, 9, 8, 8, 5, 7, 5, + 6, 6, 24, 24, 6, 24, 12, 12, 2, 2, 6, 5, 9, 21, 9, 2, + 2, 9, 25, 9, 26, 12, 11, 11, 2, 6, 5, 21, 17, 2, 2, 26, + 26, 23, 2, 12, 17, 12, 21, 12, 12, 21, 7, 2, 2, 7, 7, 21, + 21, 2, 1, 1, 21, 23, 26, 26, 1, 21, 6, 7, 7, 12, 12, 7, + 21, 7, 12, 1, 12, 6, 6, 12, 12, 26, 7, 26, 26, 7, 2, 1, + 12, 2, 6, 2, 24, 7, 7, 6, 1, 12, 12, 10, 10, 10, 10, 12, + 21, 6, 2, 10, 10, 2, 15, 26, 26, 2, 2, 21, 7, 10, 15, 7, + 2, 23, 21, 26, 10, 7, 21, 15, 15, 2, 17, 7, 29, 7, 7, 22, + 18, 2, 14, 14, 14, 7, 10, 21, 17, 21, 11, 12, 5, 2, 5, 6, + 8, 8, 8, 24, 5, 24, 2, 24, 9, 24, 24, 2, 29, 29, 29, 1, + 17, 17, 20, 19, 22, 20, 27, 28, 1, 29, 21, 20, 19, 21, 21, 16, + 16, 21, 25, 22, 18, 21, 21, 29, 1, 2, 15, 6, 18, 6, 23, 2, + 12, 11, 9, 26, 26, 9, 26, 5, 5, 26, 14, 9, 5, 14, 14, 15, + 25, 26, 26, 22, 18, 26, 18, 25, 18, 22, 5, 12, 2, 5, 22, 21, + 21, 22, 18, 17, 26, 6, 7, 14, 17, 22, 18, 18, 26, 14, 17, 6, + 14, 6, 12, 24, 24, 6, 26, 15, 6, 21, 11, 21, 24, 9, 6, 9, + 23, 26, 6, 10, 4, 4, 3, 3, 7, 25, 17, 16, 16, 22, 16, 16, + 25, 17, 25, 2, 25, 24, 2, 15, 12, 15, 14, 2, 21, 14, 7, 15, + 12, 17, 21, 1, 26, 10, 10, 1, 23, 15, 0, 1, 2, 3, 4, 5, + 6, 7, 8, 9, 0, 10, 11, 12, 13, 0, 14, 0, 0, 0, 0, 0, + 15, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, - 0, 21, 22, 23, 0, 0, 0, 24, 25, 26, 27, 28, 29, 30, 31, 32, - 33, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 34, 0, 35, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 20, 0, 21, 22, 23, 0, 0, 0, 24, + 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 35, + 0, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 37, 38, 0, 0, 0, 0, - 0, 0, 39, 40, 0, 0, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 1, 2, 0, 0, 0, 0, 3, 0, 0, 0, 4, 5, - 6, 7, 0, 8, 9, 10, 0, 11, 12, 13, 14, 15, 16, 17, 16, 18, - 16, 19, 16, 19, 16, 19, 0, 19, 16, 20, 16, 19, 21, 19, 0, 22, - 23, 24, 25, 26, 27, 28, 29, 30, 31, 0, 32, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 33, 0, 0, 0, 0, 0, 0, 34, 0, 0, 35, - 0, 0, 36, 0, 37, 0, 0, 0, 38, 39, 40, 41, 42, 43, 44, 45, - 46, 0, 0, 47, 0, 0, 0, 48, 0, 0, 0, 49, 0, 0, 0, 0, - 0, 0, 0, 50, 0, 51, 0, 52, 53, 0, 54, 0, 0, 0, 0, 0, - 0, 55, 56, 57, 0, 0, 0, 0, 58, 0, 0, 59, 60, 61, 62, 63, - 0, 0, 64, 65, 0, 0, 0, 66, 0, 0, 0, 0, 67, 0, 0, 0, - 68, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 69, - 0, 0, 0, 70, 0, 71, 0, 0, 72, 0, 0, 73, 0, 0, 0, 0, - 0, 0, 0, 0, 74, 0, 0, 0, 0, 0, 75, 0, 0, 76, 77, 0, - 0, 78, 79, 0, 80, 62, 0, 81, 82, 0, 0, 83, 84, 85, 0, 0, - 0, 86, 0, 87, 0, 0, 51, 88, 51, 0, 89, 0, 90, 0, 0, 0, - 79, 0, 0, 0, 91, 92, 0, 93, 94, 95, 96, 0, 0, 0, 0, 0, - 51, 0, 0, 0, 0, 97, 98, 0, 0, 0, 0, 99,100, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0,101, 0, 0,102, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0,103,104, 0, 0,105, 0, 0, 0, 0, 0, 0, - 106, 0, 0, 0,100, 0, 0, 0, 0, 0,107,108, 0, 0, 0, 0, - 0, 0, 0,109, 0,110, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, - 5, 6, 7, 0, 8, 0, 0, 0, 0, 9, 10, 11, 12, 0, 0, 0, - 0, 13, 0, 0, 14, 15, 0, 16, 0, 17, 18, 0, 0, 19, 0, 20, - 21, 0, 0, 0, 0, 0, 22, 23, 0, 24, 25, 0, 0, 26, 0, 0, - 0, 27, 0, 0, 28, 29, 30, 31, 0, 0, 0, 32, 33, 34, 0, 0, - 33, 0, 0, 35, 33, 0, 0, 0, 33, 36, 0, 0, 0, 0, 0, 37, - 38, 0, 0, 0, 0, 0, 0, 39, 40, 0, 0, 0, 0, 0, 0, 41, - 42, 0, 0, 0, 0, 43, 0, 44, 0, 0, 0, 45, 46, 0, 0, 0, - 47, 0, 0, 0, 0, 0, 0, 48, 49, 0, 0, 0, 0, 50, 0, 0, - 0, 51, 0, 52, 0, 53, 0, 0, 0, 0, 54, 0, 0, 0, 0, 55, - 0, 56, 0, 0, 0, 0, 57, 58, 0, 0, 0, 59, 60, 0, 0, 0, - 0, 0, 0, 61, 52, 0, 62, 63, 0, 0, 64, 0, 0, 0, 65, 66, - 0, 0, 0, 67, 0, 68, 69, 70, 71, 72, 1, 73, 0, 74, 75, 76, - 0, 0, 77, 78, 0, 0, 0, 79, 0, 0, 1, 1, 0, 0, 80, 0, - 0, 81, 0, 0, 0, 0, 77, 82, 0, 83, 0, 0, 0, 0, 0, 78, - 84, 0, 85, 0, 52, 0, 1, 78, 0, 0, 86, 0, 0, 87, 0, 0, - 0, 0, 0, 88, 57, 0, 0, 0, 0, 0, 0, 89, 90, 0, 0, 84, - 0, 0, 33, 0, 0, 91, 0, 0, 0, 0, 92, 0, 0, 0, 0, 49, - 0, 0, 93, 0, 0, 0, 0, 94, 95, 0, 0, 96, 0, 0, 97, 0, - 0, 0, 98, 0, 0, 0, 99, 0,100, 93, 0, 0,101, 0, 0, 0, - 84, 0, 0,102, 0, 0, 0,103,104, 0, 0,105,106, 0, 0, 0, - 0, 0, 0,107, 0, 0,108, 0, 0, 0, 0,109, 33, 0,110,111, - 112, 35, 0, 0,113, 0, 0, 0,114, 0, 0, 0, 0, 0, 0,115, - 0, 0,116, 0, 0, 0, 0,117, 88, 0, 0, 0, 0, 0, 57, 0, - 0, 0, 0, 52,118, 0, 0, 0, 0,119, 0, 0,120, 0, 0, 0, - 0,118, 0, 0, 0, 0, 0,121, 0, 0, 0,122, 0, 0, 0,123, - 0,124, 0, 0, 0, 0,125,126,127, 0,128, 0,129, 0, 0, 0, - 130,131,132, 0, 0, 0, 35, 0, 0, 0,133, 0, 0,134, 0, 0, - 135, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 3, 4, - 5, 6, 7, 4, 4, 8, 9, 10, 1, 11, 12, 13, 14, 15, 16, 17, - 18, 1, 1, 1, 19, 1, 0, 0, 20, 21, 22, 1, 23, 4, 21, 24, - 25, 26, 27, 28, 29, 30, 0, 0, 1, 1, 31, 0, 0, 0, 32, 33, - 34, 35, 1, 36, 37, 0, 0, 0, 0, 38, 1, 39, 14, 39, 40, 41, - 42, 0, 0, 0, 43, 36, 44, 45, 21, 45, 46, 0, 0, 0, 19, 1, - 21, 0, 0, 47, 0, 38, 48, 1, 1, 49, 49, 50, 0, 0, 51, 0, - 0, 0, 52, 1, 0, 0, 38, 14, 4, 1, 1, 1, 53, 21, 43, 52, - 54, 21, 35, 1, 0, 0, 0, 55, 0, 0, 0, 56, 57, 58, 0, 0, - 0, 0, 0, 59, 0, 60, 0, 0, 0, 0, 61, 62, 0, 0, 63, 0, - 0, 0, 64, 0, 0, 0, 65, 0, 0, 0, 66, 0, 0, 0, 67, 0, - 0, 0, 68, 0, 0, 69, 70, 0, 71, 72, 73, 74, 75, 76, 0, 0, - 0, 77, 0, 0, 0, 78, 79, 0, 0, 0, 0, 47, 0, 0, 0, 49, - 0, 80, 0, 0, 0, 62, 0, 0, 63, 0, 0, 81, 0, 0, 82, 0, - 0, 0, 83, 0, 0, 19, 84, 0, 62, 0, 0, 0, 0, 49, 1, 85, - 1, 52, 15, 86, 36, 10, 21, 87, 0, 55, 0, 0, 0, 0, 19, 10, - 1, 0, 0, 0, 0, 0, 88, 0, 0, 89, 0, 0, 88, 0, 0, 0, - 0, 78, 0, 0, 87, 9, 12, 4, 90, 8, 91, 47, 0, 58, 50, 0, - 21, 1, 21, 92, 93, 1, 1, 1, 1, 94, 95, 96, 97, 1, 98, 58, - 81, 99,100, 4, 58, 0, 0, 0, 0, 0, 0, 19, 50, 0, 0, 0, - 0, 0, 0, 61, 0, 0,101,102, 0, 0,103, 0, 0, 1, 1, 50, - 0, 0, 0, 38, 0, 63, 0, 0, 0, 0, 0, 62, 0, 0,104, 68, - 61, 0, 0, 0, 78, 0, 0, 0,105,106, 58, 38, 81, 0, 0, 0, - 0, 0, 0,107, 1, 14, 4, 12, 84, 0, 0, 0, 0, 38, 87, 0, - 0, 0, 0,108, 0, 0,109, 61, 0,110, 0, 0, 0, 1, 0, 0, - 0, 0, 19, 58, 0,111, 14, 52,112, 41, 0, 0, 62, 0, 0, 61, - 0, 0,113, 0, 87, 0, 0, 0, 61, 62, 0, 0, 62, 0, 89, 0, - 0,113, 0, 0, 0, 0,114, 0, 0, 0, 78, 55, 0, 38, 1, 58, - 1, 58, 0, 0, 63, 89, 0, 0,115, 0, 0, 0, 55, 0, 0, 0, - 0,115, 0, 0, 0, 0, 61, 0, 0, 0, 0, 79, 0, 61, 0, 0, - 0, 0, 56, 0, 89, 80, 0, 0, 8, 91, 0, 0, 1, 87, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 37, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 38, 39, 0, 0, 0, 0, 0, 0, 40, 41, 42, 0, 43, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 0, 0, + 0, 0, 3, 0, 0, 0, 4, 5, 6, 7, 0, 8, 9, 10, 0, 11, + 12, 13, 14, 15, 16, 17, 16, 18, 16, 19, 16, 19, 16, 19, 0, 19, + 16, 20, 16, 19, 21, 19, 0, 22, 23, 24, 25, 26, 27, 28, 29, 30, + 31, 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 33, 0, 0, + 0, 0, 0, 0, 34, 0, 0, 35, 0, 0, 36, 0, 37, 0, 0, 0, + 38, 39, 40, 41, 42, 43, 44, 45, 46, 0, 0, 47, 0, 0, 0, 48, + 0, 0, 0, 49, 0, 0, 0, 0, 0, 0, 0, 50, 0, 51, 0, 52, + 53, 0, 54, 0, 0, 0, 0, 0, 0, 55, 56, 57, 0, 0, 0, 0, + 58, 0, 0, 59, 60, 61, 62, 63, 0, 0, 64, 65, 0, 0, 0, 66, + 0, 0, 0, 0, 67, 0, 0, 0, 68, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 69, 0, 0, 0, 70, 0, 71, 0, 0, + 72, 0, 0, 73, 0, 0, 0, 0, 0, 0, 0, 0, 74, 0, 0, 0, + 0, 0, 75, 76, 0, 77, 78, 0, 0, 79, 80, 0, 81, 62, 0, 82, + 83, 0, 0, 84, 85, 86, 0, 0, 0, 87, 0, 88, 0, 0, 51, 89, + 51, 0, 90, 0, 91, 0, 0, 0, 80, 0, 0, 0, 92, 93, 0, 94, + 95, 96, 97, 0, 0, 0, 0, 0, 51, 0, 0, 0, 0, 98, 99, 0, + 0, 0, 0, 0, 0,100, 0, 0, 0, 0, 0,101,102, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,103, 0, 0,104, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,105,106, 0, 0,107, 0, 0, 0, 0, 0, 0, + 108, 0,109, 0,102, 0, 0, 0, 0, 0,110,111, 0, 0, 0, 0, + 0, 0, 0,112, 0, 0, 0, 0, 0, 0, 0,113, 0,114, 0, 0, + 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 0, 8, 0, 0, 0, + 0, 9, 10, 11, 12, 0, 0, 0, 0, 13, 0, 0, 14, 15, 0, 16, + 0, 17, 18, 0, 0, 19, 0, 20, 21, 0, 0, 0, 0, 0, 22, 23, + 0, 24, 25, 0, 0, 26, 0, 0, 0, 27, 0, 0, 28, 29, 30, 31, + 0, 0, 0, 32, 33, 34, 0, 0, 33, 0, 0, 35, 33, 0, 0, 0, + 33, 36, 0, 0, 0, 0, 0, 37, 38, 0, 0, 0, 0, 0, 0, 39, + 40, 0, 0, 0, 0, 0, 0, 41, 42, 0, 0, 0, 0, 43, 0, 44, + 0, 0, 0, 45, 46, 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, 48, + 49, 0, 0, 0, 0, 50, 0, 0, 0, 51, 0, 52, 0, 53, 0, 0, + 0, 0, 54, 0, 0, 0, 0, 55, 0, 56, 0, 0, 0, 0, 57, 58, + 0, 0, 0, 59, 60, 0, 0, 0, 0, 0, 0, 61, 52, 0, 62, 63, + 0, 0, 64, 0, 0, 0, 65, 66, 0, 0, 0, 67, 0, 68, 69, 70, + 71, 72, 1, 73, 0, 74, 75, 76, 0, 0, 77, 78, 0, 0, 0, 79, + 0, 0, 1, 1, 0, 0, 80, 0, 0, 81, 0, 0, 0, 0, 77, 82, + 0, 83, 0, 0, 0, 0, 0, 78, 84, 0, 85, 0, 52, 0, 1, 78, + 0, 0, 86, 0, 0, 87, 0, 0, 0, 0, 0, 88, 57, 0, 0, 0, + 0, 0, 0, 89, 90, 0, 0, 84, 0, 0, 33, 0, 0, 91, 0, 0, + 0, 0, 92, 0, 0, 0, 0, 49, 0, 0, 93, 0, 0, 0, 0, 94, + 95, 0, 0, 96, 0, 0, 97, 0, 0, 0, 98, 0, 0, 0, 99, 0, + 0, 0, 0,100,101, 93, 0, 0,102, 0, 0, 0, 84, 0, 0,103, + 0, 0, 0,104,105, 0, 0,106,107, 0, 0, 0, 0, 0, 0,108, + 0, 0,109, 0, 0, 0, 0,110, 33, 0,111,112,113, 35, 0, 0, + 114, 0, 0, 0,115, 0, 0, 0, 0, 0, 0,116, 0, 0,117, 0, + 0, 0, 0,118, 88, 0, 0, 0, 0, 0, 57, 0, 0, 0, 0, 52, + 119, 0, 0, 0, 0,120, 0, 0,121, 0, 0, 0, 0,119, 0, 0, + 122, 0, 0, 0, 0, 0, 0,123, 0, 0, 0,124, 0, 0, 0,125, + 0,126, 0, 0, 0, 0,127,128,129, 0,130, 0,131, 0, 0, 0, + 132,133,134, 0, 77, 0, 0, 0, 0, 0, 35, 0, 0, 0,135, 0, + 0, 0,136, 0, 0,137, 0, 0,138, 0, 0, 0, 0, 0, 0, 0, + 1, 1, 1, 1, 1, 2, 3, 4, 5, 6, 7, 4, 4, 8, 9, 10, + 1, 11, 12, 13, 14, 15, 16, 17, 18, 1, 1, 1, 19, 1, 0, 0, + 20, 21, 22, 1, 23, 4, 21, 24, 25, 26, 27, 28, 29, 30, 0, 0, + 1, 1, 31, 0, 0, 0, 32, 33, 34, 35, 1, 36, 37, 0, 0, 0, + 0, 38, 1, 39, 14, 39, 40, 41, 42, 0, 0, 0, 43, 36, 44, 45, + 21, 45, 46, 0, 0, 0, 19, 1, 21, 0, 0, 47, 0, 38, 48, 1, + 1, 49, 49, 50, 0, 0, 51, 0, 0, 0, 52, 1, 0, 0, 38, 14, + 4, 1, 1, 1, 53, 21, 43, 52, 54, 21, 35, 1, 0, 0, 0, 55, + 0, 0, 0, 56, 57, 58, 0, 0, 0, 0, 0, 59, 0, 60, 0, 0, + 0, 0, 61, 62, 0, 0, 63, 0, 0, 0, 64, 0, 0, 0, 65, 0, + 0, 0, 66, 0, 0, 0, 67, 0, 0, 0, 68, 0, 0, 69, 70, 0, + 71, 72, 73, 74, 75, 76, 0, 0, 0, 77, 0, 0, 0, 78, 79, 0, + 0, 0, 0, 47, 0, 0, 0, 49, 0, 80, 0, 0, 0, 62, 0, 0, + 63, 0, 0, 81, 0, 0, 82, 0, 0, 0, 83, 0, 0, 19, 84, 0, + 62, 0, 0, 0, 0, 49, 1, 85, 1, 52, 15, 86, 36, 10, 21, 87, + 0, 55, 0, 0, 0, 0, 19, 10, 1, 0, 0, 0, 0, 0, 88, 0, + 0, 89, 0, 0, 88, 0, 0, 0, 0, 78, 0, 0, 87, 9, 12, 4, + 90, 8, 91, 47, 0, 58, 50, 0, 21, 1, 21, 92, 93, 1, 1, 1, + 1, 94, 95, 96, 97, 1, 98, 58, 81, 99,100, 4, 58, 0, 0, 0, + 0, 0, 0, 19, 50, 0, 0, 0, 0, 0, 0, 61, 0, 0,101,102, + 0, 0,103, 0, 0, 1, 1, 50, 0, 0, 0, 38, 0, 63, 0, 0, + 0, 0, 0, 62, 0, 0,104, 68, 61, 0, 0, 0, 78, 0, 0, 0, + 105,106, 58, 38, 81, 0, 0, 0, 0, 0, 0,107, 1, 14, 4, 12, + 84, 0, 0, 0, 0, 38, 87, 0, 0, 0, 0,108, 0, 0,109, 61, + 0,110, 0, 0, 0, 1, 0, 0, 0, 0, 19, 58, 0, 0, 0, 51, + 0,111, 14, 52,112, 41, 0, 0, 62, 0, 0, 61, 0, 0,113, 0, + 87, 0, 0, 0, 61, 62, 0, 0, 62, 0, 89, 0, 0,113, 0, 0, + 0, 0,114, 0, 0, 0, 78, 55, 0, 38, 1, 58, 1, 58, 0, 0, + 63, 89, 0, 0,115, 0, 0, 0, 55, 0, 0, 0, 0,115, 0, 0, + 0, 0, 61, 0, 0, 0, 0, 79, 0, 61, 0, 0, 0, 0, 56, 0, + 89, 80, 0, 0, 79, 0, 0, 0, 8, 91, 0, 0, 1, 87, 0, 0, 116, 0, 0, 0, 0, 0, 0,117, 0,118,119,120,121, 0,104, 4, 122, 49, 23, 0, 0, 0, 38, 50, 38, 58, 0, 0, 1, 87, 1, 1, - 1, 1, 39, 1, 48,105, 87, 0, 0, 0, 0, 1, 4,122, 0, 0, - 0, 1,123, 0, 0, 0, 0, 0,230,230,230,230,230,232,220,220, - 220,220,232,216,220,220,220,220,220,202,202,220,220,220,220,202, - 202,220,220,220, 1, 1, 1, 1, 1,220,220,220,220,230,230,230, - 230,240,230,220,220,220,230,230,230,220,220, 0,230,230,230,220, - 220,220,220,230,232,220,220,230,233,234,234,233,234,234,233,230, - 0, 0, 0,230, 0,220,230,230,230,230,220,230,230,230,222,220, - 230,230,220,220,230,222,228,230, 10, 11, 12, 13, 14, 15, 16, 17, - 18, 19, 19, 20, 21, 22, 0, 23, 0, 24, 25, 0,230,220, 0, 18, - 30, 31, 32, 0, 0, 0, 0, 27, 28, 29, 30, 31, 32, 33, 34,230, - 230,220,220,230,220,230,230,220, 35, 0, 0, 0, 0, 0,230,230, - 230, 0, 0,230,230, 0,220,230,230,220, 0, 0, 0, 36, 0, 0, - 230,220,230,230,220,220,230,220,220,230,220,230,220,230,230, 0, - 0,220, 0, 0,230,230, 0,230, 0,230,230,230,230,230, 0, 0, - 0,220,220,220,230,220,220,220,230,230, 0,220, 27, 28, 29,230, - 7, 0, 0, 0, 0, 9, 0, 0, 0,230,220,230,230, 0, 0, 0, - 0, 0,230, 0, 0, 84, 91, 0, 0, 0, 0, 9, 9, 0, 0, 0, - 0, 0, 9, 0,103,103, 9, 0,107,107,107,107,118,118, 9, 0, - 122,122,122,122,220,220, 0, 0, 0,220, 0,220, 0,216, 0, 0, - 0,129,130, 0,132, 0, 0, 0, 0, 0,130,130,130,130, 0, 0, - 130, 0,230,230, 9, 0,230,230, 0, 0,220, 0, 0, 0, 0, 7, - 0, 9, 9, 0, 9, 9, 0, 0, 0,230, 0, 0, 0,228, 0, 0, - 0,222,230,220,220, 0, 0, 0,230, 0, 0,220,230,220, 0,220, - 230,230,230, 0, 0, 0, 9, 9, 0, 0, 7, 0,230, 0, 1, 1, - 1, 0, 0, 0,230,234,214,220,202,230,230,230,230,230,232,228, - 228,220,218,230,233,220,230,220,230,230, 1, 1, 1, 1, 1,230, - 0, 1, 1,230,220,230, 1, 1, 0, 0,218,228,232,222,224,224, - 0, 8, 8, 0, 0, 0, 0,220,230, 0,230,230,220, 0, 0,230, - 0, 0, 26, 0, 0,220, 0,230,230, 1,220, 0, 0,230,220, 0, - 0, 0,220,220, 0, 0,230,220, 0, 9, 7, 0, 0, 7, 9, 0, - 0, 0, 9, 7, 6, 6, 0, 0, 0, 0, 1, 0, 0,216,216, 1, - 1, 1, 0, 0, 0,226,216,216,216,216,216, 0,220,220,220, 0, - 230,230, 7, 0, 16, 17, 17, 17, 17, 17, 17, 33, 17, 17, 17, 19, - 17, 17, 17, 17, 20,101, 17,113,129,169, 17, 27, 28, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 1, 1, 39, 1, 48,105, 87, 0, 0, 0, 0, 1, 0, 0, 0,123, + 4,122, 0, 0, 0, 1,124, 0, 0, 0, 0, 0,230,230,230,230, + 230,232,220,220,220,220,232,216,220,220,220,220,220,202,202,220, + 220,220,220,202,202,220,220,220, 1, 1, 1, 1, 1,220,220,220, + 220,230,230,230,230,240,230,220,220,220,230,230,230,220,220, 0, + 230,230,230,220,220,220,220,230,232,220,220,230,233,234,234,233, + 234,234,233,230, 0, 0, 0,230, 0,220,230,230,230,230,220,230, + 230,230,222,220,230,230,220,220,230,222,228,230, 10, 11, 12, 13, + 14, 15, 16, 17, 18, 19, 19, 20, 21, 22, 0, 23, 0, 24, 25, 0, + 230,220, 0, 18, 30, 31, 32, 0, 0, 0, 0, 27, 28, 29, 30, 31, + 32, 33, 34,230,230,220,220,230,220,230,230,220, 35, 0, 0, 0, + 0, 0,230,230,230, 0, 0,230,230, 0,220,230,230,220, 0, 0, + 0, 36, 0, 0,230,220,230,230,220,220,230,220,220,230,220,230, + 220,230,230, 0, 0,220, 0, 0,230,230, 0,230, 0,230,230,230, + 230,230, 0, 0, 0,220,220,220,230,220,220,220,230,230, 0,220, + 27, 28, 29,230, 7, 0, 0, 0, 0, 9, 0, 0, 0,230,220,230, + 230, 0, 0, 0, 0, 0,230, 0, 0, 84, 91, 0, 0, 0, 0, 9, + 9, 0, 0, 0, 0, 0, 9, 0,103,103, 9, 0,107,107,107,107, + 118,118, 9, 0,122,122,122,122,220,220, 0, 0, 0,220, 0,220, + 0,216, 0, 0, 0,129,130, 0,132, 0, 0, 0, 0, 0,130,130, + 130,130, 0, 0,130, 0,230,230, 9, 0,230,230, 0, 0,220, 0, + 0, 0, 0, 7, 0, 9, 9, 0, 9, 9, 0, 0, 0,230, 0, 0, + 0,228, 0, 0, 0,222,230,220,220, 0, 0, 0,230, 0, 0,220, + 230,220, 0,220,230,230,230, 0, 0, 0, 9, 9, 0, 0, 7, 0, + 230, 0, 1, 1, 1, 0, 0, 0,230,234,214,220,202,230,230,230, + 230,230,232,228,228,220,218,230,233,220,230,220,230,230, 1, 1, + 1, 1, 1,230, 0, 1, 1,230,220,230, 1, 1, 0, 0,218,228, + 232,222,224,224, 0, 8, 8, 0, 0, 0, 0,220,230, 0,230,230, + 220, 0, 0,230, 0, 0, 26, 0, 0,220, 0,230,230, 1,220, 0, + 0,230,220, 0, 0, 0,220,220, 0, 0,230,220, 0, 9, 7, 0, + 0, 7, 9, 0, 0, 0, 9, 7, 6, 6, 0, 0, 0, 0, 1, 0, + 0,216,216, 1, 1, 1, 0, 0, 0,226,216,216,216,216,216, 0, + 220,220,220, 0,232,232,220,230,230,230, 7, 0, 16, 17, 17, 17, + 17, 17, 17, 33, 17, 17, 17, 19, 17, 17, 17, 17, 20,101, 17,113, + 129,169, 17, 27, 28, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17,237, 0, 1, 2, 2, 0, 3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 5, 0, 0, 0, 0, 6, 7, 8, 9, 0, 0, 0, 10, 11, 12, 13, - 14, 15, 16, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, - 0, 0, 21, 22, 0, 0, 0, 0, 23, 24, 25, 26, 0, 27, 0, 28, - 29, 30, 31, 32, 0, 0, 0, 0, 0, 0, 0, 33, 34, 35, 36, 0, - 0, 0, 0, 0, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 38, 39, - 0, 0, 0, 0, 1, 2, 40, 41, 0, 1, 2, 2, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 2, 0, 0, 0, 0, - 0, 0, 3, 4, 0, 0, 5, 0, 0, 0, 6, 0, 0, 0, 0, 0, - 0, 0, 7, 1, 0, 0, 0, 0, 0, 0, 8, 9, 0, 0, 0, 0, - 0, 0, 10, 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 10, 0, 0, 0, 10, 0, 0, 0, 0, 0, 0, 11, 12, - 0, 13, 0, 14, 15, 16, 0, 0, 0, 0, 0, 1, 17, 18, 0, 19, - 7, 1, 0, 0, 0, 20, 20, 7, 20, 20, 20, 20, 20, 20, 20, 8, - 21, 0, 22, 0, 7, 23, 24, 0, 20, 20, 25, 0, 0, 0, 26, 27, - 1, 7, 20, 20, 20, 20, 20, 1, 28, 29, 30, 31, 0, 0, 20, 0, - 0, 0, 0, 0, 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 20, 20, - 20, 1, 0, 0, 8, 21, 32, 4, 0, 10, 0, 33, 7, 20, 20, 20, - 0, 0, 0, 0, 8, 34, 34, 35, 36, 34, 37, 0, 38, 1, 20, 20, - 0, 0, 39, 0, 1, 1, 0, 8, 21, 1, 20, 0, 0, 0, 1, 0, - 0, 40, 1, 1, 0, 0, 8, 21, 0, 1, 0, 1, 0, 1, 0, 0, - 0, 0, 26, 34, 34, 34, 34, 34, 34, 34, 34, 34, 21, 7, 20, 41, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 21, 0, 42, 43, 44, 0, 45, - 0, 8, 21, 0, 0, 0, 0, 0, 0, 0, 0, 46, 7, 1, 10, 1, - 0, 0, 0, 1, 20, 20, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 26, 34, 9, 0, 0, 20, 20, 1, 20, 20, 0, 0, 0, 0, 0, - 0, 0, 26, 21, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 3, 47, 48, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, - 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 9, 10, 11, 11, 11, 11, 12, 13, 13, 13, 13, 14, 15, 16, 17, 18, - 19, 20, 21, 13, 22, 13, 13, 13, 13, 23, 24, 24, 25, 26, 13, 13, - 13, 27, 28, 29, 13, 30, 31, 32, 33, 34, 35, 36, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 37, 7, 38, 39, 7, 40, 7, 7, 7, 41, 13, 42, 7, 7, 43, 13, + 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17,237, 0, 1, 2, 2, + 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, 6, 7, 8, + 9, 0, 0, 0, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 20, 0, 0, 21, 22, 0, 0, 0, 0, + 23, 24, 25, 26, 0, 27, 0, 28, 29, 30, 31, 32, 0, 0, 0, 0, + 0, 0, 0, 33, 34, 35, 36, 0, 0, 0, 0, 0, 37, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 38, 39, 0, 0, 0, 0, 1, 2, 40, 41, + 0, 1, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, + 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 3, 4, 0, 0, 5, 0, + 0, 0, 6, 0, 0, 0, 0, 0, 0, 0, 7, 1, 0, 0, 0, 0, + 0, 0, 8, 9, 0, 0, 0, 0, 0, 0, 10, 0, 0, 10, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 0, 0, 0, 10, + 0, 0, 0, 0, 0, 0, 11, 12, 0, 13, 0, 14, 15, 16, 0, 0, + 0, 0, 0, 1, 17, 18, 0, 19, 7, 1, 0, 0, 0, 20, 20, 7, + 20, 20, 20, 20, 20, 20, 20, 8, 21, 0, 22, 0, 7, 23, 24, 0, + 20, 20, 25, 0, 0, 0, 26, 27, 1, 7, 20, 20, 20, 20, 20, 1, + 28, 29, 30, 31, 0, 0, 20, 0, 0, 0, 0, 0, 0, 0, 10, 0, + 0, 0, 0, 0, 0, 0, 20, 20, 20, 1, 0, 0, 8, 21, 32, 4, + 0, 10, 0, 33, 7, 20, 20, 20, 0, 0, 0, 0, 8, 34, 34, 35, + 36, 34, 37, 0, 38, 1, 20, 20, 0, 0, 39, 0, 1, 1, 0, 8, + 21, 1, 20, 0, 0, 0, 1, 0, 0, 40, 1, 1, 0, 0, 8, 21, + 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 26, 34, 34, 34, 34, 34, + 34, 34, 34, 34, 21, 7, 20, 41, 34, 34, 34, 34, 34, 34, 34, 34, + 34, 21, 0, 42, 43, 44, 0, 45, 0, 8, 21, 0, 0, 0, 0, 0, + 0, 0, 0, 46, 7, 1, 10, 1, 0, 0, 0, 1, 20, 20, 1, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 26, 34, 9, 0, 0, 20, 20, + 1, 20, 20, 0, 0, 0, 0, 0, 0, 0, 26, 21, 0, 1, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 47, 48, 0, 0, 0, + 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, + 7, 7, 7, 7, 7, 7, 7, 7, 9, 10, 11, 11, 11, 11, 12, 13, + 13, 13, 13, 14, 15, 16, 17, 18, 19, 20, 21, 13, 22, 13, 13, 13, + 13, 23, 24, 24, 25, 26, 13, 13, 13, 27, 28, 29, 13, 30, 31, 32, + 33, 34, 35, 36, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, + 7, 7, 7, 7, 7, 7, 7, 7, 37, 7, 38, 39, 7, 40, 7, 7, + 7, 41, 13, 42, 7, 7, 43, 7, 44, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, @@ -3459,130 +3501,131 @@ _hb_ucd_u8[17564] = 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 44, 0, 0, 1, - 2, 2, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, - 32, 32, 33, 34, 35, 36, 37, 37, 37, 37, 37, 38, 39, 40, 41, 42, - 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 2, 2, 53, 54, 55, 56, - 57, 58, 59, 59, 59, 59, 60, 59, 59, 59, 59, 59, 59, 59, 61, 61, - 59, 59, 59, 59, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, - 74, 75, 76, 77, 78, 59, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, + 13, 13, 13, 13, 45, 0, 0, 1, 2, 2, 2, 3, 4, 5, 6, 7, + 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, + 24, 25, 26, 27, 28, 29, 30, 31, 32, 32, 33, 34, 35, 36, 37, 37, + 37, 37, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, + 51, 52, 2, 2, 53, 54, 55, 56, 57, 58, 59, 59, 59, 59, 60, 59, + 59, 59, 59, 59, 59, 59, 61, 61, 59, 59, 59, 59, 62, 63, 64, 65, + 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 59, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, - 70, 70, 70, 70, 70, 70, 70, 70, 70, 79, 70, 70, 70, 70, 80, 80, - 80, 80, 80, 80, 80, 80, 80, 81, 82, 82, 83, 84, 85, 86, 87, 88, - 89, 90, 91, 92, 93, 94, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, + 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, + 70, 79, 70, 70, 70, 70, 80, 80, 80, 80, 80, 80, 80, 80, 80, 81, + 82, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 95, 96, 96, + 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, + 32, 32, 32, 32, 32, 95, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, 97, 98, 99,100,101,101, + 102,103,104,105,106,107,108,109,110,111, 96,112,113,114,115,116, + 117,118,119,119,120,121,122,123,124,125,126,127,128,129,130,131, + 132, 96,133,134,135,136,137,138,139,140,141,142,143, 96,144,145, + 96,146,147,148,149, 96,150,151,152,153,154,155,156, 96,157,158, + 159,160, 96,161,162,163,164,164,164,164,164,164,164,165,166,164, + 167, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96,168,169,169,169,169,169,169,169,169,170, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,171,171, + 171,171,172, 96, 96, 96,173,173,173,173,174,175,176,177, 96, 96, + 96, 96,178,179,180,181,182,182,182,182,182,182,182,182,182,182, + 182,182,182,182,182,182,182,182,182,182,182,182,182,182,182,182, + 182,182,182,182,182,183,182,182,182,182,182,182,184,184,184,185, + 186, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96,187,188,189,190,191,191,192, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,193,194, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 70, 70, 97, 98, 99,100,101,101,102,103,104,105,106,107,108,109, - 110,111, 96,112,113,114,115,116,117,118,119,119,120,121,122,123, - 124,125,126,127,128,129,130,131,132, 96,133,134,135,136,137,138, - 139,140,141,142,143, 96,144,145, 96,146,147,148,149, 96,150,151, - 152,153,154,155, 96, 96,156,157,158,159, 96,160, 96,161,162,162, - 162,162,162,162,162,163,164,162,165, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,166,167,167, - 167,167,167,167,167,167,168, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96,169,169,169,169,170, 96, 96, 96,171,171, - 171,171,172,173,174,175, 96, 96, 96, 96,176,177,178,179,180,180, - 180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180, - 180,180,180,180,180,180,180,180,180,180,180,180,180,181,180,180, - 180,180,180,180,182,182,182,183,184, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,185,186,187, - 188,189,189,190, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96,191,192, 96, 96, 96, 96, 96, 96, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96,193,194, 59,195, - 196,197,198,199,200, 96,201,202,203, 59, 59,204, 59,205,206,206, - 206,206,206,207, 96, 96, 96, 96, 96, 96, 96, 96,208, 96,209, 96, - 210, 96, 96,211, 96, 96, 96, 96, 96, 96, 96, 96, 96,212,213,214, - 215, 96, 96, 96, 96, 96,216,217,218, 96,219,220, 96, 96,221,222, - 59,223,224, 96, 59, 59, 59, 59, 59, 59, 59,225,226,227,228,229, - 59, 59,230,231, 59,232, 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, - 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,233, 70, 70, 70, 70, - 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,234, 70,235, 70, + 96, 96, 96, 96,195,196, 59,197,198,199,200,201,202, 96,203,204, + 205, 59, 59,206, 59,207,208,208,208,208,208,209, 96, 96, 96, 96, + 96, 96, 96, 96,210, 96,211,212,213, 96, 96,214, 96, 96, 96,215, + 96, 96, 96, 96, 96,216,217,218,219, 96, 96, 96, 96, 96,220,221, + 222, 96,223,224, 96, 96,225,226, 59,227,228, 96, 59, 59, 59, 59, + 59, 59, 59,229,230,231,232,233, 59, 59,234,235, 59,236, 96, 96, + 96, 96, 96, 96, 96, 96, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, + 70, 70, 70,237, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, + 70, 70, 70, 70,238, 70,239, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, - 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,236, 70, 70, 70, 70, - 70, 70, 70, 70, 70,237, 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, - 70, 70,238, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 70, 70, - 70, 70, 70, 70,239, 96, 96, 96, 96, 96, 96, 96, 96, 96,240, 96, - 241,242, 0, 1, 2, 2, 0, 1, 2, 2, 2, 3, 4, 5, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 0, 0, 0, 0, 0, 0, 0, - 19, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, 0, 19, 0, - 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 0, 0, 0, 0, 0, - 26, 26, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 9, 9, - 9, 9, 0, 9, 9, 9, 2, 2, 9, 9, 9, 9, 0, 9, 2, 2, - 2, 2, 9, 0, 9, 0, 9, 9, 9, 2, 9, 2, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 2, 9, 9, 9, 9, 9, 9, 9, - 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 1, 1, 6, 2, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 2, 4, 4, 4, 2, 2, 4, 4, 4, 2, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 2, 2, - 2, 2, 2, 2, 2, 2, 14, 14, 14, 2, 2, 2, 2, 14, 14, 14, - 14, 14, 14, 2, 2, 2, 3, 3, 3, 3, 3, 0, 3, 3, 3, 3, - 3, 3, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 0, 3, 3, 3, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 1, 3, - 3, 3, 3, 3, 3, 3, 37, 37, 37, 37, 37, 37, 37, 37, 37, 37, - 37, 37, 37, 37, 2, 37, 37, 37, 37, 2, 2, 37, 37, 37, 38, 38, - 38, 38, 38, 38, 38, 38, 38, 38, 2, 2, 2, 2, 2, 2, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, 64, 2, 2, 64, 64, 64, 90, 90, - 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 2, 2, 90, 90, - 90, 90, 90, 90, 90, 2, 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, - 95, 95, 2, 2, 95, 2, 37, 37, 37, 2, 2, 2, 2, 2, 3, 3, - 3, 3, 3, 3, 3, 2, 3, 3, 2, 2, 2, 2, 2, 2, 3, 3, - 0, 3, 3, 3, 3, 3, 7, 7, 7, 7, 7, 7, 7, 7, 7, 1, - 1, 1, 1, 7, 7, 7, 7, 7, 7, 7, 0, 0, 7, 7, 5, 5, - 5, 5, 2, 5, 5, 5, 5, 5, 5, 5, 5, 2, 2, 5, 5, 2, - 2, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 2, - 5, 5, 5, 5, 5, 5, 5, 2, 5, 2, 2, 2, 5, 5, 5, 5, - 2, 2, 5, 5, 5, 5, 5, 2, 2, 5, 5, 5, 5, 2, 2, 2, - 2, 2, 2, 2, 2, 5, 2, 2, 2, 2, 5, 5, 2, 5, 5, 5, - 5, 5, 2, 2, 5, 5, 5, 5, 5, 5, 5, 5, 5, 2, 2, 11, - 11, 11, 2, 11, 11, 11, 11, 11, 11, 2, 2, 2, 2, 11, 11, 2, - 2, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 2, - 11, 11, 11, 11, 11, 11, 11, 2, 11, 11, 2, 11, 11, 2, 11, 11, - 2, 2, 11, 2, 11, 11, 11, 2, 2, 11, 11, 11, 2, 2, 2, 11, - 2, 2, 2, 2, 2, 2, 2, 11, 11, 11, 11, 2, 11, 2, 2, 2, - 2, 2, 2, 2, 11, 11, 11, 11, 11, 11, 11, 11, 11, 2, 2, 10, - 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, 10, 10, 2, 10, 10, 10, - 2, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 2, - 10, 10, 10, 10, 10, 10, 10, 2, 10, 10, 2, 10, 10, 10, 10, 10, - 2, 2, 10, 10, 10, 10, 10, 10, 2, 10, 10, 10, 2, 2, 10, 2, - 2, 2, 2, 2, 2, 2, 10, 10, 10, 10, 2, 2, 10, 10, 10, 10, - 2, 2, 2, 2, 2, 2, 2, 10, 10, 10, 10, 10, 10, 10, 2, 21, - 21, 21, 2, 21, 21, 21, 21, 21, 21, 21, 21, 2, 2, 21, 21, 2, - 2, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 2, - 21, 21, 21, 21, 21, 21, 21, 2, 21, 21, 2, 21, 21, 21, 21, 21, - 2, 2, 21, 21, 21, 21, 21, 2, 2, 21, 21, 21, 2, 2, 2, 2, - 2, 2, 2, 21, 21, 21, 2, 2, 2, 2, 21, 21, 2, 21, 21, 21, - 21, 21, 2, 2, 21, 21, 2, 2, 22, 22, 2, 22, 22, 22, 22, 22, - 22, 2, 2, 2, 22, 22, 22, 2, 22, 22, 22, 22, 2, 2, 2, 22, - 22, 2, 22, 2, 22, 22, 2, 2, 2, 22, 22, 2, 2, 2, 22, 22, - 22, 22, 22, 22, 22, 22, 22, 22, 2, 2, 2, 2, 22, 22, 22, 2, - 2, 2, 2, 2, 2, 22, 2, 2, 2, 2, 2, 2, 22, 22, 22, 22, - 22, 2, 2, 2, 2, 2, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, - 23, 23, 23, 2, 23, 23, 23, 2, 23, 23, 23, 23, 23, 23, 23, 23, - 2, 2, 23, 23, 23, 23, 23, 2, 23, 23, 23, 23, 2, 2, 2, 2, - 2, 2, 2, 23, 23, 2, 23, 23, 23, 2, 2, 23, 2, 2, 23, 23, - 23, 23, 2, 2, 23, 23, 2, 2, 2, 2, 2, 2, 2, 23, 16, 16, - 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 2, 16, 16, 16, 2, - 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 2, 16, 16, 16, 16, 16, - 2, 2, 16, 16, 16, 16, 16, 2, 16, 16, 16, 16, 2, 2, 2, 2, - 2, 2, 2, 16, 16, 2, 16, 16, 16, 16, 2, 2, 16, 16, 2, 16, - 16, 2, 2, 2, 2, 2, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 2, 20, 20, 20, 2, 20, 20, 20, 20, 20, 20, 2, 2, - 2, 2, 20, 20, 20, 20, 20, 20, 20, 20, 2, 2, 20, 20, 2, 36, - 36, 36, 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 2, 2, 2, 36, 36, 36, 36, 36, 36, 36, 36, - 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, 2, 36, 2, 2, 2, 2, - 36, 2, 2, 2, 2, 36, 36, 36, 36, 36, 36, 2, 36, 2, 2, 2, - 2, 2, 2, 2, 36, 36, 2, 2, 36, 36, 36, 2, 2, 2, 2, 24, - 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, - 24, 2, 2, 2, 2, 0, 24, 24, 24, 24, 2, 2, 2, 2, 2, 18, - 18, 2, 18, 2, 18, 18, 18, 18, 18, 2, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 2, 18, 2, 18, 18, 18, - 18, 18, 18, 18, 2, 2, 18, 18, 18, 18, 18, 2, 18, 2, 18, 18, + 70, 70, 70,240, 70, 70, 70, 70, 70, 70, 70, 70, 70,241, 96, 96, + 96, 96, 96, 96, 96, 96, 70, 70, 70, 70,242, 96, 96, 96, 96, 96, + 96, 96, 96, 96, 96, 96, 70, 70, 70, 70, 70, 70,243, 70, 70, 70, + 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70,244, 96, 96, + 96, 96, 96, 96, 96, 96,245, 96,246,247, 0, 1, 2, 2, 0, 1, + 2, 2, 2, 3, 4, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, + 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, + 19, 0, 0, 0, 0, 0, 0, 0, 19, 0, 0, 0, 0, 0, 19, 19, + 19, 19, 19, 19, 19, 0, 19, 0, 0, 0, 0, 0, 0, 0, 19, 19, + 19, 19, 19, 0, 0, 0, 0, 0, 26, 26, 0, 0, 0, 0, 1, 1, + 1, 1, 1, 1, 1, 1, 9, 9, 9, 9, 0, 9, 9, 9, 2, 2, + 9, 9, 9, 9, 0, 9, 2, 2, 2, 2, 9, 0, 9, 0, 9, 9, + 9, 2, 9, 2, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 2, 9, 9, 9, 9, 9, 9, 9, 55, 55, 55, 55, 55, 55, 55, 55, + 55, 55, 55, 55, 55, 55, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, + 6, 6, 6, 1, 1, 6, 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, + 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 4, 4, + 4, 2, 2, 4, 4, 4, 2, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 2, 2, 2, 2, 2, 2, 2, 2, 14, 14, + 14, 2, 2, 2, 2, 14, 14, 14, 14, 14, 14, 2, 2, 2, 3, 3, + 3, 3, 3, 0, 3, 3, 3, 3, 3, 3, 0, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 3, 3, 3, 0, 0, 3, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 3, 3, 1, 3, 3, 3, 3, 3, 3, 3, 37, 37, + 37, 37, 37, 37, 37, 37, 37, 37, 37, 37, 37, 37, 2, 37, 37, 37, + 37, 2, 2, 37, 37, 37, 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, + 2, 2, 2, 2, 2, 2, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, + 64, 2, 2, 64, 64, 64, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, + 90, 90, 90, 90, 2, 2, 90, 90, 90, 90, 90, 90, 90, 2, 95, 95, + 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, 2, 2, 95, 2, 37, 37, + 37, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 2, 3, 3, + 2, 2, 2, 2, 2, 2, 3, 3, 0, 3, 3, 3, 3, 3, 7, 7, + 7, 7, 7, 7, 7, 7, 7, 1, 1, 1, 1, 7, 7, 7, 7, 7, + 7, 7, 0, 0, 7, 7, 5, 5, 5, 5, 2, 5, 5, 5, 5, 5, + 5, 5, 5, 2, 2, 5, 5, 2, 2, 5, 5, 5, 5, 5, 5, 5, + 5, 5, 5, 5, 5, 5, 5, 2, 5, 5, 5, 5, 5, 5, 5, 2, + 5, 2, 2, 2, 5, 5, 5, 5, 2, 2, 5, 5, 5, 5, 5, 2, + 2, 5, 5, 5, 5, 2, 2, 2, 2, 2, 2, 2, 2, 5, 2, 2, + 2, 2, 5, 5, 2, 5, 5, 5, 5, 5, 2, 2, 5, 5, 5, 5, + 5, 5, 5, 5, 5, 2, 2, 11, 11, 11, 2, 11, 11, 11, 11, 11, + 11, 2, 2, 2, 2, 11, 11, 2, 2, 11, 11, 11, 11, 11, 11, 11, + 11, 11, 11, 11, 11, 11, 11, 2, 11, 11, 11, 11, 11, 11, 11, 2, + 11, 11, 2, 11, 11, 2, 11, 11, 2, 2, 11, 2, 11, 11, 11, 2, + 2, 11, 11, 11, 2, 2, 2, 11, 2, 2, 2, 2, 2, 2, 2, 11, + 11, 11, 11, 2, 11, 2, 2, 2, 2, 2, 2, 2, 11, 11, 11, 11, + 11, 11, 11, 11, 11, 2, 2, 10, 10, 10, 2, 10, 10, 10, 10, 10, + 10, 10, 10, 10, 2, 10, 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, + 10, 10, 10, 10, 10, 10, 10, 2, 10, 10, 10, 10, 10, 10, 10, 2, + 10, 10, 2, 10, 10, 10, 10, 10, 2, 2, 10, 10, 10, 10, 10, 10, + 2, 10, 10, 10, 2, 2, 10, 2, 2, 2, 2, 2, 2, 2, 10, 10, + 10, 10, 2, 2, 10, 10, 10, 10, 2, 2, 2, 2, 2, 2, 2, 10, + 10, 10, 10, 10, 10, 10, 2, 21, 21, 21, 2, 21, 21, 21, 21, 21, + 21, 21, 21, 2, 2, 21, 21, 2, 2, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 2, 21, 21, 21, 21, 21, 21, 21, 2, + 21, 21, 2, 21, 21, 21, 21, 21, 2, 2, 21, 21, 21, 21, 21, 2, + 2, 21, 21, 21, 2, 2, 2, 2, 2, 2, 2, 21, 21, 21, 2, 2, + 2, 2, 21, 21, 2, 21, 21, 21, 21, 21, 2, 2, 21, 21, 2, 2, + 22, 22, 2, 22, 22, 22, 22, 22, 22, 2, 2, 2, 22, 22, 22, 2, + 22, 22, 22, 22, 2, 2, 2, 22, 22, 2, 22, 2, 22, 22, 2, 2, + 2, 22, 22, 2, 2, 2, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, + 2, 2, 2, 2, 22, 22, 22, 2, 2, 2, 2, 2, 2, 22, 2, 2, + 2, 2, 2, 2, 22, 22, 22, 22, 22, 2, 2, 2, 2, 2, 23, 23, + 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 2, 23, 23, 23, 2, + 23, 23, 23, 23, 23, 23, 23, 23, 2, 2, 23, 23, 23, 23, 23, 2, + 23, 23, 23, 23, 2, 2, 2, 2, 2, 2, 2, 23, 23, 2, 23, 23, + 23, 2, 2, 23, 2, 2, 23, 23, 23, 23, 2, 2, 23, 23, 2, 2, + 2, 2, 2, 2, 2, 23, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, + 16, 16, 16, 2, 16, 16, 16, 2, 16, 16, 16, 16, 16, 16, 16, 16, + 16, 16, 2, 16, 16, 16, 16, 16, 2, 2, 16, 16, 16, 16, 16, 2, + 16, 16, 16, 16, 2, 2, 2, 2, 2, 2, 2, 16, 16, 2, 16, 16, + 16, 16, 2, 2, 16, 16, 2, 16, 16, 16, 2, 2, 2, 2, 20, 20, + 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 2, 20, 20, 20, 2, + 20, 20, 20, 20, 20, 20, 2, 2, 2, 2, 20, 20, 20, 20, 20, 20, + 20, 20, 2, 2, 20, 20, 2, 36, 36, 36, 2, 36, 36, 36, 36, 36, + 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 2, 2, 2, + 36, 36, 36, 36, 36, 36, 36, 36, 2, 36, 36, 36, 36, 36, 36, 36, + 36, 36, 2, 36, 2, 2, 2, 2, 36, 2, 2, 2, 2, 36, 36, 36, + 36, 36, 36, 2, 36, 2, 2, 2, 2, 2, 2, 2, 36, 36, 2, 2, + 36, 36, 36, 2, 2, 2, 2, 24, 24, 24, 24, 24, 24, 24, 24, 24, + 24, 24, 24, 24, 24, 24, 24, 24, 24, 2, 2, 2, 2, 0, 24, 24, + 24, 24, 2, 2, 2, 2, 2, 18, 18, 2, 18, 2, 18, 18, 18, 18, + 18, 2, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 2, 18, 2, 18, 18, 18, 18, 18, 18, 18, 2, 2, 18, 18, + 18, 18, 18, 2, 18, 2, 18, 18, 18, 18, 18, 18, 18, 2, 18, 18, 2, 2, 18, 18, 18, 18, 25, 25, 25, 25, 25, 25, 25, 25, 2, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 2, 2, 2, 25, 25, 25, 25, 25, 2, 25, 25, 25, 25, 25, 25, 25, 0, 0, 0, 0, 25, @@ -3741,49 +3784,50 @@ _hb_ucd_u8[17564] = 130, 2, 2, 2, 2, 2, 2, 2,130,130,130,130,130,130,144,144, 144,144,144,144,144,144,144,144, 2, 2, 2, 2, 2, 2,156,156, 156,156,156,156,156,156,156,156, 2,156,156,156, 2, 2,156,156, - 2, 2, 2, 2, 2, 2,147,147,147,147,147,147,147,147,148,148, - 148,148,148,148,148,148,148,148, 2, 2, 2, 2, 2, 2,158,158, - 158,158,158,158,158,158,158,158, 2, 2, 2, 2, 2, 2,153,153, - 153,153,153,153,153,153,153,153,153,153, 2, 2, 2, 2,149,149, - 149,149,149,149,149,149,149,149,149,149,149,149,149, 2, 94, 94, - 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, 2, 2, 2, 2, - 94, 94, 94, 94, 94, 94, 2, 2, 2, 2, 2, 2, 2, 94, 85, 85, - 85, 85, 85, 85, 85, 85, 85, 85, 85, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 85, 2, 2,101,101,101,101,101,101,101,101,101, 2, - 2, 2, 2, 2, 2, 2,101,101, 2, 2, 2, 2, 2, 2, 96, 96, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 2, 96, 96,111,111, - 111,111,111,111,111,111,111,111,111,111,111,111,111, 2,100,100, - 100,100,100,100,100,100, 2, 36, 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 2, 2, 2,108,108,108,108,108,108,108,108,108,108, - 2,108,108,108,108,108,108,108,108,108,108,108,108, 2,129,129, - 129,129,129,129,129, 2,129, 2,129,129,129,129, 2,129,129,129, - 129,129,129,129,129,129,129,129,129,129,129,129, 2,129,129,129, - 2, 2, 2, 2, 2, 2,109,109,109,109,109,109,109,109,109,109, - 109, 2, 2, 2, 2, 2,109,109, 2, 2, 2, 2, 2, 2,107,107, - 107,107, 2,107,107,107,107,107,107,107,107, 2, 2,107,107, 2, - 2,107,107,107,107,107,107,107,107,107,107,107,107,107,107, 2, - 107,107,107,107,107,107,107, 2,107,107, 2,107,107,107,107,107, - 2, 1,107,107,107,107,107, 2, 2,107,107,107, 2, 2,107, 2, - 2, 2, 2, 2, 2,107, 2, 2, 2, 2, 2,107,107,107,107,107, - 107,107, 2, 2,107,107,107,107,107,107,107, 2, 2, 2,137,137, - 137,137,137,137,137,137,137,137,137,137, 2,137,137,137,137,137, - 2, 2, 2, 2, 2, 2,124,124,124,124,124,124,124,124,124,124, - 2, 2, 2, 2, 2, 2,123,123,123,123,123,123,123,123,123,123, - 123,123,123,123, 2, 2,114,114,114,114,114,114,114,114,114,114, - 114,114,114, 2, 2, 2,114,114, 2, 2, 2, 2, 2, 2, 32, 32, - 32, 32, 32, 2, 2, 2,102,102,102,102,102,102,102,102,102,102, - 2, 2, 2, 2, 2, 2,126,126,126,126,126,126,126,126,126,126, - 126, 2, 2,126,126,126,126,126,126,126, 2, 2, 2, 2,126,126, - 126,126,126,126,126, 2,142,142,142,142,142,142,142,142,142,142, - 142,142, 2, 2, 2, 2,125,125,125,125,125,125,125,125,125,125, - 125, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,125,154,154, - 154,154,154,154,154, 2, 2,154, 2, 2,154,154,154,154,154,154, - 154,154, 2,154,154, 2,154,154,154,154,154,154,154,154,154,154, - 154,154,154,154, 2,154,154, 2, 2,154,154,154,154,154,154,154, - 2, 2, 2, 2, 2, 2,150,150,150,150,150,150,150,150, 2, 2, - 150,150,150,150,150,150,150,150,150,150,150, 2, 2, 2,141,141, - 141,141,141,141,141,141,140,140,140,140,140,140,140,140,140,140, - 140, 2, 2, 2, 2, 2,121,121,121,121,121,121,121,121,121, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3,147,147, + 147,147,147,147,147,147,148,148,148,148,148,148,148,148,148,148, + 2, 2, 2, 2, 2, 2,158,158,158,158,158,158,158,158,158,158, + 2, 2, 2, 2, 2, 2,153,153,153,153,153,153,153,153,153,153, + 153,153, 2, 2, 2, 2,149,149,149,149,149,149,149,149,149,149, + 149,149,149,149,149, 2, 94, 94, 94, 94, 94, 94, 94, 94, 94, 94, + 94, 94, 94, 94, 2, 2, 2, 2, 94, 94, 94, 94, 94, 94, 2, 2, + 2, 2, 2, 2, 2, 94, 85, 85, 85, 85, 85, 85, 85, 85, 85, 85, + 85, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 85, 2, 2,101,101, + 101,101,101,101,101,101,101, 2, 2, 2, 2, 2, 2, 2,101,101, + 2, 2, 2, 2, 2, 2, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, + 96, 96, 96, 2, 96, 96,111,111,111,111,111,111,111,111,111,111, + 111,111,111,111,111, 2,100,100,100,100,100,100,100,100, 2, 36, + 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 2, 2, 2,108,108, + 108,108,108,108,108,108,108,108, 2,108,108,108,108,108,108,108, + 2, 2, 2, 2, 2, 2,129,129,129,129,129,129,129, 2,129, 2, + 129,129,129,129, 2,129,129,129,129,129,129,129,129,129,129,129, + 129,129,129,129, 2,129,129,129, 2, 2, 2, 2, 2, 2,109,109, + 109,109,109,109,109,109,109,109,109, 2, 2, 2, 2, 2,109,109, + 2, 2, 2, 2, 2, 2,107,107,107,107, 2,107,107,107,107,107, + 107,107,107, 2, 2,107,107, 2, 2,107,107,107,107,107,107,107, + 107,107,107,107,107,107,107, 2,107,107,107,107,107,107,107, 2, + 107,107, 2,107,107,107,107,107, 2, 1,107,107,107,107,107, 2, + 2,107,107,107, 2, 2,107, 2, 2, 2, 2, 2, 2,107, 2, 2, + 2, 2, 2,107,107,107,107,107,107,107, 2, 2,107,107,107,107, + 107,107,107, 2, 2, 2,137,137,137,137,137,137,137,137,137,137, + 137,137, 2,137,137,137,137,137, 2, 2, 2, 2, 2, 2,124,124, + 124,124,124,124,124,124,124,124, 2, 2, 2, 2, 2, 2,123,123, + 123,123,123,123,123,123,123,123,123,123,123,123, 2, 2,114,114, + 114,114,114,114,114,114,114,114,114,114,114, 2, 2, 2,114,114, + 2, 2, 2, 2, 2, 2, 32, 32, 32, 32, 32, 2, 2, 2,102,102, + 102,102,102,102,102,102,102,102, 2, 2, 2, 2, 2, 2,126,126, + 126,126,126,126,126,126,126,126,126, 2, 2,126,126,126,126,126, + 126,126, 2, 2, 2, 2,126,126,126,126,126,126,126, 2,142,142, + 142,142,142,142,142,142,142,142,142,142, 2, 2, 2, 2,125,125, + 125,125,125,125,125,125,125,125,125, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2,125,154,154,154,154,154,154,154, 2, 2,154, + 2, 2,154,154,154,154,154,154,154,154, 2,154,154, 2,154,154, + 154,154,154,154,154,154,154,154,154,154,154,154, 2,154,154, 2, + 2,154,154,154,154,154,154,154, 2, 2, 2, 2, 2, 2,150,150, + 150,150,150,150,150,150, 2, 2,150,150,150,150,150,150,150,150, + 150,150,150, 2, 2, 2,141,141,141,141,141,141,141,141,140,140, + 140,140,140,140,140,140,140,140,140, 2, 2, 2, 2, 2,121,121, + 121,121,121,121,121,121,121, 2, 2, 2, 2, 2, 2, 2, 7, 7, 2, 2, 2, 2, 2, 2,133,133,133,133,133,133,133,133,133, 2, 133,133,133,133,133,133,133,133,133,133,133,133,133, 2,133,133, 133,133,133,133, 2, 2,133,133,133,133,133, 2, 2, 2,134,134, @@ -3795,29 +3839,31 @@ _hb_ucd_u8[17564] = 143,143,143,143,143,143,143,143,143,143,143,143,143,143,143,143, 143,143,143,143,143, 2,143,143, 2,143,143,143,143,143,143, 2, 2, 2, 2, 2, 2, 2,143,143, 2, 2, 2, 2, 2, 2,145,145, - 145,145,145,145,145,145,145, 2, 2, 2, 2, 2, 2, 2, 86, 2, + 145,145,145,145,145,145,145, 2, 2, 2, 2, 2, 2, 2,163,163, + 163,163,163,163,163,163,163, 2,163,163,163,163,163,163,163,163, + 163, 2, 2, 2,163,163,163,163, 2, 2, 2, 2, 2, 2, 86, 2, 2, 2, 2, 2, 2, 2, 22, 22, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 22, 63, 63, 63, 63, 63, 63, 63, 63, 63, 63, 2, 2, 2, 2, 2, 2, 63, 63, 63, 63, 63, 63, 63, 2, 63, 63, 63, 63, 63, 2, 2, 2, 63, 63, 63, 63, 2, 2, 2, 2,157,157, 157,157,157,157,157,157,157,157,157, 2, 2, 2, 2, 2, 80, 80, - 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 2, 80, 2, - 2, 2, 2, 2, 2, 2,127,127,127,127,127,127,127,127,127,127, - 127,127,127,127,127, 2, 79, 2, 2, 2, 2, 2, 2, 2,115,115, - 115,115,115,115,115,115,115,115,115,115,115,115,115, 2,115,115, - 2, 2, 2, 2,115,115,159,159,159,159,159,159,159,159,159,159, - 159,159,159,159,159, 2,159,159, 2, 2, 2, 2, 2, 2,103,103, - 103,103,103,103,103,103,103,103,103,103,103,103, 2, 2,119,119, - 119,119,119,119,119,119,119,119,119,119,119,119, 2, 2,119,119, - 2,119,119,119,119,119, 2, 2, 2, 2, 2,119,119,119,146,146, - 146,146,146,146,146,146,146,146,146, 2, 2, 2, 2, 2, 99, 99, - 99, 99, 99, 99, 99, 99, 99, 99, 99, 2, 2, 2, 2, 99, 2, 2, - 2, 2, 2, 2, 2, 99,136,139, 13, 13,155, 2, 2, 2,136,136, - 136,136,136,136,136,136,155,155,155,155,155,155,155,155,155,155, - 155,155,155,155, 2, 2,136, 2, 2, 2, 2, 2, 2, 2, 17, 17, - 17, 17, 2, 17, 17, 17, 17, 17, 17, 17, 2, 17, 17, 2, 17, 15, - 15, 15, 15, 15, 15, 15, 17, 17, 17, 2, 2, 2, 2, 2, 15, 15, - 15, 2, 2, 2, 2, 2, 2, 2, 2, 2, 17, 17, 17, 17,139,139, + 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 80, 2, 2,127,127, + 127,127,127,127,127,127,127,127,127,127,127,127,127, 2, 79, 2, + 2, 2, 2, 2, 2, 2,115,115,115,115,115,115,115,115,115,115, + 115,115,115,115,115, 2,115,115, 2, 2, 2, 2,115,115,159,159, + 159,159,159,159,159,159,159,159,159,159,159,159,159, 2,159,159, + 2, 2, 2, 2, 2, 2,103,103,103,103,103,103,103,103,103,103, + 103,103,103,103, 2, 2,119,119,119,119,119,119,119,119,119,119, + 119,119,119,119, 2, 2,119,119, 2,119,119,119,119,119, 2, 2, + 2, 2, 2,119,119,119,146,146,146,146,146,146,146,146,146,146, + 146, 2, 2, 2, 2, 2, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, + 99, 2, 2, 2, 2, 99, 2, 2, 2, 2, 2, 2, 2, 99,136,139, + 13, 13,155, 2, 2, 2,136,136,136,136,136,136,136,136,155,155, + 155,155,155,155,155,155,155,155,155,155,155,155, 2, 2,136, 2, + 2, 2, 2, 2, 2, 2, 17, 17, 17, 17, 2, 17, 17, 17, 17, 17, + 17, 17, 2, 17, 17, 2, 17, 15, 15, 15, 15, 15, 15, 15, 17, 17, + 17, 2, 2, 2, 2, 2, 2, 2, 15, 2, 2, 2, 2, 2, 15, 15, + 15, 2, 2, 17, 2, 2, 2, 2, 2, 2, 17, 17, 17, 17,139,139, 139,139,139,139,139,139,139,139,139,139, 2, 2, 2, 2,105,105, 105,105,105,105,105,105,105,105,105, 2, 2, 2, 2, 2,105,105, 105,105,105, 2, 2, 2,105, 2, 2, 2, 2, 2, 2, 2,105,105, @@ -3831,24 +3877,27 @@ _hb_ucd_u8[17564] = 0, 0, 0, 2, 0, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0,131,131,131,131,131,131,131,131,131,131, 131,131, 2, 2, 2, 2, 2, 2, 2,131,131,131,131,131, 2,131, - 131,131,131,131,131,131, 56, 56, 56, 56, 56, 56, 56, 2, 56, 2, - 2, 56, 56, 56, 56, 56, 56, 56, 2, 56, 56, 2, 56, 56, 56, 56, - 56, 2, 2, 2, 2, 2,151,151,151,151,151,151,151,151,151,151, - 151,151,151, 2, 2, 2,151,151,151,151,151,151, 2, 2,151,151, - 2, 2, 2, 2,151,151,160,160,160,160,160,160,160,160,160,160, - 160,160,160,160,160, 2,152,152,152,152,152,152,152,152,152,152, - 2, 2, 2, 2, 2,152, 30, 30, 30, 30, 2, 30, 30, 2,113,113, - 113,113,113,113,113,113,113,113,113,113,113, 2, 2,113,113,113, - 113,113,113,113,113, 2,132,132,132,132,132,132,132,132,132,132, - 132,132, 2, 2, 2, 2,132,132, 2, 2, 2, 2,132,132, 3, 3, - 3, 3, 2, 3, 3, 3, 2, 3, 3, 2, 3, 2, 2, 3, 2, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 3, 3, 3, 3, 2, 3, - 2, 3, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, 3, 2, 3, - 2, 3, 2, 3, 3, 3, 2, 3, 2, 3, 2, 3, 2, 3, 2, 3, - 3, 3, 3, 2, 3, 2, 3, 3, 2, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 2, 2, 2, 2, 2, 3, 3, 3, 2, 3, 3, 3, 2, 2, - 2, 2, 2, 2, 0, 0, 15, 0, 0, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 0, 0, 0, 13, 2, 2, 2, 2, 2, 2, 2, 13, 13, + 131,131,131,131,131,131, 2, 2, 2, 2, 2, 19, 19, 19, 56, 56, + 56, 56, 56, 56, 56, 2, 56, 2, 2, 56, 56, 56, 56, 56, 56, 56, + 2, 56, 56, 2, 56, 56, 56, 56, 56, 2, 2, 2, 2, 2, 6, 6, + 6, 6, 6, 6, 2, 2, 2, 2, 2, 2, 2, 2, 2, 6,151,151, + 151,151,151,151,151,151,151,151,151,151,151, 2, 2, 2,151,151, + 151,151,151,151, 2, 2,151,151, 2, 2, 2, 2,151,151,160,160, + 160,160,160,160,160,160,160,160,160,160,160,160,160, 2,152,152, + 152,152,152,152,152,152,152,152, 2, 2, 2, 2, 2,152,164,164, + 164,164,164,164,164,164,164,164, 2, 2, 2, 2, 2, 2, 30, 30, + 30, 30, 2, 30, 30, 2,113,113,113,113,113,113,113,113,113,113, + 113,113,113, 2, 2,113,113,113,113,113,113,113,113, 2,132,132, + 132,132,132,132,132,132,132,132,132,132, 2, 2, 2, 2,132,132, + 2, 2, 2, 2,132,132, 3, 3, 3, 3, 2, 3, 3, 3, 2, 3, + 3, 2, 3, 2, 2, 3, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 2, 3, 3, 3, 3, 2, 3, 2, 3, 2, 2, 2, 2, 2, 2, + 3, 2, 2, 2, 2, 3, 2, 3, 2, 3, 2, 3, 3, 3, 2, 3, + 2, 3, 2, 3, 2, 3, 2, 3, 3, 3, 3, 2, 3, 2, 3, 3, + 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 2, 2, 2, 2, 3, + 3, 3, 2, 3, 3, 3, 2, 2, 2, 2, 2, 2, 0, 0, 15, 0, + 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 2, 2, + 2, 0, 0, 0, 0, 0, 13, 2, 2, 2, 2, 2, 2, 2, 13, 13, 13, 2, 2, 2, 2, 2, 2, 0, 2, 2, 2, 2, 2, 2, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 9, 9, 9, 10, 9, 11, 12, 13, 9, 9, 9, 14, 9, 9, 15, 9, 9, 9, 9, 9, 9, 9, 9, 9, @@ -3926,7 +3975,7 @@ _hb_ucd_u8[17564] = 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, }; static const uint16_t -_hb_ucd_u16[9200] = +_hb_ucd_u16[9320] = { 0, 0, 1, 2, 3, 4, 5, 6, 0, 0, 7, 8, 9, 10, 11, 12, 13, 13, 13, 14, 15, 13, 13, 16, 17, 18, 19, 20, 21, 22, 13, 23, @@ -4000,509 +4049,517 @@ _hb_ucd_u16[9200] = 48, 48, 48, 468, 48, 469, 48, 470, 48, 471, 472, 140, 140, 140, 140, 140, 48, 48, 48, 48, 196, 140, 140, 140, 9, 9, 9, 473, 11, 11, 11, 474, 48, 48, 475, 192, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 271, 476, - 48, 48, 477, 478, 140, 140, 140, 140, 48, 464, 479, 48, 62, 480, 140, 48, - 481, 140, 140, 48, 482, 140, 48, 314, 483, 48, 48, 484, 485, 457, 486, 487, - 222, 48, 48, 488, 489, 48, 196, 192, 490, 48, 491, 492, 493, 48, 48, 494, - 222, 48, 48, 495, 496, 497, 498, 499, 48, 97, 500, 501, 140, 140, 140, 140, - 502, 503, 504, 48, 48, 505, 506, 192, 507, 83, 84, 508, 509, 510, 511, 512, - 48, 48, 48, 513, 514, 515, 478, 140, 48, 48, 48, 516, 517, 192, 140, 140, - 48, 48, 518, 519, 520, 521, 140, 140, 48, 48, 48, 522, 523, 192, 524, 140, - 48, 48, 525, 526, 192, 140, 140, 140, 48, 173, 527, 528, 314, 140, 140, 140, - 48, 48, 500, 529, 140, 140, 140, 140, 140, 140, 9, 9, 11, 11, 148, 530, - 531, 532, 48, 533, 534, 192, 140, 140, 140, 140, 535, 48, 48, 536, 537, 140, - 538, 48, 48, 539, 540, 541, 48, 48, 542, 543, 544, 48, 48, 48, 48, 196, - 84, 48, 518, 545, 546, 148, 175, 547, 48, 548, 549, 550, 140, 140, 140, 140, - 551, 48, 48, 552, 553, 192, 554, 48, 555, 556, 192, 140, 140, 140, 140, 140, - 140, 140, 140, 140, 140, 140, 48, 557, 140, 140, 140, 100, 271, 558, 559, 560, - 48, 207, 140, 140, 140, 140, 140, 140, 272, 272, 272, 272, 272, 272, 561, 562, - 48, 48, 48, 48, 388, 140, 140, 140, 140, 48, 48, 48, 48, 48, 48, 563, - 48, 48, 200, 564, 140, 140, 140, 140, 48, 48, 48, 48, 314, 140, 140, 140, - 48, 48, 48, 196, 48, 200, 370, 48, 48, 48, 48, 200, 192, 48, 204, 565, - 48, 48, 48, 566, 567, 568, 569, 570, 48, 140, 140, 140, 140, 140, 140, 140, - 140, 140, 140, 140, 9, 9, 11, 11, 271, 571, 140, 140, 140, 140, 140, 140, - 48, 48, 48, 48, 572, 573, 574, 574, 575, 576, 140, 140, 140, 140, 577, 578, + 48, 48, 477, 478, 140, 140, 140, 479, 48, 464, 480, 48, 62, 481, 140, 48, + 482, 140, 140, 48, 483, 140, 48, 314, 484, 48, 48, 485, 486, 457, 487, 488, + 222, 48, 48, 489, 490, 48, 196, 192, 491, 48, 492, 493, 494, 48, 48, 495, + 222, 48, 48, 496, 497, 498, 499, 500, 48, 97, 501, 502, 503, 140, 140, 140, + 504, 505, 506, 48, 48, 507, 508, 192, 509, 83, 84, 510, 511, 512, 513, 514, + 48, 48, 48, 515, 516, 517, 478, 140, 48, 48, 48, 518, 519, 192, 140, 140, + 48, 48, 520, 521, 522, 523, 140, 140, 48, 48, 48, 524, 525, 192, 526, 140, + 48, 48, 527, 528, 192, 140, 140, 140, 48, 173, 529, 530, 314, 140, 140, 140, + 48, 48, 501, 531, 140, 140, 140, 140, 140, 140, 9, 9, 11, 11, 148, 532, + 533, 534, 48, 535, 536, 192, 140, 140, 140, 140, 537, 48, 48, 538, 539, 140, + 540, 48, 48, 541, 542, 543, 48, 48, 544, 545, 546, 48, 48, 48, 48, 196, + 547, 140, 140, 140, 140, 140, 140, 140, 84, 48, 520, 548, 549, 148, 175, 550, + 48, 551, 552, 553, 140, 140, 140, 140, 554, 48, 48, 555, 556, 192, 557, 48, + 558, 559, 192, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 48, 560, + 561, 115, 48, 562, 563, 192, 140, 140, 140, 140, 140, 100, 271, 564, 565, 566, + 48, 207, 140, 140, 140, 140, 140, 140, 272, 272, 272, 272, 272, 272, 567, 568, + 48, 48, 48, 48, 388, 140, 140, 140, 140, 48, 48, 48, 48, 48, 48, 569, + 48, 48, 48, 570, 571, 572, 140, 140, 48, 48, 48, 48, 314, 140, 140, 140, + 48, 48, 48, 196, 48, 200, 370, 48, 48, 48, 48, 200, 192, 48, 204, 573, + 48, 48, 48, 574, 575, 576, 577, 578, 48, 140, 140, 140, 140, 140, 140, 140, + 140, 140, 140, 140, 9, 9, 11, 11, 271, 579, 140, 140, 140, 140, 140, 140, + 48, 48, 48, 48, 580, 581, 582, 582, 583, 584, 140, 140, 140, 140, 585, 586, 48, 48, 48, 48, 48, 48, 48, 440, 48, 48, 48, 48, 48, 199, 140, 140, - 196, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 579, - 48, 48, 580, 140, 140, 580, 581, 48, 48, 48, 48, 48, 48, 48, 48, 206, - 48, 48, 48, 48, 48, 48, 71, 151, 196, 582, 583, 140, 140, 140, 140, 140, - 32, 32, 584, 32, 585, 209, 209, 209, 209, 209, 209, 209, 323, 140, 140, 140, - 209, 209, 209, 209, 209, 209, 209, 324, 209, 209, 586, 209, 209, 209, 587, 588, - 589, 209, 590, 209, 209, 209, 288, 140, 209, 209, 209, 209, 591, 140, 140, 140, - 140, 140, 140, 140, 140, 140, 271, 592, 209, 209, 209, 209, 209, 287, 271, 461, - 9, 593, 11, 594, 595, 596, 241, 9, 597, 598, 599, 600, 601, 9, 593, 11, - 602, 603, 11, 604, 605, 606, 607, 9, 608, 11, 9, 593, 11, 594, 595, 11, - 241, 9, 597, 607, 9, 608, 11, 9, 593, 11, 609, 9, 610, 611, 612, 613, - 11, 614, 9, 615, 616, 617, 618, 11, 619, 9, 620, 11, 621, 622, 622, 622, - 32, 32, 32, 623, 32, 32, 624, 625, 626, 627, 45, 140, 140, 140, 140, 140, - 628, 629, 140, 140, 140, 140, 140, 140, 630, 631, 632, 140, 140, 140, 140, 140, - 48, 48, 151, 633, 634, 140, 140, 140, 140, 48, 635, 140, 48, 48, 636, 637, - 140, 140, 140, 140, 140, 140, 638, 200, 48, 48, 48, 48, 639, 585, 140, 140, - 9, 9, 597, 11, 640, 370, 140, 140, 140, 140, 140, 140, 140, 140, 140, 498, - 271, 271, 641, 642, 140, 140, 140, 140, 498, 271, 643, 644, 140, 140, 140, 140, - 645, 48, 646, 647, 648, 649, 650, 651, 652, 206, 653, 206, 140, 140, 140, 654, - 209, 209, 325, 209, 209, 209, 209, 209, 209, 323, 334, 655, 655, 655, 209, 324, - 656, 209, 209, 209, 209, 209, 209, 209, 209, 209, 657, 140, 140, 140, 658, 209, - 659, 209, 209, 325, 660, 661, 324, 140, 209, 209, 209, 209, 209, 209, 209, 662, - 209, 209, 209, 209, 209, 663, 426, 426, 209, 209, 209, 209, 209, 209, 209, 323, - 209, 209, 209, 209, 209, 660, 325, 427, 325, 209, 209, 209, 664, 176, 209, 209, - 664, 209, 657, 661, 140, 140, 140, 140, 209, 209, 209, 209, 209, 323, 657, 665, - 287, 209, 426, 288, 324, 176, 664, 287, 209, 666, 209, 209, 288, 140, 140, 192, - 48, 48, 48, 48, 48, 48, 140, 140, 48, 48, 48, 196, 48, 48, 48, 48, + 196, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 587, + 48, 48, 588, 589, 140, 590, 591, 48, 48, 48, 48, 48, 48, 48, 48, 206, + 48, 48, 48, 48, 48, 48, 71, 151, 196, 592, 593, 140, 140, 140, 140, 140, + 32, 32, 594, 32, 595, 209, 209, 209, 209, 209, 209, 209, 323, 140, 140, 140, + 209, 209, 209, 209, 209, 209, 209, 324, 209, 209, 596, 209, 209, 209, 597, 598, + 599, 209, 600, 209, 209, 209, 288, 140, 209, 209, 209, 209, 601, 140, 140, 140, + 140, 140, 140, 140, 271, 602, 271, 602, 209, 209, 209, 209, 209, 287, 271, 461, + 9, 603, 11, 604, 605, 606, 241, 9, 607, 608, 609, 610, 611, 9, 603, 11, + 612, 613, 11, 614, 615, 616, 617, 9, 618, 11, 9, 603, 11, 604, 605, 11, + 241, 9, 607, 617, 9, 618, 11, 9, 603, 11, 619, 9, 620, 621, 622, 623, + 11, 624, 9, 625, 626, 627, 628, 11, 629, 9, 630, 11, 631, 632, 632, 632, + 32, 32, 32, 633, 32, 32, 634, 635, 636, 637, 45, 140, 140, 140, 140, 140, + 638, 639, 640, 140, 140, 140, 140, 140, 641, 642, 643, 27, 27, 27, 644, 140, + 645, 140, 140, 140, 140, 140, 140, 140, 48, 48, 151, 646, 647, 140, 140, 140, + 140, 48, 648, 140, 48, 48, 649, 650, 140, 140, 140, 140, 140, 48, 651, 192, + 140, 140, 140, 140, 140, 140, 652, 200, 48, 48, 48, 48, 653, 595, 140, 140, + 9, 9, 607, 11, 654, 370, 140, 140, 140, 140, 140, 140, 140, 140, 140, 499, + 271, 271, 655, 656, 140, 140, 140, 140, 499, 271, 657, 658, 140, 140, 140, 140, + 659, 48, 660, 661, 662, 663, 664, 665, 666, 206, 667, 206, 140, 140, 140, 668, + 209, 209, 325, 209, 209, 209, 209, 209, 209, 323, 334, 669, 669, 669, 209, 324, + 670, 209, 209, 209, 209, 209, 209, 209, 209, 209, 671, 140, 140, 140, 672, 209, + 673, 209, 209, 325, 674, 675, 324, 140, 209, 209, 209, 209, 209, 209, 209, 676, + 209, 209, 209, 209, 209, 677, 426, 426, 209, 209, 209, 209, 209, 209, 209, 678, + 209, 209, 209, 209, 209, 176, 325, 427, 325, 209, 209, 209, 679, 176, 209, 209, + 679, 209, 671, 675, 140, 140, 140, 140, 209, 209, 209, 209, 209, 323, 671, 426, + 674, 209, 209, 680, 681, 325, 674, 674, 209, 682, 209, 209, 288, 140, 140, 192, + 48, 48, 48, 48, 48, 48, 140, 140, 48, 48, 48, 207, 48, 48, 48, 48, 48, 204, 48, 48, 48, 48, 48, 48, 48, 48, 478, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 100, 140, 48, 204, 140, 140, 140, 140, 140, 140, - 48, 48, 48, 48, 71, 140, 140, 140, 667, 140, 668, 668, 668, 668, 668, 668, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 140, - 391, 391, 391, 391, 391, 391, 391, 669, 391, 391, 391, 391, 391, 391, 391, 670, - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 3, 1, 2, 2, 3, - 0, 0, 0, 0, 0, 4, 0, 4, 2, 2, 5, 2, 2, 2, 5, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 6, 0, 0, 0, 0, 7, 8, 0, 0, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 10, 11, - 12, 13, 14, 14, 15, 14, 14, 14, 14, 14, 14, 14, 16, 17, 14, 14, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 19, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 20, 21, 21, 21, 22, 20, 21, 21, 21, 21, - 21, 23, 24, 25, 25, 25, 25, 25, 25, 26, 25, 25, 25, 27, 28, 26, - 29, 30, 31, 32, 31, 31, 31, 31, 33, 34, 35, 31, 31, 31, 36, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 29, 31, 31, 31, 31, - 37, 38, 37, 37, 37, 37, 37, 37, 37, 39, 31, 31, 31, 31, 31, 31, - 40, 40, 40, 40, 40, 40, 41, 26, 42, 42, 42, 42, 42, 42, 42, 43, - 44, 44, 44, 44, 44, 45, 44, 46, 47, 47, 47, 48, 37, 49, 31, 31, - 31, 50, 51, 31, 31, 31, 31, 31, 31, 31, 31, 31, 52, 31, 31, 31, - 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 54, 53, 55, 53, 53, 53, - 56, 57, 58, 59, 59, 60, 61, 62, 57, 63, 64, 65, 66, 59, 59, 67, - 68, 69, 70, 71, 71, 72, 73, 74, 69, 75, 76, 77, 78, 71, 79, 26, - 80, 81, 82, 83, 83, 84, 85, 86, 81, 87, 88, 26, 89, 83, 90, 91, - 92, 93, 94, 95, 95, 96, 97, 98, 93, 99, 100, 101, 102, 95, 95, 26, - 103, 104, 105, 106, 107, 104, 108, 109, 104, 105, 110, 26, 111, 108, 108, 112, - 113, 114, 115, 113, 113, 115, 113, 116, 114, 117, 118, 119, 120, 113, 121, 113, - 122, 123, 124, 122, 122, 124, 125, 126, 123, 127, 128, 128, 129, 122, 130, 26, - 131, 132, 133, 131, 131, 131, 131, 131, 132, 133, 134, 131, 135, 131, 131, 131, - 136, 137, 138, 139, 137, 137, 140, 141, 138, 142, 143, 137, 144, 137, 145, 26, - 146, 147, 147, 147, 147, 147, 147, 148, 147, 147, 147, 149, 26, 26, 26, 26, - 150, 151, 152, 152, 153, 152, 152, 154, 155, 154, 152, 156, 26, 26, 26, 26, - 157, 157, 157, 157, 157, 157, 157, 157, 157, 158, 157, 157, 157, 159, 158, 157, - 157, 157, 157, 158, 157, 157, 157, 160, 157, 160, 161, 162, 26, 26, 26, 26, - 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, 163, - 163, 163, 163, 163, 164, 164, 164, 164, 165, 166, 164, 164, 164, 164, 164, 167, - 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, 168, - 169, 169, 169, 169, 169, 169, 169, 169, 169, 170, 171, 170, 169, 169, 169, 169, - 169, 170, 169, 169, 169, 169, 170, 171, 170, 169, 171, 169, 169, 169, 169, 169, - 169, 169, 170, 169, 169, 169, 169, 169, 169, 169, 169, 172, 169, 169, 169, 173, - 169, 169, 169, 174, 175, 175, 175, 175, 175, 175, 175, 175, 175, 175, 176, 176, - 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, - 178, 178, 178, 179, 180, 180, 180, 180, 180, 180, 180, 180, 180, 181, 180, 182, - 183, 183, 184, 185, 186, 186, 187, 26, 188, 188, 189, 26, 190, 191, 192, 26, - 193, 193, 193, 193, 193, 193, 193, 193, 193, 193, 193, 194, 193, 195, 193, 195, - 196, 197, 197, 198, 197, 197, 197, 197, 197, 197, 197, 197, 197, 197, 197, 199, - 197, 197, 197, 197, 197, 200, 177, 177, 177, 177, 177, 177, 177, 177, 201, 26, - 202, 202, 202, 203, 202, 204, 202, 204, 205, 202, 206, 206, 206, 207, 208, 26, - 209, 209, 209, 209, 209, 210, 209, 209, 209, 211, 209, 212, 193, 193, 193, 193, - 213, 213, 213, 214, 215, 215, 215, 215, 215, 215, 215, 216, 215, 215, 215, 217, - 215, 218, 215, 218, 215, 219, 9, 9, 9, 220, 26, 26, 26, 26, 26, 26, - 221, 221, 221, 221, 221, 221, 221, 221, 221, 222, 221, 221, 221, 221, 221, 223, - 224, 224, 224, 224, 224, 224, 224, 224, 225, 225, 225, 225, 225, 225, 226, 227, - 228, 228, 228, 228, 228, 228, 228, 229, 228, 230, 231, 231, 231, 231, 231, 231, - 18, 232, 164, 164, 164, 164, 164, 233, 224, 26, 234, 9, 235, 236, 237, 238, - 2, 2, 2, 2, 239, 240, 2, 2, 2, 2, 2, 241, 242, 243, 2, 244, - 2, 2, 2, 2, 2, 2, 2, 245, 9, 9, 9, 9, 9, 9, 9, 9, - 14, 14, 246, 246, 14, 14, 14, 14, 246, 246, 14, 247, 14, 14, 14, 246, - 14, 14, 14, 14, 14, 14, 248, 14, 248, 14, 249, 250, 14, 14, 251, 252, - 0, 253, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 254, 0, 255, 256, - 0, 257, 2, 258, 0, 0, 0, 0, 259, 26, 9, 9, 9, 9, 260, 26, - 0, 0, 0, 0, 261, 262, 4, 0, 0, 263, 0, 0, 2, 2, 2, 2, - 2, 264, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 48, 48, 48, 48, 71, 48, 48, 48, 48, 48, 48, 140, 140, 140, 140, 140, + 683, 140, 570, 570, 570, 570, 570, 570, 32, 32, 32, 32, 32, 32, 32, 32, + 32, 32, 32, 32, 32, 32, 32, 140, 391, 391, 391, 391, 391, 391, 391, 684, + 391, 391, 391, 391, 391, 391, 391, 685, 0, 0, 0, 0, 0, 0, 0, 0, + 1, 2, 2, 3, 1, 2, 2, 3, 0, 0, 0, 0, 0, 4, 0, 4, + 2, 2, 5, 2, 2, 2, 5, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 6, + 0, 0, 0, 0, 7, 8, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 10, 11, 12, 13, 14, 14, 15, 14, 14, 14, + 14, 14, 14, 14, 16, 17, 14, 14, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 19, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 20, 21, + 21, 21, 22, 20, 21, 21, 21, 21, 21, 23, 24, 25, 25, 25, 25, 25, + 25, 26, 25, 25, 25, 27, 28, 26, 29, 30, 31, 32, 31, 31, 31, 31, + 33, 34, 35, 31, 31, 31, 36, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 29, 31, 31, 31, 31, 37, 38, 37, 37, 37, 37, 37, 37, + 37, 39, 31, 31, 31, 31, 31, 31, 40, 40, 40, 40, 40, 40, 41, 26, + 42, 42, 42, 42, 42, 42, 42, 43, 44, 44, 44, 44, 44, 45, 44, 46, + 47, 47, 47, 48, 37, 49, 31, 31, 31, 50, 51, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 52, 31, 31, 31, 53, 53, 53, 53, 53, 53, 53, 53, + 53, 53, 54, 53, 55, 53, 53, 53, 56, 57, 58, 59, 59, 60, 61, 62, + 57, 63, 64, 65, 66, 59, 59, 67, 68, 69, 70, 71, 71, 72, 73, 74, + 69, 75, 76, 77, 78, 71, 79, 26, 80, 81, 82, 83, 83, 84, 85, 86, + 81, 87, 88, 26, 89, 83, 90, 91, 92, 93, 94, 95, 95, 96, 97, 98, + 93, 99, 100, 101, 102, 95, 95, 26, 103, 104, 105, 106, 107, 104, 108, 109, + 104, 105, 110, 26, 111, 108, 108, 112, 113, 114, 115, 113, 113, 115, 113, 116, + 114, 117, 118, 119, 120, 113, 121, 113, 122, 123, 124, 122, 122, 124, 125, 126, + 123, 127, 128, 128, 129, 122, 130, 26, 131, 132, 133, 131, 131, 131, 131, 131, + 132, 133, 134, 131, 135, 131, 131, 131, 136, 137, 138, 139, 137, 137, 140, 141, + 138, 142, 143, 137, 144, 137, 145, 26, 146, 147, 147, 147, 147, 147, 147, 148, + 147, 147, 147, 149, 26, 26, 26, 26, 150, 151, 152, 152, 153, 152, 152, 154, + 155, 156, 152, 157, 26, 26, 26, 26, 158, 158, 158, 158, 158, 158, 158, 158, + 158, 159, 158, 158, 158, 160, 159, 158, 158, 158, 158, 159, 158, 158, 158, 161, + 158, 161, 162, 163, 26, 26, 26, 26, 164, 164, 164, 164, 164, 164, 164, 164, + 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 165, 165, 165, 165, + 166, 167, 165, 165, 165, 165, 165, 168, 169, 169, 169, 169, 169, 169, 169, 169, + 169, 169, 169, 169, 169, 169, 169, 169, 170, 170, 170, 170, 170, 170, 170, 170, + 170, 171, 172, 171, 170, 170, 170, 170, 170, 171, 170, 170, 170, 170, 171, 172, + 171, 170, 172, 170, 170, 170, 170, 170, 170, 170, 171, 170, 170, 170, 170, 170, + 170, 170, 170, 173, 170, 170, 170, 174, 170, 170, 170, 175, 176, 176, 176, 176, + 176, 176, 176, 176, 176, 176, 177, 177, 178, 178, 178, 178, 178, 178, 178, 178, + 178, 178, 178, 178, 178, 178, 178, 178, 179, 179, 179, 180, 181, 181, 181, 181, + 181, 181, 181, 181, 181, 182, 181, 183, 184, 184, 185, 186, 187, 187, 188, 26, + 189, 189, 190, 26, 191, 192, 193, 26, 194, 194, 194, 194, 194, 194, 194, 194, + 194, 194, 194, 195, 194, 196, 194, 196, 197, 198, 198, 199, 198, 198, 198, 198, + 198, 198, 198, 198, 198, 198, 198, 200, 198, 198, 198, 198, 198, 201, 178, 178, + 178, 178, 178, 178, 178, 178, 202, 26, 203, 203, 203, 204, 203, 205, 203, 205, + 206, 203, 207, 207, 207, 208, 209, 26, 210, 210, 210, 210, 210, 211, 210, 210, + 210, 212, 210, 213, 194, 194, 194, 194, 214, 214, 214, 215, 216, 216, 216, 216, + 216, 216, 216, 217, 216, 216, 216, 218, 216, 219, 216, 219, 216, 220, 9, 9, + 9, 221, 26, 26, 26, 26, 26, 26, 222, 222, 222, 222, 222, 222, 222, 222, + 222, 223, 222, 222, 222, 222, 222, 224, 225, 225, 225, 225, 225, 225, 225, 225, + 226, 226, 226, 226, 226, 226, 227, 228, 229, 229, 229, 229, 229, 229, 229, 230, + 229, 231, 232, 232, 232, 232, 232, 232, 18, 233, 165, 165, 165, 165, 165, 234, + 225, 26, 235, 9, 236, 237, 238, 239, 2, 2, 2, 2, 240, 241, 2, 2, + 2, 2, 2, 242, 243, 244, 2, 245, 2, 2, 2, 2, 2, 2, 2, 246, + 9, 9, 9, 9, 9, 9, 9, 9, 14, 14, 247, 247, 14, 14, 14, 14, + 247, 247, 14, 248, 14, 14, 14, 247, 14, 14, 14, 14, 14, 14, 249, 14, + 249, 14, 250, 251, 14, 14, 252, 253, 0, 254, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 255, 0, 256, 257, 0, 258, 2, 259, 0, 0, 0, 0, + 260, 26, 9, 9, 9, 9, 261, 26, 0, 0, 0, 0, 262, 263, 4, 0, + 0, 264, 0, 0, 2, 2, 2, 2, 2, 265, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 257, 26, 26, 26, 0, 265, 26, 26, 0, 0, 0, 0, - 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, 266, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 267, 0, - 0, 0, 268, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 269, 269, 269, 269, 269, 269, 269, 269, 269, 269, 269, 269, 2, 2, 2, 2, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 270, 271, - 164, 164, 164, 164, 165, 166, 272, 272, 272, 272, 272, 272, 272, 273, 274, 273, - 169, 169, 171, 26, 171, 171, 171, 171, 171, 171, 171, 171, 18, 18, 18, 18, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 275, 26, 26, 26, 26, - 276, 276, 276, 277, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 278, 26, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 279, 26, 26, 26, 0, 280, - 281, 0, 0, 0, 282, 283, 0, 284, 285, 286, 286, 286, 286, 286, 286, 286, - 286, 286, 287, 288, 289, 290, 290, 290, 290, 290, 290, 290, 290, 290, 290, 291, - 292, 293, 293, 293, 293, 293, 294, 168, 168, 168, 168, 168, 168, 168, 168, 168, - 168, 295, 0, 0, 293, 293, 293, 293, 0, 0, 0, 0, 280, 26, 290, 290, - 168, 168, 168, 295, 0, 0, 0, 0, 0, 0, 0, 0, 168, 168, 168, 296, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 290, 290, 290, 290, 290, 297, - 290, 290, 290, 290, 290, 290, 290, 290, 290, 290, 290, 0, 0, 0, 0, 0, - 276, 276, 276, 276, 276, 276, 276, 276, 0, 0, 0, 0, 0, 0, 0, 0, - 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, 298, - 298, 299, 298, 298, 298, 298, 298, 298, 300, 26, 301, 301, 301, 301, 301, 301, - 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, 302, - 302, 302, 302, 302, 302, 303, 26, 26, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 26, - 0, 0, 0, 0, 305, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 306, 2, 2, 2, 2, 2, 2, 2, 307, 308, 309, 26, 26, 310, 2, - 311, 311, 311, 311, 311, 312, 0, 313, 314, 314, 314, 314, 314, 314, 314, 26, - 315, 315, 315, 315, 315, 315, 315, 315, 316, 317, 315, 318, 53, 53, 53, 53, - 319, 319, 319, 319, 319, 320, 321, 321, 321, 321, 322, 323, 168, 168, 168, 324, - 325, 325, 325, 325, 325, 325, 325, 325, 325, 326, 325, 327, 163, 163, 163, 328, - 329, 329, 329, 329, 329, 329, 330, 26, 329, 331, 329, 332, 163, 163, 163, 163, - 333, 333, 333, 333, 333, 333, 333, 333, 334, 26, 26, 335, 336, 336, 337, 26, - 338, 338, 338, 26, 171, 171, 2, 2, 2, 2, 2, 339, 340, 341, 175, 175, - 175, 175, 175, 175, 175, 175, 175, 175, 336, 336, 336, 336, 336, 342, 336, 343, - 168, 168, 168, 168, 344, 26, 168, 168, 295, 345, 168, 168, 168, 168, 168, 344, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 258, 26, 26, 26, + 0, 266, 26, 26, 0, 0, 0, 0, 267, 267, 267, 267, 267, 267, 267, 267, + 267, 267, 267, 267, 267, 267, 267, 267, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 268, 0, 0, 0, 269, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 270, 270, 270, 270, 270, 270, 270, 270, + 270, 270, 270, 270, 2, 2, 2, 2, 17, 17, 17, 17, 17, 17, 17, 17, + 17, 17, 17, 17, 17, 17, 271, 272, 165, 165, 165, 165, 166, 167, 273, 273, + 273, 273, 273, 273, 273, 274, 275, 274, 170, 170, 172, 26, 172, 172, 172, 172, + 172, 172, 172, 172, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 276, 26, 26, 26, 26, 277, 277, 277, 278, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 277, 279, 26, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 280, 26, 26, 26, 0, 281, 282, 0, 0, 0, 283, 284, 0, 285, + 286, 287, 287, 287, 287, 287, 287, 287, 287, 287, 288, 289, 290, 291, 291, 291, + 291, 291, 291, 291, 291, 291, 291, 292, 293, 294, 294, 294, 294, 294, 295, 169, + 169, 169, 169, 169, 169, 169, 169, 169, 169, 296, 0, 0, 294, 294, 294, 294, + 0, 0, 0, 0, 281, 26, 291, 291, 169, 169, 169, 296, 0, 0, 0, 0, + 0, 0, 0, 0, 169, 169, 169, 297, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 291, 291, 291, 291, 291, 298, 291, 291, 291, 291, 291, 291, 291, 291, + 291, 291, 291, 0, 0, 0, 0, 0, 277, 277, 277, 277, 277, 277, 277, 277, + 0, 0, 0, 0, 0, 0, 0, 0, 299, 299, 299, 299, 299, 299, 299, 299, + 299, 299, 299, 299, 299, 299, 299, 299, 299, 300, 299, 299, 299, 299, 299, 299, + 301, 26, 302, 302, 302, 302, 302, 302, 303, 303, 303, 303, 303, 303, 303, 303, + 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 303, 304, 26, 26, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 305, 305, 305, 305, + 305, 305, 305, 305, 305, 305, 305, 26, 0, 0, 0, 0, 306, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 307, 2, 2, 2, 2, 2, 2, + 2, 308, 309, 310, 26, 26, 311, 2, 312, 312, 312, 312, 312, 313, 0, 314, + 315, 315, 315, 315, 315, 315, 315, 26, 316, 316, 316, 316, 316, 316, 316, 316, + 317, 318, 316, 319, 53, 53, 53, 53, 320, 320, 320, 320, 320, 321, 322, 322, + 322, 322, 323, 324, 169, 169, 169, 325, 326, 326, 326, 326, 326, 326, 326, 326, + 326, 327, 326, 328, 164, 164, 164, 329, 330, 330, 330, 330, 330, 330, 331, 26, + 330, 332, 330, 333, 164, 164, 164, 164, 334, 334, 334, 334, 334, 334, 334, 334, + 335, 26, 26, 336, 337, 337, 338, 26, 339, 339, 339, 26, 172, 172, 2, 2, + 2, 2, 2, 340, 341, 342, 176, 176, 176, 176, 176, 176, 176, 176, 176, 176, + 337, 337, 337, 337, 337, 343, 337, 344, 169, 169, 169, 169, 345, 26, 169, 169, + 296, 346, 169, 169, 169, 169, 169, 345, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 280, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 347, 26, 26, 26, 26, 348, 26, 349, 350, 25, 25, 351, 352, + 353, 25, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 354, 26, 355, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 356, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 357, 31, 31, 31, 31, 31, + 31, 358, 26, 26, 26, 26, 31, 31, 9, 9, 0, 314, 9, 359, 0, 0, + 0, 0, 360, 0, 258, 281, 361, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 362, 363, 0, 0, 0, 1, 2, 2, 3, + 1, 2, 2, 3, 364, 291, 290, 291, 291, 291, 291, 365, 169, 169, 169, 296, + 366, 366, 366, 367, 258, 258, 26, 368, 369, 370, 369, 369, 371, 369, 369, 372, + 369, 373, 369, 373, 26, 26, 26, 26, 369, 369, 369, 369, 369, 369, 369, 369, + 369, 369, 369, 369, 369, 369, 369, 374, 375, 0, 0, 0, 0, 0, 376, 0, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 253, 0, 377, 378, 26, 26, 26, + 26, 26, 0, 0, 0, 0, 0, 379, 380, 380, 380, 381, 382, 382, 382, 382, + 382, 382, 383, 26, 384, 0, 0, 281, 385, 385, 385, 385, 386, 387, 388, 388, + 388, 389, 390, 390, 390, 390, 390, 391, 392, 392, 392, 393, 394, 394, 394, 394, + 395, 394, 396, 26, 26, 26, 26, 26, 397, 397, 397, 397, 397, 397, 397, 397, + 397, 397, 398, 398, 398, 398, 398, 398, 399, 399, 399, 400, 399, 401, 402, 402, + 402, 402, 403, 402, 402, 402, 402, 403, 404, 404, 404, 404, 404, 26, 405, 405, + 405, 405, 405, 405, 406, 407, 408, 409, 408, 409, 410, 408, 411, 408, 411, 412, + 26, 26, 26, 26, 26, 26, 26, 26, 413, 413, 413, 413, 413, 413, 413, 413, + 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 413, 414, 26, + 413, 413, 415, 26, 413, 26, 26, 26, 416, 2, 2, 2, 2, 2, 417, 308, + 26, 26, 26, 26, 26, 26, 26, 26, 418, 419, 420, 420, 420, 420, 421, 422, + 423, 423, 424, 423, 425, 425, 425, 425, 426, 426, 426, 427, 428, 426, 26, 26, + 26, 26, 26, 26, 429, 429, 430, 431, 432, 432, 432, 433, 434, 434, 434, 435, + 26, 26, 26, 26, 26, 26, 26, 26, 436, 436, 436, 436, 437, 437, 437, 438, + 437, 437, 439, 437, 437, 437, 437, 437, 440, 441, 442, 443, 444, 444, 445, 446, + 444, 447, 444, 447, 448, 448, 448, 448, 449, 449, 449, 449, 26, 26, 26, 26, + 450, 450, 450, 450, 451, 452, 451, 26, 453, 453, 453, 453, 453, 453, 454, 455, + 456, 456, 457, 456, 458, 458, 459, 458, 460, 460, 461, 462, 26, 463, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 464, 464, 464, 464, 464, 464, 464, 464, + 464, 465, 26, 26, 26, 26, 26, 26, 466, 466, 466, 466, 466, 466, 467, 26, + 466, 466, 466, 466, 466, 466, 467, 468, 469, 469, 469, 469, 469, 26, 469, 470, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 31, 31, 31, 50, 471, 471, 471, 471, 471, 472, 473, 26, + 26, 26, 26, 26, 26, 26, 26, 474, 475, 475, 475, 475, 475, 26, 476, 476, + 476, 476, 476, 477, 26, 26, 478, 478, 478, 479, 26, 26, 26, 26, 480, 480, + 480, 481, 26, 26, 482, 482, 483, 26, 484, 484, 484, 484, 484, 484, 484, 484, + 484, 485, 486, 484, 484, 484, 485, 487, 488, 488, 488, 488, 488, 488, 488, 488, + 489, 490, 491, 491, 491, 492, 491, 493, 494, 494, 494, 494, 494, 494, 495, 494, + 494, 26, 496, 496, 496, 496, 497, 26, 498, 498, 498, 498, 498, 498, 498, 498, + 498, 498, 498, 498, 499, 137, 500, 26, 501, 501, 502, 501, 501, 501, 501, 501, + 503, 26, 26, 26, 26, 26, 26, 26, 504, 505, 506, 507, 506, 508, 509, 509, + 509, 509, 509, 509, 509, 510, 509, 511, 512, 513, 514, 515, 515, 516, 517, 518, + 513, 519, 520, 521, 522, 523, 523, 26, 524, 524, 524, 524, 524, 524, 524, 524, + 524, 524, 524, 525, 526, 26, 26, 26, 527, 527, 527, 527, 527, 527, 527, 527, + 527, 26, 527, 528, 26, 26, 26, 26, 529, 529, 529, 529, 529, 529, 530, 529, + 529, 529, 529, 530, 26, 26, 26, 26, 531, 531, 531, 531, 531, 531, 531, 531, + 532, 26, 531, 533, 198, 534, 26, 26, 535, 535, 535, 535, 535, 535, 535, 536, + 535, 536, 26, 26, 26, 26, 26, 26, 537, 537, 537, 538, 537, 539, 537, 537, + 540, 26, 26, 26, 26, 26, 26, 26, 541, 541, 541, 541, 541, 541, 541, 542, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 543, 543, 543, 543, + 543, 543, 543, 543, 543, 543, 544, 545, 546, 547, 548, 549, 549, 549, 550, 551, + 546, 26, 549, 552, 26, 26, 26, 26, 26, 26, 26, 26, 553, 554, 553, 553, + 553, 553, 553, 554, 555, 26, 26, 26, 556, 556, 556, 556, 556, 556, 556, 556, + 556, 26, 557, 557, 557, 557, 557, 557, 557, 557, 557, 557, 558, 26, 178, 178, + 559, 559, 559, 559, 559, 559, 559, 560, 53, 561, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 562, 563, 562, 562, 562, 562, 564, 562, + 565, 26, 562, 562, 562, 566, 567, 567, 567, 567, 568, 567, 567, 569, 570, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 571, 572, 573, 573, 573, 573, 571, 574, + 573, 26, 573, 575, 576, 577, 578, 578, 578, 579, 580, 581, 578, 582, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 583, 583, 583, 584, 585, 585, 586, 585, 585, 585, 585, 587, + 585, 585, 585, 588, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 589, 26, + 108, 108, 108, 108, 108, 108, 590, 591, 592, 592, 592, 592, 592, 592, 592, 592, + 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 593, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 592, 592, 592, 592, 592, 592, 592, 592, + 592, 592, 592, 592, 592, 594, 595, 26, 592, 592, 592, 592, 592, 592, 592, 592, + 596, 26, 26, 26, 26, 26, 26, 26, 26, 26, 597, 597, 597, 597, 597, 597, + 597, 597, 597, 597, 597, 597, 598, 26, 599, 599, 599, 599, 599, 599, 599, 599, + 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, 599, + 599, 599, 600, 26, 26, 26, 26, 26, 601, 601, 601, 601, 601, 601, 601, 601, + 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, 601, + 602, 26, 26, 26, 26, 26, 26, 26, 305, 305, 305, 305, 305, 305, 305, 305, + 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 305, 603, + 604, 604, 604, 605, 604, 606, 607, 607, 607, 607, 607, 607, 607, 607, 607, 608, + 607, 609, 610, 610, 610, 611, 611, 26, 612, 612, 612, 612, 612, 612, 612, 612, + 613, 26, 612, 614, 614, 612, 612, 615, 612, 612, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 617, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 618, 618, 618, 618, 618, 618, 618, 618, + 618, 619, 618, 618, 618, 618, 618, 618, 618, 620, 618, 618, 26, 26, 26, 26, + 26, 26, 26, 26, 621, 26, 347, 26, 622, 622, 622, 622, 622, 622, 622, 622, + 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, 622, + 622, 622, 622, 622, 622, 622, 622, 26, 623, 623, 623, 623, 623, 623, 623, 623, + 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, 623, + 623, 623, 624, 26, 26, 26, 26, 26, 622, 625, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 279, 276, 276, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 346, 26, 26, 26, 26, - 347, 26, 348, 349, 25, 25, 350, 351, 352, 25, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 353, 26, 354, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 355, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 356, 31, 31, 31, 31, 31, 31, 357, 26, 26, 26, 26, 31, 31, - 9, 9, 0, 313, 9, 358, 0, 0, 0, 0, 359, 0, 257, 280, 360, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 361, - 362, 0, 0, 0, 1, 2, 2, 3, 1, 2, 2, 3, 363, 290, 289, 290, - 290, 290, 290, 364, 168, 168, 168, 295, 365, 365, 365, 366, 257, 257, 26, 367, - 368, 369, 368, 368, 370, 368, 368, 371, 368, 372, 368, 372, 26, 26, 26, 26, - 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 368, 373, - 374, 0, 0, 0, 0, 0, 375, 0, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 252, 0, 376, 377, 26, 26, 26, 26, 26, 0, 0, 0, 0, 0, 378, - 379, 379, 379, 380, 381, 381, 381, 381, 381, 381, 382, 26, 383, 0, 0, 280, - 384, 384, 384, 384, 385, 386, 387, 387, 387, 388, 389, 389, 389, 389, 389, 390, - 391, 391, 391, 392, 393, 393, 393, 393, 394, 393, 395, 26, 26, 26, 26, 26, - 396, 396, 396, 396, 396, 396, 396, 396, 396, 396, 397, 397, 397, 397, 397, 397, - 398, 398, 398, 399, 398, 400, 401, 401, 401, 401, 402, 401, 401, 401, 401, 402, - 403, 403, 403, 403, 403, 26, 404, 404, 404, 404, 404, 404, 405, 406, 407, 408, - 407, 408, 409, 407, 410, 407, 410, 411, 26, 26, 26, 26, 26, 26, 26, 26, - 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, 412, - 412, 412, 412, 412, 412, 412, 413, 26, 412, 412, 414, 26, 412, 26, 26, 26, - 415, 2, 2, 2, 2, 2, 416, 307, 26, 26, 26, 26, 26, 26, 26, 26, - 417, 418, 419, 419, 419, 419, 420, 421, 422, 422, 423, 422, 424, 424, 424, 424, - 425, 425, 425, 426, 427, 425, 26, 26, 26, 26, 26, 26, 428, 428, 429, 430, - 431, 431, 431, 432, 433, 433, 433, 434, 26, 26, 26, 26, 26, 26, 26, 26, - 435, 435, 435, 435, 436, 436, 436, 437, 436, 436, 438, 436, 436, 436, 436, 436, - 439, 440, 441, 442, 443, 443, 444, 445, 443, 446, 443, 446, 447, 447, 447, 447, - 448, 448, 448, 448, 26, 26, 26, 26, 449, 449, 449, 449, 450, 451, 450, 26, - 452, 452, 452, 452, 452, 452, 453, 454, 455, 455, 456, 455, 457, 457, 458, 457, - 459, 459, 460, 461, 26, 462, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 463, 463, 463, 463, 463, 463, 463, 463, 463, 464, 26, 26, 26, 26, 26, 26, - 465, 465, 465, 465, 465, 465, 466, 26, 465, 465, 465, 465, 465, 465, 466, 467, - 468, 468, 468, 468, 468, 26, 468, 469, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 31, 31, 31, 50, - 470, 470, 470, 470, 470, 471, 472, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 473, 473, 473, 473, 473, 26, 474, 474, 474, 474, 474, 475, 26, 26, 476, 476, - 476, 477, 26, 26, 26, 26, 478, 478, 478, 479, 26, 26, 480, 480, 481, 26, - 482, 482, 482, 482, 482, 482, 482, 482, 482, 483, 484, 482, 482, 482, 483, 485, - 486, 486, 486, 486, 486, 486, 486, 486, 487, 488, 489, 489, 489, 490, 489, 491, - 492, 492, 492, 492, 492, 492, 493, 492, 492, 26, 494, 494, 494, 494, 495, 26, - 496, 496, 496, 496, 496, 496, 496, 496, 496, 496, 496, 496, 497, 137, 498, 26, - 499, 499, 500, 499, 499, 499, 499, 501, 26, 26, 26, 26, 26, 26, 26, 26, - 502, 503, 504, 505, 504, 506, 507, 507, 507, 507, 507, 507, 507, 508, 507, 509, - 510, 511, 512, 513, 513, 514, 515, 516, 511, 517, 518, 519, 520, 521, 521, 26, - 522, 522, 522, 522, 522, 522, 522, 522, 522, 522, 522, 523, 524, 26, 26, 26, - 525, 525, 525, 525, 525, 525, 525, 525, 525, 26, 525, 526, 26, 26, 26, 26, - 527, 527, 527, 527, 527, 527, 528, 527, 527, 527, 527, 528, 26, 26, 26, 26, - 529, 529, 529, 529, 529, 529, 529, 529, 530, 26, 529, 531, 197, 532, 26, 26, - 533, 533, 533, 533, 533, 533, 533, 534, 533, 534, 26, 26, 26, 26, 26, 26, - 535, 535, 535, 536, 535, 537, 535, 535, 538, 26, 26, 26, 26, 26, 26, 26, - 539, 539, 539, 539, 539, 539, 539, 540, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 541, 541, 541, 541, 541, 541, 541, 541, 541, 541, 542, 543, - 544, 545, 546, 547, 547, 547, 548, 549, 544, 26, 547, 550, 26, 26, 26, 26, - 26, 26, 26, 26, 551, 552, 551, 551, 551, 551, 551, 552, 553, 26, 26, 26, - 554, 554, 554, 554, 554, 554, 554, 554, 554, 26, 555, 555, 555, 555, 555, 555, - 555, 555, 555, 555, 556, 26, 177, 177, 557, 557, 557, 557, 557, 557, 557, 558, - 559, 560, 559, 559, 559, 559, 561, 559, 562, 26, 559, 559, 559, 563, 564, 564, - 564, 564, 565, 564, 564, 566, 567, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 568, 569, 570, 570, 570, 570, 568, 571, 570, 26, 570, 572, 573, 574, 575, 575, - 575, 576, 577, 578, 575, 579, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 580, 580, 580, 581, - 26, 26, 26, 26, 26, 26, 582, 26, 108, 108, 108, 108, 108, 108, 583, 584, - 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, - 585, 585, 585, 586, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 585, 587, 588, 26, - 585, 585, 585, 585, 585, 585, 585, 585, 589, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 590, 590, 590, 590, 590, 590, 590, 590, 590, 590, 590, 590, 591, 26, - 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, 592, - 592, 592, 592, 592, 592, 593, 592, 594, 26, 26, 26, 26, 26, 26, 26, 26, - 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, 595, - 595, 595, 595, 595, 595, 595, 595, 595, 596, 26, 26, 26, 26, 26, 26, 26, - 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, 304, - 304, 304, 304, 304, 304, 304, 304, 597, 598, 598, 598, 599, 598, 600, 601, 601, - 601, 601, 601, 601, 601, 601, 601, 602, 601, 603, 604, 604, 604, 605, 605, 26, - 606, 606, 606, 606, 606, 606, 606, 606, 607, 26, 606, 608, 608, 606, 606, 609, - 606, 606, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 610, 610, 610, 610, 610, 610, 610, 610, - 610, 610, 610, 611, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 612, 612, 612, 612, 612, 612, 612, 612, 612, 613, 612, 612, 612, 612, 612, 612, - 612, 614, 612, 612, 26, 26, 26, 26, 26, 26, 26, 26, 615, 26, 346, 26, - 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, - 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 616, 26, - 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, - 617, 617, 617, 617, 617, 617, 617, 617, 617, 617, 618, 26, 26, 26, 26, 26, - 616, 619, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 620, 621, - 622, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, - 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, 286, - 286, 286, 286, 286, 623, 26, 26, 26, 26, 26, 624, 26, 625, 26, 626, 626, - 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, - 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 626, 627, - 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 628, 629, 628, 630, - 628, 631, 628, 632, 280, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 9, 9, 9, 9, 9, 633, 9, 9, 220, 26, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 280, 26, 26, 26, 26, 26, 26, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 275, 26, - 0, 0, 0, 0, 257, 362, 0, 0, 0, 0, 0, 0, 634, 635, 0, 636, - 637, 638, 0, 0, 0, 639, 0, 0, 0, 0, 0, 0, 0, 265, 26, 26, - 14, 14, 14, 14, 14, 14, 14, 14, 246, 26, 26, 26, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 0, 0, 280, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 257, 26, 0, 0, 0, 259, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 254, 0, 0, 0, 0, 0, - 0, 0, 0, 254, 640, 641, 0, 642, 643, 0, 0, 0, 0, 0, 0, 0, - 268, 644, 254, 254, 0, 0, 0, 645, 646, 647, 648, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 275, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 267, 0, 0, 0, 0, 0, 0, - 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, 649, - 649, 650, 26, 651, 652, 649, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 2, 2, 2, 347, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 653, 269, 269, 654, 655, 656, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 657, 657, 657, 657, 657, 658, 657, 659, 657, 660, 26, 26, 26, 26, 26, 26, - 26, 26, 661, 661, 661, 662, 26, 26, 663, 663, 663, 663, 663, 663, 663, 664, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 171, 665, 169, 171, - 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, 666, - 666, 666, 666, 666, 666, 666, 666, 666, 667, 666, 668, 26, 26, 26, 26, 26, - 669, 669, 669, 669, 669, 669, 669, 669, 669, 670, 669, 671, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 362, 0, - 0, 0, 0, 0, 0, 0, 376, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 362, 0, 0, 0, 0, 0, 0, 275, 26, 26, 26, 26, 26, 26, 26, 26, - 672, 31, 31, 31, 673, 674, 675, 676, 677, 678, 673, 679, 673, 675, 675, 680, - 31, 681, 31, 682, 683, 681, 31, 682, 26, 26, 26, 26, 26, 26, 51, 26, - 0, 0, 0, 0, 0, 280, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 280, 26, 0, 257, 362, 0, 362, 0, 362, 0, 0, 0, 275, 26, - 0, 0, 0, 0, 0, 275, 26, 26, 26, 26, 26, 26, 684, 0, 0, 0, - 685, 26, 0, 0, 0, 0, 0, 280, 0, 259, 313, 26, 275, 26, 26, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 686, 0, 376, 0, 376, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 280, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 259, 0, 280, 259, 26, - 0, 280, 0, 0, 0, 0, 0, 0, 0, 26, 0, 313, 0, 0, 0, 0, - 0, 26, 0, 0, 0, 275, 313, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 280, 26, 0, 275, 376, 376, - 257, 26, 0, 0, 0, 376, 0, 265, 275, 26, 0, 313, 0, 26, 257, 26, - 0, 0, 359, 0, 0, 0, 0, 0, 0, 265, 26, 26, 26, 26, 0, 313, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 26, 26, 26, 26, - 276, 276, 276, 276, 276, 276, 276, 687, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 279, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 276, 346, 26, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 276, 687, 26, 26, 26, - 276, 276, 276, 279, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, - 276, 276, 276, 276, 276, 276, 276, 276, 276, 688, 26, 26, 26, 26, 26, 26, - 689, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 26, 26, 26, 26, 26, 26, 626, 627, 628, 287, 287, 287, 287, 287, 287, 287, + 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, + 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 287, 629, 26, 630, 26, + 26, 26, 631, 26, 632, 26, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, + 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, 633, + 633, 633, 633, 633, 633, 633, 633, 634, 635, 635, 635, 635, 635, 635, 635, 635, + 635, 635, 635, 635, 635, 636, 635, 637, 635, 638, 635, 639, 281, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 9, 9, 9, 9, 9, 640, 9, 9, + 221, 26, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 281, 26, 26, 26, 26, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 276, 26, 0, 0, 0, 0, 258, 363, 0, 0, + 0, 0, 0, 0, 641, 642, 0, 643, 644, 645, 0, 0, 0, 646, 0, 0, + 0, 0, 0, 0, 0, 266, 26, 26, 14, 14, 14, 14, 14, 14, 14, 14, + 247, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 0, 0, 281, 26, 0, 0, 281, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 258, 26, 0, 0, 0, 260, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 255, 0, 0, 0, 0, 0, 0, 0, 0, 255, 647, 648, 0, 649, + 650, 0, 0, 0, 0, 0, 0, 0, 269, 651, 255, 255, 0, 0, 0, 652, + 653, 654, 655, 0, 0, 0, 0, 0, 0, 0, 0, 0, 276, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 268, 0, 0, 0, 0, 0, 0, 656, 656, 656, 656, 656, 656, 656, 656, + 656, 656, 656, 656, 656, 656, 656, 656, 656, 657, 26, 658, 659, 656, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 2, 2, 2, 348, 660, 308, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 661, 270, 270, 662, 663, 664, 18, 18, + 18, 18, 18, 18, 18, 665, 26, 26, 26, 666, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 667, 667, 667, 667, 667, 668, 667, 669, + 667, 670, 26, 26, 26, 26, 26, 26, 26, 26, 671, 671, 671, 672, 26, 26, + 673, 673, 673, 673, 673, 673, 673, 674, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 675, 675, 675, 675, 675, 676, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 172, 677, 170, 172, 678, 678, 678, 678, 678, 678, 678, 678, + 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, 678, + 679, 678, 680, 26, 26, 26, 26, 26, 681, 681, 681, 681, 681, 681, 681, 681, + 681, 682, 681, 683, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 363, 0, 0, 0, 0, 0, 0, 0, 377, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 363, 0, 0, 0, 0, 0, 0, 276, + 26, 26, 26, 26, 26, 26, 26, 26, 684, 31, 31, 31, 685, 686, 687, 688, + 689, 690, 685, 691, 685, 687, 687, 692, 31, 693, 31, 694, 695, 693, 31, 694, + 26, 26, 26, 26, 26, 26, 51, 26, 0, 0, 0, 0, 0, 281, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 281, 26, 0, 258, 363, 0, + 363, 0, 363, 0, 0, 0, 276, 26, 0, 0, 0, 0, 0, 276, 26, 26, + 26, 26, 26, 26, 696, 0, 0, 0, 697, 26, 0, 0, 0, 0, 0, 281, + 0, 260, 314, 26, 276, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 698, 0, 377, 0, 377, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 258, 699, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 314, 0, 281, 260, 26, 0, 281, 0, 0, 0, 0, 0, 0, + 0, 26, 0, 314, 0, 0, 0, 0, 0, 26, 0, 0, 0, 276, 314, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 281, 26, 0, 276, 0, 377, 0, 260, 0, 0, 0, 0, 0, 269, + 276, 696, 0, 281, 0, 260, 0, 260, 0, 0, 360, 0, 0, 0, 0, 0, + 0, 266, 26, 26, 26, 26, 0, 314, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 26, 26, 26, 26, 277, 277, 277, 277, 277, 277, 277, 347, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 280, 277, 277, 277, 277, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 347, 26, 277, 277, + 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 277, 277, 277, 700, 26, 26, 26, 277, 277, 277, 280, 26, 26, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 277, 277, 277, 277, 277, 277, 277, 277, + 277, 701, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 277, 26, 26, + 26, 26, 26, 26, 26, 26, 26, 26, 702, 26, 26, 26, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, + 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 939, 940, 941, 942, 946, 948, 0, 962, + 969, 970, 971, 976,1001,1002,1003,1008, 0,1033,1040,1041,1042,1043,1047, 0, + 0,1080,1081,1082,1086,1110, 0, 0,1124,1125,1126,1127,1131,1133, 0,1147, + 1154,1155,1156,1161,1187,1188,1189,1193, 0,1219,1226,1227,1228,1229,1233, 0, + 0,1267,1268,1269,1273,1298, 0,1303, 943,1128, 944,1129, 954,1139, 958,1143, + 959,1144, 960,1145, 961,1146, 964,1149, 0, 0, 973,1158, 974,1159, 975,1160, + 983,1168, 978,1163, 988,1173, 990,1175, 991,1176, 993,1178, 994,1179, 0, 0, + 1004,1190,1005,1191,1006,1192,1014,1199,1007, 0, 0, 0,1016,1201,1020,1206, + 0,1022,1208,1025,1211,1023,1209, 0, 0, 0, 0,1032,1218,1037,1223,1035, + 1221, 0, 0, 0,1044,1230,1045,1231,1049,1235, 0, 0,1058,1244,1064,1250, + 1060,1246,1066,1252,1067,1253,1072,1258,1069,1255,1077,1264,1074,1261, 0, 0, + 1083,1270,1084,1271,1085,1272,1088,1275,1089,1276,1096,1283,1103,1290,1111,1299, + 1115,1118,1307,1120,1309,1121,1310, 0,1053,1239, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,1093,1280, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 949,1134,1010,1195,1050,1236,1090,1277,1341,1368,1340, + 1367,1342,1369,1339,1366, 0,1320,1347,1418,1419,1323,1350, 0, 0, 992,1177, + 1018,1204,1055,1241,1416,1417,1415,1424,1202, 0, 0, 0, 987,1172, 0, 0, + 1031,1217,1321,1348,1322,1349,1338,1365, 950,1135, 951,1136, 979,1164, 980,1165, + 1011,1196,1012,1197,1051,1237,1052,1238,1061,1247,1062,1248,1091,1278,1092,1279, + 1071,1257,1076,1263, 0, 0, 997,1182, 0, 0, 0, 0, 0, 0, 945,1130, + 982,1167,1337,1364,1335,1362,1046,1232,1422,1423,1113,1301, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 8, 9, 0, 10,1425, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0,1314,1427, 5, + 1434,1438,1443, 0,1450, 0,1455,1461,1514, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1446,1458,1468,1476,1480,1486,1517, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1489,1503,1494,1500,1508, 0, 0, 0, 0,1520,1521, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0,1526,1528, 0,1525, 0, 0, 0,1522, + 0, 0, 0, 0,1536,1532,1539, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1534, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1556, 0, 0, 0, 0, 0, 0,1548,1550, 0,1547, 0, 0, 0,1567, + 0, 0, 0, 0,1558,1554,1561, 0, 0, 0, 0, 0, 0, 0,1568,1569, + 0, 0, 0, 0, 0, 0, 0, 0, 0,1529,1551, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0,1523,1545,1524,1546, 0, 0,1527,1549, + 0, 0,1570,1571,1530,1552,1531,1553, 0, 0,1533,1555,1535,1557,1537,1559, + 0, 0,1572,1573,1544,1566,1538,1560,1540,1562,1541,1563,1542,1564, 0, 0, + 1543,1565, 0, 0, 0, 0, 0, 0, 0, 0,1606,1607,1609,1608,1610, 0, + 0, 0, 0, 0, 0, 0, 0, 0,1613, 0,1611, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1612, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1620, 0, 0, 0, 0, 0, 0, 0,1623, 0, 0,1624, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1614,1615,1616,1617,1618,1619,1621,1622, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1628,1629, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1625,1626, 0,1627, 0, 0, 0,1634, 0, 0,1635, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1630,1631,1632, 0, 0,1633, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1639, 0, 0,1638,1640, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1636,1637, 0, 0, 0, 0, 0, 0,1641, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1642,1644,1643, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1645, 0, 0, 0, 0, 0, 0, 0,1646, 0, 0, 0, 0, 0, 0,1648, + 1649, 0,1647,1650, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1651,1653,1652, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1654, 0,1655,1657,1656, 0, 0, 0, 0,1659, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1660, 0, 0, 0, 0,1661, 0, 0, 0, 0,1662, + 0, 0, 0, 0,1663, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1658, 0, 0, 0, 0, 0, 0, 0, 0, 0,1664, 0,1665,1673, 0, + 1674, 0, 0, 0, 0, 0, 0, 0, 0,1666, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1668, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1669, 0, 0, 0, 0,1670, 0, 0, 0, 0,1671, + 0, 0, 0, 0,1672, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0,1667, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1675, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1676, 0, + 1677, 0,1678, 0,1679, 0,1680, 0, 0, 0,1681, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1682, 0,1683, 0, 0,1684,1685, 0,1686, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 953,1138, 955,1140, 956,1141, 957,1142, + 1324,1351, 963,1148, 965,1150, 968,1153, 966,1151, 967,1152,1378,1380,1379,1381, + 984,1169, 985,1170,1420,1421, 986,1171, 989,1174, 995,1180, 998,1183, 996,1181, + 999,1184,1000,1185,1015,1200,1329,1356,1017,1203,1019,1205,1021,1207,1024,1210, + 1687,1688,1027,1213,1026,1212,1028,1214,1029,1215,1030,1216,1034,1220,1036,1222, + 1039,1225,1038,1224,1334,1361,1336,1363,1382,1384,1383,1385,1056,1242,1057,1243, + 1059,1245,1063,1249,1689,1690,1065,1251,1068,1254,1070,1256,1386,1387,1388,1389, + 1691,1692,1073,1259,1075,1262,1079,1266,1078,1265,1095,1282,1098,1285,1097,1284, + 1390,1391,1392,1393,1099,1286,1100,1287,1101,1288,1102,1289,1105,1292,1104,1291, + 1106,1294,1107,1295,1108,1296,1114,1302,1119,1308,1122,1311,1123,1312,1186,1260, + 1293,1305, 0,1394, 0, 0, 0, 0, 952,1137, 947,1132,1317,1344,1316,1343, + 1319,1346,1318,1345,1693,1695,1371,1375,1370,1374,1373,1377,1372,1376,1694,1696, + 981,1166, 977,1162, 972,1157,1326,1353,1325,1352,1328,1355,1327,1354,1697,1698, + 1009,1194,1013,1198,1054,1240,1048,1234,1331,1358,1330,1357,1333,1360,1332,1359, + 1699,1700,1396,1401,1395,1400,1398,1403,1397,1402,1399,1404,1094,1281,1087,1274, + 1406,1411,1405,1410,1408,1413,1407,1412,1409,1414,1109,1297,1117,1306,1116,1304, + 1112,1300, 0, 0, 0, 0, 0, 0,1471,1472,1701,1705,1702,1706,1703,1707, + 1430,1431,1715,1719,1716,1720,1717,1721,1477,1478,1729,1731,1730,1732, 0, 0, + 1435,1436,1733,1735,1734,1736, 0, 0,1481,1482,1737,1741,1738,1742,1739,1743, + 1439,1440,1751,1755,1752,1756,1753,1757,1490,1491,1765,1768,1766,1769,1767,1770, + 1447,1448,1771,1774,1772,1775,1773,1776,1495,1496,1777,1779,1778,1780, 0, 0, + 1451,1452,1781,1783,1782,1784, 0, 0,1504,1505,1785,1788,1786,1789,1787,1790, + 0,1459, 0,1791, 0,1792, 0,1793,1509,1510,1794,1798,1795,1799,1796,1800, + 1462,1463,1808,1812,1809,1813,1810,1814,1467, 21,1475, 22,1479, 23,1485, 24, + 1493, 27,1499, 28,1507, 29, 0, 0,1704,1708,1709,1710,1711,1712,1713,1714, + 1718,1722,1723,1724,1725,1726,1727,1728,1740,1744,1745,1746,1747,1748,1749,1750, + 1754,1758,1759,1760,1761,1762,1763,1764,1797,1801,1802,1803,1804,1805,1806,1807, + 1811,1815,1816,1817,1818,1819,1820,1821,1470,1469,1822,1474,1465, 0,1473,1825, + 1429,1428,1426, 12,1432, 0, 26, 0, 0,1315,1823,1484,1466, 0,1483,1829, + 1433, 13,1437, 14,1441,1826,1827,1828,1488,1487,1513, 19, 0, 0,1492,1515, + 1445,1444,1442, 15, 0,1831,1832,1833,1502,1501,1516, 25,1497,1498,1506,1518, + 1457,1456,1454, 17,1453,1313, 11, 3, 0, 0,1824,1512,1519, 0,1511,1830, + 1449, 16,1460, 18,1464, 4, 0, 0, 30, 31, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 0, + 0, 0, 2, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1834,1835, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1836, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1837,1839,1838, 0, 0, 0, 0,1840, 0, 0, 0, + 0,1841, 0, 0,1842, 0, 0, 0, 0, 0, 0, 0,1843, 0,1844, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0,1845, 0, 0,1846, 0, 0,1847, + 0,1848, 0, 0, 0, 0, 0, 0, 937, 0,1850, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1849, 936, 938,1851,1852, 0, 0,1853,1854, 0, 0, + 1855,1856, 0, 0, 0, 0, 0, 0,1857,1858, 0, 0,1861,1862, 0, 0, + 1863,1864, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1867,1868,1869,1870,1859,1860,1865,1866, 0, 0, 0, 0, + 0, 0,1871,1872,1873,1874, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 32, 33, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1875, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1877, 0,1878, 0,1879, 0,1880, 0,1881, 0,1882, 0, + 1883, 0,1884, 0,1885, 0,1886, 0,1887, 0,1888, 0, 0,1889, 0,1890, + 0,1891, 0, 0, 0, 0, 0, 0,1892,1893, 0,1894,1895, 0,1896,1897, + 0,1898,1899, 0,1900,1901, 0, 0, 0, 0, 0, 0,1876, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1902, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0,1904, 0,1905, 0,1906, 0,1907, 0,1908, 0,1909, 0, + 1910, 0,1911, 0,1912, 0,1913, 0,1914, 0,1915, 0, 0,1916, 0,1917, + 0,1918, 0, 0, 0, 0, 0, 0,1919,1920, 0,1921,1922, 0,1923,1924, + 0,1925,1926, 0,1927,1928, 0, 0, 0, 0, 0, 0,1903, 0, 0,1929, + 1930,1931,1932, 0, 0, 0,1933, 0, 710, 385, 724, 715, 455, 103, 186, 825, + 825, 242, 751, 205, 241, 336, 524, 601, 663, 676, 688, 738, 411, 434, 474, 500, + 649, 746, 799, 108, 180, 416, 482, 662, 810, 275, 462, 658, 692, 344, 618, 679, + 293, 388, 440, 492, 740, 116, 146, 168, 368, 414, 481, 527, 606, 660, 665, 722, + 781, 803, 809, 538, 553, 588, 642, 758, 811, 701, 233, 299, 573, 612, 487, 540, + 714, 779, 232, 267, 412, 445, 457, 585, 594, 766, 167, 613, 149, 148, 560, 589, + 648, 768, 708, 345, 411, 704, 105, 259, 313, 496, 518, 174, 542, 120, 307, 101, + 430, 372, 584, 183, 228, 529, 650, 697, 424, 732, 428, 349, 632, 355, 517, 110, + 135, 147, 403, 580, 624, 700, 750, 170, 193, 245, 297, 374, 463, 543, 763, 801, + 812, 815, 162, 384, 420, 730, 287, 330, 337, 366, 459, 476, 509, 558, 591, 610, + 726, 652, 734, 759, 154, 163, 198, 473, 683, 697, 292, 311, 353, 423, 572, 494, + 113, 217, 259, 280, 314, 499, 506, 603, 608, 752, 778, 782, 788, 117, 557, 748, + 774, 320, 109, 126, 260, 265, 373, 411, 479, 523, 655, 737, 823, 380, 765, 161, + 395, 398, 438, 451, 502, 516, 537, 583, 791, 136, 340, 769, 122, 273, 446, 727, + 305, 322, 400, 496, 771, 155, 190, 269, 377, 391, 406, 432, 501, 519, 599, 684, + 687, 749, 776, 175, 452, 191, 480, 510, 659, 772, 805, 813, 397, 444, 619, 566, + 568, 575, 491, 471, 707, 111, 636, 156, 153, 288, 346, 578, 256, 435, 383, 729, + 680, 767, 694, 295, 128, 210, 0, 0, 227, 0, 379, 0, 0, 150, 493, 525, + 544, 551, 552, 556, 783, 576, 604, 0, 661, 0, 703, 0, 0, 735, 743, 0, + 0, 0, 793, 794, 795, 808, 741, 773, 118, 127, 130, 166, 169, 177, 207, 213, + 215, 226, 229, 268, 270, 317, 327, 329, 335, 369, 375, 381, 404, 441, 448, 458, + 477, 484, 503, 539, 545, 547, 546, 548, 549, 550, 554, 555, 561, 564, 569, 591, + 593, 595, 598, 607, 620, 625, 625, 651, 690, 695, 705, 706, 716, 717, 733, 735, + 777, 786, 790, 315, 869, 623, 0, 0, 102, 145, 134, 115, 129, 138, 165, 171, + 207, 202, 206, 212, 227, 231, 240, 243, 250, 254, 294, 296, 303, 308, 319, 325, + 321, 329, 326, 335, 341, 357, 360, 362, 370, 379, 388, 389, 393, 421, 424, 438, + 456, 454, 458, 465, 477, 535, 485, 490, 493, 507, 512, 514, 521, 522, 525, 526, + 528, 533, 532, 541, 565, 569, 574, 586, 591, 597, 607, 637, 647, 674, 691, 693, + 695, 698, 703, 699, 705, 704, 702, 706, 709, 717, 728, 736, 747, 754, 770, 777, + 783, 784, 786, 787, 790, 802, 825, 848, 847, 857, 55, 65, 66, 883, 892, 916, + 822, 824, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,1586, 0,1605, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1602,1603,1934,1935,1574,1575,1576,1577,1579,1580,1581,1583,1584, 0, + 1585,1587,1588,1589,1591, 0,1592, 0,1593,1594, 0,1595,1596, 0,1598,1599, + 1600,1601,1604,1582,1578,1590,1597, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1936, 0,1937, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1938, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1939,1940, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1941,1942, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,1944,1943, 0,1945, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0,1946,1947, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1948, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0,1949,1950,1951,1952,1953,1954,1955, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 939, 940, 941, 942, 946, 948, 0, 962, 969, 970, 971, 976,1001,1002,1003,1008, - 0,1033,1040,1041,1042,1043,1047, 0, 0,1080,1081,1082,1086,1110, 0, 0, - 1124,1125,1126,1127,1131,1133, 0,1147,1154,1155,1156,1161,1187,1188,1189,1193, - 0,1219,1226,1227,1228,1229,1233, 0, 0,1267,1268,1269,1273,1298, 0,1303, - 943,1128, 944,1129, 954,1139, 958,1143, 959,1144, 960,1145, 961,1146, 964,1149, - 0, 0, 973,1158, 974,1159, 975,1160, 983,1168, 978,1163, 988,1173, 990,1175, - 991,1176, 993,1178, 994,1179, 0, 0,1004,1190,1005,1191,1006,1192,1014,1199, - 1007, 0, 0, 0,1016,1201,1020,1206, 0,1022,1208,1025,1211,1023,1209, 0, - 0, 0, 0,1032,1218,1037,1223,1035,1221, 0, 0, 0,1044,1230,1045,1231, - 1049,1235, 0, 0,1058,1244,1064,1250,1060,1246,1066,1252,1067,1253,1072,1258, - 1069,1255,1077,1264,1074,1261, 0, 0,1083,1270,1084,1271,1085,1272,1088,1275, - 1089,1276,1096,1283,1103,1290,1111,1299,1115,1118,1307,1120,1309,1121,1310, 0, - 1053,1239, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1093, - 1280, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 949,1134,1010, - 1195,1050,1236,1090,1277,1341,1368,1340,1367,1342,1369,1339,1366, 0,1320,1347, - 1418,1419,1323,1350, 0, 0, 992,1177,1018,1204,1055,1241,1416,1417,1415,1424, - 1202, 0, 0, 0, 987,1172, 0, 0,1031,1217,1321,1348,1322,1349,1338,1365, - 950,1135, 951,1136, 979,1164, 980,1165,1011,1196,1012,1197,1051,1237,1052,1238, - 1061,1247,1062,1248,1091,1278,1092,1279,1071,1257,1076,1263, 0, 0, 997,1182, - 0, 0, 0, 0, 0, 0, 945,1130, 982,1167,1337,1364,1335,1362,1046,1232, - 1422,1423,1113,1301, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 8, 9, 0, 10,1425, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 0, 0, 0,1314,1427, 5,1434,1438,1443, 0,1450, 0,1455,1461, - 1514, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1446,1458,1468,1476,1480,1486, - 1517, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1489,1503,1494,1500,1508, 0, - 0, 0, 0,1520,1521, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1526,1528, 0,1525, 0, 0, 0,1522, 0, 0, 0, 0,1536,1532,1539, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1534, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1556, 0, 0, 0, 0, 0, 0, - 1548,1550, 0,1547, 0, 0, 0,1567, 0, 0, 0, 0,1558,1554,1561, 0, - 0, 0, 0, 0, 0, 0,1568,1569, 0, 0, 0, 0, 0, 0, 0, 0, - 0,1529,1551, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1523,1545,1524,1546, 0, 0,1527,1549, 0, 0,1570,1571,1530,1552,1531,1553, - 0, 0,1533,1555,1535,1557,1537,1559, 0, 0,1572,1573,1544,1566,1538,1560, - 1540,1562,1541,1563,1542,1564, 0, 0,1543,1565, 0, 0, 0, 0, 0, 0, - 0, 0,1606,1607,1609,1608,1610, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1613, 0,1611, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,1612, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1620, 0, 0, 0, 0, 0, 0, - 0,1623, 0, 0,1624, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1614,1615,1616,1617,1618,1619,1621,1622, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1628,1629, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1625,1626, 0,1627, - 0, 0, 0,1634, 0, 0,1635, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1630,1631,1632, 0, 0,1633, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1639, 0, 0,1638,1640, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1636,1637, 0, 0, - 0, 0, 0, 0,1641, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1642,1644,1643, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1645, 0, 0, 0, 0, 0, 0, 0, - 1646, 0, 0, 0, 0, 0, 0,1648,1649, 0,1647,1650, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1651,1653,1652, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1654, 0,1655,1657,1656, 0, - 0, 0, 0,1659, 0, 0, 0, 0, 0, 0, 0, 0, 0,1660, 0, 0, - 0, 0,1661, 0, 0, 0, 0,1662, 0, 0, 0, 0,1663, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1658, 0, 0, 0, 0, 0, 0, - 0, 0, 0,1664, 0,1665,1673, 0,1674, 0, 0, 0, 0, 0, 0, 0, - 0,1666, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,1668, 0, 0, 0, 0, 0, 0, 0, 0, 0,1669, 0, 0, - 0, 0,1670, 0, 0, 0, 0,1671, 0, 0, 0, 0,1672, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,1667, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0,1675, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0,1676, 0,1677, 0,1678, 0,1679, 0,1680, 0, - 0, 0,1681, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1682, 0,1683, 0, 0, - 1684,1685, 0,1686, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 953,1138, 955,1140, 956,1141, 957,1142,1324,1351, 963,1148, 965,1150, 968,1153, - 966,1151, 967,1152,1378,1380,1379,1381, 984,1169, 985,1170,1420,1421, 986,1171, - 989,1174, 995,1180, 998,1183, 996,1181, 999,1184,1000,1185,1015,1200,1329,1356, - 1017,1203,1019,1205,1021,1207,1024,1210,1687,1688,1027,1213,1026,1212,1028,1214, - 1029,1215,1030,1216,1034,1220,1036,1222,1039,1225,1038,1224,1334,1361,1336,1363, - 1382,1384,1383,1385,1056,1242,1057,1243,1059,1245,1063,1249,1689,1690,1065,1251, - 1068,1254,1070,1256,1386,1387,1388,1389,1691,1692,1073,1259,1075,1262,1079,1266, - 1078,1265,1095,1282,1098,1285,1097,1284,1390,1391,1392,1393,1099,1286,1100,1287, - 1101,1288,1102,1289,1105,1292,1104,1291,1106,1294,1107,1295,1108,1296,1114,1302, - 1119,1308,1122,1311,1123,1312,1186,1260,1293,1305, 0,1394, 0, 0, 0, 0, - 952,1137, 947,1132,1317,1344,1316,1343,1319,1346,1318,1345,1693,1695,1371,1375, - 1370,1374,1373,1377,1372,1376,1694,1696, 981,1166, 977,1162, 972,1157,1326,1353, - 1325,1352,1328,1355,1327,1354,1697,1698,1009,1194,1013,1198,1054,1240,1048,1234, - 1331,1358,1330,1357,1333,1360,1332,1359,1699,1700,1396,1401,1395,1400,1398,1403, - 1397,1402,1399,1404,1094,1281,1087,1274,1406,1411,1405,1410,1408,1413,1407,1412, - 1409,1414,1109,1297,1117,1306,1116,1304,1112,1300, 0, 0, 0, 0, 0, 0, - 1471,1472,1701,1705,1702,1706,1703,1707,1430,1431,1715,1719,1716,1720,1717,1721, - 1477,1478,1729,1731,1730,1732, 0, 0,1435,1436,1733,1735,1734,1736, 0, 0, - 1481,1482,1737,1741,1738,1742,1739,1743,1439,1440,1751,1755,1752,1756,1753,1757, - 1490,1491,1765,1768,1766,1769,1767,1770,1447,1448,1771,1774,1772,1775,1773,1776, - 1495,1496,1777,1779,1778,1780, 0, 0,1451,1452,1781,1783,1782,1784, 0, 0, - 1504,1505,1785,1788,1786,1789,1787,1790, 0,1459, 0,1791, 0,1792, 0,1793, - 1509,1510,1794,1798,1795,1799,1796,1800,1462,1463,1808,1812,1809,1813,1810,1814, - 1467, 21,1475, 22,1479, 23,1485, 24,1493, 27,1499, 28,1507, 29, 0, 0, - 1704,1708,1709,1710,1711,1712,1713,1714,1718,1722,1723,1724,1725,1726,1727,1728, - 1740,1744,1745,1746,1747,1748,1749,1750,1754,1758,1759,1760,1761,1762,1763,1764, - 1797,1801,1802,1803,1804,1805,1806,1807,1811,1815,1816,1817,1818,1819,1820,1821, - 1470,1469,1822,1474,1465, 0,1473,1825,1429,1428,1426, 12,1432, 0, 26, 0, - 0,1315,1823,1484,1466, 0,1483,1829,1433, 13,1437, 14,1441,1826,1827,1828, - 1488,1487,1513, 19, 0, 0,1492,1515,1445,1444,1442, 15, 0,1831,1832,1833, - 1502,1501,1516, 25,1497,1498,1506,1518,1457,1456,1454, 17,1453,1313, 11, 3, - 0, 0,1824,1512,1519, 0,1511,1830,1449, 16,1460, 18,1464, 4, 0, 0, - 30, 31, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 20, 0, 0, 0, 2, 6, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1834,1835, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1836, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1837,1839,1838, - 0, 0, 0, 0,1840, 0, 0, 0, 0,1841, 0, 0,1842, 0, 0, 0, - 0, 0, 0, 0,1843, 0,1844, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0,1845, 0, 0,1846, 0, 0,1847, 0,1848, 0, 0, 0, 0, 0, 0, - 937, 0,1850, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1849, 936, 938, - 1851,1852, 0, 0,1853,1854, 0, 0,1855,1856, 0, 0, 0, 0, 0, 0, - 1857,1858, 0, 0,1861,1862, 0, 0,1863,1864, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1867,1868,1869,1870, - 1859,1860,1865,1866, 0, 0, 0, 0, 0, 0,1871,1872,1873,1874, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 33, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1875, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1877, 0,1878, 0, - 1879, 0,1880, 0,1881, 0,1882, 0,1883, 0,1884, 0,1885, 0,1886, 0, - 1887, 0,1888, 0, 0,1889, 0,1890, 0,1891, 0, 0, 0, 0, 0, 0, - 1892,1893, 0,1894,1895, 0,1896,1897, 0,1898,1899, 0,1900,1901, 0, 0, - 0, 0, 0, 0,1876, 0, 0, 0, 0, 0, 0, 0, 0, 0,1902, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1904, 0,1905, 0, - 1906, 0,1907, 0,1908, 0,1909, 0,1910, 0,1911, 0,1912, 0,1913, 0, - 1914, 0,1915, 0, 0,1916, 0,1917, 0,1918, 0, 0, 0, 0, 0, 0, - 1919,1920, 0,1921,1922, 0,1923,1924, 0,1925,1926, 0,1927,1928, 0, 0, - 0, 0, 0, 0,1903, 0, 0,1929,1930,1931,1932, 0, 0, 0,1933, 0, - 710, 385, 724, 715, 455, 103, 186, 825, 825, 242, 751, 205, 241, 336, 524, 601, - 663, 676, 688, 738, 411, 434, 474, 500, 649, 746, 799, 108, 180, 416, 482, 662, - 810, 275, 462, 658, 692, 344, 618, 679, 293, 388, 440, 492, 740, 116, 146, 168, - 368, 414, 481, 527, 606, 660, 665, 722, 781, 803, 809, 538, 553, 588, 642, 758, - 811, 701, 233, 299, 573, 612, 487, 540, 714, 779, 232, 267, 412, 445, 457, 585, - 594, 766, 167, 613, 149, 148, 560, 589, 648, 768, 708, 345, 411, 704, 105, 259, - 313, 496, 518, 174, 542, 120, 307, 101, 430, 372, 584, 183, 228, 529, 650, 697, - 424, 732, 428, 349, 632, 355, 517, 110, 135, 147, 403, 580, 624, 700, 750, 170, - 193, 245, 297, 374, 463, 543, 763, 801, 812, 815, 162, 384, 420, 730, 287, 330, - 337, 366, 459, 476, 509, 558, 591, 610, 726, 652, 734, 759, 154, 163, 198, 473, - 683, 697, 292, 311, 353, 423, 572, 494, 113, 217, 259, 280, 314, 499, 506, 603, - 608, 752, 778, 782, 788, 117, 557, 748, 774, 320, 109, 126, 260, 265, 373, 411, - 479, 523, 655, 737, 823, 380, 765, 161, 395, 398, 438, 451, 502, 516, 537, 583, - 791, 136, 340, 769, 122, 273, 446, 727, 305, 322, 400, 496, 771, 155, 190, 269, - 377, 391, 406, 432, 501, 519, 599, 684, 687, 749, 776, 175, 452, 191, 480, 510, - 659, 772, 805, 813, 397, 444, 619, 566, 568, 575, 491, 471, 707, 111, 636, 156, - 153, 288, 346, 578, 256, 435, 383, 729, 680, 767, 694, 295, 128, 210, 0, 0, - 227, 0, 379, 0, 0, 150, 493, 525, 544, 551, 552, 556, 783, 576, 604, 0, - 661, 0, 703, 0, 0, 735, 743, 0, 0, 0, 793, 794, 795, 808, 741, 773, - 118, 127, 130, 166, 169, 177, 207, 213, 215, 226, 229, 268, 270, 317, 327, 329, - 335, 369, 375, 381, 404, 441, 448, 458, 477, 484, 503, 539, 545, 547, 546, 548, - 549, 550, 554, 555, 561, 564, 569, 591, 593, 595, 598, 607, 620, 625, 625, 651, - 690, 695, 705, 706, 716, 717, 733, 735, 777, 786, 790, 315, 869, 623, 0, 0, - 102, 145, 134, 115, 129, 138, 165, 171, 207, 202, 206, 212, 227, 231, 240, 243, - 250, 254, 294, 296, 303, 308, 319, 325, 321, 329, 326, 335, 341, 357, 360, 362, - 370, 379, 388, 389, 393, 421, 424, 438, 456, 454, 458, 465, 477, 535, 485, 490, - 493, 507, 512, 514, 521, 522, 525, 526, 528, 533, 532, 541, 565, 569, 574, 586, - 591, 597, 607, 637, 647, 674, 691, 693, 695, 698, 703, 699, 705, 704, 702, 706, - 709, 717, 728, 736, 747, 754, 770, 777, 783, 784, 786, 787, 790, 802, 825, 848, - 847, 857, 55, 65, 66, 883, 892, 916, 822, 824, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1586, 0,1605, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1602,1603,1934,1935,1574,1575, - 1576,1577,1579,1580,1581,1583,1584, 0,1585,1587,1588,1589,1591, 0,1592, 0, - 1593,1594, 0,1595,1596, 0,1598,1599,1600,1601,1604,1582,1578,1590,1597, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1936, 0,1937, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1938, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1939,1940, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1941,1942, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1944,1943, 0,1945, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1946,1947, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0,1948, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1949,1950, - 1951,1952,1953,1954,1955, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,1956,1957,1958,1960,1959, - 1961, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 106, 104, 107, 826, 114, 118, 119, 121, 123, 124, 127, 125, 34, 830, 130, 131, - 132, 137, 827, 35, 133, 139, 829, 142, 143, 112, 144, 145, 924, 151, 152, 37, - 157, 158, 159, 160, 38, 165, 166, 169, 171, 172, 173, 174, 176, 177, 178, 179, - 181, 182, 182, 182, 833, 468, 184, 185, 834, 187, 188, 189, 196, 192, 194, 195, - 197, 199, 200, 201, 203, 204, 204, 206, 208, 209, 211, 218, 213, 219, 214, 216, - 153, 234, 221, 222, 223, 220, 225, 224, 230, 835, 235, 236, 237, 238, 239, 244, - 836, 837, 247, 248, 249, 246, 251, 39, 40, 253, 255, 255, 838, 257, 258, 259, - 261, 839, 262, 263, 301, 264, 41, 266, 270, 272, 271, 841, 274, 842, 277, 276, - 278, 281, 282, 42, 283, 284, 285, 286, 43, 843, 44, 289, 290, 291, 293, 934, - 298, 845, 845, 621, 300, 300, 45, 852, 894, 302, 304, 46, 306, 309, 310, 312, - 316, 48, 47, 317, 846, 318, 323, 324, 325, 324, 328, 329, 333, 331, 332, 334, - 335, 336, 338, 339, 342, 343, 347, 351, 849, 350, 348, 352, 354, 359, 850, 361, - 358, 356, 49, 363, 365, 367, 364, 50, 369, 371, 851, 376, 386, 378, 53, 381, - 52, 51, 140, 141, 387, 382, 614, 78, 388, 389, 390, 394, 392, 856, 54, 399, - 396, 402, 404, 858, 405, 401, 407, 55, 408, 409, 410, 413, 859, 415, 56, 417, - 860, 418, 57, 419, 422, 424, 425, 861, 840, 862, 426, 863, 429, 431, 427, 433, - 437, 441, 438, 439, 442, 443, 864, 436, 449, 450, 58, 454, 453, 865, 447, 460, - 866, 867, 461, 466, 465, 464, 59, 467, 470, 469, 472, 828, 475, 868, 478, 870, - 483, 485, 486, 871, 488, 489, 872, 873, 495, 497, 60, 498, 61, 61, 504, 505, - 507, 508, 511, 62, 513, 874, 515, 875, 518, 844, 520, 876, 877, 878, 63, 64, - 528, 880, 879, 881, 882, 530, 531, 531, 533, 66, 534, 67, 68, 884, 536, 538, - 541, 69, 885, 549, 886, 887, 556, 559, 70, 561, 562, 563, 888, 889, 889, 567, - 71, 890, 570, 571, 72, 891, 577, 73, 581, 579, 582, 893, 587, 74, 590, 592, - 596, 75, 895, 896, 76, 897, 600, 898, 602, 605, 607, 899, 900, 609, 901, 611, - 853, 77, 615, 616, 79, 617, 252, 902, 903, 854, 855, 621, 622, 731, 80, 627, - 626, 628, 164, 629, 630, 631, 633, 904, 632, 634, 639, 640, 635, 641, 646, 651, - 638, 643, 644, 645, 905, 907, 906, 81, 653, 654, 656, 911, 657, 908, 82, 83, - 909, 910, 84, 664, 665, 666, 667, 669, 668, 671, 670, 674, 672, 673, 675, 85, - 677, 678, 86, 681, 682, 912, 685, 686, 87, 689, 36, 913, 914, 88, 89, 696, - 702, 709, 711, 915, 712, 713, 718, 719, 917, 831, 721, 720, 723, 832, 725, 728, - 918, 919, 739, 742, 744, 920, 745, 753, 756, 757, 755, 760, 761, 921, 762, 90, - 764, 922, 91, 775, 279, 780, 923, 925, 92, 93, 785, 926, 94, 927, 787, 787, - 789, 928, 792, 95, 796, 797, 798, 800, 96, 929, 802, 804, 806, 97, 98, 807, - 930, 99, 931, 932, 933, 814, 100, 816, 817, 818, 819, 820, 821, 935, 0, 0, + 0, 0, 0,1956,1957,1958,1960,1959,1961, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 106, 104, 107, 826, 114, 118, 119, 121, + 123, 124, 127, 125, 34, 830, 130, 131, 132, 137, 827, 35, 133, 139, 829, 142, + 143, 112, 144, 145, 924, 151, 152, 37, 157, 158, 159, 160, 38, 165, 166, 169, + 171, 172, 173, 174, 176, 177, 178, 179, 181, 182, 182, 182, 833, 468, 184, 185, + 834, 187, 188, 189, 196, 192, 194, 195, 197, 199, 200, 201, 203, 204, 204, 206, + 208, 209, 211, 218, 213, 219, 214, 216, 153, 234, 221, 222, 223, 220, 225, 224, + 230, 835, 235, 236, 237, 238, 239, 244, 836, 837, 247, 248, 249, 246, 251, 39, + 40, 253, 255, 255, 838, 257, 258, 259, 261, 839, 262, 263, 301, 264, 41, 266, + 270, 272, 271, 841, 274, 842, 277, 276, 278, 281, 282, 42, 283, 284, 285, 286, + 43, 843, 44, 289, 290, 291, 293, 934, 298, 845, 845, 621, 300, 300, 45, 852, + 894, 302, 304, 46, 306, 309, 310, 312, 316, 48, 47, 317, 846, 318, 323, 324, + 325, 324, 328, 329, 333, 331, 332, 334, 335, 336, 338, 339, 342, 343, 347, 351, + 849, 350, 348, 352, 354, 359, 850, 361, 358, 356, 49, 363, 365, 367, 364, 50, + 369, 371, 851, 376, 386, 378, 53, 381, 52, 51, 140, 141, 387, 382, 614, 78, + 388, 389, 390, 394, 392, 856, 54, 399, 396, 402, 404, 858, 405, 401, 407, 55, + 408, 409, 410, 413, 859, 415, 56, 417, 860, 418, 57, 419, 422, 424, 425, 861, + 840, 862, 426, 863, 429, 431, 427, 433, 437, 441, 438, 439, 442, 443, 864, 436, + 449, 450, 58, 454, 453, 865, 447, 460, 866, 867, 461, 466, 465, 464, 59, 467, + 470, 469, 472, 828, 475, 868, 478, 870, 483, 485, 486, 871, 488, 489, 872, 873, + 495, 497, 60, 498, 61, 61, 504, 505, 507, 508, 511, 62, 513, 874, 515, 875, + 518, 844, 520, 876, 877, 878, 63, 64, 528, 880, 879, 881, 882, 530, 531, 531, + 533, 66, 534, 67, 68, 884, 536, 538, 541, 69, 885, 549, 886, 887, 556, 559, + 70, 561, 562, 563, 888, 889, 889, 567, 71, 890, 570, 571, 72, 891, 577, 73, + 581, 579, 582, 893, 587, 74, 590, 592, 596, 75, 895, 896, 76, 897, 600, 898, + 602, 605, 607, 899, 900, 609, 901, 611, 853, 77, 615, 616, 79, 617, 252, 902, + 903, 854, 855, 621, 622, 731, 80, 627, 626, 628, 164, 629, 630, 631, 633, 904, + 632, 634, 639, 640, 635, 641, 646, 651, 638, 643, 644, 645, 905, 907, 906, 81, + 653, 654, 656, 911, 657, 908, 82, 83, 909, 910, 84, 664, 665, 666, 667, 669, + 668, 671, 670, 674, 672, 673, 675, 85, 677, 678, 86, 681, 682, 912, 685, 686, + 87, 689, 36, 913, 914, 88, 89, 696, 702, 709, 711, 915, 712, 713, 718, 719, + 917, 831, 721, 720, 723, 832, 725, 728, 918, 919, 739, 742, 744, 920, 745, 753, + 756, 757, 755, 760, 761, 921, 762, 90, 764, 922, 91, 775, 279, 780, 923, 925, + 92, 93, 785, 926, 94, 927, 787, 787, 789, 928, 792, 95, 796, 797, 798, 800, + 96, 929, 802, 804, 806, 97, 98, 807, 930, 99, 931, 932, 933, 814, 100, 816, + 817, 818, 819, 820, 821, 935, 0, 0, }; static const int16_t _hb_ucd_i16[196] = @@ -4525,12 +4582,12 @@ _hb_ucd_i16[196] = static inline uint_fast8_t _hb_ucd_gc (unsigned u) { - return u<1114110u?_hb_ucd_u8[6664+(((_hb_ucd_u8[1296+(((_hb_ucd_u16[((_hb_ucd_u8[544+(((_hb_ucd_u8[u>>1>>3>>3>>4])<<4)+((u>>1>>3>>3)&15u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:2; + return u<1114110u?_hb_ucd_u8[6800+(((_hb_ucd_u8[1312+(((_hb_ucd_u16[((_hb_ucd_u8[544+(((_hb_ucd_u8[u>>1>>3>>3>>4])<<4)+((u>>1>>3>>3)&15u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:2; } static inline uint_fast8_t _hb_ucd_ccc (unsigned u) { - return u<125259u?_hb_ucd_u8[8612+(((_hb_ucd_u8[8068+(((_hb_ucd_u8[7624+(((_hb_ucd_u8[7288+(((_hb_ucd_u8[7042+(u>>2>>2>>2>>3)])<<3)+((u>>2>>2>>2)&7u))])<<2)+((u>>2>>2)&3u))])<<2)+((u>>2)&3u))])<<2)+((u)&3u))]:0; + return u<125259u?_hb_ucd_u8[8792+(((_hb_ucd_u8[8236+(((_hb_ucd_u8[7776+(((_hb_ucd_u8[7424+(((_hb_ucd_u8[7178+(u>>2>>2>>2>>3)])<<3)+((u>>2>>2>>2)&7u))])<<2)+((u>>2>>2)&3u))])<<2)+((u>>2)&3u))])<<2)+((u)&3u))]:0; } static inline unsigned _hb_ucd_b4 (const uint8_t* a, unsigned i) @@ -4540,24 +4597,24 @@ _hb_ucd_b4 (const uint8_t* a, unsigned i) static inline int_fast16_t _hb_ucd_bmg (unsigned u) { - return u<65380u?_hb_ucd_i16[((_hb_ucd_u8[9356+(((_hb_ucd_u8[9236+(((_hb_ucd_b4(9108+_hb_ucd_u8,u>>2>>3>>3))<<3)+((u>>2>>3)&7u))])<<3)+((u>>2)&7u))])<<2)+((u)&3u)]:0; + return u<65380u?_hb_ucd_i16[((_hb_ucd_u8[9540+(((_hb_ucd_u8[9420+(((_hb_ucd_b4(9292+_hb_ucd_u8,u>>2>>3>>3))<<3)+((u>>2>>3)&7u))])<<3)+((u>>2)&7u))])<<2)+((u)&3u)]:0; } static inline uint_fast8_t _hb_ucd_sc (unsigned u) { - return u<918000u?_hb_ucd_u8[10862+(((_hb_ucd_u16[2000+(((_hb_ucd_u8[10142+(((_hb_ucd_u8[9692+(u>>3>>4>>4)])<<4)+((u>>3>>4)&15u))])<<4)+((u>>3)&15u))])<<3)+((u)&7u))]:2; + return u<918000u?_hb_ucd_u8[11062+(((_hb_ucd_u16[2040+(((_hb_ucd_u8[10326+(((_hb_ucd_u8[9876+(u>>3>>4>>4)])<<4)+((u>>3>>4)&15u))])<<4)+((u>>3)&15u))])<<3)+((u)&7u))]:2; } static inline uint_fast16_t _hb_ucd_dm (unsigned u) { - return u<195102u?_hb_ucd_u16[5888+(((_hb_ucd_u8[16764+(((_hb_ucd_u8[16382+(u>>4>>5)])<<5)+((u>>4)&31u))])<<4)+((u)&15u))]:0; + return u<195102u?_hb_ucd_u16[6008+(((_hb_ucd_u8[17068+(((_hb_ucd_u8[16686+(u>>4>>5)])<<5)+((u>>4)&31u))])<<4)+((u)&15u))]:0; } #else static const uint8_t -_hb_ucd_u8[13246] = +_hb_ucd_u8[13370] = { 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 9, 10, 7, 7, 7, 7, 7, 11, 12, 12, 12, 13, @@ -4565,7 +4622,7 @@ _hb_ucd_u8[13246] = 7, 24, 21, 21, 21, 25, 26, 27, 21, 28, 29, 30, 31, 32, 33, 34, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 35, 21, 36, - 7, 7, 37, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 7, 7, 7, 7, 35, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, @@ -4587,7 +4644,7 @@ _hb_ucd_u8[13246] = 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 38, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 37, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, @@ -4610,28 +4667,27 @@ _hb_ucd_u8[13246] = 34, 34,109,110,111,112,113,114,115,116,117,118, 34, 34, 34,119, 120,121,122,123,124,125,126,127, 34,128,129,111,130,131,132,133, 134,135,136,137,138,139,140,111,141,142,111,143,144,145,146,111, - 147,148,149,150,151,152,111,111,153,154,155,156,111,157,111,158, - 34, 34, 34, 34, 34, 34, 34, 34,159, 34, 34,111,111,111,111,111, - 111,111,111,111,111,111,111,111,111,111,111,111,111,111,111,160, - 34, 34, 34, 34, 34, 34, 34, 34,161,111,111,111,111,111,111,111, + 147,148,149,150,151,152,153,111,154,155,156,157,111,158,159,160, + 34, 34, 34, 34, 34, 34, 34, 34,161, 34, 34,111,111,111,111,111, + 111,111,111,111,111,111,111,111,111,111,111,111,111,111,111,162, + 34, 34, 34, 34, 34, 34, 34, 34,163,111,111,111,111,111,111,111, 111,111,111,111,111,111,111,111,111,111,111,111,111,111,111,111, 111,111,111,111,111,111,111,111, 34, 34, 34, 34, 34,111,111,111, - 34, 34, 34, 34,162,163,164, 34,111,111,111,111,165,166,167,168, + 34, 34, 34, 34,164,165,166, 34,111,111,111,111,167,168,169,170, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34,111,111,111,111,111, 111,111,111,111,111,111,111,111,111,111,111,111,111,111,111,119, 34, 34, 34, 34, 34, 34,111,111,111,111,111,111,111,111,111,111, - 111,111,111,111,111,111,111,111, 34,169,111,111,111,111,111,111, - 111,111,111,111,111,111,111,111,111,111,111,111,111,111,170, 67, - 67, 67,171,172,173,130, 65,111,174,175,176,177,178,179,180,181, - 67, 67, 67, 67,182,183,111,111,111,111,111,111,111,111,184,111, - 185,111,186,111,111,187,111,111,111,111,111,111,111,111,111, 34, - 34,188,189,111,111,111,111,111,130,190,191,111, 34,192,111,111, - 67, 67,193, 67, 67,111, 67,194, 67, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 67, 67, 67,195,111,111,111,111,111,111,111,111, + 111,111,111,111,111,111,111,111, 34,171,111,111,111,111,111,111, + 111,111,111,111,111,111,111,111,111,111,111,111,111,111,172, 67, + 67, 67,173,174,175,130, 65,111,176,177,178,179,180,181,182,183, + 67, 67, 67, 67,184,185,111,111,111,111,111,111,111,111,186,111, + 187,188,189,111,111,190,111,111,111,191,111,111,111,111,111, 34, + 34,192,193,111,111,111,111,111,130,194,195,111, 34,196,111,111, + 67, 67,197, 67, 67,111, 67,198, 67, 67, 67, 67, 67, 67, 67, 67, + 67, 67, 67, 67, 67, 67, 67,199,111,111,111,111,111,111,111,111, 34, 34, 34, 34, 34, 34, 34, 34,111,111,111,111,111,111,111,111, 34, 34, 34, 34, 34,111,111,111,111,111,111,111,111,111,111,111, - 34, 34, 34, 34, 34, 34, 34,111,111,111,111,111,111,111,111,111, - 196,111,185,185,111,111,111,111,111,111,111,111,111,111,111,111, + 200,111,188,188,111,111,111,111,111,111,111,111,111,111,111,111, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 2, 4, 5, 6, 2, 7, 7, 7, 7, 7, 2, 8, 9, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 12, 13, 14, 15, 16, 16, 16, 16, 16, 16, 16, @@ -4687,7 +4743,7 @@ _hb_ucd_u8[13246] = 36, 36, 36, 36, 36, 36, 65, 43, 77, 78, 78, 43, 43, 43, 43, 43, 43, 43, 43, 43, 36, 36, 36, 36, 7, 7, 7, 85, 27, 27, 27, 84, 64, 78, 66, 36, 36, 36, 36, 36, 78, 78, 78, 77, 78, 78, 43, 43, - 43, 43, 77, 78, 78, 78, 81, 36, 86, 36, 36, 36, 36, 36, 36, 36, + 43, 43, 77, 78, 78, 78, 81, 36, 86, 82, 78, 78, 78, 78, 78, 78, 43, 78, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 64, 65, 78, 79, 43, 43, 78, 78, 78, 79, 71, 61, 61, 36, 82, 27, 27, 27, 87, 27, 27, 27, 27, 84, 36, 36, 36, 36, 36, 36, 36, 36, 43, 43, 77, @@ -4827,7 +4883,7 @@ _hb_ucd_u8[13246] = 36, 64, 2, 36, 36, 36, 36, 36, 36, 82, 78, 43, 43, 43, 43, 77, 81, 36, 58, 2, 56, 43, 57, 79, 7, 7, 7, 7, 7, 58, 58, 2, 90, 27, 27, 27, 27, 27, 27, 27, 36, 36, 36, 36, 36, 36, 78, 79, - 43, 78, 77, 43, 2, 2, 2, 43, 36, 36, 36, 36, 36, 36, 36, 64, + 43, 78, 77, 43, 2, 2, 2, 65, 36, 36, 36, 36, 36, 36, 36, 64, 77, 78, 78, 78, 78, 78, 78, 78, 36, 36, 36, 82, 78, 78, 81, 36, 36, 78, 78, 43, 43, 43, 43, 43, 36, 36, 82, 78, 43, 43, 43, 43, 78, 43, 77, 65, 36, 58, 2, 2, 7, 7, 7, 7, 7, 2, 2, 65, @@ -4848,8 +4904,10 @@ _hb_ucd_u8[13246] = 43, 43, 43, 43, 77, 43, 43, 43, 77, 43, 79, 43, 43, 43, 43, 43, 43, 43, 43, 64, 43, 43, 43, 43, 36, 36, 36, 36, 36, 78, 78, 78, 43, 77, 79, 79, 36, 36, 36, 36, 36, 64, 77, 97, 2, 2, 2, 2, - 27, 27, 84, 61, 61, 61, 53, 20,150, 61, 61, 61, 61, 61, 61, 61, - 61, 61, 61, 61, 61, 61, 61, 21, 43, 43, 57, 2, 2, 2, 2, 2, + 43, 82, 36, 36, 36, 36, 36, 36, 36, 36, 78, 43, 43, 43, 43, 78, + 77, 57, 2, 2, 2, 2, 2, 2, 27, 27, 84, 61, 61, 61, 53, 20, + 150, 61, 61, 61, 61, 61, 61, 61, 61, 61, 61, 61, 61, 61, 61, 21, + 65, 36, 36, 64, 43, 43, 43, 43, 43, 43, 57, 2, 2, 2, 2, 2, 43, 43, 43, 57, 2, 2, 61, 61, 40, 40, 89, 61, 61, 61, 61, 61, 7, 7, 7, 7, 7,167, 27, 27, 27, 87, 36, 36, 36, 36, 36, 36, 27, 27, 27, 30, 2, 2, 2, 2, 82, 78, 78, 78, 78, 78, 78, 78, @@ -4872,462 +4930,469 @@ _hb_ucd_u8[13246] = 16, 16, 16, 16, 16, 39, 16, 16, 43, 43, 43, 68, 40, 40, 40, 40, 7, 7, 7, 7, 7, 7, 7, 71, 36, 36, 36, 36, 36, 36, 36, 43, 36, 36, 36, 36, 36, 36, 43, 43, 7, 7, 7, 7, 7, 7, 7,170, - 16, 16, 43, 43, 43, 68, 40, 40, 27, 27, 27, 27, 27, 27,145, 27, - 171, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27,145, - 27, 27, 27, 27, 27, 27, 84, 61, 61, 61, 61, 61, 61, 25, 41, 41, - 0, 0, 29, 21, 21, 21, 23, 21, 22, 18, 21, 25, 21, 17, 13, 13, - 25, 25, 25, 21, 21, 9, 9, 9, 9, 22, 21, 18, 24, 16, 24, 5, - 5, 5, 5, 22, 25, 18, 25, 0, 23, 23, 26, 21, 24, 26, 7, 20, - 25, 1, 26, 24, 26, 25, 15, 15, 24, 15, 7, 19, 15, 21, 9, 25, - 9, 5, 5, 25, 5, 9, 5, 7, 7, 7, 9, 8, 8, 5, 7, 5, - 6, 6, 24, 24, 6, 24, 12, 12, 6, 5, 9, 21, 25, 9, 26, 12, - 11, 11, 9, 6, 5, 21, 17, 17, 17, 26, 26, 23, 23, 12, 17, 12, - 21, 12, 12, 21, 7, 21, 1, 1, 21, 23, 26, 26, 1, 21, 6, 7, - 7, 12, 12, 7, 21, 7, 12, 1, 12, 6, 6, 12, 12, 26, 7, 26, - 26, 7, 21, 1, 24, 7, 7, 6, 1, 12, 12, 10, 10, 10, 10, 12, - 21, 6, 10, 7, 7, 10, 23, 7, 15, 26, 13, 21, 13, 7, 15, 7, - 12, 23, 21, 26, 21, 15, 17, 7, 29, 7, 7, 22, 18, 18, 14, 14, - 14, 7, 10, 21, 17, 21, 11, 12, 5, 6, 8, 8, 8, 24, 5, 24, - 9, 24, 29, 29, 29, 1, 20, 19, 22, 20, 27, 28, 1, 29, 21, 20, - 19, 21, 21, 16, 16, 21, 25, 22, 18, 21, 21, 29, 15, 6, 18, 6, - 12, 11, 9, 26, 26, 9, 26, 5, 5, 26, 14, 9, 5, 14, 14, 15, - 25, 26, 26, 22, 18, 26, 18, 25, 18, 22, 5, 12, 22, 21, 21, 22, - 18, 17, 26, 6, 7, 14, 17, 22, 26, 14, 17, 6, 14, 6, 12, 24, - 24, 6, 26, 15, 6, 21, 11, 21, 24, 9, 6, 9, 23, 26, 6, 10, - 4, 4, 3, 3, 7, 25, 17, 16, 16, 22, 16, 16, 25, 17, 7, 1, - 25, 24, 26, 1, 2, 2, 12, 15, 21, 14, 7, 15, 12, 17, 13, 15, - 26, 10, 10, 1, 13, 23, 23, 15, 0, 1, 2, 3, 4, 5, 6, 7, - 8, 9, 0, 10, 11, 12, 13, 0, 14, 0, 0, 0, 0, 0, 15, 0, - 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 36, 36, 36, 36, 36, 75, 43, 43, 16, 16, 43, 43, 43, 68, 40, 40, + 27, 27, 27, 27, 27, 27,145, 27,171, 27, 27, 27, 27, 27, 27, 27, + 27, 27, 27, 27, 27, 27, 27,145, 27, 27, 27, 27, 27, 27, 84, 61, + 61, 61, 61, 61, 61, 25, 41, 41, 0, 0, 29, 21, 21, 21, 23, 21, + 22, 18, 21, 25, 21, 17, 13, 13, 25, 25, 25, 21, 21, 9, 9, 9, + 9, 22, 21, 18, 24, 16, 24, 5, 5, 5, 5, 22, 25, 18, 25, 0, + 23, 23, 26, 21, 24, 26, 7, 20, 25, 1, 26, 24, 26, 25, 15, 15, + 24, 15, 7, 19, 15, 21, 9, 25, 9, 5, 5, 25, 5, 9, 5, 7, + 7, 7, 9, 8, 8, 5, 7, 5, 6, 6, 24, 24, 6, 24, 12, 12, + 6, 5, 9, 21, 25, 9, 26, 12, 11, 11, 9, 6, 5, 21, 17, 17, + 17, 26, 26, 23, 23, 12, 17, 12, 21, 12, 12, 21, 7, 21, 1, 1, + 21, 23, 26, 26, 1, 21, 6, 7, 7, 12, 12, 7, 21, 7, 12, 1, + 12, 6, 6, 12, 12, 26, 7, 26, 26, 7, 21, 1, 24, 7, 7, 6, + 1, 12, 12, 10, 10, 10, 10, 12, 21, 6, 10, 7, 7, 10, 23, 7, + 15, 26, 13, 21, 13, 7, 15, 7, 12, 23, 21, 26, 21, 15, 17, 7, + 29, 7, 7, 22, 18, 18, 14, 14, 14, 7, 10, 21, 17, 21, 11, 12, + 5, 6, 8, 8, 8, 24, 5, 24, 9, 24, 29, 29, 29, 1, 20, 19, + 22, 20, 27, 28, 1, 29, 21, 20, 19, 21, 21, 16, 16, 21, 25, 22, + 18, 21, 21, 29, 15, 6, 18, 6, 12, 11, 9, 26, 26, 9, 26, 5, + 5, 26, 14, 9, 5, 14, 14, 15, 25, 26, 26, 22, 18, 26, 18, 25, + 18, 22, 5, 12, 22, 21, 21, 22, 18, 17, 26, 6, 7, 14, 17, 22, + 26, 14, 17, 6, 14, 6, 12, 24, 24, 6, 26, 15, 6, 21, 11, 21, + 24, 9, 6, 9, 23, 26, 6, 10, 4, 4, 3, 3, 7, 25, 17, 16, + 16, 22, 16, 16, 25, 17, 7, 1, 25, 24, 26, 1, 2, 2, 12, 15, + 21, 14, 7, 15, 12, 17, 13, 15, 26, 10, 10, 1, 13, 23, 23, 15, + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 10, 11, 12, 13, 0, + 14, 0, 0, 0, 0, 0, 15, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 17, 18, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 20, 0, 21, 22, 23, 0, 0, 0, 24, 25, 26, - 27, 28, 29, 30, 31, 32, 33, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 0, 21, + 22, 23, 0, 0, 0, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 34, 0, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 35, 0, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 37, 38, 0, 0, 0, 0, 0, 0, 39, 40, 0, 0, 41, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 0, 0, 0, 0, - 3, 0, 0, 0, 4, 5, 6, 7, 0, 8, 9, 10, 0, 11, 12, 13, - 14, 15, 16, 17, 16, 18, 16, 19, 16, 19, 16, 19, 0, 19, 16, 20, - 16, 19, 21, 19, 0, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 0, - 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 33, 0, 0, 0, 0, - 0, 0, 34, 0, 0, 35, 0, 0, 36, 0, 37, 0, 0, 0, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 0, 0, 47, 0, 0, 0, 48, 0, 0, - 0, 49, 0, 0, 0, 0, 0, 0, 0, 50, 0, 51, 0, 52, 53, 0, - 54, 0, 0, 0, 0, 0, 0, 55, 56, 57, 0, 0, 0, 0, 58, 0, - 0, 59, 60, 61, 62, 63, 0, 0, 64, 65, 0, 0, 0, 66, 0, 0, - 0, 0, 67, 0, 0, 0, 68, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 69, 0, 0, 0, 70, 0, 71, 0, 0, 72, 0, - 0, 73, 0, 0, 0, 0, 0, 0, 0, 0, 74, 0, 0, 0, 0, 0, - 75, 0, 0, 76, 77, 0, 0, 78, 79, 0, 80, 62, 0, 81, 82, 0, - 0, 83, 84, 85, 0, 0, 0, 86, 0, 87, 0, 0, 51, 88, 51, 0, - 89, 0, 90, 0, 0, 0, 79, 0, 0, 0, 91, 92, 0, 93, 94, 95, - 96, 0, 0, 0, 0, 0, 51, 0, 0, 0, 0, 97, 98, 0, 0, 0, - 0, 99,100, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,101, 0, 0, - 102, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,103,104, 0, 0,105, - 0, 0, 0, 0, 0, 0,106, 0, 0, 0,100, 0, 0, 0, 0, 0, - 107,108, 0, 0, 0, 0, 0, 0, 0,109, 0,110, 0, 0, 0, 0, - 0, 0, 1, 2, 3, 4, 5, 6, 7, 0, 8, 0, 0, 0, 0, 9, - 10, 11, 12, 0, 0, 0, 0, 13, 0, 0, 14, 15, 0, 16, 0, 17, - 18, 0, 0, 19, 0, 20, 21, 0, 0, 0, 0, 0, 22, 23, 0, 24, - 25, 0, 0, 26, 0, 0, 0, 27, 0, 0, 28, 29, 30, 31, 0, 0, - 0, 32, 33, 34, 0, 0, 33, 0, 0, 35, 33, 0, 0, 0, 33, 36, - 0, 0, 0, 0, 0, 37, 38, 0, 0, 0, 0, 0, 0, 39, 40, 0, - 0, 0, 0, 0, 0, 41, 42, 0, 0, 0, 0, 43, 0, 44, 0, 0, - 0, 45, 46, 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, 48, 49, 0, - 0, 0, 0, 50, 0, 0, 0, 51, 0, 52, 0, 53, 0, 0, 0, 0, - 54, 0, 0, 0, 0, 55, 0, 56, 0, 0, 0, 0, 57, 58, 0, 0, - 0, 59, 60, 0, 0, 0, 0, 0, 0, 61, 52, 0, 62, 63, 0, 0, - 64, 0, 0, 0, 65, 66, 0, 0, 0, 67, 0, 68, 69, 70, 71, 72, - 1, 73, 0, 74, 75, 76, 0, 0, 77, 78, 0, 0, 0, 79, 0, 0, - 1, 1, 0, 0, 80, 0, 0, 81, 0, 0, 0, 0, 77, 82, 0, 83, - 0, 0, 0, 0, 0, 78, 84, 0, 85, 0, 52, 0, 1, 78, 0, 0, - 86, 0, 0, 87, 0, 0, 0, 0, 0, 88, 57, 0, 0, 0, 0, 0, - 0, 89, 90, 0, 0, 84, 0, 0, 33, 0, 0, 91, 0, 0, 0, 0, - 92, 0, 0, 0, 0, 49, 0, 0, 93, 0, 0, 0, 0, 94, 95, 0, - 0, 96, 0, 0, 97, 0, 0, 0, 98, 0, 0, 0, 99, 0,100, 93, - 0, 0,101, 0, 0, 0, 84, 0, 0,102, 0, 0, 0,103,104, 0, - 0,105,106, 0, 0, 0, 0, 0, 0,107, 0, 0,108, 0, 0, 0, - 0,109, 33, 0,110,111,112, 35, 0, 0,113, 0, 0, 0,114, 0, - 0, 0, 0, 0, 0,115, 0, 0,116, 0, 0, 0, 0,117, 88, 0, - 0, 0, 0, 0, 57, 0, 0, 0, 0, 52,118, 0, 0, 0, 0,119, - 0, 0,120, 0, 0, 0, 0,118, 0, 0, 0, 0, 0,121, 0, 0, - 0,122, 0, 0, 0,123, 0,124, 0, 0, 0, 0,125,126,127, 0, - 128, 0,129, 0, 0, 0,130,131,132, 0, 0, 0, 35, 0, 0, 0, - 133, 0, 0,134, 0, 0,135, 0, 0, 0, 0, 0, 0, 0, 1, 1, - 1, 1, 1, 2, 3, 4, 5, 6, 7, 4, 4, 8, 9, 10, 1, 11, - 12, 13, 14, 15, 16, 17, 18, 1, 1, 1, 19, 1, 0, 0, 20, 21, - 22, 1, 23, 4, 21, 24, 25, 26, 27, 28, 29, 30, 0, 0, 1, 1, - 31, 0, 0, 0, 32, 33, 34, 35, 1, 36, 37, 0, 0, 0, 0, 38, - 1, 39, 14, 39, 40, 41, 42, 0, 0, 0, 43, 36, 44, 45, 21, 45, - 46, 0, 0, 0, 19, 1, 21, 0, 0, 47, 0, 38, 48, 1, 1, 49, - 49, 50, 0, 0, 51, 0, 0, 0, 52, 1, 0, 0, 38, 14, 4, 1, - 1, 1, 53, 21, 43, 52, 54, 21, 35, 1, 0, 0, 0, 55, 0, 0, - 0, 56, 57, 58, 0, 0, 0, 0, 0, 59, 0, 60, 0, 0, 0, 0, - 61, 62, 0, 0, 63, 0, 0, 0, 64, 0, 0, 0, 65, 0, 0, 0, - 66, 0, 0, 0, 67, 0, 0, 0, 68, 0, 0, 69, 70, 0, 71, 72, - 73, 74, 75, 76, 0, 0, 0, 77, 0, 0, 0, 78, 79, 0, 0, 0, - 0, 47, 0, 0, 0, 49, 0, 80, 0, 0, 0, 62, 0, 0, 63, 0, - 0, 81, 0, 0, 82, 0, 0, 0, 83, 0, 0, 19, 84, 0, 62, 0, - 0, 0, 0, 49, 1, 85, 1, 52, 15, 86, 36, 10, 21, 87, 0, 55, - 0, 0, 0, 0, 19, 10, 1, 0, 0, 0, 0, 0, 88, 0, 0, 89, - 0, 0, 88, 0, 0, 0, 0, 78, 0, 0, 87, 9, 12, 4, 90, 8, - 91, 47, 0, 58, 50, 0, 21, 1, 21, 92, 93, 1, 1, 1, 1, 94, - 95, 96, 97, 1, 98, 58, 81, 99,100, 4, 58, 0, 0, 0, 0, 0, - 0, 19, 50, 0, 0, 0, 0, 0, 0, 61, 0, 0,101,102, 0, 0, - 103, 0, 0, 1, 1, 50, 0, 0, 0, 38, 0, 63, 0, 0, 0, 0, - 0, 62, 0, 0,104, 68, 61, 0, 0, 0, 78, 0, 0, 0,105,106, - 58, 38, 81, 0, 0, 0, 0, 0, 0,107, 1, 14, 4, 12, 84, 0, - 0, 0, 0, 38, 87, 0, 0, 0, 0,108, 0, 0,109, 61, 0,110, - 0, 0, 0, 1, 0, 0, 0, 0, 19, 58, 0,111, 14, 52,112, 41, - 0, 0, 62, 0, 0, 61, 0, 0,113, 0, 87, 0, 0, 0, 61, 62, - 0, 0, 62, 0, 89, 0, 0,113, 0, 0, 0, 0,114, 0, 0, 0, - 78, 55, 0, 38, 1, 58, 1, 58, 0, 0, 63, 89, 0, 0,115, 0, - 0, 0, 55, 0, 0, 0, 0,115, 0, 0, 0, 0, 61, 0, 0, 0, - 0, 79, 0, 61, 0, 0, 0, 0, 56, 0, 89, 80, 0, 0, 8, 91, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 37, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 38, 39, 0, 0, 0, 0, 0, 0, + 40, 41, 42, 0, 43, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 1, 2, 0, 0, 0, 0, 3, 0, 0, 0, 4, 5, 6, 7, + 0, 8, 9, 10, 0, 11, 12, 13, 14, 15, 16, 17, 16, 18, 16, 19, + 16, 19, 16, 19, 0, 19, 16, 20, 16, 19, 21, 19, 0, 22, 23, 24, + 25, 26, 27, 28, 29, 30, 31, 0, 32, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 33, 0, 0, 0, 0, 0, 0, 34, 0, 0, 35, 0, 0, + 36, 0, 37, 0, 0, 0, 38, 39, 40, 41, 42, 43, 44, 45, 46, 0, + 0, 47, 0, 0, 0, 48, 0, 0, 0, 49, 0, 0, 0, 0, 0, 0, + 0, 50, 0, 51, 0, 52, 53, 0, 54, 0, 0, 0, 0, 0, 0, 55, + 56, 57, 0, 0, 0, 0, 58, 0, 0, 59, 60, 61, 62, 63, 0, 0, + 64, 65, 0, 0, 0, 66, 0, 0, 0, 0, 67, 0, 0, 0, 68, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 69, 0, 0, + 0, 70, 0, 71, 0, 0, 72, 0, 0, 73, 0, 0, 0, 0, 0, 0, + 0, 0, 74, 0, 0, 0, 0, 0, 75, 76, 0, 77, 78, 0, 0, 79, + 80, 0, 81, 62, 0, 82, 83, 0, 0, 84, 85, 86, 0, 0, 0, 87, + 0, 88, 0, 0, 51, 89, 51, 0, 90, 0, 91, 0, 0, 0, 80, 0, + 0, 0, 92, 93, 0, 94, 95, 96, 97, 0, 0, 0, 0, 0, 51, 0, + 0, 0, 0, 98, 99, 0, 0, 0, 0, 0, 0,100, 0, 0, 0, 0, + 0,101,102, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,103, 0, 0, + 104, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,105,106, 0, 0,107, + 0, 0, 0, 0, 0, 0,108, 0,109, 0,102, 0, 0, 0, 0, 0, + 110,111, 0, 0, 0, 0, 0, 0, 0,112, 0, 0, 0, 0, 0, 0, + 0,113, 0,114, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, + 7, 0, 8, 0, 0, 0, 0, 9, 10, 11, 12, 0, 0, 0, 0, 13, + 0, 0, 14, 15, 0, 16, 0, 17, 18, 0, 0, 19, 0, 20, 21, 0, + 0, 0, 0, 0, 22, 23, 0, 24, 25, 0, 0, 26, 0, 0, 0, 27, + 0, 0, 28, 29, 30, 31, 0, 0, 0, 32, 33, 34, 0, 0, 33, 0, + 0, 35, 33, 0, 0, 0, 33, 36, 0, 0, 0, 0, 0, 37, 38, 0, + 0, 0, 0, 0, 0, 39, 40, 0, 0, 0, 0, 0, 0, 41, 42, 0, + 0, 0, 0, 43, 0, 44, 0, 0, 0, 45, 46, 0, 0, 0, 47, 0, + 0, 0, 0, 0, 0, 48, 49, 0, 0, 0, 0, 50, 0, 0, 0, 51, + 0, 52, 0, 53, 0, 0, 0, 0, 54, 0, 0, 0, 0, 55, 0, 56, + 0, 0, 0, 0, 57, 58, 0, 0, 0, 59, 60, 0, 0, 0, 0, 0, + 0, 61, 52, 0, 62, 63, 0, 0, 64, 0, 0, 0, 65, 66, 0, 0, + 0, 67, 0, 68, 69, 70, 71, 72, 1, 73, 0, 74, 75, 76, 0, 0, + 77, 78, 0, 0, 0, 79, 0, 0, 1, 1, 0, 0, 80, 0, 0, 81, + 0, 0, 0, 0, 77, 82, 0, 83, 0, 0, 0, 0, 0, 78, 84, 0, + 85, 0, 52, 0, 1, 78, 0, 0, 86, 0, 0, 87, 0, 0, 0, 0, + 0, 88, 57, 0, 0, 0, 0, 0, 0, 89, 90, 0, 0, 84, 0, 0, + 33, 0, 0, 91, 0, 0, 0, 0, 92, 0, 0, 0, 0, 49, 0, 0, + 93, 0, 0, 0, 0, 94, 95, 0, 0, 96, 0, 0, 97, 0, 0, 0, + 98, 0, 0, 0, 99, 0, 0, 0, 0,100,101, 93, 0, 0,102, 0, + 0, 0, 84, 0, 0,103, 0, 0, 0,104,105, 0, 0,106,107, 0, + 0, 0, 0, 0, 0,108, 0, 0,109, 0, 0, 0, 0,110, 33, 0, + 111,112,113, 35, 0, 0,114, 0, 0, 0,115, 0, 0, 0, 0, 0, + 0,116, 0, 0,117, 0, 0, 0, 0,118, 88, 0, 0, 0, 0, 0, + 57, 0, 0, 0, 0, 52,119, 0, 0, 0, 0,120, 0, 0,121, 0, + 0, 0, 0,119, 0, 0,122, 0, 0, 0, 0, 0, 0,123, 0, 0, + 0,124, 0, 0, 0,125, 0,126, 0, 0, 0, 0,127,128,129, 0, + 130, 0,131, 0, 0, 0,132,133,134, 0, 77, 0, 0, 0, 0, 0, + 35, 0, 0, 0,135, 0, 0, 0,136, 0, 0,137, 0, 0,138, 0, + 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 3, 4, 5, 6, + 7, 4, 4, 8, 9, 10, 1, 11, 12, 13, 14, 15, 16, 17, 18, 1, + 1, 1, 19, 1, 0, 0, 20, 21, 22, 1, 23, 4, 21, 24, 25, 26, + 27, 28, 29, 30, 0, 0, 1, 1, 31, 0, 0, 0, 32, 33, 34, 35, + 1, 36, 37, 0, 0, 0, 0, 38, 1, 39, 14, 39, 40, 41, 42, 0, + 0, 0, 43, 36, 44, 45, 21, 45, 46, 0, 0, 0, 19, 1, 21, 0, + 0, 47, 0, 38, 48, 1, 1, 49, 49, 50, 0, 0, 51, 0, 0, 0, + 52, 1, 0, 0, 38, 14, 4, 1, 1, 1, 53, 21, 43, 52, 54, 21, + 35, 1, 0, 0, 0, 55, 0, 0, 0, 56, 57, 58, 0, 0, 0, 0, + 0, 59, 0, 60, 0, 0, 0, 0, 61, 62, 0, 0, 63, 0, 0, 0, + 64, 0, 0, 0, 65, 0, 0, 0, 66, 0, 0, 0, 67, 0, 0, 0, + 68, 0, 0, 69, 70, 0, 71, 72, 73, 74, 75, 76, 0, 0, 0, 77, + 0, 0, 0, 78, 79, 0, 0, 0, 0, 47, 0, 0, 0, 49, 0, 80, + 0, 0, 0, 62, 0, 0, 63, 0, 0, 81, 0, 0, 82, 0, 0, 0, + 83, 0, 0, 19, 84, 0, 62, 0, 0, 0, 0, 49, 1, 85, 1, 52, + 15, 86, 36, 10, 21, 87, 0, 55, 0, 0, 0, 0, 19, 10, 1, 0, + 0, 0, 0, 0, 88, 0, 0, 89, 0, 0, 88, 0, 0, 0, 0, 78, + 0, 0, 87, 9, 12, 4, 90, 8, 91, 47, 0, 58, 50, 0, 21, 1, + 21, 92, 93, 1, 1, 1, 1, 94, 95, 96, 97, 1, 98, 58, 81, 99, + 100, 4, 58, 0, 0, 0, 0, 0, 0, 19, 50, 0, 0, 0, 0, 0, + 0, 61, 0, 0,101,102, 0, 0,103, 0, 0, 1, 1, 50, 0, 0, + 0, 38, 0, 63, 0, 0, 0, 0, 0, 62, 0, 0,104, 68, 61, 0, + 0, 0, 78, 0, 0, 0,105,106, 58, 38, 81, 0, 0, 0, 0, 0, + 0,107, 1, 14, 4, 12, 84, 0, 0, 0, 0, 38, 87, 0, 0, 0, + 0,108, 0, 0,109, 61, 0,110, 0, 0, 0, 1, 0, 0, 0, 0, + 19, 58, 0, 0, 0, 51, 0,111, 14, 52,112, 41, 0, 0, 62, 0, + 0, 61, 0, 0,113, 0, 87, 0, 0, 0, 61, 62, 0, 0, 62, 0, + 89, 0, 0,113, 0, 0, 0, 0,114, 0, 0, 0, 78, 55, 0, 38, + 1, 58, 1, 58, 0, 0, 63, 89, 0, 0,115, 0, 0, 0, 55, 0, + 0, 0, 0,115, 0, 0, 0, 0, 61, 0, 0, 0, 0, 79, 0, 61, + 0, 0, 0, 0, 56, 0, 89, 80, 0, 0, 79, 0, 0, 0, 8, 91, 0, 0, 1, 87, 0, 0,116, 0, 0, 0, 0, 0, 0,117, 0,118, 119,120,121, 0,104, 4,122, 49, 23, 0, 0, 0, 38, 50, 38, 58, 0, 0, 1, 87, 1, 1, 1, 1, 39, 1, 48,105, 87, 0, 0, 0, - 0, 1, 4,122, 0, 0, 0, 1,123, 0, 0, 0, 0, 0,230,230, - 230,230,230,232,220,220,220,220,232,216,220,220,220,220,220,202, - 202,220,220,220,220,202,202,220,220,220, 1, 1, 1, 1, 1,220, - 220,220,220,230,230,230,230,240,230,220,220,220,230,230,230,220, - 220, 0,230,230,230,220,220,220,220,230,232,220,220,230,233,234, - 234,233,234,234,233,230, 0, 0, 0,230, 0,220,230,230,230,230, - 220,230,230,230,222,220,230,230,220,220,230,222,228,230, 10, 11, - 12, 13, 14, 15, 16, 17, 18, 19, 19, 20, 21, 22, 0, 23, 0, 24, - 25, 0,230,220, 0, 18, 30, 31, 32, 0, 0, 0, 0, 27, 28, 29, - 30, 31, 32, 33, 34,230,230,220,220,230,220,230,230,220, 35, 0, - 0, 0, 0, 0,230,230,230, 0, 0,230,230, 0,220,230,230,220, - 0, 0, 0, 36, 0, 0,230,220,230,230,220,220,230,220,220,230, - 220,230,220,230,230, 0, 0,220, 0, 0,230,230, 0,230, 0,230, - 230,230,230,230, 0, 0, 0,220,220,220,230,220,220,220,230,230, - 0,220, 27, 28, 29,230, 7, 0, 0, 0, 0, 9, 0, 0, 0,230, - 220,230,230, 0, 0, 0, 0, 0,230, 0, 0, 84, 91, 0, 0, 0, - 0, 9, 9, 0, 0, 0, 0, 0, 9, 0,103,103, 9, 0,107,107, - 107,107,118,118, 9, 0,122,122,122,122,220,220, 0, 0, 0,220, - 0,220, 0,216, 0, 0, 0,129,130, 0,132, 0, 0, 0, 0, 0, - 130,130,130,130, 0, 0,130, 0,230,230, 9, 0,230,230, 0, 0, - 220, 0, 0, 0, 0, 7, 0, 9, 9, 0, 9, 9, 0, 0, 0,230, - 0, 0, 0,228, 0, 0, 0,222,230,220,220, 0, 0, 0,230, 0, - 0,220,230,220, 0,220,230,230,230, 0, 0, 0, 9, 9, 0, 0, - 7, 0,230, 0, 1, 1, 1, 0, 0, 0,230,234,214,220,202,230, - 230,230,230,230,232,228,228,220,218,230,233,220,230,220,230,230, - 1, 1, 1, 1, 1,230, 0, 1, 1,230,220,230, 1, 1, 0, 0, - 218,228,232,222,224,224, 0, 8, 8, 0, 0, 0, 0,220,230, 0, - 230,230,220, 0, 0,230, 0, 0, 26, 0, 0,220, 0,230,230, 1, - 220, 0, 0,230,220, 0, 0, 0,220,220, 0, 0,230,220, 0, 9, - 7, 0, 0, 7, 9, 0, 0, 0, 9, 7, 6, 6, 0, 0, 0, 0, - 1, 0, 0,216,216, 1, 1, 1, 0, 0, 0,226,216,216,216,216, - 216, 0,220,220,220, 0,230,230, 7, 0, 16, 17, 17, 33, 17, 49, - 17, 17, 84, 97,135,145, 26, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 0, 1, 0, 0, 0,123, 4,122, 0, 0, 0, 1,124, 0, 0, 0, + 0, 0,230,230,230,230,230,232,220,220,220,220,232,216,220,220, + 220,220,220,202,202,220,220,220,220,202,202,220,220,220, 1, 1, + 1, 1, 1,220,220,220,220,230,230,230,230,240,230,220,220,220, + 230,230,230,220,220, 0,230,230,230,220,220,220,220,230,232,220, + 220,230,233,234,234,233,234,234,233,230, 0, 0, 0,230, 0,220, + 230,230,230,230,220,230,230,230,222,220,230,230,220,220,230,222, + 228,230, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 19, 20, 21, 22, + 0, 23, 0, 24, 25, 0,230,220, 0, 18, 30, 31, 32, 0, 0, 0, + 0, 27, 28, 29, 30, 31, 32, 33, 34,230,230,220,220,230,220,230, + 230,220, 35, 0, 0, 0, 0, 0,230,230,230, 0, 0,230,230, 0, + 220,230,230,220, 0, 0, 0, 36, 0, 0,230,220,230,230,220,220, + 230,220,220,230,220,230,220,230,230, 0, 0,220, 0, 0,230,230, + 0,230, 0,230,230,230,230,230, 0, 0, 0,220,220,220,230,220, + 220,220,230,230, 0,220, 27, 28, 29,230, 7, 0, 0, 0, 0, 9, + 0, 0, 0,230,220,230,230, 0, 0, 0, 0, 0,230, 0, 0, 84, + 91, 0, 0, 0, 0, 9, 9, 0, 0, 0, 0, 0, 9, 0,103,103, + 9, 0,107,107,107,107,118,118, 9, 0,122,122,122,122,220,220, + 0, 0, 0,220, 0,220, 0,216, 0, 0, 0,129,130, 0,132, 0, + 0, 0, 0, 0,130,130,130,130, 0, 0,130, 0,230,230, 9, 0, + 230,230, 0, 0,220, 0, 0, 0, 0, 7, 0, 9, 9, 0, 9, 9, + 0, 0, 0,230, 0, 0, 0,228, 0, 0, 0,222,230,220,220, 0, + 0, 0,230, 0, 0,220,230,220, 0,220,230,230,230, 0, 0, 0, + 9, 9, 0, 0, 7, 0,230, 0, 1, 1, 1, 0, 0, 0,230,234, + 214,220,202,230,230,230,230,230,232,228,228,220,218,230,233,220, + 230,220,230,230, 1, 1, 1, 1, 1,230, 0, 1, 1,230,220,230, + 1, 1, 0, 0,218,228,232,222,224,224, 0, 8, 8, 0, 0, 0, + 0,220,230, 0,230,230,220, 0, 0,230, 0, 0, 26, 0, 0,220, + 0,230,230, 1,220, 0, 0,230,220, 0, 0, 0,220,220, 0, 0, + 230,220, 0, 9, 7, 0, 0, 7, 9, 0, 0, 0, 9, 7, 6, 6, + 0, 0, 0, 0, 1, 0, 0,216,216, 1, 1, 1, 0, 0, 0,226, + 216,216,216,216,216, 0,220,220,220, 0,232,232,220,230,230,230, + 7, 0, 16, 17, 17, 33, 17, 49, 17, 17, 84, 97,135,145, 26, 17, + 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, + 17,177, 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 3, 5, 3, 3, 3, + 3, 3, 6, 7, 8, 3, 3, 3, 3, 3, 9, 10, 11, 12, 13, 3, + 3, 3, 3, 3, 3, 3, 3, 14, 3, 15, 3, 3, 3, 3, 3, 3, + 16, 17, 18, 19, 20, 21, 3, 3, 3, 22, 23, 24, 3, 3, 3, 3, + 3, 3, 25, 3, 3, 3, 3, 3, 3, 3, 3, 26, 3, 3, 27, 28, + 0, 1, 0, 0, 0, 0, 0, 1, 0, 2, 0, 0, 0, 3, 0, 0, + 0, 3, 0, 0, 0, 0, 0, 4, 0, 5, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 0, 0, 0, 7, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 9, 0, 0, 0, 0, 0, + 0, 9, 0, 9, 0, 0, 0, 0, 0, 0, 0, 10, 11, 12, 13, 0, + 0, 14, 15, 16, 6, 0, 17, 18, 19, 19, 19, 20, 21, 22, 23, 24, + 19, 25, 0, 26, 27, 19, 19, 28, 29, 30, 0, 31, 0, 0, 0, 8, + 0, 0, 0, 0, 0, 0, 0, 19, 28, 0, 32, 33, 9, 34, 35, 19, + 0, 0, 36, 37, 38, 39, 40, 19, 0, 41, 42, 43, 44, 31, 0, 1, + 45, 42, 0, 0, 0, 0, 0, 32, 14, 14, 0, 0, 0, 0, 14, 0, + 0, 46, 47, 47, 47, 47, 48, 49, 47, 47, 47, 47, 50, 51, 52, 53, + 43, 21, 0, 0, 0, 0, 0, 0, 0, 54, 6, 55, 0, 14, 19, 1, + 0, 0, 0, 0, 56, 57, 0, 0, 0, 0, 0, 19, 58, 31, 0, 0, + 0, 0, 0, 0, 0, 59, 14, 0, 0, 0, 0, 1, 0, 2, 0, 0, + 0, 3, 0, 0, 0, 60, 61, 0, 0, 0, 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 2, 3, 0, 4, 5, 0, 0, 6, 0, 0, 0, 7, + 0, 0, 0, 1, 1, 0, 0, 8, 9, 0, 8, 9, 0, 0, 0, 0, + 8, 9, 10, 11, 12, 0, 0, 0, 13, 0, 0, 0, 0, 14, 15, 16, + 17, 0, 0, 0, 1, 0, 0, 18, 19, 0, 0, 0, 20, 0, 0, 0, + 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 8, 21, 9, + 0, 0, 22, 0, 0, 0, 0, 1, 0, 23, 24, 25, 0, 0, 26, 0, + 0, 0, 8, 21, 27, 0, 1, 0, 0, 1, 1, 1, 1, 0, 1, 28, + 29, 30, 0, 31, 32, 20, 1, 1, 0, 0, 0, 8, 21, 9, 1, 4, + 5, 0, 0, 0, 33, 9, 0, 1, 1, 1, 0, 8, 21, 21, 21, 21, + 34, 1, 35, 21, 21, 21, 9, 36, 0, 0, 37, 38, 1, 0, 39, 0, + 0, 0, 1, 0, 1, 0, 0, 0, 0, 8, 21, 9, 1, 0, 0, 0, + 40, 0, 8, 21, 21, 21, 21, 21, 21, 21, 21, 9, 0, 1, 1, 1, + 1, 8, 21, 21, 21, 9, 0, 0, 0, 41, 0, 42, 43, 0, 0, 0, + 1, 44, 0, 0, 0, 45, 8, 9, 1, 0, 0, 0, 8, 21, 21, 21, + 9, 0, 1, 0, 1, 1, 8, 21, 21, 9, 0, 4, 5, 8, 9, 1, + 0, 0, 0, 1, 2, 3, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, + 13, 14, 3, 3, 3, 3, 3, 3, 3, 15, 3, 16, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17,177, 0, 1, 2, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 3, - 3, 3, 3, 3, 5, 3, 3, 3, 3, 3, 6, 7, 8, 3, 3, 3, - 3, 3, 9, 10, 11, 12, 13, 3, 3, 3, 3, 3, 3, 3, 3, 14, - 3, 15, 3, 3, 3, 3, 3, 3, 16, 17, 18, 19, 20, 21, 3, 3, - 3, 22, 23, 24, 3, 3, 3, 3, 3, 3, 25, 3, 3, 3, 3, 3, - 3, 3, 3, 26, 3, 3, 27, 28, 0, 1, 0, 0, 0, 0, 0, 1, - 0, 2, 0, 0, 0, 3, 0, 0, 0, 3, 0, 0, 0, 0, 0, 4, - 0, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 6, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 8, 9, 0, 0, 0, 0, 0, 0, 9, 0, 9, 0, 0, 0, 0, - 0, 0, 0, 10, 11, 12, 13, 0, 0, 14, 15, 16, 6, 0, 17, 18, - 19, 19, 19, 20, 21, 22, 23, 24, 19, 25, 0, 26, 27, 19, 19, 28, - 29, 30, 0, 31, 0, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 19, - 28, 0, 32, 33, 9, 34, 35, 19, 0, 0, 36, 37, 38, 39, 40, 19, - 0, 41, 42, 43, 44, 31, 0, 1, 45, 42, 0, 0, 0, 0, 0, 32, - 14, 14, 0, 0, 0, 0, 14, 0, 0, 46, 47, 47, 47, 47, 48, 49, - 47, 47, 47, 47, 50, 51, 52, 53, 43, 21, 0, 0, 0, 0, 0, 0, - 0, 54, 6, 55, 0, 14, 19, 1, 0, 0, 0, 0, 56, 57, 0, 0, - 0, 0, 0, 19, 58, 31, 0, 0, 0, 0, 0, 0, 0, 59, 14, 0, - 0, 0, 0, 1, 0, 2, 0, 0, 0, 3, 0, 0, 0, 60, 61, 0, - 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 2, 3, 0, 4, - 5, 0, 0, 6, 0, 0, 0, 7, 0, 0, 0, 1, 1, 0, 0, 8, - 9, 0, 8, 9, 0, 0, 0, 0, 8, 9, 10, 11, 12, 0, 0, 0, - 13, 0, 0, 0, 0, 14, 15, 16, 17, 0, 0, 0, 1, 0, 0, 18, - 19, 0, 0, 0, 20, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1, - 1, 1, 1, 1, 0, 8, 21, 9, 0, 0, 22, 0, 0, 0, 0, 1, - 0, 23, 24, 25, 0, 0, 26, 0, 0, 0, 8, 21, 27, 0, 1, 0, - 0, 1, 1, 1, 1, 0, 1, 28, 29, 30, 0, 31, 32, 20, 1, 1, - 0, 0, 0, 8, 21, 9, 1, 4, 5, 0, 0, 0, 33, 9, 0, 1, - 1, 1, 0, 8, 21, 21, 21, 21, 34, 1, 35, 21, 21, 21, 9, 36, - 0, 0, 37, 38, 1, 0, 39, 0, 0, 0, 1, 0, 1, 0, 0, 0, - 0, 8, 21, 9, 1, 0, 0, 0, 40, 0, 8, 21, 21, 21, 21, 21, - 21, 21, 21, 9, 0, 1, 1, 1, 1, 8, 21, 21, 21, 9, 0, 0, - 0, 41, 0, 42, 43, 0, 0, 0, 1, 44, 0, 0, 0, 45, 8, 9, - 1, 0, 0, 0, 8, 21, 21, 21, 9, 0, 1, 0, 1, 1, 8, 21, - 21, 9, 0, 4, 5, 8, 9, 1, 0, 0, 0, 1, 2, 3, 3, 4, - 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 3, 3, 3, 3, 3, 3, - 3, 15, 16, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 18, 0, 0, 1, 2, 3, - 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 17, 17, - 18, 17, 19, 20, 21, 22, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, - 23, 23, 24, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, - 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 25, 25, 26, 27, - 28, 29, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, - 30, 30, 30, 30, 30, 30, 30, 30, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 32, 33, 34, 35, 36, 37, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 52, 53, 31, - 31, 31, 31, 54, 55, 55, 56, 31, 31, 31, 31, 31, 31, 31, 57, 58, + 17, 17, 18, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, + 12, 13, 14, 15, 16, 17, 17, 17, 18, 17, 19, 20, 21, 22, 23, 23, + 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 24, 23, 23, 23, 23, 23, + 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, + 23, 23, 23, 23, 25, 25, 26, 27, 28, 29, 30, 30, 30, 30, 30, 30, + 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, - 59, 60, 31, 61, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, - 62, 63, 64, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 65, 66, 67, 31, 31, 31, 31, 68, 31, 31, 31, 31, 31, - 31, 31, 31, 69, 70, 71, 17, 17, 72, 73, 31, 74, 75, 76, 31, 77, - 78, 31, 79, 80, 17, 81, 17, 17, 17, 17, 31, 31, 23, 23, 23, 23, - 23, 23, 31, 31, 31, 31, 31, 31, 23, 82, 31, 31, 23, 23, 23, 23, - 23, 23, 23, 23, 23, 83, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 84, 0, 0, 1, - 0, 1, 2, 3, 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, - 4, 4, 4, 4, 4, 4, 5, 6, 7, 8, 9, 10, 11, 11, 12, 11, - 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 19, 27, - 28, 29, 30, 30, 31, 31, 32, 32, 33, 33, 34, 34, 35, 35, 36, 36, - 37, 37, 38, 38, 39, 40, 41, 41, 42, 42, 42, 43, 44, 44, 45, 46, - 47, 47, 47, 47, 48, 48, 48, 48, 48, 48, 49, 50, 51, 51, 51, 51, - 51, 51, 51, 51, 51, 51, 52, 53, 54, 55, 56, 56, 57, 58, 59, 51, - 60, 61, 62, 63, 64, 65, 66, 7, 67, 67, 68, 69, 70, 71, 72, 73, - 74, 75, 76, 7, 4, 4, 4, 4, 77, 77, 77, 77, 78, 79, 80, 81, - 82, 83, 84, 0, 0, 0, 0, 0, 0, 0, 0, 0, 85, 85, 85, 85, - 0, 0, 0, 0, 86, 87, 88, 88, 89, 90, 48, 91, 0, 0, 92, 92, - 92, 92, 92, 93, 94, 95, 96, 97, 98, 47, 99,100,101,102, 0,103, - 104,105, 0, 0, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, - 92, 92, 92, 0,106,106,106,106,106,106,106,106,106,106,106,107, - 108,108,108,108,108, 11,109,110,111, 4,112, 4,113,114,115,116, - 117,118,119,120,121,122,123,124,125,126, 50,127, 47, 47, 47, 47, - 47, 47, 47, 47,128,128,128,128,128,128,128,128,128,128,128,128, - 92, 92, 92, 92, 92, 92, 92, 92,129,130, 19, 19, 19, 19, 19, 19, - 131, 19, 19, 19,132,133, 19,134,135,136,137,101,138,138,138,138, - 0, 77,139,140,128,128,141,142,143,144,145,146,147,148,149,150, - 151,152,153,153,154,154,154,154,154,154, 4, 4,155,156,157,158, - 159,160,161,162,163,164,165,166,167,168,169,169,170,170,171,171, - 172,172,128,128, 19, 19,173,173,174,175,176,177,178,178,179,180, - 181,182,183,184,185,185,186,187,188,189,128,128,190,190,191,191, - 128,128,192,192,193,194,195,195,196,196,128,128,197,197,198,198, - 199,199,200,200,201,202,203,204,128,128,128,128,205,206,207,207, - 208,209,210,210,128,128,211,211,128,128,212, 34,213,213,213,213, - 213,213,213,213,213,213,213,213,213,213,128,128,128,128,128,128, - 128,128,214,214,215,215,215,215,215,215,215,215,215,215,128,128, - 128,128,128,128,216,216,216,216,216,216,216,216,216,216,128,128, - 128,128,128,128,110,110,110,110,110,110,110,110,110,217,218,219, - 220,220,220,220,221,221,221,221,222,222,222,223,224,224,224,224, - 224,224,224,224,224,224,224,224,225,225,225,225,225,225,225,225, - 224,224,128,128,128,128,128,128,128,128,104,104,226,227,227,227, - 228,229,230,230,230,230,230,230,128,128,128,128,231,231,232, 0, - 128,128,128,128,128,128,128,128, 7,233, 0, 0, 0, 0, 0, 0, - 0,234,235, 0, 77, 77, 0, 0, 0, 0,128,128,236,236,236,236, - 236,236,236,236,236,236,236,236,128,128,128,128,128,128,128,128, - 4, 4,128,128, 86, 86,128,128,237,237,128,128,128,128,238,239, - 128,128,128,128,128,128,128,128,128,128, 48, 48,240,240,240,240, - 241,241,128,128, 0, 0, 0, 0, 0, 0,128,128, 19, 19, 19, 19, - 128,128,128,128,242, 0,128,128, 0, 0, 0, 0, 92, 92,128,128, - 128,128,128,128, 92, 92, 92, 92, 92, 92,128,128, 0, 0,128,128, - 7, 7, 7, 7, 0, 0, 0, 0, 1, 2, 1, 2, 0, 0, 3, 3, - 4, 5, 4, 5, 4, 4, 4, 4, 4, 4, 4, 6, 0, 0, 7, 0, - 8, 8, 8, 8, 8, 8, 8, 9, 10, 11, 11, 11, 11, 11, 12, 11, - 13, 13, 13, 13, 14, 13, 13, 13, 13, 13, 13, 15, 16, 16, 16, 16, - 16, 17, 18, 18, 18, 18, 18, 18, 19, 20, 21, 21, 22, 23, 21, 24, - 21, 21, 21, 21, 21, 25, 21, 21, 26, 26, 26, 26, 26, 21, 21, 21, - 27, 27, 27, 27, 28, 28, 28, 28, 29, 29, 29, 29, 30, 30, 26, 21, - 21, 21, 31, 21, 32, 32, 32, 32, 32, 33, 34, 32, 35, 35, 35, 35, - 36, 36, 36, 36, 37, 37, 37, 37, 38, 38, 38, 38, 39, 39, 39, 39, - 40, 40, 40, 40, 41, 41, 41, 41, 42, 42, 42, 42, 43, 43, 43, 43, - 44, 44, 44, 45, 44, 44, 44, 44, 46, 46, 46, 46, 47, 47, 47, 47, - 47, 48, 47, 47, 49, 49, 49, 49, 49, 49, 50, 50, 50, 50, 50, 51, - 52, 52, 52, 52, 53, 53, 53, 53, 53, 53, 54, 54, 54, 54, 54, 54, - 55, 55, 55, 55, 56, 56, 57, 57, 57, 57, 58, 57, 59, 59, 60, 61, - 62, 62, 63, 63, 64, 64, 64, 64, 65, 66, 66, 66, 66, 66, 66, 66, - 66, 66, 66, 55, 67, 67, 67, 67, 67, 68, 68, 68, 69, 69, 69, 69, - 69, 69, 64, 64, 70, 70, 71, 71, 71, 71, 71, 71, 71, 71, 71, 8, - 72, 72, 72, 72, 73, 73, 73, 73, 74, 74, 74, 74, 75, 75, 75, 75, - 75, 76, 76, 76, 13, 50, 50, 50, 73, 77, 78, 79, 4, 4, 80, 4, - 4, 81, 82, 83, 4, 4, 4, 84, 11, 11, 11, 11, 85, 0, 0, 0, - 0, 0, 0, 86, 0, 4, 0, 0, 0, 8, 8, 8, 0, 0, 87, 88, - 89, 0, 4, 4, 6, 0, 0, 0, 90, 90, 90, 90, 91, 91, 91, 91, - 91, 91, 4, 4, 92, 92, 92, 92, 50, 50, 50, 93, 93, 93, 93, 93, - 53, 53, 13, 13, 94, 94, 94, 94, 94, 94, 94, 0, 95, 0, 96, 97, - 98, 99, 99, 99, 99,100,101,102,102,102,102,103,104,104,104,105, - 52, 0,104,104, 0, 0, 0,102, 52, 52, 0, 0, 0, 0, 52,106, - 0,102,102,107,102,102,102,102,102,108, 0, 0,109,109,109,109, - 109,110,110,110,111,111,111,111, 13, 13,112,112,112,112,112,112, - 0, 0,113, 4,114, 4, 4, 4,115,115,115, 0,116,116,116,116, - 117,117,117,117,117,117, 32, 32,118,118,119,120,120,120, 52, 52, - 121,121,121,121,122,121, 49, 49,123,123,123,123,123,123, 49, 49, - 124,124,124,124,124,124,125,125, 53, 53, 53, 4, 4,126,127, 54, - 125,125,125,125,128,128,128,128, 4,129, 18, 18, 18, 21, 21, 21, - 21, 21, 21,130, 8, 0,131, 0, 0, 0, 0, 21, 21, 21, 21,132, - 0, 0, 1, 2, 1, 2,133,101,102,134, 52, 52,135,135,135,135, - 11, 0, 11, 11, 11, 0, 0,136,137,137,138,138,138,138,139, 0, - 140,140,140,141,141,142,142,142,143,143,144,144,144,144,144,144, - 145,145,145,145,145,146,146,146,147,147,147,148,148,148,148,148, - 149,149,149,150,150,150,150,151,151,151,151,151,152,152,152,152, - 153,153,153,153,154,154,155,155,156,156,156,156,156,156,157,157, - 158,158,159,159,159,159,159,159,160,160,161,161,161,161,161,161, - 162,162,162,162,162,162,163,163,164,164,164,164,165,165,165,165, - 166,166,166,166,167,167,168,168,169,169,169,169,170,170,170,170, - 171,171,171,171,172,172,172,172,173,173,173,173,174,174,174,175, - 175,175,175,176,176,176,176,177,177,177,178,178,179,179,179,179, - 180,180,180,180,180,181,181,181,182,182,182,182,182,183,183,183, - 184,184,184,184,184,184,185, 43,186,186,186,186,187,187,187,188, - 188,188,188,188,189,189,189,190,189,189,189,189,191,191,191,191, - 192,192,192,192,193,193,193,193,194,194,194,194,194,194, 66, 66, - 195,195,195,195,196,196,196,196,197,197,197,197,198,198,198,198, - 199,199,199,199,200,200,200,200,201,201,201,201,201,202,202,202, - 202,202,202, 55,203,203,203,203,204,204,204,204,204,204,204,205, - 205,205,205,205,206,206,206,206,206,206,207,207,207,207,207,207, - 208,208,208,208,110,110,110,110,209,209,209,209,210,210,210,210, - 211,211,211,211,212,212,212,212,213,213,213,214,214,214,214,214, - 214,215,215,215,216,216,216,216,217,217,217,217,218,218,218,218, - 218,218,219, 94,220,220,220,220,221,221,221,221,222, 99, 99, 99, - 99, 99, 99, 99, 99, 99,102,102,102, 99,223,224,224,224,224,224, - 225,225,225,225,225,225, 0, 0, 8, 0, 0, 0, 0, 0,226,227, - 228, 0,229, 0,230,230,230,230,231,231,231,231,232,232,232,232, - 233,233,233,233,234,234,234,234,235,235,235,235,236, 0, 0, 0, - 0, 0, 0, 0, 1, 2, 2, 2, 2, 2, 3, 0, 0, 0, 4, 0, - 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, 5, 0, 2, 5, 6, 0, - 7, 7, 7, 7, 8, 9, 8, 10, 8, 11, 8, 8, 8, 8, 8, 8, - 12, 13, 13, 13, 14, 14, 14, 14, 14, 15, 14, 14, 16, 17, 17, 17, - 17, 17, 17, 17, 18, 19, 19, 19, 19, 19, 19, 19, 20, 21, 20, 22, - 20, 20, 23, 23, 20, 20, 20, 20, 22, 20, 24, 7, 7, 25, 20, 20, - 26, 20, 20, 20, 20, 20, 20, 21, 27, 27, 27, 27, 28, 28, 28, 28, - 29, 29, 29, 29, 30, 30, 30, 30, 31, 31, 31, 31, 32, 20, 20, 20, - 33, 33, 33, 33, 34, 35, 33, 33, 33, 36, 33, 33, 37, 37, 37, 37, + 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, + 48, 49, 50, 51, 52, 52, 53, 31, 31, 31, 31, 54, 55, 55, 56, 31, + 31, 31, 31, 31, 31, 31, 57, 58, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 31, 59, 60, 31, 61, 62, 62, 62, 62, + 62, 62, 62, 62, 62, 62, 62, 62, 62, 63, 64, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 65, 66, 67, 31, 31, + 31, 31, 68, 31, 31, 31, 31, 31, 31, 31, 31, 69, 70, 71, 17, 17, + 72, 73, 31, 74, 75, 76, 77, 78, 79, 31, 80, 81, 17, 82, 17, 17, + 17, 17, 31, 31, 23, 23, 23, 23, 23, 23, 31, 31, 31, 31, 31, 31, + 23, 83, 31, 31, 23, 23, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, + 31, 31, 31, 31, 84, 0, 0, 1, 0, 1, 2, 3, 0, 1, 2, 3, + 4, 5, 6, 7, 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 5, 6, + 7, 8, 9, 10, 11, 11, 12, 11, 13, 14, 15, 16, 17, 18, 19, 20, + 21, 22, 23, 24, 25, 26, 19, 27, 28, 29, 30, 30, 31, 31, 32, 32, + 33, 33, 34, 34, 35, 35, 36, 36, 37, 37, 38, 38, 39, 40, 41, 41, + 42, 42, 42, 43, 44, 44, 45, 46, 47, 47, 47, 47, 48, 48, 48, 48, + 48, 48, 49, 50, 51, 51, 51, 51, 51, 51, 51, 51, 51, 51, 52, 53, + 54, 55, 56, 56, 57, 58, 59, 51, 60, 61, 62, 63, 64, 65, 66, 7, + 67, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 7, 4, 4, 4, 4, + 77, 77, 77, 77, 78, 79, 80, 81, 82, 83, 84, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 85, 85, 85, 85, 0, 0, 0, 0, 86, 87, 88, 88, + 89, 90, 48, 91, 0, 0, 92, 92, 92, 92, 92, 93, 94, 95, 96, 97, + 98, 47, 99,100,101,102, 0,103,104,105, 0, 0, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 0,106,106,106,106, + 106,106,106,106,106,106,106,107,108,108,108,108,108, 11,109,110, + 111, 4,112, 4,113,114,115,116,117,118,119,120,121,122,123,124, + 125,126, 50,127, 47, 47, 47, 47, 47, 47, 47, 47,128,128,128,128, + 128,128,128,128,128,128,128,128, 92, 92, 92, 92, 92, 92, 92, 92, + 129,130, 19, 19, 19, 19, 19, 19,131, 19, 19, 19,132,133, 19,134, + 135,136,137,101,138,138,138,138, 0, 77,139,140,128,128,141,142, + 143,144,145,146,147,148,149,150,151,152,153,153,154,154,154,154, + 154,154, 4, 4,155,156,157,158,159,160,161,162,163,164,165,166, + 167,168,169,169,170,170,171,171,172,172,128,128, 19, 19,173,174, + 175,176,177,178,179,179,180,181,182,183,184,185,186,186,187,188, + 189,190,128,128,191,191,192,192,128,128,193,193,194,195,196,196, + 197,197,128,128,198,198,199,199,200,200,201,201,202,203,204,205, + 28, 28,128,128,206,207,208,208,209,210,211,211,128,128,212,212, + 213,213,214, 34,215,215,215,215,215,215,215,215,215,215,215,215, + 215,215,128,128,128,128,128,128,128,128,216,216,217,217,217,217, + 217,217,217,217,217,217,128,128,128,128,128,128,218,218,218,218, + 218,218,218,218,218,218,128,128,128,128,128,128,110,110,110,110, + 110,110,110,110,110,219,220,221,222,222,222,222,223,223,223,223, + 224,224,224,225,226,226,226,226,226,226,226,226,226,226,226,226, + 227,227,227,227,227,227,227,227,226,226,128,128,128,128,128,128, + 128,128,104,104,228,229,229,229,230,231,232,232,232,232,232,232, + 128,128,128,128,233,233,234, 0,128,128,128,128,128,128,128,128, + 7,235, 0, 0, 0, 0, 0, 0, 0,236,237, 0, 77, 77, 0, 0, + 0, 0,128,128,238,238,238,238,238,238,238,238,238,238,238,238, + 128,128,128,128,128,128,128,128, 4, 4,128,128,239, 11, 11, 11, + 240,240,128,128,128,128,241,242,128,128,128,128,128,128,243,243, + 128,128,128,128,128,128,128,128,128,128, 48, 48,244,244,244,244, + 245,245,128,128, 0, 0, 0, 0, 0, 0,128,128, 19, 19, 19, 19, + 128,128,128,128,246, 0,128,128, 0, 0, 0, 0, 92, 92,128,128, + 128,128,128,128, 0, 0,128,128, 7, 7, 7, 7, 0, 0, 0, 0, + 1, 2, 1, 2, 0, 0, 3, 3, 4, 5, 4, 5, 4, 4, 4, 4, + 4, 4, 4, 6, 0, 0, 7, 0, 8, 8, 8, 8, 8, 8, 8, 9, + 10, 11, 11, 11, 11, 11, 12, 11, 13, 13, 13, 13, 14, 13, 13, 13, + 13, 13, 13, 15, 16, 16, 16, 16, 16, 17, 18, 18, 18, 18, 18, 18, + 19, 20, 21, 21, 22, 23, 21, 24, 21, 21, 21, 21, 21, 25, 21, 21, + 26, 26, 26, 26, 26, 21, 21, 21, 27, 27, 27, 27, 28, 28, 28, 28, + 29, 29, 29, 29, 30, 30, 26, 21, 21, 21, 31, 21, 32, 32, 32, 32, + 32, 33, 34, 32, 35, 35, 35, 35, 36, 36, 36, 36, 37, 37, 37, 37, 38, 38, 38, 38, 39, 39, 39, 39, 40, 40, 40, 40, 41, 41, 41, 41, - 42, 42, 42, 42, 43, 43, 43, 43, 44, 44, 44, 44, 45, 45, 45, 45, - 46, 46, 46, 46, 46, 46, 46, 47, 48, 48, 48, 48, 49, 49, 49, 49, - 49, 50, 51, 49, 52, 52, 52, 52, 53, 53, 53, 53, 53, 53, 54, 53, - 55, 55, 55, 55, 56, 56, 56, 56, 57, 57, 57, 57, 58, 58, 58, 58, - 59, 59, 59, 59, 60, 60, 60, 60, 60, 60, 61, 62, 63, 63, 63, 63, - 64, 64, 64, 64, 64, 65, 0, 0, 66, 66, 66, 66, 67, 67, 67, 67, - 68, 68, 68, 68, 69, 70, 71, 71, 71, 71, 71, 71, 72, 72, 72, 72, - 73, 73, 73, 73, 74, 74, 74, 74, 75, 75, 75, 75, 76, 76, 76, 76, - 77, 77, 77, 77, 78, 78, 78, 78, 79, 79, 79, 79, 80, 80, 80, 80, - 81, 81, 81, 81, 82, 7, 7, 7, 83, 7, 84, 85, 0, 84, 86, 0, - 2, 87, 88, 2, 2, 2, 2, 89, 90, 87, 91, 2, 2, 2, 92, 2, - 2, 2, 2, 93, 0, 0, 0, 86, 1, 0, 0, 94, 0, 95, 96, 0, - 4, 0, 0, 0, 0, 0, 0, 4, 97, 97, 97, 97, 98, 98, 98, 98, - 13, 13, 13, 13, 99, 99, 99, 99,100,100,100,100, 0,101, 0, 0, - 102,100,103,104, 0, 0,100, 0,105,106,106,106,106,106,106,106, - 106,106,107,105,108,109,109,109,109,109,109,109,109,109,110,108, - 111,111,111,111,112, 55, 55, 55, 55, 55, 55,113,109,109,109,110, - 109,109, 0, 0,114,114,114,114,115,115,115,115,116,116,116,116, - 117,117,117,117, 96, 2, 2, 2, 2, 2, 94, 2,118,118,118,118, - 119,119,119,119,120,120,120,120,121,121,121,121,121,121,121,122, - 123,123,123,123,124,124,124,124,124,124,124,125,126,126,126,126, - 127,127,127,127,128,128,128,128, 2, 2, 3, 2, 2,129,130, 0, - 131,131,131,131,132, 17, 17, 18, 20, 20, 20,133, 7, 7, 7,134, - 20, 20, 20, 23, 0,135,109,109,109,109,109,136,137,137,137,137, - 0, 0, 0,138,139,139,139,139,140,140,140,140, 84, 0, 0, 0, - 141,141,141,141,142,142,142,142,143,143,143,143,144,144,144,144, - 145,145,145,145,146,146,146,146,147,147,147,147,148,148,148,148, - 149,149,149,149,150,150,150,150,151,151,151,151,152,152,152,152, - 153,153,153,153,154,154,154,154,155,155,155,155,156,156,156,156, - 157,157,157,157,158,158,158,158,159,159,159,159,160,160,160,160, - 161,161,161,161,162,162,162,162,163,163,163,163,164,164,164,164, - 165,165,165,165,166,166,166,166,167,167,167,167,168,168,168,168, + 42, 42, 42, 42, 43, 43, 43, 43, 44, 44, 44, 45, 44, 44, 44, 44, + 46, 46, 46, 46, 47, 47, 47, 47, 47, 48, 47, 47, 49, 49, 49, 49, + 49, 49, 50, 50, 50, 50, 50, 51, 52, 52, 52, 52, 53, 53, 53, 53, + 53, 53, 54, 54, 54, 54, 54, 54, 55, 55, 55, 55, 56, 56, 57, 57, + 57, 57, 58, 57, 59, 59, 60, 61, 62, 62, 63, 63, 64, 64, 64, 64, + 65, 66, 66, 66, 66, 66, 66, 66, 66, 66, 66, 55, 67, 67, 67, 67, + 67, 68, 68, 68, 69, 69, 69, 69, 69, 69, 64, 64, 70, 70, 71, 71, + 71, 71, 71, 71, 71, 71, 71, 8, 72, 72, 72, 72, 73, 73, 73, 73, + 74, 74, 74, 74, 75, 75, 75, 75, 75, 76, 76, 76, 13, 50, 50, 50, + 73, 77, 78, 79, 4, 4, 80, 4, 4, 81, 82, 83, 4, 4, 4, 84, + 11, 11, 11, 11, 85, 0, 0, 0, 0, 0, 0, 86, 0, 4, 0, 0, + 0, 8, 8, 8, 0, 0, 87, 88, 89, 0, 4, 4, 6, 0, 0, 0, + 90, 90, 90, 90, 91, 91, 91, 91, 91, 91, 4, 4, 92, 92, 92, 92, + 50, 50, 50, 93, 93, 93, 93, 93, 53, 53, 13, 13, 94, 94, 94, 94, + 94, 94, 94, 0, 95, 0, 96, 97, 98, 99, 99, 99, 99,100,101,102, + 102,102,102,103,104,104,104,105, 52, 0,104,104, 0, 0, 0,102, + 52, 52, 0, 0, 0, 0, 52,106, 0,102,102,107,102,102,102,102, + 102,108, 0, 0,109,109,109,109,109,110,110,110,111,111,111,111, + 13, 13,112,112,112,112,112,112, 0, 0,113, 4,114, 4, 4, 4, + 115,115,115, 0,116,116,116,116,117,117,117,117,117,117, 32, 32, + 118,118,119,120,120,120, 52, 52,121,121,121,121,122,121, 49, 49, + 123,123,123,123,123,123, 49, 49,124,124,124,124,124,124,125,125, + 53, 53, 53, 4, 4,126,127, 54,125,125,125,125,128,128,128,128, + 4,129, 18, 18, 18, 21, 21, 21, 21, 21, 21,130, 8, 0,131, 0, + 0, 0, 0, 21, 21, 21, 21,132, 0, 0, 1, 2, 1, 2,133,101, + 102,134, 52, 52,135,135,135,135, 11, 0, 11, 11, 11, 0, 0,136, + 137,137,138,138,138,138,139, 0,140,140,140,141,141,142,142,142, + 143,143,144,144,144,144,144,144,145,145,145,145,145,146,146,146, + 147,147,147,148,148,148,148,148,149,149,149,150,150,150,150,151, + 151,151,151,151,152,152,152,152,153,153,153,153,154,154,155,155, + 156,156,156,156,156,156,157,157,158,158,159,159,159,159,159,159, + 160,160,161,161,161,161,161,161,162,162,162,162,162,162,163,163, + 164,164,164,164,165,165,165,165,166,166,166,166,167,167,168,168, 169,169,169,169,170,170,170,170,171,171,171,171,172,172,172,172, - 173,173,173,173,174,174,174,174,175,175,175,175,176,176,176,176, - 177,177,177,177,178,178,178,178,179,179,179,179,180,180,180,180, - 181,181,181,181,182,182,182,182,183,183,183,183,184,184,184,184, - 185,185,185,185,186, 45, 45, 45,187,187,187,187,188,188,188,188, - 189,189,189,189,190,190,190,190,190,190,191,190,192,192,192,192, - 193,193,193,193,194,194,194,194,195,195,195,195,196,196,196,196, + 173,173,173,173,173,173,173,174,175,175,175,176,176,176,176,177, + 177,177,177,178,178,178,179,179,180,180,180,180,181,181,181,181, + 181,182,182,182,183,183,183,183,183,184,184,184,185,185,185,185, + 185,185,186, 43,187,187,187,187,188,188,188,189,189,189,189,189, + 190,190,190,191,190,190,190,190,192,192,192,192,193,193,193,193, + 194,194,194,194,195,195,195,195,195,195, 66, 66,196,196,196,196, 197,197,197,197,198,198,198,198,199,199,199,199,200,200,200,200, - 201,201,201,201,202,202,202,202,203,203,203,203,204,204,204,204, - 205,205,205,205,206,206,206,206,207,207,207,207,208,208,208,208, - 209,209,209,209,210,210,210,210,211,211,211,211,212,212,212,212, - 213,213,213,213,214,214,214,214,215,215,215,215,216,216,216,216, - 217,217,217,217,218,218,218,218,219,219,219,219,220,221,221,221, - 222,222,222,222,221,221,221,221,223,106,106,106,106,109,109,109, - 224,224,224,224,225,225,225,225, 0,226, 86, 0, 0, 0,226, 7, - 82,138, 7, 0, 0, 0,227, 86,228,228,228,228,229,229,229,229, - 230,230,230,230,231,231,231,231,232,232,232,232,233,233,233,233, - 234, 0, 0, 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 0, 0, 0, 19, 0, 19, 0, 0, 0, 0, 0, 26, 26, - 1, 1, 1, 1, 9, 9, 9, 9, 0, 9, 9, 9, 9, 9, 0, 9, - 9, 0, 9, 0, 9, 9, 55, 55, 55, 55, 55, 55, 6, 6, 6, 6, - 6, 1, 1, 6, 6, 4, 4, 4, 4, 4, 4, 4, 4, 14, 14, 14, - 14, 14, 14, 14, 3, 3, 3, 3, 3, 0, 3, 3, 0, 3, 3, 3, - 3, 3, 3, 0, 3, 3, 3, 1, 1, 1, 3, 3, 1, 3, 3, 3, - 37, 37, 37, 37, 38, 38, 38, 38, 64, 64, 64, 64, 90, 90, 90, 90, - 95, 95, 95, 95, 3, 3, 0, 3, 7, 7, 7, 7, 7, 1, 1, 1, - 1, 7, 7, 7, 0, 0, 7, 7, 5, 5, 5, 5, 11, 11, 11, 11, - 10, 10, 10, 10, 21, 21, 21, 21, 22, 22, 22, 22, 23, 23, 23, 23, - 16, 16, 16, 16, 20, 20, 20, 20, 36, 36, 36, 36, 24, 24, 24, 24, - 24, 24, 24, 0, 18, 18, 18, 18, 25, 25, 25, 25, 25, 0, 0, 0, - 0, 25, 25, 25, 33, 33, 33, 33, 8, 8, 8, 8, 8, 8, 8, 0, - 12, 12, 12, 12, 30, 30, 30, 30, 29, 29, 29, 29, 28, 28, 28, 28, - 34, 34, 34, 34, 35, 35, 35, 35, 35, 35, 35, 0, 0, 0, 35, 35, - 45, 45, 45, 45, 44, 44, 44, 44, 44, 0, 0, 0, 43, 43, 43, 43, - 46, 46, 46, 46, 31, 31, 31, 31, 32, 32, 0, 0, 32, 0, 32, 32, - 32, 32, 32, 32, 48, 48, 48, 48, 52, 52, 52, 52, 58, 58, 58, 58, - 54, 54, 54, 54, 91, 91, 91, 91, 62, 62, 62, 62, 76, 76, 76, 76, - 93, 93, 93, 93, 70, 70, 70, 70, 73, 73, 73, 73, 1, 1, 1, 0, - 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, - 19, 19, 9, 9, 9, 9, 9, 6, 19, 9, 9, 9, 9, 9, 19, 19, - 9, 9, 9, 19, 6, 19, 19, 19, 19, 19, 19, 9, 0, 0, 0, 19, - 0, 0, 9, 0, 0, 0, 19, 19, 27, 27, 27, 27, 56, 56, 56, 56, - 61, 61, 61, 61, 13, 13, 13, 13, 0, 13, 0, 13, 0, 13, 13, 13, - 13, 13, 1, 1, 1, 1, 12, 12, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 1, 1, 0, 0, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 0, - 26, 26, 26, 26, 26, 12, 12, 12, 12, 12, 12, 0, 39, 39, 39, 39, - 86, 86, 86, 86, 77, 77, 77, 77, 79, 79, 79, 79, 60, 60, 60, 60, - 65, 65, 65, 65, 75, 75, 75, 75, 69, 69, 69, 69, 69, 69, 0, 69, - 74, 74, 74, 74, 84, 84, 84, 84, 84, 84, 84, 0, 68, 68, 68, 68, - 92, 92, 92, 92, 87, 87, 87, 87, 19, 9, 19, 19, 19, 19, 0, 0, - 2, 2, 2, 2, 19, 19, 19, 4, 3, 3, 0, 0, 1, 1, 6, 6, - 0, 0, 17, 17, 17, 17, 0, 0, 49, 49, 49, 49, 0, 1, 1, 1, - 71, 71, 71, 71, 67, 67, 67, 67, 42, 42, 42, 42, 41, 41, 41, 41, - 118,118,118,118, 53, 53, 53, 53, 59, 59, 59, 59, 40, 40, 40, 40, - 51, 51, 51, 51, 50, 50, 50, 50,135,135,135,135,106,106,106,106, - 104,104,104,104,161,161,161,161,110,110,110,110, 47, 47, 47, 47, - 81, 81, 81, 81,120,120,120,120,116,116,116,116,128,128,128,128, - 66, 66, 66, 66, 72, 72, 72, 72, 98, 98, 98, 98, 97, 97, 97, 97, - 57, 57, 57, 57, 88, 88, 88, 88,117,117,117,117,112,112,112,112, - 78, 78, 78, 78, 83, 83, 83, 83, 82, 82, 82, 82,122,122,122,122, - 89, 89, 89, 89,130,130,130,130,144,144,144,144,156,156,156,156, - 147,147,147,147,148,148,148,148,158,158,158,158,153,153,153,153, - 149,149,149,149, 94, 94, 94, 94, 85, 85, 85, 85,101,101,101,101, - 96, 96, 96, 96,111,111,111,111,100,100,100,100,100, 36, 36, 36, - 108,108,108,108,129,129,129,129,109,109,109,109,107,107,107,107, - 107,107,107, 1,137,137,137,137,124,124,124,124,123,123,123,123, - 114,114,114,114,102,102,102,102,126,126,126,126,142,142,142,142, - 125,125,125,125,154,154,154,154,150,150,150,150,141,141,141,141, - 140,140,140,140,121,121,121,121,133,133,133,133,134,134,134,134, - 138,138,138,138,143,143,143,143,145,145,145,145, 63, 63, 63, 63, + 201,201,201,201,202,202,202,202,202,203,203,203,203,203,203, 55, + 204,204,204,204,205,205,205,205,205,205,205,206,206,206,206,206, + 207,207,207,207,207,207,208,208,208,208,208,208,209,209,209,209, + 210,210,210,210,110,110,110,110,211,211,211,211,212,212,212,212, + 213,213,213,213,214,214,214,214,215,215,215,216,216,216,216,216, + 216,217,217,217,218,218,218,218,219,219,219,219,220,220,220,220, + 220,220,221, 94,222,222,222,222,223,223,223,223,224, 99, 99, 99, + 99, 99, 99, 99, 99, 99,102,225, 99,226,102,227,227,227,227,227, + 228,228,228,228,228,228, 0, 0, 8, 0, 0, 0, 0, 0,229,230, + 231, 0,232, 0,233,233,233,233, 91, 91, 91, 13,234,234,234,234, + 235,235,235,235,236,236,236,236,237,237,237,237,238,238,238,238, + 239,239,239,239,240, 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 2, + 2, 2, 3, 0, 0, 0, 4, 0, 2, 2, 2, 2, 2, 3, 2, 2, + 2, 2, 5, 0, 2, 5, 6, 0, 7, 7, 7, 7, 8, 9, 8, 10, + 8, 11, 8, 8, 8, 8, 8, 8, 12, 13, 13, 13, 14, 14, 14, 14, + 14, 15, 14, 14, 16, 17, 17, 17, 17, 17, 17, 17, 18, 19, 19, 19, + 19, 19, 19, 19, 20, 21, 20, 22, 20, 20, 23, 23, 20, 20, 20, 20, + 22, 20, 24, 7, 7, 25, 20, 20, 26, 20, 20, 20, 20, 20, 20, 21, + 27, 27, 27, 27, 28, 28, 28, 28, 29, 29, 29, 29, 30, 30, 30, 30, + 31, 31, 31, 31, 32, 20, 20, 20, 33, 33, 33, 33, 34, 35, 33, 33, + 33, 36, 33, 33, 37, 37, 37, 37, 38, 38, 38, 38, 39, 39, 39, 39, + 40, 40, 40, 40, 41, 41, 41, 41, 42, 42, 42, 42, 43, 43, 43, 43, + 44, 44, 44, 44, 45, 45, 45, 45, 46, 46, 46, 46, 46, 46, 46, 47, + 48, 48, 48, 48, 49, 49, 49, 49, 49, 50, 51, 49, 52, 52, 52, 52, + 53, 53, 53, 53, 53, 53, 54, 53, 55, 55, 55, 55, 56, 56, 56, 56, + 57, 57, 57, 57, 58, 58, 58, 58, 59, 59, 59, 59, 60, 60, 60, 60, + 60, 60, 61, 62, 63, 63, 63, 63, 64, 64, 64, 64, 64, 65, 0, 0, + 66, 66, 66, 66, 67, 67, 67, 67, 68, 68, 68, 68, 69, 70, 71, 71, + 71, 71, 71, 71, 72, 72, 72, 72, 73, 73, 73, 73, 74, 74, 74, 74, + 75, 75, 75, 75, 76, 76, 76, 76, 77, 77, 77, 77, 78, 78, 78, 78, + 79, 79, 79, 79, 80, 80, 80, 80, 81, 81, 81, 81, 82, 7, 7, 7, + 83, 7, 84, 85, 0, 84, 86, 0, 2, 87, 88, 2, 2, 2, 2, 89, + 90, 87, 91, 2, 2, 2, 92, 2, 2, 2, 2, 93, 0, 0, 0, 86, + 1, 0, 0, 94, 0, 95, 96, 0, 4, 0, 0, 0, 0, 0, 0, 4, + 97, 97, 97, 97, 98, 98, 98, 98, 13, 13, 13, 13, 99, 99, 99, 99, + 100,100,100,100, 0,101, 0, 0,102,100,103,104, 0, 0,100, 0, + 105,106,106,106,106,106,106,106,106,106,107,105,108,109,109,109, + 109,109,109,109,109,109,110,108,111,111,111,111,112, 55, 55, 55, + 55, 55, 55,113,109,109,109,110,109,109, 0, 0,114,114,114,114, + 115,115,115,115,116,116,116,116,117,117,117,117, 96, 2, 2, 2, + 2, 2, 94, 2,118,118,118,118,119,119,119,119,120,120,120,120, + 121,121,121,121,121,121,121,122,123,123,123,123,124,124,124,124, + 124,124,124,125,126,126,126,126,127,127,127,127,128,128,128,128, + 2, 2, 3, 2, 2,129,130, 0,131,131,131,131,132, 17, 17, 18, + 20, 20, 20,133, 7, 7, 7,134, 20, 20, 20, 23, 0,135,109,109, + 109,109,109,136,137,137,137,137, 0, 0, 0,138,139,139,139,139, + 140,140,140,140, 84, 0, 0, 0,141,141,141,141,142,142,142,142, + 143,143,143,143,144,144,144,144,145,145,145,145,146,146,146,146, + 147,147,147,147,148,148,148,148,149,149,149,149,150,150,150,150, + 151,151,151,151,152,152,152,152,153,153,153,153,154,154,154,154, + 155,155,155,155,156,156,156,156,157,157,157,157,158,158,158,158, + 159,159,159,159,160,160,160,160,161,161,161,161,162,162,162,162, + 163,163,163,163,164,164,164,164,165,165,165,165,166,166,166,166, + 167,167,167,167,168,168,168,168,169,169,169,169,170,170,170,170, + 171,171,171,171,172,172,172,172,173,173,173,173,174,174,174,174, + 174,174,174,175,176,176,176,176,177,177,177,177,178,178,178,178, + 179,179,179,179,180,180,180,180,181,181,181,181,182,182,182,182, + 183,183,183,183,184,184,184,184,185,185,185,185,186,186,186,186, + 187, 45, 45, 45,188,188,188,188,189,189,189,189,190,190,190,190, + 191,191,191,191,191,191,192,191,193,193,193,193,194,194,194,194, + 195,195,195,195,196,196,196,196,197,197,197,197,198,198,198,198, + 199,199,199,199,200,200,200,200,201,201,201,201,202,202,202,202, + 203,203,203,203,204,204,204,204,205,205,205,205,206,206,206,206, + 207,207,207,207,208,208,208,208,209,209,209,209,210,210,210,210, + 211,211,211,211,212,212,212,212,213,213,213,213,214,214,214,214, + 215,215,215,215,216,216,216,216,217,217,217,217,218,218,218,218, + 219,219,219,219,220,220,220,220,221,221,221,221,222,223,223,223, + 224,224,224,224,223,223,223,223,225,106,106,106,226,106,106,106, + 106,227,109,109,228,228,228,228,229,229,229,229, 0,230, 86, 0, + 0, 0,230, 7, 82,138, 7, 0, 0, 0,231, 86,232,232,232,232, + 233,233,233,233,234,234,234,234,235,235,235,235,236,236,236,236, + 237,237,237,237,238,238,238,238,239, 0, 0, 0, 0, 0, 0, 0, + 0, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 0, 0, 0, 19, 0, + 19, 0, 0, 0, 0, 0, 26, 26, 1, 1, 1, 1, 9, 9, 9, 9, + 0, 9, 9, 9, 9, 9, 0, 9, 9, 0, 9, 0, 9, 9, 55, 55, + 55, 55, 55, 55, 6, 6, 6, 6, 6, 1, 1, 6, 6, 4, 4, 4, + 4, 4, 4, 4, 4, 14, 14, 14, 14, 14, 14, 14, 3, 3, 3, 3, + 3, 0, 3, 3, 0, 3, 3, 3, 3, 3, 3, 0, 3, 3, 3, 1, + 1, 1, 3, 3, 1, 3, 3, 3, 37, 37, 37, 37, 38, 38, 38, 38, + 64, 64, 64, 64, 90, 90, 90, 90, 95, 95, 95, 95, 3, 3, 0, 3, + 7, 7, 7, 7, 7, 1, 1, 1, 1, 7, 7, 7, 0, 0, 7, 7, + 5, 5, 5, 5, 11, 11, 11, 11, 10, 10, 10, 10, 21, 21, 21, 21, + 22, 22, 22, 22, 23, 23, 23, 23, 16, 16, 16, 16, 20, 20, 20, 20, + 36, 36, 36, 36, 24, 24, 24, 24, 24, 24, 24, 0, 18, 18, 18, 18, + 25, 25, 25, 25, 25, 0, 0, 0, 0, 25, 25, 25, 33, 33, 33, 33, + 8, 8, 8, 8, 8, 8, 8, 0, 12, 12, 12, 12, 30, 30, 30, 30, + 29, 29, 29, 29, 28, 28, 28, 28, 34, 34, 34, 34, 35, 35, 35, 35, + 35, 35, 35, 0, 0, 0, 35, 35, 45, 45, 45, 45, 44, 44, 44, 44, + 44, 0, 0, 0, 43, 43, 43, 43, 46, 46, 46, 46, 31, 31, 31, 31, + 32, 32, 0, 0, 32, 0, 32, 32, 32, 32, 32, 32, 48, 48, 48, 48, + 52, 52, 52, 52, 58, 58, 58, 58, 54, 54, 54, 54, 91, 91, 91, 91, + 62, 62, 62, 62, 76, 76, 76, 76, 93, 93, 93, 93, 70, 70, 70, 70, + 73, 73, 73, 73, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 0, 0, + 0, 1, 0, 0, 1, 1, 0, 0, 19, 19, 9, 9, 9, 9, 9, 6, + 19, 9, 9, 9, 9, 9, 19, 19, 9, 9, 9, 19, 6, 19, 19, 19, + 19, 19, 19, 9, 0, 0, 0, 19, 0, 0, 9, 0, 0, 0, 19, 19, + 27, 27, 27, 27, 56, 56, 56, 56, 61, 61, 61, 61, 13, 13, 13, 13, + 0, 13, 0, 13, 0, 13, 13, 13, 13, 13, 1, 1, 1, 1, 12, 12, + 0, 15, 15, 15, 15, 15, 15, 15, 15, 1, 1, 0, 0, 17, 17, 17, + 17, 17, 17, 17, 17, 17, 17, 0, 26, 26, 26, 26, 26, 12, 12, 12, + 12, 12, 12, 0, 39, 39, 39, 39, 86, 86, 86, 86, 77, 77, 77, 77, + 79, 79, 79, 79, 60, 60, 60, 60, 65, 65, 65, 65, 75, 75, 75, 75, + 69, 69, 69, 69, 69, 69, 0, 69, 74, 74, 74, 74, 84, 84, 84, 84, + 84, 84, 84, 0, 68, 68, 68, 68, 92, 92, 92, 92, 87, 87, 87, 87, + 19, 9, 19, 19, 19, 19, 0, 0, 2, 2, 2, 2, 19, 19, 19, 4, + 3, 3, 0, 0, 1, 1, 6, 6, 0, 0, 17, 17, 17, 17, 0, 0, + 49, 49, 49, 49, 0, 1, 1, 1, 71, 71, 71, 71, 67, 67, 67, 67, + 42, 42, 42, 42, 41, 41, 41, 41,118,118,118,118, 53, 53, 53, 53, + 59, 59, 59, 59, 40, 40, 40, 40, 51, 51, 51, 51, 50, 50, 50, 50, + 135,135,135,135,106,106,106,106,104,104,104,104,161,161,161,161, + 110,110,110,110, 47, 47, 47, 47, 81, 81, 81, 81,120,120,120,120, + 116,116,116,116,128,128,128,128, 66, 66, 66, 66, 72, 72, 72, 72, + 98, 98, 98, 98, 97, 97, 97, 97, 57, 57, 57, 57, 88, 88, 88, 88, + 117,117,117,117,112,112,112,112, 78, 78, 78, 78, 83, 83, 83, 83, + 82, 82, 82, 82,122,122,122,122, 89, 89, 89, 89,130,130,130,130, + 144,144,144,144,156,156,156,156,156, 3, 3, 3,147,147,147,147, + 148,148,148,148,158,158,158,158,153,153,153,153,149,149,149,149, + 94, 94, 94, 94, 85, 85, 85, 85,101,101,101,101, 96, 96, 96, 96, + 111,111,111,111,100,100,100,100,100, 36, 36, 36,108,108,108,108, + 129,129,129,129,109,109,109,109,107,107,107,107,107,107,107, 1, + 137,137,137,137,124,124,124,124,123,123,123,123,114,114,114,114, + 102,102,102,102,126,126,126,126,142,142,142,142,125,125,125,125, + 154,154,154,154,150,150,150,150,141,141,141,141,140,140,140,140, + 121,121,121,121,133,133,133,133,134,134,134,134,138,138,138,138, + 143,143,143,143,145,145,145,145,163,163,163,163, 63, 63, 63, 63, 157,157,157,157, 80, 80, 80, 80,127,127,127,127,115,115,115,115, 159,159,159,159,103,103,103,103,119,119,119,119,146,146,146,146, 99, 99, 99, 99,136,139, 13, 13,155,155,155,155,136,136,136,136, - 17, 15, 15, 15,139,139,139,139,105,105,105,105, 0, 0, 0, 1, - 0, 0, 1, 1,131,131,131,131,151,151,151,151,160,160,160,160, - 152,152,152,152,113,113,113,113,132,132,132,132, 15, 0, 0, 0, - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 9, 9, 9, 10, 9, 11, - 12, 13, 9, 9, 9, 14, 9, 9, 15, 9, 9, 9, 9, 9, 9, 9, + 17, 15, 15, 15, 17, 17, 15, 15, 15, 17, 17, 17,139,139,139,139, + 105,105,105,105, 0, 0, 0, 1, 0, 0, 1, 1,131,131,131,131, + 151,151,151,151,160,160,160,160,152,152,152,152,164,164,164,164, + 113,113,113,113,132,132,132,132, 15, 0, 0, 0, 0, 1, 2, 3, + 4, 5, 6, 7, 8, 9, 9, 9, 9, 10, 9, 11, 12, 13, 9, 9, + 9, 14, 9, 9, 15, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 16, 17, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 18, 19, 20, 9, 21, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 16, 17, 9, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 18, 19, 20, 9, 21, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 22, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 22, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, @@ -5336,60 +5401,60 @@ _hb_ucd_u8[13246] = 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 23, 24, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, - 7, 8, 9, 10, 11, 12, 0, 0, 13, 14, 15, 16, 17, 18, 19, 20, - 21, 22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 23, 0, 0, 24, 25, 26, 27, 28, 29, 30, 0, 0, 31, 32, - 0, 33, 0, 34, 0, 35, 0, 0, 0, 0, 36, 37, 38, 39, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 41, 42, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 9, 9, 9, 9, 9, 9, 9, 9, 23, 24, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, + 11, 12, 0, 0, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 0, + 0, 24, 25, 26, 27, 28, 29, 30, 0, 0, 31, 32, 0, 33, 0, 34, + 0, 35, 0, 0, 0, 0, 36, 37, 38, 39, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 40, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 41, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 43, 44, 0, 45, 0, 0, 0, 0, 0, 0, 46, 47, 0, 0, 0, 0, - 0, 48, 0, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 50, 51, 0, 0, 0, 52, 0, 0, 53, 0, 0, 0, 0, 0, - 0, 0, 54, 0, 0, 0, 0, 0, 0, 0, 55, 0, 0, 0, 0, 0, - 0, 0, 56, 0, 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 43, 44, 0, 45, + 0, 0, 0, 0, 0, 0, 46, 47, 0, 0, 0, 0, 0, 48, 0, 49, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 50, 51, + 0, 0, 0, 52, 0, 0, 53, 0, 0, 0, 0, 0, 0, 0, 54, 0, + 0, 0, 0, 0, 0, 0, 55, 0, 0, 0, 0, 0, 0, 0, 56, 0, + 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 58, 59, + 60, 61, 62, 63, 64, 65, 0, 0, 0, 0, 0, 0, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 58, 59, 60, 61, 62, 63, 64, 65, 0, 0, 0, 0, 0, 0, - 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 67, 68, - 0, 69, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 71, 72, - 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, - 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99,100,101,102,103, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 67, 68, 0, 69, 70, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 71, 72, 73, 74, 75, 76, + 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, + 93, 94, 95, 96, 97, 98, 99,100,101,102,103, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,104, 0, 0, 0, + 0, 0, 0,105,106, 0,107, 0, 0, 0,108, 0,109, 0,110, 0, + 111,112,113, 0,114, 0, 0, 0,115, 0, 0, 0,116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 104, 0, 0, 0, 0, 0, 0,105,106, 0,107, 0, 0, 0,108, 0, - 109, 0,110, 0,111,112,113, 0,114, 0, 0, 0,115, 0, 0, 0, - 116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,117, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0,117, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,118,119, + 120,121, 0,122,123,124,125,126, 0,127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0,118,119,120,121, 0,122,123,124,125,126, 0,127, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,128,129,130,131,132,133, + 134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149, + 150,151,152,153,154,155,156,157, 0, 0, 0,158,159,160,161, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,128,129, - 130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145, - 146,147,148,149,150,151,152,153,154,155,156,157, 0, 0, 0,158, - 159,160,161, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0,162,163, 0, 0, 0, 0, 0, 0, 0, - 164, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0,162,163, 0, 0, 0, 0, 0, 0, 0,164, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0,165, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,166, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0,167, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,165, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0,168, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,166, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0,167, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,168, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0,169,170, 0, 0, 0, 0,171,172, 0, 0, 0,173,174, - 175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190, - 191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,169, + 170, 0, 0, 0, 0,171,172, 0, 0, 0,173,174,175,176,177,178, + 179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194, + 195,196,197,198,199,200,201,202,203,204,205,206, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, + 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, }; static const uint16_t -_hb_ucd_u16[4888] = +_hb_ucd_u16[4920] = { 0, 0, 1, 2, 3, 4, 5, 6, 0, 0, 7, 8, 9, 10, 11, 12, 13, 13, 13, 14, 15, 13, 13, 16, 17, 18, 19, 20, 21, 22, 13, 23, @@ -5456,39 +5521,41 @@ _hb_ucd_u16[4888] = 359, 47, 47, 360, 145, 66, 47, 361, 47, 362, 145, 145, 363, 47, 364, 66, 47, 47, 47, 365, 47, 366, 47, 366, 47, 365, 144, 145, 145, 145, 145, 145, 9, 9, 9, 9, 11, 11, 11, 367, 47, 47, 368, 160, 160, 160, 160, 160, - 145, 145, 145, 145, 145, 145, 145, 145, 47, 47, 369, 47, 47, 47, 47, 47, + 145, 145, 145, 145, 145, 145, 145, 145, 47, 47, 369, 47, 47, 47, 47, 143, 47, 362, 370, 47, 60, 371, 66, 47, 372, 66, 66, 47, 373, 145, 47, 47, 374, 47, 47, 360, 375, 376, 377, 378, 180, 47, 47, 379, 380, 47, 47, 160, 97, 47, 381, 382, 383, 47, 47, 384, 180, 47, 47, 385, 386, 387, 388, 145, - 47, 47, 389, 390, 32, 32, 32, 32, 47, 47, 365, 47, 47, 391, 172, 160, + 47, 47, 389, 390, 359, 32, 32, 32, 47, 47, 365, 47, 47, 391, 172, 160, 92, 47, 47, 113, 392, 393, 394, 32, 47, 47, 47, 395, 396, 397, 47, 47, 47, 47, 47, 398, 399, 160, 160, 160, 47, 47, 400, 401, 402, 403, 32, 32, 47, 47, 47, 404, 405, 160, 66, 66, 47, 47, 406, 407, 160, 160, 160, 160, 47, 143, 408, 409, 47, 47, 47, 47, 47, 47, 389, 410, 66, 66, 66, 66, 9, 9, 9, 9, 11, 11, 128, 411, 47, 47, 47, 412, 413, 160, 160, 160, 47, 47, 47, 47, 47, 414, 415, 416, 417, 47, 47, 418, 419, 420, 47, 47, - 421, 422, 66, 47, 47, 47, 47, 47, 47, 47, 400, 423, 424, 128, 145, 425, - 47, 156, 426, 427, 32, 32, 32, 32, 47, 47, 47, 359, 428, 160, 47, 47, - 429, 430, 160, 160, 160, 160, 160, 160, 47, 47, 47, 47, 47, 47, 47, 431, - 47, 47, 47, 47, 145, 432, 433, 434, 219, 219, 219, 219, 219, 219, 219, 66, - 47, 47, 47, 47, 47, 47, 47, 424, 47, 47, 47, 208, 208, 208, 208, 208, - 47, 47, 47, 47, 47, 47, 305, 47, 47, 47, 47, 47, 160, 47, 47, 435, - 47, 47, 47, 436, 437, 438, 439, 47, 9, 9, 9, 9, 9, 9, 11, 11, - 145, 440, 66, 66, 66, 66, 66, 66, 47, 47, 47, 47, 391, 441, 416, 416, - 442, 443, 27, 27, 27, 27, 444, 416, 47, 445, 208, 208, 208, 208, 208, 208, - 32, 32, 32, 32, 32, 146, 146, 146, 146, 146, 146, 146, 146, 146, 446, 447, - 448, 146, 449, 146, 146, 146, 146, 146, 146, 146, 146, 146, 450, 146, 146, 146, - 9, 451, 11, 452, 453, 11, 196, 9, 454, 455, 9, 456, 11, 9, 451, 11, - 452, 453, 11, 196, 9, 454, 455, 9, 456, 11, 9, 451, 11, 452, 453, 11, - 196, 9, 454, 455, 9, 456, 11, 9, 451, 11, 196, 9, 457, 458, 459, 460, - 11, 461, 9, 462, 463, 464, 465, 11, 466, 9, 467, 11, 468, 160, 160, 160, - 32, 32, 32, 469, 32, 32, 470, 471, 472, 473, 32, 32, 32, 32, 32, 32, - 474, 11, 11, 11, 11, 11, 11, 11, 32, 32, 32, 32, 32, 32, 32, 32, - 47, 47, 47, 475, 476, 146, 146, 146, 47, 47, 477, 32, 47, 47, 478, 479, - 47, 47, 47, 47, 355, 32, 32, 32, 9, 9, 454, 11, 480, 305, 66, 66, - 145, 145, 481, 482, 145, 145, 145, 145, 145, 145, 483, 145, 145, 145, 145, 145, - 47, 47, 47, 47, 47, 47, 47, 226, 484, 146, 146, 146, 146, 146, 146, 146, - 146, 146, 146, 146, 146, 146, 146, 485, 146, 146, 146, 146, 146, 146, 146, 160, + 421, 422, 66, 47, 47, 47, 47, 47, 66, 66, 66, 66, 66, 66, 66, 66, + 47, 47, 400, 423, 424, 128, 145, 425, 47, 156, 426, 427, 32, 32, 32, 32, + 47, 47, 47, 359, 428, 160, 47, 47, 429, 430, 160, 160, 160, 160, 160, 160, + 47, 47, 47, 47, 47, 47, 47, 431, 432, 47, 47, 433, 434, 160, 160, 160, + 47, 47, 47, 47, 145, 435, 436, 437, 219, 219, 219, 219, 219, 219, 219, 66, + 47, 47, 47, 47, 47, 47, 47, 424, 47, 47, 47, 208, 438, 32, 32, 32, + 47, 47, 47, 47, 47, 47, 305, 47, 47, 47, 47, 47, 160, 47, 47, 439, + 47, 47, 47, 440, 441, 442, 443, 47, 9, 9, 9, 9, 9, 9, 11, 11, + 145, 444, 66, 66, 66, 66, 66, 66, 47, 47, 47, 47, 391, 445, 416, 416, + 446, 447, 27, 27, 27, 27, 448, 416, 47, 449, 208, 208, 208, 208, 208, 208, + 32, 32, 32, 32, 32, 146, 146, 146, 146, 146, 146, 146, 146, 146, 450, 451, + 452, 146, 453, 146, 146, 146, 146, 146, 146, 146, 146, 146, 454, 146, 146, 146, + 9, 455, 11, 456, 457, 11, 196, 9, 458, 459, 9, 460, 11, 9, 455, 11, + 456, 457, 11, 196, 9, 458, 459, 9, 460, 11, 9, 455, 11, 456, 457, 11, + 196, 9, 458, 459, 9, 460, 11, 9, 455, 11, 196, 9, 461, 462, 463, 464, + 11, 465, 9, 466, 467, 468, 469, 11, 470, 9, 471, 11, 472, 160, 160, 160, + 32, 32, 32, 473, 32, 32, 474, 475, 476, 477, 32, 32, 32, 32, 32, 32, + 478, 11, 11, 11, 11, 11, 11, 11, 32, 32, 32, 27, 27, 27, 27, 27, + 32, 32, 32, 32, 32, 32, 32, 32, 47, 47, 47, 479, 480, 146, 146, 146, + 47, 47, 481, 32, 47, 47, 482, 483, 47, 47, 47, 47, 47, 47, 484, 160, + 47, 47, 47, 47, 355, 32, 32, 32, 9, 9, 458, 11, 485, 305, 66, 66, + 145, 145, 486, 487, 145, 145, 145, 145, 145, 145, 488, 145, 145, 145, 145, 145, + 47, 47, 47, 47, 47, 47, 47, 226, 489, 146, 146, 146, 146, 146, 146, 146, + 146, 146, 146, 146, 146, 146, 146, 490, 146, 146, 146, 146, 146, 146, 146, 160, 208, 208, 208, 208, 208, 208, 208, 208, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 939, 940, 941, 942, 946, 948, 0, 962, 969, 970, 971, 976,1001,1002,1003,1008, 0,1033,1040,1041,1042,1043,1047, 0, @@ -5712,12 +5779,12 @@ _hb_ucd_i16[92] = static inline uint_fast8_t _hb_ucd_gc (unsigned u) { - return u<1114112u?_hb_ucd_u8[5056+(((_hb_ucd_u8[1168+(((_hb_ucd_u16[((_hb_ucd_u8[544+(((_hb_ucd_u8[u>>1>>3>>3>>4])<<4)+((u>>1>>3>>3)&15u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:2; + return u<1114112u?_hb_ucd_u8[5080+(((_hb_ucd_u8[1152+(((_hb_ucd_u16[((_hb_ucd_u8[544+(((_hb_ucd_u8[u>>1>>3>>3>>4])<<4)+((u>>1>>3>>3)&15u))])<<3)+((u>>1>>3)&7u)])<<3)+((u>>1)&7u))])<<1)+((u)&1u))]:2; } static inline uint_fast8_t _hb_ucd_ccc (unsigned u) { - return u<125259u?_hb_ucd_u8[6970+(((_hb_ucd_u8[6426+(((_hb_ucd_u8[5982+(((_hb_ucd_u8[5646+(((_hb_ucd_u8[5400+(u>>2>>2>>2>>3)])<<3)+((u>>2>>2>>2)&7u))])<<2)+((u>>2>>2)&3u))])<<2)+((u>>2)&3u))])<<2)+((u)&3u))]:0; + return u<125259u?_hb_ucd_u8[7038+(((_hb_ucd_u8[6482+(((_hb_ucd_u8[6022+(((_hb_ucd_u8[5670+(((_hb_ucd_u8[5424+(u>>2>>2>>2>>3)])<<3)+((u>>2>>2>>2)&7u))])<<2)+((u>>2>>2)&3u))])<<2)+((u>>2)&3u))])<<2)+((u)&3u))]:0; } static inline unsigned _hb_ucd_b4 (const uint8_t* a, unsigned i) @@ -5727,17 +5794,17 @@ _hb_ucd_b4 (const uint8_t* a, unsigned i) static inline int_fast16_t _hb_ucd_bmg (unsigned u) { - return u<65380u?_hb_ucd_i16[((_hb_ucd_u8[7858+(((_hb_ucd_u8[7626+(((_hb_ucd_u8[7530+(((_hb_ucd_b4(7466+_hb_ucd_u8,u>>1>>2>>3>>3))<<3)+((u>>1>>2>>3)&7u))])<<3)+((u>>1>>2)&7u))])<<2)+((u>>1)&3u))])<<1)+((u)&1u)]:0; + return u<65380u?_hb_ucd_i16[((_hb_ucd_u8[7930+(((_hb_ucd_u8[7698+(((_hb_ucd_u8[7602+(((_hb_ucd_b4(7538+_hb_ucd_u8,u>>1>>2>>3>>3))<<3)+((u>>1>>2>>3)&7u))])<<3)+((u>>1>>2)&7u))])<<2)+((u>>1)&3u))])<<1)+((u)&1u)]:0; } static inline uint_fast8_t _hb_ucd_sc (unsigned u) { - return u<918016u?_hb_ucd_u8[11124+(((_hb_ucd_u8[10176+(((_hb_ucd_u8[9204+(((_hb_ucd_u8[8524+(((_hb_ucd_u8[8220+(((_hb_ucd_u8[8106+(u>>2>>2>>2>>3>>4)])<<4)+((u>>2>>2>>2>>3)&15u))])<<3)+((u>>2>>2>>2)&7u))])<<2)+((u>>2>>2)&3u))])<<2)+((u>>2)&3u))])<<2)+((u)&3u))]:2; + return u<918016u?_hb_ucd_u8[11228+(((_hb_ucd_u8[10264+(((_hb_ucd_u8[9276+(((_hb_ucd_u8[8596+(((_hb_ucd_u8[8292+(((_hb_ucd_u8[8178+(u>>2>>2>>2>>3>>4)])<<4)+((u>>2>>2>>2>>3)&15u))])<<3)+((u>>2>>2>>2)&7u))])<<2)+((u>>2>>2)&3u))])<<2)+((u>>2)&3u))])<<2)+((u)&3u))]:2; } static inline uint_fast16_t _hb_ucd_dm (unsigned u) { - return u<195102u?_hb_ucd_u16[1576+(((_hb_ucd_u8[12446+(((_hb_ucd_u8[12064+(u>>4>>5)])<<5)+((u>>4)&31u))])<<4)+((u)&15u))]:0; + return u<195102u?_hb_ucd_u16[1608+(((_hb_ucd_u8[12570+(((_hb_ucd_u8[12188+(u>>4>>5)])<<5)+((u>>4)&31u))])<<4)+((u)&15u))]:0; } #endif diff --git a/thirdparty/harfbuzz/src/hb-unicode-emoji-table.hh b/thirdparty/harfbuzz/src/hb-unicode-emoji-table.hh index 036c71a424..13b1c4b1d4 100644 --- a/thirdparty/harfbuzz/src/hb-unicode-emoji-table.hh +++ b/thirdparty/harfbuzz/src/hb-unicode-emoji-table.hh @@ -6,16 +6,16 @@ * * on file with this header: * - * # emoji-data-14.0.0.txt - * # Date: 2021-08-26, 17:22:22 GMT - * # © 2021 Unicode®, Inc. + * # emoji-data.txt + * # Date: 2022-08-02, 00:26:10 GMT + * # © 2022 Unicode®, Inc. * # Unicode and the Unicode Logo are registered trademarks of Unicode, Inc. in the U.S. and other countries. - * # For terms of use, see http://www.unicode.org/terms_of_use.html + * # For terms of use, see https://www.unicode.org/terms_of_use.html * # * # Emoji Data for UTS #51 - * # Used with Emoji Version 14.0 and subsequent minor revisions (if any) + * # Used with Emoji Version 15.0 and subsequent minor revisions (if any) * # - * # For documentation and usage, see http://www.unicode.org/reports/tr51 + * # For documentation and usage, see https://www.unicode.org/reports/tr51 */ #ifndef HB_UNICODE_EMOJI_TABLE_HH diff --git a/thirdparty/harfbuzz/src/hb-version.h b/thirdparty/harfbuzz/src/hb-version.h index a1586a58b6..fa7403cae7 100644 --- a/thirdparty/harfbuzz/src/hb-version.h +++ b/thirdparty/harfbuzz/src/hb-version.h @@ -47,7 +47,7 @@ HB_BEGIN_DECLS * * The minor component of the library version available at compile-time. */ -#define HB_VERSION_MINOR 1 +#define HB_VERSION_MINOR 2 /** * HB_VERSION_MICRO: * @@ -60,7 +60,7 @@ HB_BEGIN_DECLS * * A string literal containing the library version available at compile-time. */ -#define HB_VERSION_STRING "5.1.0" +#define HB_VERSION_STRING "5.2.0" /** * HB_VERSION_ATLEAST: diff --git a/thirdparty/libpng/LICENSE b/thirdparty/libpng/LICENSE index e0c5b531cf..c8ad24eecf 100644 --- a/thirdparty/libpng/LICENSE +++ b/thirdparty/libpng/LICENSE @@ -4,8 +4,8 @@ COPYRIGHT NOTICE, DISCLAIMER, and LICENSE PNG Reference Library License version 2 --------------------------------------- - * Copyright (c) 1995-2019 The PNG Reference Library Authors. - * Copyright (c) 2018-2019 Cosmin Truta. + * Copyright (c) 1995-2022 The PNG Reference Library Authors. + * Copyright (c) 2018-2022 Cosmin Truta. * Copyright (c) 2000-2002, 2004, 2006-2018 Glenn Randers-Pehrson. * Copyright (c) 1996-1997 Andreas Dilger. * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. diff --git a/thirdparty/libpng/arm/arm_init.c b/thirdparty/libpng/arm/arm_init.c index a34ecdbef7..ab22525b38 100644 --- a/thirdparty/libpng/arm/arm_init.c +++ b/thirdparty/libpng/arm/arm_init.c @@ -1,7 +1,7 @@ /* arm_init.c - NEON optimised filter functions * - * Copyright (c) 2018 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 2014,2016 Glenn Randers-Pehrson * Written by Mans Rullgard, 2011. * @@ -10,9 +10,7 @@ * and license in png.h */ -/* Below, after checking __linux__, various non-C90 POSIX 1003.1 functions are - * called. - */ +/* This module requires POSIX 1003.1 functions. */ #define _POSIX_SOURCE 1 #include "../pngpriv.h" @@ -33,21 +31,23 @@ * has partial support is contrib/arm-neon/linux.c - a generic Linux * implementation which reads /proc/cpufino. */ +#include <signal.h> /* for sig_atomic_t */ + #ifndef PNG_ARM_NEON_FILE -# ifdef __linux__ -# define PNG_ARM_NEON_FILE "contrib/arm-neon/linux.c" +# if defined(__aarch64__) || defined(_M_ARM64) + /* ARM Neon is expected to be unconditionally available on ARM64. */ +# error "PNG_ARM_NEON_CHECK_SUPPORTED must not be defined on this platform" +# elif defined(__linux__) +# define PNG_ARM_NEON_FILE "contrib/arm-neon/linux.c" +# else +# error "No support for run-time ARM Neon checking; use compile-time options" # endif #endif -#ifdef PNG_ARM_NEON_FILE - -#include <signal.h> /* for sig_atomic_t */ static int png_have_neon(png_structp png_ptr); -#include PNG_ARM_NEON_FILE - -#else /* PNG_ARM_NEON_FILE */ -# error "PNG_ARM_NEON_FILE undefined: no support for run-time ARM NEON checks" -#endif /* PNG_ARM_NEON_FILE */ +#ifdef PNG_ARM_NEON_FILE +# include PNG_ARM_NEON_FILE +#endif #endif /* PNG_ARM_NEON_CHECK_SUPPORTED */ #ifndef PNG_ALIGNED_MEMORY_SUPPORTED diff --git a/thirdparty/libpng/arm/filter_neon_intrinsics.c b/thirdparty/libpng/arm/filter_neon_intrinsics.c index 553c0be21c..4466d48b20 100644 --- a/thirdparty/libpng/arm/filter_neon_intrinsics.c +++ b/thirdparty/libpng/arm/filter_neon_intrinsics.c @@ -18,7 +18,7 @@ /* This code requires -mfpu=neon on the command line: */ #if PNG_ARM_NEON_IMPLEMENTATION == 1 /* intrinsics code from pngpriv.h */ -#if defined(_MSC_VER) && defined(_M_ARM64) +#if defined(_MSC_VER) && !defined(__clang__) && defined(_M_ARM64) # include <arm64_neon.h> #else # include <arm_neon.h> diff --git a/thirdparty/libpng/arm/palette_neon_intrinsics.c b/thirdparty/libpng/arm/palette_neon_intrinsics.c index b4d1fd2abf..92c7d6f9f6 100644 --- a/thirdparty/libpng/arm/palette_neon_intrinsics.c +++ b/thirdparty/libpng/arm/palette_neon_intrinsics.c @@ -14,7 +14,7 @@ #if PNG_ARM_NEON_IMPLEMENTATION == 1 -#if defined(_MSC_VER) && defined(_M_ARM64) +#if defined(_MSC_VER) && !defined(__clang__) && defined(_M_ARM64) # include <arm64_neon.h> #else # include <arm_neon.h> @@ -30,8 +30,6 @@ png_riffle_palette_neon(png_structrp png_ptr) int num_trans = png_ptr->num_trans; int i; - png_debug(1, "in png_riffle_palette_neon"); - /* Initially black, opaque. */ uint8x16x4_t w = {{ vdupq_n_u8(0x00), @@ -40,6 +38,8 @@ png_riffle_palette_neon(png_structrp png_ptr) vdupq_n_u8(0xff), }}; + png_debug(1, "in png_riffle_palette_neon"); + /* First, riffle the RGB colours into an RGBA8 palette. * The alpha component is set to opaque for now. */ @@ -65,11 +65,12 @@ png_do_expand_palette_rgba8_neon(png_structrp png_ptr, png_row_infop row_info, png_uint_32 row_width = row_info->width; const png_uint_32 *riffled_palette = (const png_uint_32 *)png_ptr->riffled_palette; - const png_int_32 pixels_per_chunk = 4; - int i; + const png_uint_32 pixels_per_chunk = 4; + png_uint_32 i; png_debug(1, "in png_do_expand_palette_rgba8_neon"); + PNG_UNUSED(row) if (row_width < pixels_per_chunk) return 0; @@ -109,10 +110,11 @@ png_do_expand_palette_rgb8_neon(png_structrp png_ptr, png_row_infop row_info, png_uint_32 row_width = row_info->width; png_const_bytep palette = (png_const_bytep)png_ptr->palette; const png_uint_32 pixels_per_chunk = 8; - int i; + png_uint_32 i; png_debug(1, "in png_do_expand_palette_rgb8_neon"); + PNG_UNUSED(row) if (row_width <= pixels_per_chunk) return 0; diff --git a/thirdparty/libpng/png.c b/thirdparty/libpng/png.c index 757c755f97..fc09564262 100644 --- a/thirdparty/libpng/png.c +++ b/thirdparty/libpng/png.c @@ -1,7 +1,7 @@ /* png.c - location for general purpose libpng functions * - * Copyright (c) 2018-2019 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -14,7 +14,7 @@ #include "pngpriv.h" /* Generate a compiler error if there is an old png.h in the search path. */ -typedef png_libpng_version_1_6_37 Your_png_h_is_not_version_1_6_37; +typedef png_libpng_version_1_6_38 Your_png_h_is_not_version_1_6_38; #ifdef __GNUC__ /* The version tests may need to be added to, but the problem warning has @@ -720,7 +720,7 @@ png_init_io(png_structrp png_ptr, png_FILE_p fp) * * Where UNSIGNED_MAX is the appropriate maximum unsigned value, so when the * negative integral value is added the result will be an unsigned value - * correspnding to the 2's complement representation. + * corresponding to the 2's complement representation. */ void PNGAPI png_save_int_32(png_bytep buf, png_int_32 i) @@ -815,8 +815,8 @@ png_get_copyright(png_const_structrp png_ptr) return PNG_STRING_COPYRIGHT #else return PNG_STRING_NEWLINE \ - "libpng version 1.6.37" PNG_STRING_NEWLINE \ - "Copyright (c) 2018-2019 Cosmin Truta" PNG_STRING_NEWLINE \ + "libpng version 1.6.38" PNG_STRING_NEWLINE \ + "Copyright (c) 2018-2022 Cosmin Truta" PNG_STRING_NEWLINE \ "Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson" \ PNG_STRING_NEWLINE \ "Copyright (c) 1996-1997 Andreas Dilger" PNG_STRING_NEWLINE \ @@ -1843,12 +1843,12 @@ png_icc_profile_error(png_const_structrp png_ptr, png_colorspacerp colorspace, # ifdef PNG_WARNINGS_SUPPORTED else { - char number[PNG_NUMBER_BUFFER_SIZE]; /* +24 = 114*/ + char number[PNG_NUMBER_BUFFER_SIZE]; /* +24 = 114 */ pos = png_safecat(message, (sizeof message), pos, png_format_number(number, number+(sizeof number), PNG_NUMBER_FORMAT_x, value)); - pos = png_safecat(message, (sizeof message), pos, "h: "); /*+2 = 116*/ + pos = png_safecat(message, (sizeof message), pos, "h: "); /* +2 = 116 */ } # endif /* The 'reason' is an arbitrary message, allow +79 maximum 195 */ diff --git a/thirdparty/libpng/png.h b/thirdparty/libpng/png.h index b12174ba35..5fb494fb1a 100644 --- a/thirdparty/libpng/png.h +++ b/thirdparty/libpng/png.h @@ -1,9 +1,9 @@ /* png.h - header file for PNG reference library * - * libpng version 1.6.37 - April 14, 2019 + * libpng version 1.6.38 - September 14, 2022 * - * Copyright (c) 2018-2019 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -15,7 +15,7 @@ * libpng versions 0.89, June 1996, through 0.96, May 1997: Andreas Dilger * libpng versions 0.97, January 1998, through 1.6.35, July 2018: * Glenn Randers-Pehrson - * libpng versions 1.6.36, December 2018, through 1.6.37, April 2019: + * libpng versions 1.6.36, December 2018, through 1.6.38, September 2022: * Cosmin Truta * See also "Contributing Authors", below. */ @@ -27,8 +27,8 @@ * PNG Reference Library License version 2 * --------------------------------------- * - * * Copyright (c) 1995-2019 The PNG Reference Library Authors. - * * Copyright (c) 2018-2019 Cosmin Truta. + * * Copyright (c) 1995-2022 The PNG Reference Library Authors. + * * Copyright (c) 2018-2022 Cosmin Truta. * * Copyright (c) 2000-2002, 2004, 2006-2018 Glenn Randers-Pehrson. * * Copyright (c) 1996-1997 Andreas Dilger. * * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -239,7 +239,7 @@ * ... * 1.5.30 15 10530 15.so.15.30[.0] * ... - * 1.6.37 16 10637 16.so.16.37[.0] + * 1.6.38 16 10638 16.so.16.38[.0] * * Henceforth the source version will match the shared-library major and * minor numbers; the shared-library major version number will be used for @@ -278,8 +278,8 @@ */ /* Version information for png.h - this should match the version in png.c */ -#define PNG_LIBPNG_VER_STRING "1.6.37" -#define PNG_HEADER_VERSION_STRING " libpng version 1.6.37 - April 14, 2019\n" +#define PNG_LIBPNG_VER_STRING "1.6.38" +#define PNG_HEADER_VERSION_STRING " libpng version 1.6.38 - September 14, 2022\n" #define PNG_LIBPNG_VER_SONUM 16 #define PNG_LIBPNG_VER_DLLNUM 16 @@ -287,7 +287,7 @@ /* These should match the first 3 components of PNG_LIBPNG_VER_STRING: */ #define PNG_LIBPNG_VER_MAJOR 1 #define PNG_LIBPNG_VER_MINOR 6 -#define PNG_LIBPNG_VER_RELEASE 37 +#define PNG_LIBPNG_VER_RELEASE 38 /* This should be zero for a public release, or non-zero for a * development version. [Deprecated] @@ -318,7 +318,7 @@ * From version 1.0.1 it is: * XXYYZZ, where XX=major, YY=minor, ZZ=release */ -#define PNG_LIBPNG_VER 10637 /* 1.6.37 */ +#define PNG_LIBPNG_VER 10638 /* 1.6.38 */ /* Library configuration: these options cannot be changed after * the library has been built. @@ -330,10 +330,6 @@ # include "pnglibconf.h" #endif -#define PNG_APNG_SUPPORTED -#define PNG_READ_APNG_SUPPORTED -#define PNG_WRITE_APNG_SUPPORTED - #ifndef PNG_VERSION_INFO_ONLY /* Machine specific configuration. */ # include "pngconf.h" @@ -429,21 +425,10 @@ extern "C" { * See pngconf.h for base types that vary by machine/system */ -#ifdef PNG_APNG_SUPPORTED -/* dispose_op flags from inside fcTL */ -#define PNG_DISPOSE_OP_NONE 0x00U -#define PNG_DISPOSE_OP_BACKGROUND 0x01U -#define PNG_DISPOSE_OP_PREVIOUS 0x02U - -/* blend_op flags from inside fcTL */ -#define PNG_BLEND_OP_SOURCE 0x00U -#define PNG_BLEND_OP_OVER 0x01U -#endif /* PNG_APNG_SUPPORTED */ - /* This triggers a compiler error in png.c, if png.c and png.h * do not agree upon the version number. */ -typedef char* png_libpng_version_1_6_37; +typedef char* png_libpng_version_1_6_38; /* Basic control structions. Read libpng-manual.txt or libpng.3 for more info. * @@ -761,10 +746,6 @@ typedef png_unknown_chunk * * png_unknown_chunkpp; #define PNG_INFO_sCAL 0x4000U /* ESR, 1.0.6 */ #define PNG_INFO_IDAT 0x8000U /* ESR, 1.0.6 */ #define PNG_INFO_eXIf 0x10000U /* GR-P, 1.6.31 */ -#ifdef PNG_APNG_SUPPORTED -#define PNG_INFO_acTL 0x20000U -#define PNG_INFO_fcTL 0x40000U -#endif /* This is used for the transformation routines, as some of them * change these values for the row. It also should enable using @@ -802,10 +783,6 @@ typedef PNG_CALLBACK(void, *png_write_status_ptr, (png_structp, png_uint_32, #ifdef PNG_PROGRESSIVE_READ_SUPPORTED typedef PNG_CALLBACK(void, *png_progressive_info_ptr, (png_structp, png_infop)); typedef PNG_CALLBACK(void, *png_progressive_end_ptr, (png_structp, png_infop)); -#ifdef PNG_APNG_SUPPORTED -typedef PNG_CALLBACK(void, *png_progressive_frame_ptr, (png_structp, - png_uint_32)); -#endif /* The following callback receives png_uint_32 row_number, int pass for the * png_bytep data of the row. When transforming an interlaced image the @@ -1469,7 +1446,7 @@ PNG_EXPORT(66, void, png_set_crc_action, (png_structrp png_ptr, int crit_action, * mainly useful for testing, as the defaults should work with most users. * Those users who are tight on memory or want faster performance at the * expense of compression can modify them. See the compression library - * header file (zlib.h) for an explination of the compression functions. + * header file (zlib.h) for an explanation of the compression functions. */ /* Set the filtering method(s) used by libpng. Currently, the only valid @@ -1524,7 +1501,7 @@ PNG_FIXED_EXPORT(209, void, png_set_filter_heuristics_fixed, * 0 - 9, corresponding directly to the zlib compression levels 0 - 9 * (0 - no compression, 9 - "maximal" compression). Note that tests have * shown that zlib compression levels 3-6 usually perform as well as level 9 - * for PNG images, and do considerably fewer caclulations. In the future, + * for PNG images, and do considerably fewer calculations. In the future, * these values may not correspond directly to the zlib compression levels. */ #ifdef PNG_WRITE_CUSTOMIZE_COMPRESSION_SUPPORTED @@ -3249,74 +3226,6 @@ PNG_EXPORT(244, int, png_set_option, (png_structrp png_ptr, int option, /******************************************************************************* * END OF HARDWARE AND SOFTWARE OPTIONS ******************************************************************************/ -#ifdef PNG_APNG_SUPPORTED -PNG_EXPORT(250, png_uint_32, png_get_acTL, (png_structp png_ptr, - png_infop info_ptr, png_uint_32 *num_frames, png_uint_32 *num_plays)); - -PNG_EXPORT(251, png_uint_32, png_set_acTL, (png_structp png_ptr, - png_infop info_ptr, png_uint_32 num_frames, png_uint_32 num_plays)); - -PNG_EXPORT(252, png_uint_32, png_get_num_frames, (png_structp png_ptr, - png_infop info_ptr)); - -PNG_EXPORT(253, png_uint_32, png_get_num_plays, (png_structp png_ptr, - png_infop info_ptr)); - -PNG_EXPORT(254, png_uint_32, png_get_next_frame_fcTL, - (png_structp png_ptr, png_infop info_ptr, png_uint_32 *width, - png_uint_32 *height, png_uint_32 *x_offset, png_uint_32 *y_offset, - png_uint_16 *delay_num, png_uint_16 *delay_den, png_byte *dispose_op, - png_byte *blend_op)); - -PNG_EXPORT(255, png_uint_32, png_set_next_frame_fcTL, - (png_structp png_ptr, png_infop info_ptr, png_uint_32 width, - png_uint_32 height, png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, png_byte dispose_op, - png_byte blend_op)); - -PNG_EXPORT(256, png_uint_32, png_get_next_frame_width, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(257, png_uint_32, png_get_next_frame_height, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(258, png_uint_32, png_get_next_frame_x_offset, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(259, png_uint_32, png_get_next_frame_y_offset, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(260, png_uint_16, png_get_next_frame_delay_num, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(261, png_uint_16, png_get_next_frame_delay_den, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(262, png_byte, png_get_next_frame_dispose_op, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(263, png_byte, png_get_next_frame_blend_op, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(264, png_byte, png_get_first_frame_is_hidden, - (png_structp png_ptr, png_infop info_ptr)); -PNG_EXPORT(265, png_uint_32, png_set_first_frame_is_hidden, - (png_structp png_ptr, png_infop info_ptr, png_byte is_hidden)); - -#ifdef PNG_READ_APNG_SUPPORTED -PNG_EXPORT(266, void, png_read_frame_head, (png_structp png_ptr, - png_infop info_ptr)); -#ifdef PNG_PROGRESSIVE_READ_SUPPORTED -PNG_EXPORT(267, void, png_set_progressive_frame_fn, (png_structp png_ptr, - png_progressive_frame_ptr frame_info_fn, - png_progressive_frame_ptr frame_end_fn)); -#endif /* PNG_PROGRESSIVE_READ_SUPPORTED */ -#endif /* PNG_READ_APNG_SUPPORTED */ - -#ifdef PNG_WRITE_APNG_SUPPORTED -PNG_EXPORT(268, void, png_write_frame_head, (png_structp png_ptr, - png_infop info_ptr, png_bytepp row_pointers, - png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, png_byte dispose_op, - png_byte blend_op)); - -PNG_EXPORT(269, void, png_write_frame_tail, (png_structp png_ptr, - png_infop info_ptr)); -#endif /* PNG_WRITE_APNG_SUPPORTED */ -#endif /* PNG_APNG_SUPPORTED */ /* Maintainer: Put new public prototypes here ^, in libpng.3, in project * defs, and in scripts/symbols.def. @@ -3326,11 +3235,7 @@ PNG_EXPORT(269, void, png_write_frame_tail, (png_structp png_ptr, * one to use is one more than this.) */ #ifdef PNG_EXPORT_LAST_ORDINAL -#ifdef PNG_APNG_SUPPORTED - PNG_EXPORT_LAST_ORDINAL(269); -#else PNG_EXPORT_LAST_ORDINAL(249); -#endif /* PNG_APNG_SUPPORTED */ #endif #ifdef __cplusplus diff --git a/thirdparty/libpng/pngconf.h b/thirdparty/libpng/pngconf.h index 927a769dbe..89d28f83a0 100644 --- a/thirdparty/libpng/pngconf.h +++ b/thirdparty/libpng/pngconf.h @@ -1,9 +1,9 @@ /* pngconf.h - machine-configurable file for libpng * - * libpng version 1.6.37 + * libpng version 1.6.38 * - * Copyright (c) 2018-2019 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2016,2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -180,8 +180,8 @@ * compiler-specific macros to the values required to change the calling * conventions of the various functions. */ -#if defined(_Windows) || defined(_WINDOWS) || defined(WIN32) ||\ - defined(_WIN32) || defined(__WIN32__) || defined(__CYGWIN__) +#if defined(_WIN32) || defined(__WIN32__) || defined(__NT__) || \ + defined(__CYGWIN__) /* Windows system (DOS doesn't support DLLs). Includes builds under Cygwin or * MinGW on any architecture currently supported by Windows. Also includes * Watcom builds but these need special treatment because they are not diff --git a/thirdparty/libpng/pngget.c b/thirdparty/libpng/pngget.c index 9ed101aedc..e44933c0d2 100644 --- a/thirdparty/libpng/pngget.c +++ b/thirdparty/libpng/pngget.c @@ -1151,7 +1151,7 @@ png_get_unknown_chunks(png_const_structrp png_ptr, png_inforp info_ptr, #ifdef PNG_READ_RGB_TO_GRAY_SUPPORTED png_byte PNGAPI -png_get_rgb_to_gray_status (png_const_structrp png_ptr) +png_get_rgb_to_gray_status(png_const_structrp png_ptr) { return (png_byte)(png_ptr ? png_ptr->rgb_to_gray_status : 0); } @@ -1192,27 +1192,27 @@ png_get_compression_buffer_size(png_const_structrp png_ptr) /* These functions were added to libpng 1.2.6 and were enabled * by default in libpng-1.4.0 */ png_uint_32 PNGAPI -png_get_user_width_max (png_const_structrp png_ptr) +png_get_user_width_max(png_const_structrp png_ptr) { return (png_ptr ? png_ptr->user_width_max : 0); } png_uint_32 PNGAPI -png_get_user_height_max (png_const_structrp png_ptr) +png_get_user_height_max(png_const_structrp png_ptr) { return (png_ptr ? png_ptr->user_height_max : 0); } /* This function was added to libpng 1.4.0 */ png_uint_32 PNGAPI -png_get_chunk_cache_max (png_const_structrp png_ptr) +png_get_chunk_cache_max(png_const_structrp png_ptr) { return (png_ptr ? png_ptr->user_chunk_cache_max : 0); } /* This function was added to libpng 1.4.1 */ png_alloc_size_t PNGAPI -png_get_chunk_malloc_max (png_const_structrp png_ptr) +png_get_chunk_malloc_max(png_const_structrp png_ptr) { return (png_ptr ? png_ptr->user_chunk_malloc_max : 0); } @@ -1221,13 +1221,13 @@ png_get_chunk_malloc_max (png_const_structrp png_ptr) /* These functions were added to libpng 1.4.0 */ #ifdef PNG_IO_STATE_SUPPORTED png_uint_32 PNGAPI -png_get_io_state (png_const_structrp png_ptr) +png_get_io_state(png_const_structrp png_ptr) { return png_ptr->io_state; } png_uint_32 PNGAPI -png_get_io_chunk_type (png_const_structrp png_ptr) +png_get_io_chunk_type(png_const_structrp png_ptr) { return png_ptr->chunk_name; } @@ -1246,166 +1246,4 @@ png_get_palette_max(png_const_structp png_ptr, png_const_infop info_ptr) # endif #endif -#ifdef PNG_APNG_SUPPORTED -png_uint_32 PNGAPI -png_get_acTL(png_structp png_ptr, png_infop info_ptr, - png_uint_32 *num_frames, png_uint_32 *num_plays) -{ - png_debug1(1, "in %s retrieval function", "acTL"); - - if (png_ptr != NULL && info_ptr != NULL && - (info_ptr->valid & PNG_INFO_acTL) && - num_frames != NULL && num_plays != NULL) - { - *num_frames = info_ptr->num_frames; - *num_plays = info_ptr->num_plays; - return (1); - } - - return (0); -} - -png_uint_32 PNGAPI -png_get_num_frames(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_num_frames()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->num_frames); - return (0); -} - -png_uint_32 PNGAPI -png_get_num_plays(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_num_plays()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->num_plays); - return (0); -} - -png_uint_32 PNGAPI -png_get_next_frame_fcTL(png_structp png_ptr, png_infop info_ptr, - png_uint_32 *width, png_uint_32 *height, - png_uint_32 *x_offset, png_uint_32 *y_offset, - png_uint_16 *delay_num, png_uint_16 *delay_den, - png_byte *dispose_op, png_byte *blend_op) -{ - png_debug1(1, "in %s retrieval function", "fcTL"); - - if (png_ptr != NULL && info_ptr != NULL && - (info_ptr->valid & PNG_INFO_fcTL) && - width != NULL && height != NULL && - x_offset != NULL && y_offset != NULL && - delay_num != NULL && delay_den != NULL && - dispose_op != NULL && blend_op != NULL) - { - *width = info_ptr->next_frame_width; - *height = info_ptr->next_frame_height; - *x_offset = info_ptr->next_frame_x_offset; - *y_offset = info_ptr->next_frame_y_offset; - *delay_num = info_ptr->next_frame_delay_num; - *delay_den = info_ptr->next_frame_delay_den; - *dispose_op = info_ptr->next_frame_dispose_op; - *blend_op = info_ptr->next_frame_blend_op; - return (1); - } - - return (0); -} - -png_uint_32 PNGAPI -png_get_next_frame_width(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_width()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_width); - return (0); -} - -png_uint_32 PNGAPI -png_get_next_frame_height(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_height()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_height); - return (0); -} - -png_uint_32 PNGAPI -png_get_next_frame_x_offset(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_x_offset()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_x_offset); - return (0); -} - -png_uint_32 PNGAPI -png_get_next_frame_y_offset(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_y_offset()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_y_offset); - return (0); -} - -png_uint_16 PNGAPI -png_get_next_frame_delay_num(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_delay_num()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_delay_num); - return (0); -} - -png_uint_16 PNGAPI -png_get_next_frame_delay_den(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_delay_den()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_delay_den); - return (0); -} - -png_byte PNGAPI -png_get_next_frame_dispose_op(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_dispose_op()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_dispose_op); - return (0); -} - -png_byte PNGAPI -png_get_next_frame_blend_op(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_get_next_frame_blend_op()"); - - if (png_ptr != NULL && info_ptr != NULL) - return (info_ptr->next_frame_blend_op); - return (0); -} - -png_byte PNGAPI -png_get_first_frame_is_hidden(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_first_frame_is_hidden()"); - - if (png_ptr != NULL) - return (png_byte)(png_ptr->apng_flags & PNG_FIRST_FRAME_HIDDEN); - - PNG_UNUSED(info_ptr) - - return 0; -} -#endif /* PNG_APNG_SUPPORTED */ #endif /* READ || WRITE */ diff --git a/thirdparty/libpng/pnginfo.h b/thirdparty/libpng/pnginfo.h index ac7b269132..1f98dedc42 100644 --- a/thirdparty/libpng/pnginfo.h +++ b/thirdparty/libpng/pnginfo.h @@ -263,18 +263,5 @@ defined(PNG_READ_BACKGROUND_SUPPORTED) png_bytepp row_pointers; /* the image bits */ #endif -#ifdef PNG_APNG_SUPPORTED - png_uint_32 num_frames; /* including default image */ - png_uint_32 num_plays; - png_uint_32 next_frame_width; - png_uint_32 next_frame_height; - png_uint_32 next_frame_x_offset; - png_uint_32 next_frame_y_offset; - png_uint_16 next_frame_delay_num; - png_uint_16 next_frame_delay_den; - png_byte next_frame_dispose_op; - png_byte next_frame_blend_op; -#endif - }; #endif /* PNGINFO_H */ diff --git a/thirdparty/libpng/pnglibconf.h b/thirdparty/libpng/pnglibconf.h index e1e27e957e..89d5b4c8ad 100644 --- a/thirdparty/libpng/pnglibconf.h +++ b/thirdparty/libpng/pnglibconf.h @@ -1,8 +1,8 @@ /* pnglibconf.h - library build configuration */ -/* libpng version 1.6.37 */ +/* libpng version 1.6.38 */ -/* Copyright (c) 2018-2019 Cosmin Truta */ +/* Copyright (c) 2018-2022 Cosmin Truta */ /* Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson */ /* This code is released under the libpng license. */ diff --git a/thirdparty/libpng/pngpread.c b/thirdparty/libpng/pngpread.c index 2eaeca08f7..e283627b77 100644 --- a/thirdparty/libpng/pngpread.c +++ b/thirdparty/libpng/pngpread.c @@ -195,106 +195,6 @@ png_push_read_chunk(png_structrp png_ptr, png_inforp info_ptr) chunk_name = png_ptr->chunk_name; -#ifdef PNG_READ_APNG_SUPPORTED - if (png_ptr->num_frames_read > 0 && - png_ptr->num_frames_read < info_ptr->num_frames) - { - if (chunk_name == png_IDAT) - { - /* Discard trailing IDATs for the first frame */ - if (png_ptr->mode & PNG_HAVE_fcTL || png_ptr->num_frames_read > 1) - png_error(png_ptr, "out of place IDAT"); - - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - - png_ptr->mode &= ~PNG_HAVE_CHUNK_HEADER; - return; - } - else if (chunk_name == png_fdAT) - { - if (png_ptr->buffer_size < 4) - { - png_push_save_buffer(png_ptr); - return; - } - - png_ensure_sequence_number(png_ptr, 4); - - if (!(png_ptr->mode & PNG_HAVE_fcTL)) - { - /* Discard trailing fdATs for frames other than the first */ - if (png_ptr->num_frames_read < 2) - png_error(png_ptr, "out of place fdAT"); - - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - - png_ptr->mode &= ~PNG_HAVE_CHUNK_HEADER; - return; - } - - else - { - /* frame data follows */ - png_ptr->idat_size = png_ptr->push_length - 4; - png_ptr->mode |= PNG_HAVE_IDAT; - png_ptr->process_mode = PNG_READ_IDAT_MODE; - - return; - } - } - - else if (chunk_name == png_fcTL) - { - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - - png_read_reset(png_ptr); - png_ptr->mode &= ~PNG_HAVE_fcTL; - - png_handle_fcTL(png_ptr, info_ptr, png_ptr->push_length); - - if (!(png_ptr->mode & PNG_HAVE_fcTL)) - png_error(png_ptr, "missing required fcTL chunk"); - - png_read_reinit(png_ptr, info_ptr); - png_progressive_read_reset(png_ptr); - - if (png_ptr->frame_info_fn != NULL) - (*(png_ptr->frame_info_fn))(png_ptr, png_ptr->num_frames_read); - - png_ptr->mode &= ~PNG_HAVE_CHUNK_HEADER; - - return; - } - - else - { - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - png_warning(png_ptr, "Skipped (ignored) a chunk " - "between APNG chunks"); - png_ptr->mode &= ~PNG_HAVE_CHUNK_HEADER; - return; - } - - return; - } -#endif /* PNG_READ_APNG_SUPPORTED */ - if (chunk_name == png_IDAT) { if ((png_ptr->mode & PNG_AFTER_IDAT) != 0) @@ -361,9 +261,6 @@ png_push_read_chunk(png_structrp png_ptr, png_inforp info_ptr) else if (chunk_name == png_IDAT) { -#ifdef PNG_READ_APNG_SUPPORTED - png_have_info(png_ptr, info_ptr); -#endif png_ptr->idat_size = png_ptr->push_length; png_ptr->process_mode = PNG_READ_IDAT_MODE; png_push_have_info(png_ptr, info_ptr); @@ -509,30 +406,6 @@ png_push_read_chunk(png_structrp png_ptr, png_inforp info_ptr) png_handle_iTXt(png_ptr, info_ptr, png_ptr->push_length); } #endif -#ifdef PNG_READ_APNG_SUPPORTED - else if (chunk_name == png_acTL) - { - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - - png_handle_acTL(png_ptr, info_ptr, png_ptr->push_length); - } - - else if (chunk_name == png_fcTL) - { - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - - png_handle_fcTL(png_ptr, info_ptr, png_ptr->push_length); - } - -#endif /* PNG_READ_APNG_SUPPORTED */ else { @@ -666,11 +539,7 @@ png_push_read_IDAT(png_structrp png_ptr) png_byte chunk_tag[4]; /* TODO: this code can be commoned up with the same code in push_read */ -#ifdef PNG_READ_APNG_SUPPORTED - PNG_PUSH_SAVE_BUFFER_IF_LT(12) -#else PNG_PUSH_SAVE_BUFFER_IF_LT(8) -#endif png_push_fill_buffer(png_ptr, chunk_length, 4); png_ptr->push_length = png_get_uint_31(png_ptr, chunk_length); png_reset_crc(png_ptr); @@ -678,64 +547,17 @@ png_push_read_IDAT(png_structrp png_ptr) png_ptr->chunk_name = PNG_CHUNK_FROM_STRING(chunk_tag); png_ptr->mode |= PNG_HAVE_CHUNK_HEADER; -#ifdef PNG_READ_APNG_SUPPORTED - if (png_ptr->chunk_name != png_fdAT && png_ptr->num_frames_read > 0) - { - if (png_ptr->flags & PNG_FLAG_ZSTREAM_ENDED) - { - png_ptr->process_mode = PNG_READ_CHUNK_MODE; - if (png_ptr->frame_end_fn != NULL) - (*(png_ptr->frame_end_fn))(png_ptr, png_ptr->num_frames_read); - png_ptr->num_frames_read++; - return; - } - else - { - if (png_ptr->chunk_name == png_IEND) - png_error(png_ptr, "Not enough image data"); - if (png_ptr->push_length + 4 > png_ptr->buffer_size) - { - png_push_save_buffer(png_ptr); - return; - } - png_warning(png_ptr, "Skipping (ignoring) a chunk between " - "APNG chunks"); - png_crc_finish(png_ptr, png_ptr->push_length); - png_ptr->mode &= ~PNG_HAVE_CHUNK_HEADER; - return; - } - } - else -#endif -#ifdef PNG_READ_APNG_SUPPORTED - if (png_ptr->chunk_name != png_IDAT && png_ptr->num_frames_read == 0) -#else if (png_ptr->chunk_name != png_IDAT) -#endif { png_ptr->process_mode = PNG_READ_CHUNK_MODE; if ((png_ptr->flags & PNG_FLAG_ZSTREAM_ENDED) == 0) png_error(png_ptr, "Not enough compressed data"); -#ifdef PNG_READ_APNG_SUPPORTED - if (png_ptr->frame_end_fn != NULL) - (*(png_ptr->frame_end_fn))(png_ptr, png_ptr->num_frames_read); - png_ptr->num_frames_read++; -#endif - return; } png_ptr->idat_size = png_ptr->push_length; - -#ifdef PNG_READ_APNG_SUPPORTED - if (png_ptr->num_frames_read > 0) - { - png_ensure_sequence_number(png_ptr, 4); - png_ptr->idat_size -= 4; - } -#endif } if (png_ptr->idat_size != 0 && png_ptr->save_buffer_size != 0) @@ -809,15 +631,6 @@ png_process_IDAT_data(png_structrp png_ptr, png_bytep buffer, if (!(buffer_length > 0) || buffer == NULL) png_error(png_ptr, "No IDAT data (internal error)"); -#ifdef PNG_READ_APNG_SUPPORTED - /* If the app is not APNG-aware, decode only the first frame */ - if (!(png_ptr->apng_flags & PNG_APNG_APP) && png_ptr->num_frames_read > 0) - { - png_ptr->flags |= PNG_FLAG_ZSTREAM_ENDED; - return; - } -#endif - /* This routine must process all the data it has been given * before returning, calling the row callback as required to * handle the uncompressed results. @@ -1272,18 +1085,6 @@ png_set_progressive_read_fn(png_structrp png_ptr, png_voidp progressive_ptr, png_set_read_fn(png_ptr, progressive_ptr, png_push_fill_buffer); } -#ifdef PNG_READ_APNG_SUPPORTED -void PNGAPI -png_set_progressive_frame_fn(png_structp png_ptr, - png_progressive_frame_ptr frame_info_fn, - png_progressive_frame_ptr frame_end_fn) -{ - png_ptr->frame_info_fn = frame_info_fn; - png_ptr->frame_end_fn = frame_end_fn; - png_ptr->apng_flags |= PNG_APNG_APP; -} -#endif - png_voidp PNGAPI png_get_progressive_ptr(png_const_structrp png_ptr) { diff --git a/thirdparty/libpng/pngpriv.h b/thirdparty/libpng/pngpriv.h index 57e1bf989b..2e426cf47d 100644 --- a/thirdparty/libpng/pngpriv.h +++ b/thirdparty/libpng/pngpriv.h @@ -1,7 +1,7 @@ /* pngpriv.h - private declarations for use inside libpng * - * Copyright (c) 2018-2019 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -174,7 +174,7 @@ # else /* !defined __ARM_NEON__ */ /* The 'intrinsics' code simply won't compile without this -mfpu=neon: */ -# if !defined(__aarch64__) +# if !defined(__aarch64__) && !defined(_M_ARM64) /* The assembler code currently does not work on ARM64 */ # define PNG_ARM_NEON_IMPLEMENTATION 2 # endif /* __aarch64__ */ @@ -185,6 +185,8 @@ /* Use the intrinsics code by default. */ # define PNG_ARM_NEON_IMPLEMENTATION 1 # endif +#else /* PNG_ARM_NEON_OPT == 0 */ +# define PNG_ARM_NEON_IMPLEMENTATION 0 #endif /* PNG_ARM_NEON_OPT > 0 */ #ifndef PNG_MIPS_MSA_OPT @@ -263,11 +265,15 @@ # ifndef PNG_MIPS_MSA_IMPLEMENTATION # define PNG_MIPS_MSA_IMPLEMENTATION 1 # endif +#else +# define PNG_MIPS_MSA_IMPLEMENTATION 0 #endif /* PNG_MIPS_MSA_OPT > 0 */ #if PNG_POWERPC_VSX_OPT > 0 # define PNG_FILTER_OPTIMIZATIONS png_init_filter_functions_vsx # define PNG_POWERPC_VSX_IMPLEMENTATION 1 +#else +# define PNG_POWERPC_VSX_IMPLEMENTATION 0 #endif @@ -492,16 +498,7 @@ static_cast<type>(static_cast<const void*>(value)) #else # define png_voidcast(type, value) (value) -# ifdef _WIN64 -# ifdef __GNUC__ - typedef unsigned long long png_ptruint; -# else - typedef unsigned __int64 png_ptruint; -# endif -# else - typedef unsigned long png_ptruint; -# endif -# define png_constcast(type, value) ((type)(png_ptruint)(const void*)(value)) +# define png_constcast(type, value) ((type)(void*)(const void*)(value)) # define png_aligncast(type, value) ((void*)(value)) # define png_aligncastconst(type, value) ((const void*)(value)) #endif /* __cplusplus */ @@ -543,9 +540,8 @@ # include <alloc.h> #endif -#if defined(WIN32) || defined(_Windows) || defined(_WINDOWS) || \ - defined(_WIN32) || defined(__WIN32__) -# include <windows.h> /* defines _WINDOWS_ macro */ +#if defined(_WIN32) || defined(__WIN32__) || defined(__NT__) +# include <windows.h> #endif #endif /* PNG_VERSION_INFO_ONLY */ @@ -554,24 +550,20 @@ * functions that are passed far data must be model-independent. */ -/* Memory model/platform independent fns */ +/* Platform-independent functions */ #ifndef PNG_ABORT -# ifdef _WINDOWS_ -# define PNG_ABORT() ExitProcess(0) -# else -# define PNG_ABORT() abort() -# endif +# define PNG_ABORT() abort() #endif /* These macros may need to be architecture dependent. */ -#define PNG_ALIGN_NONE 0 /* do not use data alignment */ -#define PNG_ALIGN_ALWAYS 1 /* assume unaligned accesses are OK */ +#define PNG_ALIGN_NONE 0 /* do not use data alignment */ +#define PNG_ALIGN_ALWAYS 1 /* assume unaligned accesses are OK */ #ifdef offsetof -# define PNG_ALIGN_OFFSET 2 /* use offsetof to determine alignment */ +# define PNG_ALIGN_OFFSET 2 /* use offsetof to determine alignment */ #else # define PNG_ALIGN_OFFSET -1 /* prevent the use of this */ #endif -#define PNG_ALIGN_SIZE 3 /* use sizeof to determine alignment */ +#define PNG_ALIGN_SIZE 3 /* use sizeof to determine alignment */ #ifndef PNG_ALIGN_TYPE /* Default to using aligned access optimizations and requiring alignment to a @@ -585,26 +577,25 @@ /* This is used because in some compiler implementations non-aligned * structure members are supported, so the offsetof approach below fails. * Set PNG_ALIGN_SIZE=0 for compiler combinations where unaligned access - * is good for performance. Do not do this unless you have tested the result - * and understand it. + * is good for performance. Do not do this unless you have tested the + * result and understand it. */ -# define png_alignof(type) (sizeof (type)) +# define png_alignof(type) (sizeof(type)) #else # if PNG_ALIGN_TYPE == PNG_ALIGN_OFFSET -# define png_alignof(type) offsetof(struct{char c; type t;}, t) +# define png_alignof(type) offsetof(struct{char c; type t;}, t) # else -# if PNG_ALIGN_TYPE == PNG_ALIGN_ALWAYS -# define png_alignof(type) (1) -# endif - /* Else leave png_alignof undefined to prevent use thereof */ +# if PNG_ALIGN_TYPE == PNG_ALIGN_ALWAYS +# define png_alignof(type) 1 +# endif + /* Else leave png_alignof undefined to prevent use thereof */ # endif #endif -/* This implicitly assumes alignment is always to a power of 2. */ +/* This implicitly assumes alignment is always a multiple of 2. */ #ifdef png_alignof -# define png_isaligned(ptr, type)\ - (((type)((const char*)ptr-(const char*)0) & \ - (type)(png_alignof(type)-1)) == 0) +# define png_isaligned(ptr, type) \ + (((type)(size_t)((const void*)(ptr)) & (type)(png_alignof(type)-1)) == 0) #else # define png_isaligned(ptr, type) 0 #endif @@ -637,10 +628,6 @@ #define PNG_HAVE_CHUNK_AFTER_IDAT 0x2000U /* Have another chunk after IDAT */ /* 0x4000U (unused) */ #define PNG_IS_READ_STRUCT 0x8000U /* Else is a write struct */ -#ifdef PNG_APNG_SUPPORTED -#define PNG_HAVE_acTL 0x10000U -#define PNG_HAVE_fcTL 0x20000U -#endif /* Flags for the transformations the PNG library does on the image data */ #define PNG_BGR 0x0001U @@ -877,16 +864,6 @@ #define png_tRNS PNG_U32(116, 82, 78, 83) #define png_zTXt PNG_U32(122, 84, 88, 116) -#ifdef PNG_APNG_SUPPORTED -#define png_acTL PNG_U32( 97, 99, 84, 76) -#define png_fcTL PNG_U32(102, 99, 84, 76) -#define png_fdAT PNG_U32(102, 100, 65, 84) - -/* For png_struct.apng_flags: */ -#define PNG_FIRST_FRAME_HIDDEN 0x0001U -#define PNG_APNG_APP 0x0002U -#endif - /* The following will work on (signed char*) strings, whereas the get_uint_32 * macro will fail on top-bit-set values because of the sign extension. */ @@ -1658,47 +1635,6 @@ PNG_INTERNAL_FUNCTION(void,png_colorspace_sync,(png_const_structrp png_ptr, */ #endif -#ifdef PNG_APNG_SUPPORTED -PNG_INTERNAL_FUNCTION(void,png_ensure_fcTL_is_valid,(png_structp png_ptr, - png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, - png_byte dispose_op, png_byte blend_op), PNG_EMPTY); - -#ifdef PNG_READ_APNG_SUPPORTED -PNG_INTERNAL_FUNCTION(void,png_handle_acTL,(png_structp png_ptr, png_infop info_ptr, - png_uint_32 length),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_handle_fcTL,(png_structp png_ptr, png_infop info_ptr, - png_uint_32 length),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_handle_fdAT,(png_structp png_ptr, png_infop info_ptr, - png_uint_32 length),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_have_info,(png_structp png_ptr, png_infop info_ptr),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_ensure_sequence_number,(png_structp png_ptr, - png_uint_32 length),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_read_reset,(png_structp png_ptr),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_read_reinit,(png_structp png_ptr, - png_infop info_ptr),PNG_EMPTY); -#ifdef PNG_PROGRESSIVE_READ_SUPPORTED -PNG_INTERNAL_FUNCTION(void,png_progressive_read_reset,(png_structp png_ptr),PNG_EMPTY); -#endif /* PNG_PROGRESSIVE_READ_SUPPORTED */ -#endif /* PNG_READ_APNG_SUPPORTED */ - -#ifdef PNG_WRITE_APNG_SUPPORTED -PNG_INTERNAL_FUNCTION(void,png_write_acTL,(png_structp png_ptr, - png_uint_32 num_frames, png_uint_32 num_plays),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_write_fcTL,(png_structp png_ptr, - png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, - png_byte dispose_op, png_byte blend_op),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_write_fdAT,(png_structp png_ptr, - png_const_bytep data, png_size_t length),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_write_reset,(png_structp png_ptr),PNG_EMPTY); -PNG_INTERNAL_FUNCTION(void,png_write_reinit,(png_structp png_ptr, - png_infop info_ptr, png_uint_32 width, png_uint_32 height),PNG_EMPTY); -#endif /* PNG_WRITE_APNG_SUPPORTED */ -#endif /* PNG_APNG_SUPPORTED */ - /* Added at libpng version 1.4.0 */ #ifdef PNG_COLORSPACE_SUPPORTED /* These internal functions are for maintaining the colorspace structure within diff --git a/thirdparty/libpng/pngread.c b/thirdparty/libpng/pngread.c index fa44d5a8e4..5ab9224038 100644 --- a/thirdparty/libpng/pngread.c +++ b/thirdparty/libpng/pngread.c @@ -161,9 +161,6 @@ png_read_info(png_structrp png_ptr, png_inforp info_ptr) else if (chunk_name == png_IDAT) { -#ifdef PNG_READ_APNG_SUPPORTED - png_have_info(png_ptr, info_ptr); -#endif png_ptr->idat_size = length; break; } @@ -258,17 +255,6 @@ png_read_info(png_structrp png_ptr, png_inforp info_ptr) png_handle_iTXt(png_ptr, info_ptr, length); #endif -#ifdef PNG_READ_APNG_SUPPORTED - else if (chunk_name == png_acTL) - png_handle_acTL(png_ptr, info_ptr, length); - - else if (chunk_name == png_fcTL) - png_handle_fcTL(png_ptr, info_ptr, length); - - else if (chunk_name == png_fdAT) - png_handle_fdAT(png_ptr, info_ptr, length); -#endif - else png_handle_unknown(png_ptr, info_ptr, length, PNG_HANDLE_CHUNK_AS_DEFAULT); @@ -276,72 +262,6 @@ png_read_info(png_structrp png_ptr, png_inforp info_ptr) } #endif /* SEQUENTIAL_READ */ -#ifdef PNG_READ_APNG_SUPPORTED -void PNGAPI -png_read_frame_head(png_structp png_ptr, png_infop info_ptr) -{ - png_byte have_chunk_after_DAT; /* after IDAT or after fdAT */ - - png_debug(0, "Reading frame head"); - - if (!(png_ptr->mode & PNG_HAVE_acTL)) - png_error(png_ptr, "attempt to png_read_frame_head() but " - "no acTL present"); - - /* do nothing for the main IDAT */ - if (png_ptr->num_frames_read == 0) - return; - - png_read_reset(png_ptr); - png_ptr->flags &= ~PNG_FLAG_ROW_INIT; - png_ptr->mode &= ~PNG_HAVE_fcTL; - - have_chunk_after_DAT = 0; - for (;;) - { - png_uint_32 length = png_read_chunk_header(png_ptr); - - if (png_ptr->chunk_name == png_IDAT) - { - /* discard trailing IDATs for the first frame */ - if (have_chunk_after_DAT || png_ptr->num_frames_read > 1) - png_error(png_ptr, "png_read_frame_head(): out of place IDAT"); - png_crc_finish(png_ptr, length); - } - - else if (png_ptr->chunk_name == png_fcTL) - { - png_handle_fcTL(png_ptr, info_ptr, length); - have_chunk_after_DAT = 1; - } - - else if (png_ptr->chunk_name == png_fdAT) - { - png_ensure_sequence_number(png_ptr, length); - - /* discard trailing fdATs for frames other than the first */ - if (!have_chunk_after_DAT && png_ptr->num_frames_read > 1) - png_crc_finish(png_ptr, length - 4); - else if(png_ptr->mode & PNG_HAVE_fcTL) - { - png_ptr->idat_size = length - 4; - png_ptr->mode |= PNG_HAVE_IDAT; - - break; - } - else - png_error(png_ptr, "png_read_frame_head(): out of place fdAT"); - } - else - { - png_warning(png_ptr, "Skipped (ignored) a chunk " - "between APNG chunks"); - png_crc_finish(png_ptr, length); - } - } -} -#endif /* PNG_READ_APNG_SUPPORTED */ - /* Optional call to update the users info_ptr structure */ void PNGAPI png_read_update_info(png_structrp png_ptr, png_inforp info_ptr) @@ -3532,7 +3452,6 @@ png_image_read_background(png_voidp argument) for (pass = 0; pass < passes; ++pass) { - png_bytep row = png_voidcast(png_bytep, display->first_row); unsigned int startx, stepx, stepy; png_uint_32 y; @@ -3637,8 +3556,6 @@ png_image_read_background(png_voidp argument) inrow += 2; /* gray and alpha channel */ } - - row += display->row_bytes; } } } diff --git a/thirdparty/libpng/pngrtran.c b/thirdparty/libpng/pngrtran.c index 9a8fad9f4a..238f5afe7e 100644 --- a/thirdparty/libpng/pngrtran.c +++ b/thirdparty/libpng/pngrtran.c @@ -21,7 +21,7 @@ #ifdef PNG_ARM_NEON_IMPLEMENTATION # if PNG_ARM_NEON_IMPLEMENTATION == 1 # define PNG_ARM_NEON_INTRINSICS_AVAILABLE -# if defined(_MSC_VER) && defined(_M_ARM64) +# if defined(_MSC_VER) && !defined(__clang__) && defined(_M_ARM64) # include <arm64_neon.h> # else # include <arm_neon.h> diff --git a/thirdparty/libpng/pngrutil.c b/thirdparty/libpng/pngrutil.c index ae66a48a83..ca060dd15f 100644 --- a/thirdparty/libpng/pngrutil.c +++ b/thirdparty/libpng/pngrutil.c @@ -1,7 +1,7 @@ /* pngrutil.c - utilities to read a PNG file * - * Copyright (c) 2018 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -302,7 +302,6 @@ png_read_buffer(png_structrp png_ptr, png_alloc_size_t new_size, int warn) if (buffer != NULL && new_size > png_ptr->read_buffer_size) { png_ptr->read_buffer = NULL; - png_ptr->read_buffer = NULL; png_ptr->read_buffer_size = 0; png_free(png_ptr, buffer); buffer = NULL; @@ -865,11 +864,6 @@ png_handle_IHDR(png_structrp png_ptr, png_inforp info_ptr, png_uint_32 length) filter_type = buf[11]; interlace_type = buf[12]; -#ifdef PNG_READ_APNG_SUPPORTED - png_ptr->first_frame_width = width; - png_ptr->first_frame_height = height; -#endif - /* Set internal variables */ png_ptr->width = width; png_ptr->height = height; @@ -2081,21 +2075,22 @@ png_handle_eXIf(png_structrp png_ptr, png_inforp info_ptr, png_uint_32 length) png_byte buf[1]; png_crc_read(png_ptr, buf, 1); info_ptr->eXIf_buf[i] = buf[0]; - if (i == 1 && buf[0] != 'M' && buf[0] != 'I' - && info_ptr->eXIf_buf[0] != buf[0]) + if (i == 1) { - png_crc_finish(png_ptr, length); - png_chunk_benign_error(png_ptr, "incorrect byte-order specifier"); - png_free(png_ptr, info_ptr->eXIf_buf); - info_ptr->eXIf_buf = NULL; - return; + if ((buf[0] != 'M' && buf[0] != 'I') || + (info_ptr->eXIf_buf[0] != buf[0])) + { + png_crc_finish(png_ptr, length - 2); + png_chunk_benign_error(png_ptr, "incorrect byte-order specifier"); + png_free(png_ptr, info_ptr->eXIf_buf); + info_ptr->eXIf_buf = NULL; + return; + } } } - if (png_crc_finish(png_ptr, 0) != 0) - return; - - png_set_eXIf_1(png_ptr, info_ptr, length, info_ptr->eXIf_buf); + if (png_crc_finish(png_ptr, 0) == 0) + png_set_eXIf_1(png_ptr, info_ptr, length, info_ptr->eXIf_buf); png_free(png_ptr, info_ptr->eXIf_buf); info_ptr->eXIf_buf = NULL; @@ -2131,8 +2126,9 @@ png_handle_hIST(png_structrp png_ptr, png_inforp info_ptr, png_uint_32 length) num = length / 2 ; - if (num != (unsigned int) png_ptr->num_palette || - num > (unsigned int) PNG_MAX_PALETTE_LENGTH) + if (length != num * 2 || + num != (unsigned int)png_ptr->num_palette || + num > (unsigned int)PNG_MAX_PALETTE_LENGTH) { png_crc_finish(png_ptr, length); png_chunk_benign_error(png_ptr, "invalid"); @@ -2862,179 +2858,6 @@ png_handle_iTXt(png_structrp png_ptr, png_inforp info_ptr, png_uint_32 length) } #endif -#ifdef PNG_READ_APNG_SUPPORTED -void /* PRIVATE */ -png_handle_acTL(png_structp png_ptr, png_infop info_ptr, png_uint_32 length) -{ - png_byte data[8]; - png_uint_32 num_frames; - png_uint_32 num_plays; - png_uint_32 didSet; - - png_debug(1, "in png_handle_acTL"); - - if (!(png_ptr->mode & PNG_HAVE_IHDR)) - { - png_error(png_ptr, "Missing IHDR before acTL"); - } - else if (png_ptr->mode & PNG_HAVE_IDAT) - { - png_warning(png_ptr, "Invalid acTL after IDAT skipped"); - png_crc_finish(png_ptr, length); - return; - } - else if (png_ptr->mode & PNG_HAVE_acTL) - { - png_warning(png_ptr, "Duplicate acTL skipped"); - png_crc_finish(png_ptr, length); - return; - } - else if (length != 8) - { - png_warning(png_ptr, "acTL with invalid length skipped"); - png_crc_finish(png_ptr, length); - return; - } - - png_crc_read(png_ptr, data, 8); - png_crc_finish(png_ptr, 0); - - num_frames = png_get_uint_31(png_ptr, data); - num_plays = png_get_uint_31(png_ptr, data + 4); - - /* the set function will do error checking on num_frames */ - didSet = png_set_acTL(png_ptr, info_ptr, num_frames, num_plays); - if(didSet) - png_ptr->mode |= PNG_HAVE_acTL; -} - -void /* PRIVATE */ -png_handle_fcTL(png_structp png_ptr, png_infop info_ptr, png_uint_32 length) -{ - png_byte data[22]; - png_uint_32 width; - png_uint_32 height; - png_uint_32 x_offset; - png_uint_32 y_offset; - png_uint_16 delay_num; - png_uint_16 delay_den; - png_byte dispose_op; - png_byte blend_op; - - png_debug(1, "in png_handle_fcTL"); - - png_ensure_sequence_number(png_ptr, length); - - if (!(png_ptr->mode & PNG_HAVE_IHDR)) - { - png_error(png_ptr, "Missing IHDR before fcTL"); - } - else if (png_ptr->mode & PNG_HAVE_IDAT) - { - /* for any frames other then the first this message may be misleading, - * but correct. PNG_HAVE_IDAT is unset before the frame head is read - * i can't think of a better message */ - png_warning(png_ptr, "Invalid fcTL after IDAT skipped"); - png_crc_finish(png_ptr, length-4); - return; - } - else if (png_ptr->mode & PNG_HAVE_fcTL) - { - png_warning(png_ptr, "Duplicate fcTL within one frame skipped"); - png_crc_finish(png_ptr, length-4); - return; - } - else if (length != 26) - { - png_warning(png_ptr, "fcTL with invalid length skipped"); - png_crc_finish(png_ptr, length-4); - return; - } - - png_crc_read(png_ptr, data, 22); - png_crc_finish(png_ptr, 0); - - width = png_get_uint_31(png_ptr, data); - height = png_get_uint_31(png_ptr, data + 4); - x_offset = png_get_uint_31(png_ptr, data + 8); - y_offset = png_get_uint_31(png_ptr, data + 12); - delay_num = png_get_uint_16(data + 16); - delay_den = png_get_uint_16(data + 18); - dispose_op = data[20]; - blend_op = data[21]; - - if (png_ptr->num_frames_read == 0 && (x_offset != 0 || y_offset != 0)) - { - png_warning(png_ptr, "fcTL for the first frame must have zero offset"); - return; - } - - if (info_ptr != NULL) - { - if (png_ptr->num_frames_read == 0 && - (width != info_ptr->width || height != info_ptr->height)) - { - png_warning(png_ptr, "size in first frame's fcTL must match " - "the size in IHDR"); - return; - } - - /* The set function will do more error checking */ - png_set_next_frame_fcTL(png_ptr, info_ptr, width, height, - x_offset, y_offset, delay_num, delay_den, - dispose_op, blend_op); - - png_read_reinit(png_ptr, info_ptr); - - png_ptr->mode |= PNG_HAVE_fcTL; - } -} - -void /* PRIVATE */ -png_have_info(png_structp png_ptr, png_infop info_ptr) -{ - if((info_ptr->valid & PNG_INFO_acTL) && !(info_ptr->valid & PNG_INFO_fcTL)) - { - png_ptr->apng_flags |= PNG_FIRST_FRAME_HIDDEN; - info_ptr->num_frames++; - } -} - -void /* PRIVATE */ -png_handle_fdAT(png_structp png_ptr, png_infop info_ptr, png_uint_32 length) -{ - png_ensure_sequence_number(png_ptr, length); - - /* This function is only called from png_read_end(), png_read_info(), - * and png_push_read_chunk() which means that: - * - the user doesn't want to read this frame - * - or this is an out-of-place fdAT - * in either case it is safe to ignore the chunk with a warning */ - png_warning(png_ptr, "ignoring fdAT chunk"); - png_crc_finish(png_ptr, length - 4); - PNG_UNUSED(info_ptr) -} - -void /* PRIVATE */ -png_ensure_sequence_number(png_structp png_ptr, png_uint_32 length) -{ - png_byte data[4]; - png_uint_32 sequence_number; - - if (length < 4) - png_error(png_ptr, "invalid fcTL or fdAT chunk found"); - - png_crc_read(png_ptr, data, 4); - sequence_number = png_get_uint_31(png_ptr, data); - - if (sequence_number != png_ptr->next_seq_num) - png_error(png_ptr, "fcTL or fdAT chunk with out-of-order sequence " - "number found"); - - png_ptr->next_seq_num++; -} -#endif /* PNG_READ_APNG_SUPPORTED */ - #ifdef PNG_READ_UNKNOWN_CHUNKS_SUPPORTED /* Utility function for png_handle_unknown; set up png_ptr::unknown_chunk */ static int @@ -4343,38 +4166,7 @@ png_read_IDAT_data(png_structrp png_ptr, png_bytep output, { uInt avail_in; png_bytep buffer; -#ifdef PNG_READ_APNG_SUPPORTED - png_uint_32 bytes_to_skip = 0; - - while (png_ptr->idat_size == 0 || bytes_to_skip != 0) - { - png_crc_finish(png_ptr, bytes_to_skip); - bytes_to_skip = 0; - - png_ptr->idat_size = png_read_chunk_header(png_ptr); - if (png_ptr->num_frames_read == 0) - { - if (png_ptr->chunk_name != png_IDAT) - png_error(png_ptr, "Not enough image data"); - } - else - { - if (png_ptr->chunk_name == png_IEND) - png_error(png_ptr, "Not enough image data"); - if (png_ptr->chunk_name != png_fdAT) - { - png_warning(png_ptr, "Skipped (ignored) a chunk " - "between APNG chunks"); - bytes_to_skip = png_ptr->idat_size; - continue; - } - - png_ensure_sequence_number(png_ptr, png_ptr->idat_size); - png_ptr->idat_size -= 4; - } - } -#else while (png_ptr->idat_size == 0) { png_crc_finish(png_ptr, 0); @@ -4386,7 +4178,7 @@ png_read_IDAT_data(png_structrp png_ptr, png_bytep output, if (png_ptr->chunk_name != png_IDAT) png_error(png_ptr, "Not enough image data"); } -#endif /* PNG_READ_APNG_SUPPORTED */ + avail_in = png_ptr->IDAT_read_size; if (avail_in > png_ptr->idat_size) @@ -4449,9 +4241,6 @@ png_read_IDAT_data(png_structrp png_ptr, png_bytep output, png_ptr->mode |= PNG_AFTER_IDAT; png_ptr->flags |= PNG_FLAG_ZSTREAM_ENDED; -#ifdef PNG_READ_APNG_SUPPORTED - png_ptr->num_frames_read++; -#endif if (png_ptr->zstream.avail_in > 0 || png_ptr->idat_size > 0) png_chunk_benign_error(png_ptr, "Extra compressed data"); @@ -4833,14 +4622,13 @@ defined(PNG_USER_TRANSFORM_PTR_SUPPORTED) */ { png_bytep temp = png_ptr->big_row_buf + 32; - int extra = (int)((temp - (png_bytep)0) & 0x0f); + size_t extra = (size_t)temp & 0x0f; png_ptr->row_buf = temp - extra - 1/*filter byte*/; temp = png_ptr->big_prev_row + 32; - extra = (int)((temp - (png_bytep)0) & 0x0f); + extra = (size_t)temp & 0x0f; png_ptr->prev_row = temp - extra - 1/*filter byte*/; } - #else /* Use 31 bytes of padding before and 17 bytes after row_buf. */ png_ptr->row_buf = png_ptr->big_row_buf + 31; @@ -4890,80 +4678,4 @@ defined(PNG_USER_TRANSFORM_PTR_SUPPORTED) png_ptr->flags |= PNG_FLAG_ROW_INIT; } - -#ifdef PNG_READ_APNG_SUPPORTED -/* This function is to be called after the main IDAT set has been read and - * before a new IDAT is read. It resets some parts of png_ptr - * to make them usable by the read functions again */ -void /* PRIVATE */ -png_read_reset(png_structp png_ptr) -{ - png_ptr->mode &= ~PNG_HAVE_IDAT; - png_ptr->mode &= ~PNG_AFTER_IDAT; - png_ptr->row_number = 0; - png_ptr->pass = 0; -} - -void /* PRIVATE */ -png_read_reinit(png_structp png_ptr, png_infop info_ptr) -{ - png_ptr->width = info_ptr->next_frame_width; - png_ptr->height = info_ptr->next_frame_height; - png_ptr->rowbytes = PNG_ROWBYTES(png_ptr->pixel_depth,png_ptr->width); - png_ptr->info_rowbytes = PNG_ROWBYTES(info_ptr->pixel_depth, - png_ptr->width); - if (png_ptr->prev_row) - memset(png_ptr->prev_row, 0, png_ptr->rowbytes + 1); -} - -#ifdef PNG_PROGRESSIVE_READ_SUPPORTED -/* same as png_read_reset() but for the progressive reader */ -void /* PRIVATE */ -png_progressive_read_reset(png_structp png_ptr) -{ -#ifdef PNG_READ_INTERLACING_SUPPORTED - /* Arrays to facilitate easy interlacing - use pass (0 - 6) as index */ - - /* Start of interlace block */ - const int png_pass_start[] = {0, 4, 0, 2, 0, 1, 0}; - - /* Offset to next interlace block */ - const int png_pass_inc[] = {8, 8, 4, 4, 2, 2, 1}; - - /* Start of interlace block in the y direction */ - const int png_pass_ystart[] = {0, 0, 4, 0, 2, 0, 1}; - - /* Offset to next interlace block in the y direction */ - const int png_pass_yinc[] = {8, 8, 8, 4, 4, 2, 2}; - - if (png_ptr->interlaced) - { - if (!(png_ptr->transformations & PNG_INTERLACE)) - png_ptr->num_rows = (png_ptr->height + png_pass_yinc[0] - 1 - - png_pass_ystart[0]) / png_pass_yinc[0]; - else - png_ptr->num_rows = png_ptr->height; - - png_ptr->iwidth = (png_ptr->width + - png_pass_inc[png_ptr->pass] - 1 - - png_pass_start[png_ptr->pass]) / - png_pass_inc[png_ptr->pass]; - } - else -#endif /* PNG_READ_INTERLACING_SUPPORTED */ - { - png_ptr->num_rows = png_ptr->height; - png_ptr->iwidth = png_ptr->width; - } - png_ptr->flags &= ~PNG_FLAG_ZSTREAM_ENDED; - if (inflateReset(&(png_ptr->zstream)) != Z_OK) - png_error(png_ptr, "inflateReset failed"); - png_ptr->zstream.avail_in = 0; - png_ptr->zstream.next_in = 0; - png_ptr->zstream.next_out = png_ptr->row_buf; - png_ptr->zstream.avail_out = (uInt)PNG_ROWBYTES(png_ptr->pixel_depth, - png_ptr->iwidth) + 1; -} -#endif /* PNG_PROGRESSIVE_READ_SUPPORTED */ -#endif /* PNG_READ_APNG_SUPPORTED */ #endif /* READ */ diff --git a/thirdparty/libpng/pngset.c b/thirdparty/libpng/pngset.c index a281db58ae..8c372cf415 100644 --- a/thirdparty/libpng/pngset.c +++ b/thirdparty/libpng/pngset.c @@ -1,7 +1,7 @@ /* pngset.c - storage of image information into info struct * - * Copyright (c) 2018 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -288,11 +288,6 @@ png_set_IHDR(png_const_structrp png_ptr, png_inforp info_ptr, info_ptr->pixel_depth = (png_byte)(info_ptr->channels * info_ptr->bit_depth); info_ptr->rowbytes = PNG_ROWBYTES(info_ptr->pixel_depth, width); - -#ifdef PNG_APNG_SUPPORTED - /* for non-animated png. this may be overwritten from an acTL chunk later */ - info_ptr->num_frames = 1; -#endif } #ifdef PNG_oFFs_SUPPORTED @@ -1024,6 +1019,9 @@ png_set_tRNS(png_structrp png_ptr, png_inforp info_ptr, info_ptr->trans_alpha = png_voidcast(png_bytep, png_malloc(png_ptr, PNG_MAX_PALETTE_LENGTH)); memcpy(info_ptr->trans_alpha, trans_alpha, (size_t)num_trans); + + info_ptr->valid |= PNG_INFO_tRNS; + info_ptr->free_me |= PNG_FREE_TRNS; } png_ptr->trans_alpha = info_ptr->trans_alpha; } @@ -1163,147 +1161,6 @@ png_set_sPLT(png_const_structrp png_ptr, } #endif /* sPLT */ -#ifdef PNG_APNG_SUPPORTED -png_uint_32 PNGAPI -png_set_acTL(png_structp png_ptr, png_infop info_ptr, - png_uint_32 num_frames, png_uint_32 num_plays) -{ - png_debug1(1, "in %s storage function", "acTL"); - - if (png_ptr == NULL || info_ptr == NULL) - { - png_warning(png_ptr, - "Call to png_set_acTL() with NULL png_ptr " - "or info_ptr ignored"); - return (0); - } - if (num_frames == 0) - { - png_warning(png_ptr, - "Ignoring attempt to set acTL with num_frames zero"); - return (0); - } - if (num_frames > PNG_UINT_31_MAX) - { - png_warning(png_ptr, - "Ignoring attempt to set acTL with num_frames > 2^31-1"); - return (0); - } - if (num_plays > PNG_UINT_31_MAX) - { - png_warning(png_ptr, - "Ignoring attempt to set acTL with num_plays " - "> 2^31-1"); - return (0); - } - - info_ptr->num_frames = num_frames; - info_ptr->num_plays = num_plays; - - info_ptr->valid |= PNG_INFO_acTL; - - return (1); -} - -/* delay_num and delay_den can hold any 16-bit values including zero */ -png_uint_32 PNGAPI -png_set_next_frame_fcTL(png_structp png_ptr, png_infop info_ptr, - png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, - png_byte dispose_op, png_byte blend_op) -{ - png_debug1(1, "in %s storage function", "fcTL"); - - if (png_ptr == NULL || info_ptr == NULL) - { - png_warning(png_ptr, - "Call to png_set_fcTL() with NULL png_ptr or info_ptr " - "ignored"); - return (0); - } - - png_ensure_fcTL_is_valid(png_ptr, width, height, x_offset, y_offset, - delay_num, delay_den, dispose_op, blend_op); - - if (blend_op == PNG_BLEND_OP_OVER) - { - if (!(png_ptr->color_type & PNG_COLOR_MASK_ALPHA) && - !(png_get_valid(png_ptr, info_ptr, PNG_INFO_tRNS))) - { - png_warning(png_ptr, "PNG_BLEND_OP_OVER is meaningless " - "and wasteful for opaque images, ignored"); - blend_op = PNG_BLEND_OP_SOURCE; - } - } - - info_ptr->next_frame_width = width; - info_ptr->next_frame_height = height; - info_ptr->next_frame_x_offset = x_offset; - info_ptr->next_frame_y_offset = y_offset; - info_ptr->next_frame_delay_num = delay_num; - info_ptr->next_frame_delay_den = delay_den; - info_ptr->next_frame_dispose_op = dispose_op; - info_ptr->next_frame_blend_op = blend_op; - - info_ptr->valid |= PNG_INFO_fcTL; - - return (1); -} - -void /* PRIVATE */ -png_ensure_fcTL_is_valid(png_structp png_ptr, - png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, - png_byte dispose_op, png_byte blend_op) -{ - if (width == 0 || width > PNG_UINT_31_MAX) - png_error(png_ptr, "invalid width in fcTL (> 2^31-1)"); - if (height == 0 || height > PNG_UINT_31_MAX) - png_error(png_ptr, "invalid height in fcTL (> 2^31-1)"); - if (x_offset > PNG_UINT_31_MAX) - png_error(png_ptr, "invalid x_offset in fcTL (> 2^31-1)"); - if (y_offset > PNG_UINT_31_MAX) - png_error(png_ptr, "invalid y_offset in fcTL (> 2^31-1)"); - if (width + x_offset > png_ptr->first_frame_width || - height + y_offset > png_ptr->first_frame_height) - png_error(png_ptr, "dimensions of a frame are greater than" - "the ones in IHDR"); - - if (dispose_op != PNG_DISPOSE_OP_NONE && - dispose_op != PNG_DISPOSE_OP_BACKGROUND && - dispose_op != PNG_DISPOSE_OP_PREVIOUS) - png_error(png_ptr, "invalid dispose_op in fcTL"); - - if (blend_op != PNG_BLEND_OP_SOURCE && - blend_op != PNG_BLEND_OP_OVER) - png_error(png_ptr, "invalid blend_op in fcTL"); - - PNG_UNUSED(delay_num) - PNG_UNUSED(delay_den) -} - -png_uint_32 PNGAPI -png_set_first_frame_is_hidden(png_structp png_ptr, png_infop info_ptr, - png_byte is_hidden) -{ - png_debug(1, "in png_first_frame_is_hidden()"); - - if (png_ptr == NULL) - return 0; - - if (is_hidden) - png_ptr->apng_flags |= PNG_FIRST_FRAME_HIDDEN; - else - png_ptr->apng_flags &= ~PNG_FIRST_FRAME_HIDDEN; - - PNG_UNUSED(info_ptr) - - return 1; -} -#endif /* PNG_APNG_SUPPORTED */ - #ifdef PNG_STORE_UNKNOWN_CHUNKS_SUPPORTED static png_byte check_location(png_const_structrp png_ptr, int location) @@ -1472,7 +1329,7 @@ png_set_unknown_chunk_location(png_const_structrp png_ptr, png_inforp info_ptr, #ifdef PNG_MNG_FEATURES_SUPPORTED png_uint_32 PNGAPI -png_permit_mng_features (png_structrp png_ptr, png_uint_32 mng_features) +png_permit_mng_features(png_structrp png_ptr, png_uint_32 mng_features) { png_debug(1, "in png_permit_mng_features"); @@ -1779,7 +1636,7 @@ png_set_invalid(png_const_structrp png_ptr, png_inforp info_ptr, int mask) #ifdef PNG_SET_USER_LIMITS_SUPPORTED /* This function was added to libpng 1.2.6 */ void PNGAPI -png_set_user_limits (png_structrp png_ptr, png_uint_32 user_width_max, +png_set_user_limits(png_structrp png_ptr, png_uint_32 user_width_max, png_uint_32 user_height_max) { /* Images with dimensions larger than these limits will be @@ -1795,7 +1652,7 @@ png_set_user_limits (png_structrp png_ptr, png_uint_32 user_width_max, /* This function was added to libpng 1.4.0 */ void PNGAPI -png_set_chunk_cache_max (png_structrp png_ptr, png_uint_32 user_chunk_cache_max) +png_set_chunk_cache_max(png_structrp png_ptr, png_uint_32 user_chunk_cache_max) { if (png_ptr != NULL) png_ptr->user_chunk_cache_max = user_chunk_cache_max; @@ -1803,7 +1660,7 @@ png_set_chunk_cache_max (png_structrp png_ptr, png_uint_32 user_chunk_cache_max) /* This function was added to libpng 1.4.1 */ void PNGAPI -png_set_chunk_malloc_max (png_structrp png_ptr, +png_set_chunk_malloc_max(png_structrp png_ptr, png_alloc_size_t user_chunk_malloc_max) { if (png_ptr != NULL) diff --git a/thirdparty/libpng/pngstruct.h b/thirdparty/libpng/pngstruct.h index 2a2236f92e..e591d94d58 100644 --- a/thirdparty/libpng/pngstruct.h +++ b/thirdparty/libpng/pngstruct.h @@ -1,7 +1,7 @@ /* pngstruct.h - header file for PNG reference library * - * Copyright (c) 2018-2019 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -334,18 +334,8 @@ struct png_struct_def size_t current_buffer_size; /* amount of data now in current_buffer */ int process_mode; /* what push library is currently doing */ int cur_palette; /* current push library palette index */ - #endif /* PROGRESSIVE_READ */ -#if defined(__TURBOC__) && !defined(_Windows) && !defined(__FLAT__) -/* For the Borland special 64K segment handler */ - png_bytepp offset_table_ptr; - png_bytep offset_table; - png_uint_16 offset_table_number; - png_uint_16 offset_table_count; - png_uint_16 offset_table_count_free; -#endif - #ifdef PNG_READ_QUANTIZE_SUPPORTED png_bytep palette_lookup; /* lookup table for quantizing */ png_bytep quantize_index; /* index translation for palette files */ @@ -409,27 +399,6 @@ struct png_struct_def png_byte filter_type; #endif -#ifdef PNG_APNG_SUPPORTED - png_uint_32 apng_flags; - png_uint_32 next_seq_num; /* next fcTL/fdAT chunk sequence number */ - png_uint_32 first_frame_width; - png_uint_32 first_frame_height; - -#ifdef PNG_READ_APNG_SUPPORTED - png_uint_32 num_frames_read; /* incremented after all image data of */ - /* a frame is read */ -#ifdef PNG_PROGRESSIVE_READ_SUPPORTED - png_progressive_frame_ptr frame_info_fn; /* frame info read callback */ - png_progressive_frame_ptr frame_end_fn; /* frame data read callback */ -#endif -#endif - -#ifdef PNG_WRITE_APNG_SUPPORTED - png_uint_32 num_frames_to_write; - png_uint_32 num_frames_written; -#endif -#endif /* PNG_APNG_SUPPORTED */ - /* New members added in libpng-1.2.0 */ /* New members added in libpng-1.0.2 but first enabled by default in 1.2.0 */ diff --git a/thirdparty/libpng/pngwrite.c b/thirdparty/libpng/pngwrite.c index 5e68032378..06c45d16ab 100644 --- a/thirdparty/libpng/pngwrite.c +++ b/thirdparty/libpng/pngwrite.c @@ -1,7 +1,7 @@ /* pngwrite.c - general routines to write a PNG file * - * Copyright (c) 2018-2019 Cosmin Truta + * Copyright (c) 2018-2022 Cosmin Truta * Copyright (c) 1998-2002,2004,2006-2018 Glenn Randers-Pehrson * Copyright (c) 1996-1997 Andreas Dilger * Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc. @@ -128,10 +128,6 @@ png_write_info_before_PLTE(png_structrp png_ptr, png_const_inforp info_ptr) * the application continues writing the PNG. So check the 'invalid' * flag here too. */ -#ifdef PNG_WRITE_APNG_SUPPORTED - if (info_ptr->valid & PNG_INFO_acTL) - png_write_acTL(png_ptr, info_ptr->num_frames, info_ptr->num_plays); -#endif #ifdef PNG_GAMMA_SUPPORTED # ifdef PNG_WRITE_gAMA_SUPPORTED if ((info_ptr->colorspace.flags & PNG_COLORSPACE_INVALID) == 0 && @@ -374,11 +370,6 @@ png_write_end(png_structrp png_ptr, png_inforp info_ptr) png_benign_error(png_ptr, "Wrote palette index exceeding num_palette"); #endif -#ifdef PNG_WRITE_APNG_SUPPORTED - if (png_ptr->num_frames_written != png_ptr->num_frames_to_write) - png_error(png_ptr, "Not enough frames written"); -#endif - /* See if user wants us to write information chunks */ if (info_ptr != NULL) { @@ -498,6 +489,16 @@ png_convert_from_time_t(png_timep ptime, time_t ttime) png_debug(1, "in png_convert_from_time_t"); tbuf = gmtime(&ttime); + if (tbuf == NULL) + { + /* TODO: add a safe function which takes a png_ptr argument and raises + * a png_error if the ttime argument is invalid and the call to gmtime + * fails as a consequence. + */ + memset(ptime, 0, sizeof(*ptime)); + return; + } + png_convert_from_struct_tm(ptime, tbuf); } #endif @@ -1470,43 +1471,6 @@ png_write_png(png_structrp png_ptr, png_inforp info_ptr, } #endif -#ifdef PNG_WRITE_APNG_SUPPORTED -void PNGAPI -png_write_frame_head(png_structp png_ptr, png_infop info_ptr, - png_bytepp row_pointers, png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, png_byte dispose_op, - png_byte blend_op) -{ - png_debug(1, "in png_write_frame_head"); - - /* there is a chance this has been set after png_write_info was called, - * so it would be set but not written. is there a way to be sure? */ - if (!(info_ptr->valid & PNG_INFO_acTL)) - png_error(png_ptr, "png_write_frame_head(): acTL not set"); - - png_write_reset(png_ptr); - - png_write_reinit(png_ptr, info_ptr, width, height); - - if ( !(png_ptr->num_frames_written == 0 && - (png_ptr->apng_flags & PNG_FIRST_FRAME_HIDDEN) ) ) - png_write_fcTL(png_ptr, width, height, x_offset, y_offset, - delay_num, delay_den, dispose_op, blend_op); - - PNG_UNUSED(row_pointers) -} - -void PNGAPI -png_write_frame_tail(png_structp png_ptr, png_infop info_ptr) -{ - png_debug(1, "in png_write_frame_tail"); - - png_ptr->num_frames_written++; - - PNG_UNUSED(info_ptr) -} -#endif /* PNG_WRITE_APNG_SUPPORTED */ #ifdef PNG_SIMPLIFIED_WRITE_SUPPORTED /* Initialize the write structure - general purpose utility. */ diff --git a/thirdparty/libpng/pngwutil.c b/thirdparty/libpng/pngwutil.c index b4809cda6b..16345e4c0b 100644 --- a/thirdparty/libpng/pngwutil.c +++ b/thirdparty/libpng/pngwutil.c @@ -821,11 +821,6 @@ png_write_IHDR(png_structrp png_ptr, png_uint_32 width, png_uint_32 height, /* Write the chunk */ png_write_complete_chunk(png_ptr, png_IHDR, buf, 13); -#ifdef PNG_WRITE_APNG_SUPPORTED - png_ptr->first_frame_width = width; - png_ptr->first_frame_height = height; -#endif - if ((png_ptr->do_filter) == PNG_NO_FILTERS) { if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE || @@ -1007,17 +1002,8 @@ png_compress_IDAT(png_structrp png_ptr, png_const_bytep input, optimize_cmf(data, png_image_size(png_ptr)); #endif - if (size > 0) -#ifdef PNG_WRITE_APNG_SUPPORTED - { - if (png_ptr->num_frames_written == 0) -#endif - png_write_complete_chunk(png_ptr, png_IDAT, data, size); -#ifdef PNG_WRITE_APNG_SUPPORTED - else - png_write_fdAT(png_ptr, data, size); - } -#endif /* PNG_WRITE_APNG_SUPPORTED */ + if (size > 0) + png_write_complete_chunk(png_ptr, png_IDAT, data, size); png_ptr->mode |= PNG_HAVE_IDAT; png_ptr->zstream.next_out = data; @@ -1064,17 +1050,7 @@ png_compress_IDAT(png_structrp png_ptr, png_const_bytep input, #endif if (size > 0) -#ifdef PNG_WRITE_APNG_SUPPORTED - { - if (png_ptr->num_frames_written == 0) -#endif png_write_complete_chunk(png_ptr, png_IDAT, data, size); -#ifdef PNG_WRITE_APNG_SUPPORTED - else - png_write_fdAT(png_ptr, data, size); - } -#endif /* PNG_WRITE_APNG_SUPPORTED */ - png_ptr->zstream.avail_out = 0; png_ptr->zstream.next_out = NULL; png_ptr->mode |= PNG_HAVE_IDAT | PNG_AFTER_IDAT; @@ -1909,82 +1885,6 @@ png_write_tIME(png_structrp png_ptr, png_const_timep mod_time) } #endif -#ifdef PNG_WRITE_APNG_SUPPORTED -void /* PRIVATE */ -png_write_acTL(png_structp png_ptr, - png_uint_32 num_frames, png_uint_32 num_plays) -{ - png_byte buf[8]; - - png_debug(1, "in png_write_acTL"); - - png_ptr->num_frames_to_write = num_frames; - - if (png_ptr->apng_flags & PNG_FIRST_FRAME_HIDDEN) - num_frames--; - - png_save_uint_32(buf, num_frames); - png_save_uint_32(buf + 4, num_plays); - - png_write_complete_chunk(png_ptr, png_acTL, buf, (png_size_t)8); -} - -void /* PRIVATE */ -png_write_fcTL(png_structp png_ptr, png_uint_32 width, png_uint_32 height, - png_uint_32 x_offset, png_uint_32 y_offset, - png_uint_16 delay_num, png_uint_16 delay_den, png_byte dispose_op, - png_byte blend_op) -{ - png_byte buf[26]; - - png_debug(1, "in png_write_fcTL"); - - if (png_ptr->num_frames_written == 0 && (x_offset != 0 || y_offset != 0)) - png_error(png_ptr, "x and/or y offset for the first frame aren't 0"); - if (png_ptr->num_frames_written == 0 && - (width != png_ptr->first_frame_width || - height != png_ptr->first_frame_height)) - png_error(png_ptr, "width and/or height in the first frame's fcTL " - "don't match the ones in IHDR"); - - /* more error checking */ - png_ensure_fcTL_is_valid(png_ptr, width, height, x_offset, y_offset, - delay_num, delay_den, dispose_op, blend_op); - - png_save_uint_32(buf, png_ptr->next_seq_num); - png_save_uint_32(buf + 4, width); - png_save_uint_32(buf + 8, height); - png_save_uint_32(buf + 12, x_offset); - png_save_uint_32(buf + 16, y_offset); - png_save_uint_16(buf + 20, delay_num); - png_save_uint_16(buf + 22, delay_den); - buf[24] = dispose_op; - buf[25] = blend_op; - - png_write_complete_chunk(png_ptr, png_fcTL, buf, (png_size_t)26); - - png_ptr->next_seq_num++; -} - -void /* PRIVATE */ -png_write_fdAT(png_structp png_ptr, - png_const_bytep data, png_size_t length) -{ - png_byte buf[4]; - - png_write_chunk_header(png_ptr, png_fdAT, (png_uint_32)(4 + length)); - - png_save_uint_32(buf, png_ptr->next_seq_num); - png_write_chunk_data(png_ptr, buf, 4); - - png_write_chunk_data(png_ptr, data, length); - - png_write_chunk_end(png_ptr); - - png_ptr->next_seq_num++; -} -#endif /* PNG_WRITE_APNG_SUPPORTED */ - /* Initializes the row writing capability of libpng */ void /* PRIVATE */ png_write_start_row(png_structrp png_ptr) @@ -2878,39 +2778,4 @@ png_write_filtered_row(png_structrp png_ptr, png_bytep filtered_row, } #endif /* WRITE_FLUSH */ } - -#ifdef PNG_WRITE_APNG_SUPPORTED -void /* PRIVATE */ -png_write_reset(png_structp png_ptr) -{ - png_ptr->row_number = 0; - png_ptr->pass = 0; - png_ptr->mode &= ~PNG_HAVE_IDAT; -} - -void /* PRIVATE */ -png_write_reinit(png_structp png_ptr, png_infop info_ptr, - png_uint_32 width, png_uint_32 height) -{ - if (png_ptr->num_frames_written == 0 && - (width != png_ptr->first_frame_width || - height != png_ptr->first_frame_height)) - png_error(png_ptr, "width and/or height in the first frame's fcTL " - "don't match the ones in IHDR"); - if (width > png_ptr->first_frame_width || - height > png_ptr->first_frame_height) - png_error(png_ptr, "width and/or height for a frame greater than" - "the ones in IHDR"); - - png_set_IHDR(png_ptr, info_ptr, width, height, - info_ptr->bit_depth, info_ptr->color_type, - info_ptr->interlace_type, info_ptr->compression_type, - info_ptr->filter_type); - - png_ptr->width = width; - png_ptr->height = height; - png_ptr->rowbytes = PNG_ROWBYTES(png_ptr->pixel_depth, width); - png_ptr->usr_width = png_ptr->width; -} -#endif /* PNG_WRITE_APNG_SUPPORTED */ #endif /* WRITE */ diff --git a/thirdparty/minimp3/minimp3_ex.h b/thirdparty/minimp3/minimp3_ex.h index 2871705df3..2b207a25a7 100644 --- a/thirdparty/minimp3/minimp3_ex.h +++ b/thirdparty/minimp3/minimp3_ex.h @@ -377,7 +377,7 @@ int mp3dec_load_cb(mp3dec_t *dec, mp3dec_io_t *io, uint8_t *buf, size_t buf_size samples = hdr_frame_samples(hdr)*frame_info.channels; if (3 != frame_info.layer) break; - int ret = mp3dec_check_vbrtag(hdr, frame_size, &frames, &delay, &padding); + ret = mp3dec_check_vbrtag(hdr, frame_size, &frames, &delay, &padding); if (ret > 0) { padding *= frame_info.channels; @@ -529,7 +529,8 @@ int mp3dec_iterate_buf(const uint8_t *buf, size_t buf_size, MP3D_ITERATE_CB call if (callback) { - if ((ret = callback(user_data, hdr, frame_size, free_format_bytes, buf_size, hdr - orig_buf, &frame_info))) + ret = callback(user_data, hdr, frame_size, free_format_bytes, buf_size, hdr - orig_buf, &frame_info); + if (ret != 0) return ret; } buf += frame_size; @@ -562,7 +563,7 @@ int mp3dec_iterate_cb(mp3dec_io_t *io, uint8_t *buf, size_t buf_size, MP3D_ITERA readed += id3v2size; } else { - size_t readed = io->read(buf + MINIMP3_ID3_DETECT_SIZE, buf_size - MINIMP3_ID3_DETECT_SIZE, io->read_data); + readed = io->read(buf + MINIMP3_ID3_DETECT_SIZE, buf_size - MINIMP3_ID3_DETECT_SIZE, io->read_data); if (readed > (buf_size - MINIMP3_ID3_DETECT_SIZE)) return MP3D_E_IOERROR; filled += readed; @@ -590,7 +591,8 @@ int mp3dec_iterate_cb(mp3dec_io_t *io, uint8_t *buf, size_t buf_size, MP3D_ITERA readed += i; if (callback) { - if ((ret = callback(user_data, hdr, frame_size, free_format_bytes, filled - consumed, readed, &frame_info))) + ret = callback(user_data, hdr, frame_size, free_format_bytes, filled - consumed, readed, &frame_info); + if (ret != 0) return ret; } readed += frame_size; @@ -600,7 +602,7 @@ int mp3dec_iterate_cb(mp3dec_io_t *io, uint8_t *buf, size_t buf_size, MP3D_ITERA memmove(buf, buf + consumed, filled - consumed); filled -= consumed; consumed = 0; - size_t readed = io->read(buf + filled, buf_size - filled, io->read_data); + readed = io->read(buf + filled, buf_size - filled, io->read_data); if (readed > (buf_size - filled)) return MP3D_E_IOERROR; if (readed != (buf_size - filled)) diff --git a/thirdparty/minimp3/patches/msvc-arm-fix.patch b/thirdparty/minimp3/patches/msvc-arm-fix.patch new file mode 100644 index 0000000000..bca915aceb --- /dev/null +++ b/thirdparty/minimp3/patches/msvc-arm-fix.patch @@ -0,0 +1,43 @@ +diff --git a/thirdparty/minimp3/minimp3.h b/thirdparty/minimp3/minimp3.h +index 3220ae1a85..2a9975cc86 100644 +--- a/thirdparty/minimp3/minimp3.h ++++ b/thirdparty/minimp3/minimp3.h +@@ -1566,7 +1566,18 @@ static void mp3d_synth(float *xl, mp3d_sample_t *dstl, int nch, float *lins) + + #else /* MINIMP3_FLOAT_OUTPUT */ + ++// -- GODOT start -- ++#if defined(_MSC_VER) && (defined(_M_ARM64) || defined(_M_ARM64EC) || defined(_M_ARM)) ++ static f4 g_scale; ++ g_scale = vsetq_lane_f32(1.0f/32768.0f, g_scale, 0); ++ g_scale = vsetq_lane_f32(1.0f/32768.0f, g_scale, 1); ++ g_scale = vsetq_lane_f32(1.0f/32768.0f, g_scale, 2); ++ g_scale = vsetq_lane_f32(1.0f/32768.0f, g_scale, 3); ++#else + static const f4 g_scale = { 1.0f/32768.0f, 1.0f/32768.0f, 1.0f/32768.0f, 1.0f/32768.0f }; ++#endif ++// -- GODOT end -- ++ + a = VMUL(a, g_scale); + b = VMUL(b, g_scale); + #if HAVE_SSE +@@ -1813,7 +1824,19 @@ void mp3dec_f32_to_s16(const float *in, int16_t *out, int num_samples) + int aligned_count = num_samples & ~7; + for(; i < aligned_count; i += 8) + { ++ ++// -- GODOT start -- ++#if defined(_MSC_VER) && (defined(_M_ARM64) || defined(_M_ARM64EC) || defined(_M_ARM)) ++ static f4 g_scale; ++ g_scale = vsetq_lane_f32(32768.0f, g_scale, 0); ++ g_scale = vsetq_lane_f32(32768.0f, g_scale, 1); ++ g_scale = vsetq_lane_f32(32768.0f, g_scale, 2); ++ g_scale = vsetq_lane_f32(32768.0f, g_scale, 3); ++#else + static const f4 g_scale = { 32768.0f, 32768.0f, 32768.0f, 32768.0f }; ++#endif ++// -- GODOT end -- ++ + f4 a = VMUL(VLD(&in[i ]), g_scale); + f4 b = VMUL(VLD(&in[i+4]), g_scale); + #if HAVE_SSE diff --git a/thirdparty/minimp3/patches/msvc-warnings-fixes.patch b/thirdparty/minimp3/patches/msvc-warnings-fixes.patch new file mode 100644 index 0000000000..d186d6c6f7 --- /dev/null +++ b/thirdparty/minimp3/patches/msvc-warnings-fixes.patch @@ -0,0 +1,51 @@ +diff --git a/thirdparty/minimp3/minimp3_ex.h b/thirdparty/minimp3/minimp3_ex.h +index 2871705df3..2b207a25a7 100644 +--- a/thirdparty/minimp3/minimp3_ex.h ++++ b/thirdparty/minimp3/minimp3_ex.h +@@ -377,7 +377,7 @@ int mp3dec_load_cb(mp3dec_t *dec, mp3dec_io_t *io, uint8_t *buf, size_t buf_size + samples = hdr_frame_samples(hdr)*frame_info.channels; + if (3 != frame_info.layer) + break; +- int ret = mp3dec_check_vbrtag(hdr, frame_size, &frames, &delay, &padding); ++ ret = mp3dec_check_vbrtag(hdr, frame_size, &frames, &delay, &padding); + if (ret > 0) + { + padding *= frame_info.channels; +@@ -529,7 +529,8 @@ int mp3dec_iterate_buf(const uint8_t *buf, size_t buf_size, MP3D_ITERATE_CB call + + if (callback) + { +- if ((ret = callback(user_data, hdr, frame_size, free_format_bytes, buf_size, hdr - orig_buf, &frame_info))) ++ ret = callback(user_data, hdr, frame_size, free_format_bytes, buf_size, hdr - orig_buf, &frame_info); ++ if (ret != 0) + return ret; + } + buf += frame_size; +@@ -562,7 +563,7 @@ int mp3dec_iterate_cb(mp3dec_io_t *io, uint8_t *buf, size_t buf_size, MP3D_ITERA + readed += id3v2size; + } else + { +- size_t readed = io->read(buf + MINIMP3_ID3_DETECT_SIZE, buf_size - MINIMP3_ID3_DETECT_SIZE, io->read_data); ++ readed = io->read(buf + MINIMP3_ID3_DETECT_SIZE, buf_size - MINIMP3_ID3_DETECT_SIZE, io->read_data); + if (readed > (buf_size - MINIMP3_ID3_DETECT_SIZE)) + return MP3D_E_IOERROR; + filled += readed; +@@ -590,7 +591,8 @@ int mp3dec_iterate_cb(mp3dec_io_t *io, uint8_t *buf, size_t buf_size, MP3D_ITERA + readed += i; + if (callback) + { +- if ((ret = callback(user_data, hdr, frame_size, free_format_bytes, filled - consumed, readed, &frame_info))) ++ ret = callback(user_data, hdr, frame_size, free_format_bytes, filled - consumed, readed, &frame_info); ++ if (ret != 0) + return ret; + } + readed += frame_size; +@@ -600,7 +602,7 @@ int mp3dec_iterate_cb(mp3dec_io_t *io, uint8_t *buf, size_t buf_size, MP3D_ITERA + memmove(buf, buf + consumed, filled - consumed); + filled -= consumed; + consumed = 0; +- size_t readed = io->read(buf + filled, buf_size - filled, io->read_data); ++ readed = io->read(buf + filled, buf_size - filled, io->read_data); + if (readed > (buf_size - filled)) + return MP3D_E_IOERROR; + if (readed != (buf_size - filled)) diff --git a/thirdparty/misc/patches/polypartition-hole.patch b/thirdparty/misc/patches/polypartition-hole.patch new file mode 100644 index 0000000000..2fcb5d1928 --- /dev/null +++ b/thirdparty/misc/patches/polypartition-hole.patch @@ -0,0 +1,15 @@ +diff --git a/thirdparty/misc/polypartition.h b/thirdparty/misc/polypartition.h +index fae7909079..c084bdf74c 100644 +--- a/thirdparty/misc/polypartition.h ++++ b/thirdparty/misc/polypartition.h +@@ -71,8 +71,8 @@ class TPPLPoly { + return hole; + } + +- void SetHole(bool hole) { +- this->hole = hole; ++ void SetHole(bool p_hole) { ++ this->hole = p_hole; + } + + TPPLPoint &GetPoint(long i) { diff --git a/thirdparty/misc/polypartition.h b/thirdparty/misc/polypartition.h index fae7909079..c084bdf74c 100644 --- a/thirdparty/misc/polypartition.h +++ b/thirdparty/misc/polypartition.h @@ -71,8 +71,8 @@ class TPPLPoly { return hole; } - void SetHole(bool hole) { - this->hole = hole; + void SetHole(bool p_hole) { + this->hole = p_hole; } TPPLPoint &GetPoint(long i) { diff --git a/thirdparty/openxr/include/openxr/openxr.h b/thirdparty/openxr/include/openxr/openxr.h index 6c6a52d27e..6f9b71aa68 100644 --- a/thirdparty/openxr/include/openxr/openxr.h +++ b/thirdparty/openxr/include/openxr/openxr.h @@ -2,7 +2,7 @@ #define OPENXR_H_ 1 /* -** Copyright (c) 2017-2022, The Khronos Group Inc. +** Copyright 2017-2022 The Khronos Group Inc. ** ** SPDX-License-Identifier: Apache-2.0 OR MIT */ @@ -25,7 +25,7 @@ extern "C" { ((((major) & 0xffffULL) << 48) | (((minor) & 0xffffULL) << 32) | ((patch) & 0xffffffffULL)) // OpenXR current version number. -#define XR_CURRENT_API_VERSION XR_MAKE_VERSION(1, 0, 23) +#define XR_CURRENT_API_VERSION XR_MAKE_VERSION(1, 0, 25) #define XR_VERSION_MAJOR(version) (uint16_t)(((uint64_t)(version) >> 48)& 0xffffULL) #define XR_VERSION_MINOR(version) (uint16_t)(((uint64_t)(version) >> 32) & 0xffffULL) @@ -401,6 +401,7 @@ typedef enum XrStructureType { XR_TYPE_COMPOSITION_LAYER_PASSTHROUGH_FB = 1000118003, XR_TYPE_GEOMETRY_INSTANCE_CREATE_INFO_FB = 1000118004, XR_TYPE_GEOMETRY_INSTANCE_TRANSFORM_FB = 1000118005, + XR_TYPE_SYSTEM_PASSTHROUGH_PROPERTIES2_FB = 1000118006, XR_TYPE_PASSTHROUGH_STYLE_FB = 1000118020, XR_TYPE_PASSTHROUGH_COLOR_MAP_MONO_TO_RGBA_FB = 1000118021, XR_TYPE_PASSTHROUGH_COLOR_MAP_MONO_TO_MONO_FB = 1000118022, @@ -439,6 +440,9 @@ typedef enum XrStructureType { XR_TYPE_SWAPCHAIN_STATE_SAMPLER_VULKAN_FB = 1000163000, XR_TYPE_COMPOSITION_LAYER_SPACE_WARP_INFO_FB = 1000171000, XR_TYPE_SYSTEM_SPACE_WARP_PROPERTIES_FB = 1000171001, + XR_TYPE_SEMANTIC_LABELS_FB = 1000175000, + XR_TYPE_ROOM_LAYOUT_FB = 1000175001, + XR_TYPE_BOUNDARY_2D_FB = 1000175002, XR_TYPE_DIGITAL_LENS_CONTROL_ALMALENCE = 1000196000, XR_TYPE_SPACE_CONTAINER_FB = 1000199000, XR_TYPE_PASSTHROUGH_KEYBOARD_HANDS_INTENSITY_FB = 1000203002, @@ -2603,7 +2607,7 @@ typedef struct XrHandJointsMotionRangeInfoEXT { XR_DEFINE_HANDLE(XrSceneMSFT) -#define XR_MSFT_scene_understanding_SPEC_VERSION 1 +#define XR_MSFT_scene_understanding_SPEC_VERSION 2 #define XR_MSFT_SCENE_UNDERSTANDING_EXTENSION_NAME "XR_MSFT_scene_understanding" typedef enum XrSceneComputeFeatureMSFT { @@ -2925,7 +2929,7 @@ XRAPI_ATTR XrResult XRAPI_CALL xrGetSceneMeshBuffersMSFT( #define XR_MSFT_scene_understanding_serialization 1 -#define XR_MSFT_scene_understanding_serialization_SPEC_VERSION 1 +#define XR_MSFT_scene_understanding_serialization_SPEC_VERSION 2 #define XR_MSFT_SCENE_UNDERSTANDING_SERIALIZATION_EXTENSION_NAME "XR_MSFT_scene_understanding_serialization" typedef struct XrSerializedSceneFragmentDataGetInfoMSFT { XrStructureType type; @@ -3166,7 +3170,7 @@ XRAPI_ATTR XrResult XRAPI_CALL xrGetFacialExpressionsHTC( #define XR_FB_color_space 1 -#define XR_FB_color_space_SPEC_VERSION 2 +#define XR_FB_color_space_SPEC_VERSION 3 #define XR_FB_COLOR_SPACE_EXTENSION_NAME "XR_FB_color_space" typedef enum XrColorSpaceFB { @@ -3206,7 +3210,7 @@ XRAPI_ATTR XrResult XRAPI_CALL xrSetColorSpaceFB( #define XR_FB_hand_tracking_mesh 1 -#define XR_FB_hand_tracking_mesh_SPEC_VERSION 2 +#define XR_FB_hand_tracking_mesh_SPEC_VERSION 3 #define XR_FB_HAND_TRACKING_MESH_EXTENSION_NAME "XR_FB_hand_tracking_mesh" typedef struct XrVector4sFB { int16_t x; @@ -3317,6 +3321,10 @@ XR_DEFINE_ATOM(XrAsyncRequestIdFB) typedef enum XrSpaceComponentTypeFB { XR_SPACE_COMPONENT_TYPE_LOCATABLE_FB = 0, XR_SPACE_COMPONENT_TYPE_STORABLE_FB = 1, + XR_SPACE_COMPONENT_TYPE_BOUNDED_2D_FB = 3, + XR_SPACE_COMPONENT_TYPE_BOUNDED_3D_FB = 4, + XR_SPACE_COMPONENT_TYPE_SEMANTIC_LABELS_FB = 5, + XR_SPACE_COMPONENT_TYPE_ROOM_LAYOUT_FB = 6, XR_SPACE_COMPONENT_TYPE_SPACE_CONTAINER_FB = 7, XR_SPACE_COMPONENT_TYPE_MAX_ENUM_FB = 0x7FFFFFFF } XrSpaceComponentTypeFB; @@ -3625,7 +3633,7 @@ XRAPI_ATTR XrResult XRAPI_CALL xrTriangleMeshEndVertexBufferUpdateFB( XR_DEFINE_HANDLE(XrPassthroughFB) XR_DEFINE_HANDLE(XrPassthroughLayerFB) XR_DEFINE_HANDLE(XrGeometryInstanceFB) -#define XR_FB_passthrough_SPEC_VERSION 2 +#define XR_FB_passthrough_SPEC_VERSION 3 #define XR_FB_PASSTHROUGH_EXTENSION_NAME "XR_FB_passthrough" #define XR_PASSTHROUGH_COLOR_MAP_MONO_SIZE_FB 256 @@ -3636,10 +3644,18 @@ typedef enum XrPassthroughLayerPurposeFB { XR_PASSTHROUGH_LAYER_PURPOSE_TRACKED_KEYBOARD_MASKED_HANDS_FB = 1000203002, XR_PASSTHROUGH_LAYER_PURPOSE_MAX_ENUM_FB = 0x7FFFFFFF } XrPassthroughLayerPurposeFB; +typedef XrFlags64 XrPassthroughCapabilityFlagsFB; + +// Flag bits for XrPassthroughCapabilityFlagsFB +static const XrPassthroughCapabilityFlagsFB XR_PASSTHROUGH_CAPABILITY_BIT_FB = 0x00000001; +static const XrPassthroughCapabilityFlagsFB XR_PASSTHROUGH_CAPABILITY_COLOR_BIT_FB = 0x00000002; +static const XrPassthroughCapabilityFlagsFB XR_PASSTHROUGH_CAPABILITY_LAYER_DEPTH_BIT_FB = 0x00000004; + typedef XrFlags64 XrPassthroughFlagsFB; // Flag bits for XrPassthroughFlagsFB static const XrPassthroughFlagsFB XR_PASSTHROUGH_IS_RUNNING_AT_CREATION_BIT_FB = 0x00000001; +static const XrPassthroughFlagsFB XR_PASSTHROUGH_LAYER_DEPTH_BIT_FB = 0x00000002; typedef XrFlags64 XrPassthroughStateChangedFlagsFB; @@ -3656,6 +3672,13 @@ typedef struct XrSystemPassthroughPropertiesFB { XrBool32 supportsPassthrough; } XrSystemPassthroughPropertiesFB; +// XrSystemPassthroughProperties2FB extends XrSystemProperties +typedef struct XrSystemPassthroughProperties2FB { + XrStructureType type; + const void* XR_MAY_ALIAS next; + XrPassthroughCapabilityFlagsFB capabilities; +} XrSystemPassthroughProperties2FB; + typedef struct XrPassthroughCreateInfoFB { XrStructureType type; const void* XR_MAY_ALIAS next; @@ -3801,7 +3824,7 @@ XRAPI_ATTR XrResult XRAPI_CALL xrGeometryInstanceSetTransformFB( #define XR_NULL_RENDER_MODEL_KEY_FB 0 XR_DEFINE_ATOM(XrRenderModelKeyFB) -#define XR_FB_render_model_SPEC_VERSION 2 +#define XR_FB_render_model_SPEC_VERSION 3 #define XR_FB_RENDER_MODEL_EXTENSION_NAME "XR_FB_render_model" #define XR_MAX_RENDER_MODEL_NAME_SIZE_FB 64 typedef XrFlags64 XrRenderModelFlagsFB; @@ -4007,6 +4030,11 @@ XRAPI_ATTR XrResult XRAPI_CALL xrSetViewOffsetVARJO( #endif /* !XR_NO_PROTOTYPES */ +#define XR_ML_ml2_controller_interaction 1 +#define XR_ML_ml2_controller_interaction_SPEC_VERSION 1 +#define XR_ML_ML2_CONTROLLER_INTERACTION_EXTENSION_NAME "XR_ML_ml2_controller_interaction" + + #define XR_MSFT_spatial_anchor_persistence 1 XR_DEFINE_HANDLE(XrSpatialAnchorStoreConnectionMSFT) #define XR_MAX_SPATIAL_ANCHOR_NAME_SIZE_MSFT 256 @@ -4303,6 +4331,93 @@ typedef struct XrSystemSpaceWarpPropertiesFB { +#define XR_FB_scene 1 +#define XR_FB_scene_SPEC_VERSION 1 +#define XR_FB_SCENE_EXTENSION_NAME "XR_FB_scene" +typedef struct XrExtent3DfFB { + float width; + float height; + float depth; +} XrExtent3DfFB; + +typedef struct XrOffset3DfFB { + float x; + float y; + float z; +} XrOffset3DfFB; + +typedef struct XrRect3DfFB { + XrOffset3DfFB offset; + XrExtent3DfFB extent; +} XrRect3DfFB; + +typedef struct XrSemanticLabelsFB { + XrStructureType type; + const void* XR_MAY_ALIAS next; + uint32_t bufferCapacityInput; + uint32_t bufferCountOutput; + char* buffer; +} XrSemanticLabelsFB; + +typedef struct XrRoomLayoutFB { + XrStructureType type; + const void* XR_MAY_ALIAS next; + XrUuidEXT floorUuid; + XrUuidEXT ceilingUuid; + uint32_t wallUuidCapacityInput; + uint32_t wallUuidCountOutput; + XrUuidEXT* wallUuids; +} XrRoomLayoutFB; + +typedef struct XrBoundary2DFB { + XrStructureType type; + const void* XR_MAY_ALIAS next; + uint32_t vertexCapacityInput; + uint32_t vertexCountOutput; + XrVector2f* vertices; +} XrBoundary2DFB; + +typedef XrResult (XRAPI_PTR *PFN_xrGetSpaceBoundingBox2DFB)(XrSession session, XrSpace space, XrRect2Df* boundingBox2DOutput); +typedef XrResult (XRAPI_PTR *PFN_xrGetSpaceBoundingBox3DFB)(XrSession session, XrSpace space, XrRect3DfFB* boundingBox3DOutput); +typedef XrResult (XRAPI_PTR *PFN_xrGetSpaceSemanticLabelsFB)(XrSession session, XrSpace space, XrSemanticLabelsFB* semanticLabelsOutput); +typedef XrResult (XRAPI_PTR *PFN_xrGetSpaceBoundary2DFB)(XrSession session, XrSpace space, XrBoundary2DFB* boundary2DOutput); +typedef XrResult (XRAPI_PTR *PFN_xrGetSpaceRoomLayoutFB)(XrSession session, XrSpace space, XrRoomLayoutFB* roomLayoutOutput); + +#ifndef XR_NO_PROTOTYPES +#ifdef XR_EXTENSION_PROTOTYPES +XRAPI_ATTR XrResult XRAPI_CALL xrGetSpaceBoundingBox2DFB( + XrSession session, + XrSpace space, + XrRect2Df* boundingBox2DOutput); + +XRAPI_ATTR XrResult XRAPI_CALL xrGetSpaceBoundingBox3DFB( + XrSession session, + XrSpace space, + XrRect3DfFB* boundingBox3DOutput); + +XRAPI_ATTR XrResult XRAPI_CALL xrGetSpaceSemanticLabelsFB( + XrSession session, + XrSpace space, + XrSemanticLabelsFB* semanticLabelsOutput); + +XRAPI_ATTR XrResult XRAPI_CALL xrGetSpaceBoundary2DFB( + XrSession session, + XrSpace space, + XrBoundary2DFB* boundary2DOutput); + +XRAPI_ATTR XrResult XRAPI_CALL xrGetSpaceRoomLayoutFB( + XrSession session, + XrSpace space, + XrRoomLayoutFB* roomLayoutOutput); +#endif /* XR_EXTENSION_PROTOTYPES */ +#endif /* !XR_NO_PROTOTYPES */ + + +#define XR_EXT_palm_pose 1 +#define XR_EXT_palm_pose_SPEC_VERSION 2 +#define XR_EXT_PALM_POSE_EXTENSION_NAME "XR_EXT_palm_pose" + + #define XR_ALMALENCE_digital_lens_control 1 #define XR_ALMALENCE_digital_lens_control_SPEC_VERSION 1 #define XR_ALMALENCE_DIGITAL_LENS_CONTROL_EXTENSION_NAME "XR_ALMALENCE_digital_lens_control" @@ -4329,13 +4444,13 @@ XRAPI_ATTR XrResult XRAPI_CALL xrSetDigitalLensControlALMALENCE( #define XR_FB_spatial_entity_container 1 -#define XR_FB_spatial_entity_container_SPEC_VERSION 1 +#define XR_FB_spatial_entity_container_SPEC_VERSION 2 #define XR_FB_SPATIAL_ENTITY_CONTAINER_EXTENSION_NAME "XR_FB_spatial_entity_container" typedef struct XrSpaceContainerFB { XrStructureType type; const void* XR_MAY_ALIAS next; uint32_t uuidCapacityInput; - uint32_t* uuidCountOutput; + uint32_t uuidCountOutput; XrUuidEXT* uuids; } XrSpaceContainerFB; diff --git a/thirdparty/openxr/include/openxr/openxr_platform.h b/thirdparty/openxr/include/openxr/openxr_platform.h index f0fbf6955a..b3aabb23c5 100644 --- a/thirdparty/openxr/include/openxr/openxr_platform.h +++ b/thirdparty/openxr/include/openxr/openxr_platform.h @@ -2,7 +2,7 @@ #define OPENXR_PLATFORM_H_ 1 /* -** Copyright (c) 2017-2022, The Khronos Group Inc. +** Copyright 2017-2022 The Khronos Group Inc. ** ** SPDX-License-Identifier: Apache-2.0 OR MIT */ diff --git a/thirdparty/openxr/include/openxr/openxr_reflection.h b/thirdparty/openxr/include/openxr/openxr_reflection.h index 163b54e4e4..ac6f452377 100644 --- a/thirdparty/openxr/include/openxr/openxr_reflection.h +++ b/thirdparty/openxr/include/openxr/openxr_reflection.h @@ -302,6 +302,7 @@ XR_ENUM_STR(XrResult); _(XR_TYPE_COMPOSITION_LAYER_PASSTHROUGH_FB, 1000118003) \ _(XR_TYPE_GEOMETRY_INSTANCE_CREATE_INFO_FB, 1000118004) \ _(XR_TYPE_GEOMETRY_INSTANCE_TRANSFORM_FB, 1000118005) \ + _(XR_TYPE_SYSTEM_PASSTHROUGH_PROPERTIES2_FB, 1000118006) \ _(XR_TYPE_PASSTHROUGH_STYLE_FB, 1000118020) \ _(XR_TYPE_PASSTHROUGH_COLOR_MAP_MONO_TO_RGBA_FB, 1000118021) \ _(XR_TYPE_PASSTHROUGH_COLOR_MAP_MONO_TO_MONO_FB, 1000118022) \ @@ -340,6 +341,9 @@ XR_ENUM_STR(XrResult); _(XR_TYPE_SWAPCHAIN_STATE_SAMPLER_VULKAN_FB, 1000163000) \ _(XR_TYPE_COMPOSITION_LAYER_SPACE_WARP_INFO_FB, 1000171000) \ _(XR_TYPE_SYSTEM_SPACE_WARP_PROPERTIES_FB, 1000171001) \ + _(XR_TYPE_SEMANTIC_LABELS_FB, 1000175000) \ + _(XR_TYPE_ROOM_LAYOUT_FB, 1000175001) \ + _(XR_TYPE_BOUNDARY_2D_FB, 1000175002) \ _(XR_TYPE_DIGITAL_LENS_CONTROL_ALMALENCE, 1000196000) \ _(XR_TYPE_SPACE_CONTAINER_FB, 1000199000) \ _(XR_TYPE_PASSTHROUGH_KEYBOARD_HANDS_INTENSITY_FB, 1000203002) \ @@ -660,6 +664,10 @@ XR_ENUM_STR(XrResult); #define XR_LIST_ENUM_XrSpaceComponentTypeFB(_) \ _(XR_SPACE_COMPONENT_TYPE_LOCATABLE_FB, 0) \ _(XR_SPACE_COMPONENT_TYPE_STORABLE_FB, 1) \ + _(XR_SPACE_COMPONENT_TYPE_BOUNDED_2D_FB, 3) \ + _(XR_SPACE_COMPONENT_TYPE_BOUNDED_3D_FB, 4) \ + _(XR_SPACE_COMPONENT_TYPE_SEMANTIC_LABELS_FB, 5) \ + _(XR_SPACE_COMPONENT_TYPE_ROOM_LAYOUT_FB, 6) \ _(XR_SPACE_COMPONENT_TYPE_SPACE_CONTAINER_FB, 7) \ _(XR_SPACE_COMPONENT_TYPE_MAX_ENUM_FB, 0x7FFFFFFF) @@ -847,8 +855,14 @@ XR_ENUM_STR(XrResult); #define XR_LIST_BITS_XrTriangleMeshFlagsFB(_) \ _(XR_TRIANGLE_MESH_MUTABLE_BIT_FB, 0x00000001) \ +#define XR_LIST_BITS_XrPassthroughCapabilityFlagsFB(_) \ + _(XR_PASSTHROUGH_CAPABILITY_BIT_FB, 0x00000001) \ + _(XR_PASSTHROUGH_CAPABILITY_COLOR_BIT_FB, 0x00000002) \ + _(XR_PASSTHROUGH_CAPABILITY_LAYER_DEPTH_BIT_FB, 0x00000004) \ + #define XR_LIST_BITS_XrPassthroughFlagsFB(_) \ _(XR_PASSTHROUGH_IS_RUNNING_AT_CREATION_BIT_FB, 0x00000001) \ + _(XR_PASSTHROUGH_LAYER_DEPTH_BIT_FB, 0x00000002) \ #define XR_LIST_BITS_XrPassthroughStateChangedFlagsFB(_) \ _(XR_PASSTHROUGH_STATE_CHANGED_REINIT_REQUIRED_BIT_FB, 0x00000001) \ @@ -2288,6 +2302,11 @@ XR_ENUM_STR(XrResult); _(next) \ _(supportsPassthrough) \ +#define XR_LIST_STRUCT_XrSystemPassthroughProperties2FB(_) \ + _(type) \ + _(next) \ + _(capabilities) \ + #define XR_LIST_STRUCT_XrPassthroughCreateInfoFB(_) \ _(type) \ _(next) \ @@ -2589,6 +2608,43 @@ XR_ENUM_STR(XrResult); _(recommendedMotionVectorImageRectWidth) \ _(recommendedMotionVectorImageRectHeight) \ +#define XR_LIST_STRUCT_XrExtent3DfFB(_) \ + _(width) \ + _(height) \ + _(depth) \ + +#define XR_LIST_STRUCT_XrOffset3DfFB(_) \ + _(x) \ + _(y) \ + _(z) \ + +#define XR_LIST_STRUCT_XrRect3DfFB(_) \ + _(offset) \ + _(extent) \ + +#define XR_LIST_STRUCT_XrSemanticLabelsFB(_) \ + _(type) \ + _(next) \ + _(bufferCapacityInput) \ + _(bufferCountOutput) \ + _(buffer) \ + +#define XR_LIST_STRUCT_XrRoomLayoutFB(_) \ + _(type) \ + _(next) \ + _(floorUuid) \ + _(ceilingUuid) \ + _(wallUuidCapacityInput) \ + _(wallUuidCountOutput) \ + _(wallUuids) \ + +#define XR_LIST_STRUCT_XrBoundary2DFB(_) \ + _(type) \ + _(next) \ + _(vertexCapacityInput) \ + _(vertexCountOutput) \ + _(vertices) \ + #define XR_LIST_STRUCT_XrDigitalLensControlALMALENCE(_) \ _(type) \ _(next) \ @@ -2785,6 +2841,7 @@ XR_ENUM_STR(XrResult); _(XrKeyboardTrackingQueryFB, XR_TYPE_KEYBOARD_TRACKING_QUERY_FB) \ _(XrTriangleMeshCreateInfoFB, XR_TYPE_TRIANGLE_MESH_CREATE_INFO_FB) \ _(XrSystemPassthroughPropertiesFB, XR_TYPE_SYSTEM_PASSTHROUGH_PROPERTIES_FB) \ + _(XrSystemPassthroughProperties2FB, XR_TYPE_SYSTEM_PASSTHROUGH_PROPERTIES2_FB) \ _(XrPassthroughCreateInfoFB, XR_TYPE_PASSTHROUGH_CREATE_INFO_FB) \ _(XrPassthroughLayerCreateInfoFB, XR_TYPE_PASSTHROUGH_LAYER_CREATE_INFO_FB) \ _(XrCompositionLayerPassthroughFB, XR_TYPE_COMPOSITION_LAYER_PASSTHROUGH_FB) \ @@ -2823,6 +2880,9 @@ XR_ENUM_STR(XrResult); _(XrEventDataSpaceEraseCompleteFB, XR_TYPE_EVENT_DATA_SPACE_ERASE_COMPLETE_FB) \ _(XrCompositionLayerSpaceWarpInfoFB, XR_TYPE_COMPOSITION_LAYER_SPACE_WARP_INFO_FB) \ _(XrSystemSpaceWarpPropertiesFB, XR_TYPE_SYSTEM_SPACE_WARP_PROPERTIES_FB) \ + _(XrSemanticLabelsFB, XR_TYPE_SEMANTIC_LABELS_FB) \ + _(XrRoomLayoutFB, XR_TYPE_ROOM_LAYOUT_FB) \ + _(XrBoundary2DFB, XR_TYPE_BOUNDARY_2D_FB) \ _(XrDigitalLensControlALMALENCE, XR_TYPE_DIGITAL_LENS_CONTROL_ALMALENCE) \ _(XrSpaceContainerFB, XR_TYPE_SPACE_CONTAINER_FB) \ _(XrPassthroughKeyboardHandsIntensityFB, XR_TYPE_PASSTHROUGH_KEYBOARD_HANDS_INTENSITY_FB) \ @@ -3071,6 +3131,7 @@ XR_ENUM_STR(XrResult); _(XR_VARJO_environment_depth_estimation, 124) \ _(XR_VARJO_marker_tracking, 125) \ _(XR_VARJO_view_offset, 126) \ + _(XR_ML_ml2_controller_interaction, 135) \ _(XR_MSFT_spatial_anchor_persistence, 143) \ _(XR_ULTRALEAP_hand_tracking_forearm, 150) \ _(XR_FB_spatial_entity_query, 157) \ @@ -3082,6 +3143,8 @@ XR_ENUM_STR(XrResult); _(XR_FB_swapchain_update_state_vulkan, 164) \ _(XR_KHR_swapchain_usage_input_attachment_bit, 166) \ _(XR_FB_space_warp, 172) \ + _(XR_FB_scene, 176) \ + _(XR_EXT_palm_pose, 177) \ _(XR_ALMALENCE_digital_lens_control, 197) \ _(XR_FB_spatial_entity_container, 200) \ _(XR_FB_passthrough_keyboard_hands, 204) \ diff --git a/thirdparty/openxr/src/common/unique_asset.h b/thirdparty/openxr/src/common/unique_asset.h new file mode 100644 index 0000000000..4929039a03 --- /dev/null +++ b/thirdparty/openxr/src/common/unique_asset.h @@ -0,0 +1,33 @@ +// Copyright (c) 2017-2022, The Khronos Group Inc. +// +// SPDX-License-Identifier: Apache-2.0 OR MIT +#pragma once + +#ifdef XR_USE_PLATFORM_ANDROID + +#include <memory> +#include <android/asset_manager.h> + +namespace deleters { +struct AAssetDeleter { + void operator()(AAsset* asset) const noexcept { + if (asset != nullptr) { + AAsset_close(asset); + } + } +}; + +struct AAssetDirDeleter { + void operator()(AAssetDir* dir) const noexcept { + if (dir != nullptr) { + AAssetDir_close(dir); + } + } +}; + +} // namespace deleters + +using UniqueAsset = std::unique_ptr<AAsset, deleters::AAssetDeleter>; +using UniqueAssetDir = std::unique_ptr<AAssetDir, deleters::AAssetDirDeleter>; + +#endif diff --git a/thirdparty/openxr/src/loader/android_utilities.cpp b/thirdparty/openxr/src/loader/android_utilities.cpp index 807a775820..59d9a99b74 100644 --- a/thirdparty/openxr/src/loader/android_utilities.cpp +++ b/thirdparty/openxr/src/loader/android_utilities.cpp @@ -299,7 +299,7 @@ int getActiveRuntimeVirtualManifest(wrap::android::content::Context const &conte auto hasFunctions = cursor.getInt(cursor.getColumnIndex(active_runtime::Columns::HAS_FUNCTIONS)) == 1; __android_log_print(ANDROID_LOG_INFO, TAG, "Got runtime: package: %s, so filename: %s, native lib dir: %s, has functions: %s", - packageName.c_str(), libDir.c_str(), filename.c_str(), (hasFunctions ? "yes" : "no")); + packageName.c_str(), filename.c_str(), libDir.c_str(), (hasFunctions ? "yes" : "no")); auto lib_path = libDir + "/" + filename; cursor.close(); diff --git a/thirdparty/openxr/src/loader/api_layer_interface.cpp b/thirdparty/openxr/src/loader/api_layer_interface.cpp index c3fd5bb7f1..b946e09402 100644 --- a/thirdparty/openxr/src/loader/api_layer_interface.cpp +++ b/thirdparty/openxr/src/loader/api_layer_interface.cpp @@ -53,7 +53,6 @@ XrResult ApiLayerInterface::GetApiLayerProperties(const std::string& openxr_comm uint32_t* outgoing_count, XrApiLayerProperties* api_layer_properties) { std::vector<std::unique_ptr<ApiLayerManifestFile>> manifest_files; uint32_t manifest_count = 0; - // Validate props struct before proceeding if (0 < incoming_count && nullptr != api_layer_properties) { for (uint32_t i = 0; i < incoming_count; i++) { diff --git a/thirdparty/openxr/src/loader/loader_core.cpp b/thirdparty/openxr/src/loader/loader_core.cpp index 375f1c93ba..a8bbfb4de2 100644 --- a/thirdparty/openxr/src/loader/loader_core.cpp +++ b/thirdparty/openxr/src/loader/loader_core.cpp @@ -711,9 +711,6 @@ XRLOADER_ABI_CATCH_FALLBACK XRAPI_ATTR XrResult XRAPI_CALL LoaderXrGetInstanceProcAddr(XrInstance instance, const char *name, PFN_xrVoidFunction *function) XRLOADER_ABI_TRY { - // Initialize the function to nullptr in case it does not get caught in a known case - *function = nullptr; - if (nullptr == function) { LoaderLogger::LogValidationErrorMessage("VUID-xrGetInstanceProcAddr-function-parameter", "xrGetInstanceProcAddr", "Invalid Function pointer"); @@ -726,6 +723,9 @@ XRAPI_ATTR XrResult XRAPI_CALL LoaderXrGetInstanceProcAddr(XrInstance instance, return XR_ERROR_VALIDATION_FAILURE; } + // Initialize the function to nullptr in case it does not get caught in a known case + *function = nullptr; + LoaderInstance *loader_instance = nullptr; if (instance == XR_NULL_HANDLE) { // Null instance is allowed for a few specific API entry points, otherwise return error diff --git a/thirdparty/openxr/src/loader/manifest_file.cpp b/thirdparty/openxr/src/loader/manifest_file.cpp index e4eab3949e..df99d51f8f 100644 --- a/thirdparty/openxr/src/loader/manifest_file.cpp +++ b/thirdparty/openxr/src/loader/manifest_file.cpp @@ -21,6 +21,7 @@ #include "loader_platform.hpp" #include "platform_utils.hpp" #include "loader_logger.hpp" +#include "unique_asset.h" #include <json/json.h> #include <openxr/openxr.h> @@ -50,6 +51,10 @@ #define SYSCONFDIR "/etc" #endif // !SYSCONFDIR +#ifdef XR_USE_PLATFORM_ANDROID +#include <android/asset_manager.h> +#endif + #ifdef XRLOADER_DISABLE_EXCEPTION_HANDLING #if JSON_USE_EXCEPTIONS #error \ @@ -656,17 +661,68 @@ ApiLayerManifestFile::ApiLayerManifestFile(ManifestFileType type, const std::str _description(description), _implementation_version(implementation_version) {} -void ApiLayerManifestFile::CreateIfValid(ManifestFileType type, const std::string &filename, - std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files) { - std::ifstream json_stream(filename, std::ifstream::in); +#ifdef XR_USE_PLATFORM_ANDROID +void ApiLayerManifestFile::AddManifestFilesAndroid(ManifestFileType type, + std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files) { + AAssetManager *assetManager = (AAssetManager *)Android_Get_Asset_Manager(); + std::vector<std::string> filenames; + { + std::string search_path = ""; + switch (type) { + case MANIFEST_TYPE_IMPLICIT_API_LAYER: + search_path = "openxr/1/api_layers/implicit.d/"; + break; + case MANIFEST_TYPE_EXPLICIT_API_LAYER: + search_path = "openxr/1/api_layers/explicit.d/"; + break; + default: + return; + } - std::ostringstream error_ss("ApiLayerManifestFile::CreateIfValid "); - if (!json_stream.is_open()) { - error_ss << "failed to open " << filename << ". Does it exist?"; - LoaderLogger::LogErrorMessage("", error_ss.str()); - return; + UniqueAssetDir dir{AAssetManager_openDir(assetManager, search_path.c_str())}; + if (!dir) { + return; + } + const std::string json = ".json"; + const char *fn = nullptr; + while ((fn = AAssetDir_getNextFileName(dir.get())) != nullptr) { + const std::string filename = search_path + fn; + if (filename.size() < json.size()) { + continue; + } + if (filename.compare(filename.size() - json.size(), json.size(), json) == 0) { + filenames.push_back(filename); + } + } } + for (const auto &filename : filenames) { + UniqueAsset asset{AAssetManager_open(assetManager, filename.c_str(), AASSET_MODE_BUFFER)}; + if (!asset) { + LoaderLogger::LogWarningMessage( + "", "ApiLayerManifestFile::AddManifestFilesAndroid unable to open asset " + filename + ", skipping"); + + continue; + } + size_t length = AAsset_getLength(asset.get()); + const char *buf = reinterpret_cast<const char *>(AAsset_getBuffer(asset.get())); + if (!buf) { + LoaderLogger::LogWarningMessage( + "", "ApiLayerManifestFile::AddManifestFilesAndroid unable to access asset" + filename + ", skipping"); + continue; + } + std::istringstream json_stream(std::string{buf, length}); + + CreateIfValid(ManifestFileType::MANIFEST_TYPE_EXPLICIT_API_LAYER, filename, json_stream, + &ApiLayerManifestFile::LocateLibraryInAssets, manifest_files); + } +} +#endif // XR_USE_PLATFORM_ANDROID + +void ApiLayerManifestFile::CreateIfValid(ManifestFileType type, const std::string &filename, std::istream &json_stream, + LibraryLocator locate_library, + std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files) { + std::ostringstream error_ss("ApiLayerManifestFile::CreateIfValid "); Json::CharReaderBuilder builder; std::string errors; Json::Value root_node = Json::nullValue; @@ -757,9 +813,7 @@ void ApiLayerManifestFile::CreateIfValid(ManifestFileType type, const std::strin } else { // Otherwise, treat the library path as a relative path based on the JSON file. std::string combined_path; - std::string file_parent; - if (!FileSysUtilsGetParentPath(filename, file_parent) || - !FileSysUtilsCombinePaths(file_parent, library_path, combined_path) || !FileSysUtilsPathExists(combined_path)) { + if (!locate_library(filename, library_path, combined_path)) { error_ss << filename << " library " << combined_path << " does not appear to exist"; LoaderLogger::LogErrorMessage("", error_ss.str()); return; @@ -781,6 +835,46 @@ void ApiLayerManifestFile::CreateIfValid(ManifestFileType type, const std::strin manifest_files.back()->ParseCommon(layer_root_node); } +void ApiLayerManifestFile::CreateIfValid(ManifestFileType type, const std::string &filename, + std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files) { + std::ifstream json_stream(filename, std::ifstream::in); + if (!json_stream.is_open()) { + std::ostringstream error_ss("ApiLayerManifestFile::CreateIfValid "); + error_ss << "failed to open " << filename << ". Does it exist?"; + LoaderLogger::LogErrorMessage("", error_ss.str()); + return; + } + CreateIfValid(type, filename, json_stream, &ApiLayerManifestFile::LocateLibraryRelativeToJson, manifest_files); +} + +bool ApiLayerManifestFile::LocateLibraryRelativeToJson( + const std::string &json_filename, const std::string &library_path, + std::string &out_combined_path) { // Otherwise, treat the library path as a relative path based on the JSON file. + std::string combined_path; + std::string file_parent; + if (!FileSysUtilsGetParentPath(json_filename, file_parent) || + !FileSysUtilsCombinePaths(file_parent, library_path, combined_path) || !FileSysUtilsPathExists(combined_path)) { + out_combined_path = combined_path; + return false; + } + out_combined_path = combined_path; + return true; +} + +#ifdef XR_USE_PLATFORM_ANDROID +bool ApiLayerManifestFile::LocateLibraryInAssets(const std::string & /* json_filename */, const std::string &library_path, + std::string &out_combined_path) { + std::string combined_path; + std::string file_parent = GetAndroidNativeLibraryDir(); + if (!FileSysUtilsCombinePaths(file_parent, library_path, combined_path) || !FileSysUtilsPathExists(combined_path)) { + out_combined_path = combined_path; + return false; + } + out_combined_path = combined_path; + return true; +} +#endif + void ApiLayerManifestFile::PopulateApiLayerProperties(XrApiLayerProperties &props) const { props.layerVersion = _implementation_version; props.specVersion = XR_MAKE_VERSION(_api_version.major, _api_version.minor, _api_version.patch); @@ -841,5 +935,9 @@ XrResult ApiLayerManifestFile::FindManifestFiles(ManifestFileType type, ApiLayerManifestFile::CreateIfValid(type, cur_file, manifest_files); } +#ifdef XR_USE_PLATFORM_ANDROID + ApiLayerManifestFile::AddManifestFilesAndroid(type, manifest_files); +#endif // XR_USE_PLATFORM_ANDROID + return XR_SUCCESS; } diff --git a/thirdparty/openxr/src/loader/manifest_file.hpp b/thirdparty/openxr/src/loader/manifest_file.hpp index 0d04886d84..de0aab65c2 100644 --- a/thirdparty/openxr/src/loader/manifest_file.hpp +++ b/thirdparty/openxr/src/loader/manifest_file.hpp @@ -14,6 +14,7 @@ #include <memory> #include <string> #include <vector> +#include <iosfwd> #include <unordered_map> namespace Json { @@ -79,6 +80,8 @@ class RuntimeManifestFile : public ManifestFile { std::vector<std::unique_ptr<RuntimeManifestFile>> &manifest_files); }; +using LibraryLocator = bool (*)(const std::string &json_filename, const std::string &library_path, std::string &out_combined_path); + // ApiLayerManifestFile class - // Responsible for finding and parsing API Layer-specific manifest files. class ApiLayerManifestFile : public ManifestFile { @@ -93,8 +96,19 @@ class ApiLayerManifestFile : public ManifestFile { ApiLayerManifestFile(ManifestFileType type, const std::string &filename, const std::string &layer_name, const std::string &description, const JsonVersion &api_version, const uint32_t &implementation_version, const std::string &library_path); + + static void CreateIfValid(ManifestFileType type, const std::string &filename, std::istream &json_stream, + LibraryLocator locate_library, std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files); static void CreateIfValid(ManifestFileType type, const std::string &filename, std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files); + /// @return false if we could not find the library. + static bool LocateLibraryRelativeToJson(const std::string &json_filename, const std::string &library_path, + std::string &out_combined_path); +#ifdef XR_USE_PLATFORM_ANDROID + static bool LocateLibraryInAssets(const std::string &json_filename, const std::string &library_path, + std::string &out_combined_path); + static void AddManifestFilesAndroid(ManifestFileType type, std::vector<std::unique_ptr<ApiLayerManifestFile>> &manifest_files); +#endif JsonVersion _api_version; std::string _layer_name; diff --git a/thirdparty/openxr/src/loader/runtime_interface.cpp b/thirdparty/openxr/src/loader/runtime_interface.cpp index 1a35ba013a..0f081ff9b2 100644 --- a/thirdparty/openxr/src/loader/runtime_interface.cpp +++ b/thirdparty/openxr/src/loader/runtime_interface.cpp @@ -27,6 +27,7 @@ #ifdef XR_USE_PLATFORM_ANDROID #include "android_utilities.h" +#include <android/asset_manager_jni.h> #include <json/value.h> #endif // XR_USE_PLATFORM_ANDROID @@ -50,6 +51,14 @@ class LoaderInitData { * Type alias for the platform-specific structure type. */ using StructType = XrLoaderInitInfoAndroidKHR; + /*! + * Native library path. + */ + std::string _native_library_path; + /*! + * Android asset manager. + */ + AAssetManager* _android_asset_manager; #endif /*! @@ -99,6 +108,30 @@ XrResult LoaderInitData::initialize(const XrLoaderInitInfoBaseHeaderKHR* info) { _data = *cast_info; jni::init((jni::JavaVM*)_data.applicationVM); _data.next = nullptr; + JNIEnv* Env; + ((jni::JavaVM*)(cast_info->applicationVM))->AttachCurrentThread(&Env, nullptr); + const jclass contextClass = Env->GetObjectClass((jobject)_data.applicationContext); + + const jmethodID getAssetsMethod = Env->GetMethodID(contextClass, "getAssets", "()Landroid/content/res/AssetManager;"); + const jobject AssetManagerObject = Env->CallObjectMethod((jobject)_data.applicationContext, getAssetsMethod); + _android_asset_manager = AAssetManager_fromJava(Env, AssetManagerObject); + + const jmethodID getApplicationContextMethod = + Env->GetMethodID(contextClass, "getApplicationContext", "()Landroid/content/Context;"); + const jobject contextObject = Env->CallObjectMethod((jobject)_data.applicationContext, getApplicationContextMethod); + const jmethodID getApplicationInfoMethod = + Env->GetMethodID(contextClass, "getApplicationInfo", "()Landroid/content/pm/ApplicationInfo;"); + const jobject applicationInfoObject = Env->CallObjectMethod(contextObject, getApplicationInfoMethod); + const jfieldID nativeLibraryDirField = + Env->GetFieldID(Env->GetObjectClass(applicationInfoObject), "nativeLibraryDir", "Ljava/lang/String;"); + const jobject nativeLibraryDirObject = Env->GetObjectField(applicationInfoObject, nativeLibraryDirField); + const jmethodID getBytesMethod = + Env->GetMethodID(Env->GetObjectClass(nativeLibraryDirObject), "getBytes", "(Ljava/lang/String;)[B"); + const auto bytesObject = + static_cast<jbyteArray>(Env->CallObjectMethod(nativeLibraryDirObject, getBytesMethod, Env->NewStringUTF("UTF-8"))); + const size_t length = Env->GetArrayLength(bytesObject); + const jbyte* const bytes = Env->GetByteArrayElements(bytesObject, nullptr); + _native_library_path = std::string(reinterpret_cast<const char*>(bytes), length); _initialized = true; return XR_SUCCESS; } @@ -109,6 +142,10 @@ XrResult InitializeLoader(const XrLoaderInitInfoBaseHeaderKHR* loaderInitInfo) { return LoaderInitData::instance().initialize(loaderInitInfo); } +std::string GetAndroidNativeLibraryDir() { return LoaderInitData::instance()._native_library_path; } + +void* Android_Get_Asset_Manager() { return LoaderInitData::instance()._android_asset_manager; } + #endif // XR_KHR_LOADER_INIT_SUPPORT #ifdef XR_USE_PLATFORM_ANDROID diff --git a/thirdparty/openxr/src/loader/runtime_interface.hpp b/thirdparty/openxr/src/loader/runtime_interface.hpp index 5f49b28abe..fa53ee03f2 100644 --- a/thirdparty/openxr/src/loader/runtime_interface.hpp +++ b/thirdparty/openxr/src/loader/runtime_interface.hpp @@ -31,6 +31,8 @@ class Value; //! Initialize loader, where required. XrResult InitializeLoader(const XrLoaderInitInfoBaseHeaderKHR* loaderInitInfo); XrResult GetPlatformRuntimeVirtualManifest(Json::Value& out_manifest); +std::string GetAndroidNativeLibraryDir(); +void* Android_Get_Asset_Manager(); #endif class RuntimeManifestFile; diff --git a/thirdparty/thorvg/inc/config.h b/thirdparty/thorvg/inc/config.h index 879b70442b..68935c583b 100644 --- a/thirdparty/thorvg/inc/config.h +++ b/thirdparty/thorvg/inc/config.h @@ -13,5 +13,5 @@ #define THORVG_JPG_LOADER_SUPPORT 1 -#define THORVG_VERSION_STRING "0.8.1" +#define THORVG_VERSION_STRING "0.8.2" #endif diff --git a/thirdparty/thorvg/src/lib/sw_engine/tvgSwCommon.h b/thirdparty/thorvg/src/lib/sw_engine/tvgSwCommon.h index 47b0cb83f5..157fdb8f82 100644 --- a/thirdparty/thorvg/src/lib/sw_engine/tvgSwCommon.h +++ b/thirdparty/thorvg/src/lib/sw_engine/tvgSwCommon.h @@ -1,4 +1,4 @@ -/* +/* * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. * Permission is hereby granted, free of charge, to any person obtaining a copy diff --git a/thirdparty/thorvg/src/lib/sw_engine/tvgSwFill.cpp b/thirdparty/thorvg/src/lib/sw_engine/tvgSwFill.cpp index bba6f26a0b..04014a9ec3 100644 --- a/thirdparty/thorvg/src/lib/sw_engine/tvgSwFill.cpp +++ b/thirdparty/thorvg/src/lib/sw_engine/tvgSwFill.cpp @@ -1,4 +1,4 @@ -/* +/* * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. * Permission is hereby granted, free of charge, to any person obtaining a copy diff --git a/thirdparty/thorvg/src/lib/sw_engine/tvgSwMath.cpp b/thirdparty/thorvg/src/lib/sw_engine/tvgSwMath.cpp index ced66ae35c..1027bb1f79 100644 --- a/thirdparty/thorvg/src/lib/sw_engine/tvgSwMath.cpp +++ b/thirdparty/thorvg/src/lib/sw_engine/tvgSwMath.cpp @@ -1,4 +1,4 @@ -/* +/* * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. * Permission is hereby granted, free of charge, to any person obtaining a copy diff --git a/thirdparty/thorvg/src/lib/sw_engine/tvgSwRaster.cpp b/thirdparty/thorvg/src/lib/sw_engine/tvgSwRaster.cpp index 810df8d435..bf1c10a0c3 100644 --- a/thirdparty/thorvg/src/lib/sw_engine/tvgSwRaster.cpp +++ b/thirdparty/thorvg/src/lib/sw_engine/tvgSwRaster.cpp @@ -1,4 +1,4 @@ -/* +/* * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. * Permission is hereby granted, free of charge, to any person obtaining a copy @@ -22,8 +22,8 @@ #ifdef _WIN32 #include <malloc.h> -#elif defined(__FreeBSD__) - #include <stdlib.h> +#elif __FreeBSD__ + #include<stdlib.h> #else #include <alloca.h> #endif diff --git a/thirdparty/thorvg/src/lib/sw_engine/tvgSwStroke.cpp b/thirdparty/thorvg/src/lib/sw_engine/tvgSwStroke.cpp index be4392740e..fa213cc5d3 100644 --- a/thirdparty/thorvg/src/lib/sw_engine/tvgSwStroke.cpp +++ b/thirdparty/thorvg/src/lib/sw_engine/tvgSwStroke.cpp @@ -1,4 +1,4 @@ -/* +/* * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. * Permission is hereby granted, free of charge, to any person obtaining a copy diff --git a/thirdparty/thorvg/src/loaders/external_jpg/tvgJpgLoader.cpp b/thirdparty/thorvg/src/loaders/external_jpg/tvgJpgLoader.cpp deleted file mode 100644 index 522c3c71a6..0000000000 --- a/thirdparty/thorvg/src/loaders/external_jpg/tvgJpgLoader.cpp +++ /dev/null @@ -1,164 +0,0 @@ -/* - * Copyright (c) 2021 - 2022 Samsung Electronics Co., Ltd. All rights reserved. - - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ - -#include <memory.h> -#include <turbojpeg.h> -#include "tvgLoader.h" -#include "tvgJpgLoader.h" - -/************************************************************************/ -/* Internal Class Implementation */ -/************************************************************************/ - -void JpgLoader::clear() -{ - if (freeData) free(data); - data = nullptr; - size = 0; - freeData = false; -} - -/************************************************************************/ -/* External Class Implementation */ -/************************************************************************/ - -JpgLoader::JpgLoader() -{ - jpegDecompressor = tjInitDecompress(); -} - - -JpgLoader::~JpgLoader() -{ - if (freeData) free(data); - tjDestroy(jpegDecompressor); - - //This image is shared with raster engine. - tjFree(image); -} - - -bool JpgLoader::open(const string& path) -{ - clear(); - - auto jpegFile = fopen(path.c_str(), "rb"); - if (!jpegFile) return false; - - auto ret = false; - - //determine size - if (fseek(jpegFile, 0, SEEK_END) < 0) goto finalize; - if (((size = ftell(jpegFile)) < 1)) goto finalize; - if (fseek(jpegFile, 0, SEEK_SET)) goto finalize; - - data = (unsigned char *) malloc(size); - if (!data) goto finalize; - - freeData = true; - - if (fread(data, size, 1, jpegFile) < 1) goto failure; - - int width, height, subSample, colorSpace; - if (tjDecompressHeader3(jpegDecompressor, data, size, &width, &height, &subSample, &colorSpace) < 0) { - TVGERR("JPG LOADER", "%s", tjGetErrorStr()); - goto failure; - } - - w = static_cast<float>(width); - h = static_cast<float>(height); - ret = true; - - goto finalize; - -failure: - clear(); - -finalize: - fclose(jpegFile); - return ret; -} - - -bool JpgLoader::open(const char* data, uint32_t size, bool copy) -{ - clear(); - - int width, height, subSample, colorSpace; - if (tjDecompressHeader3(jpegDecompressor, (unsigned char *) data, size, &width, &height, &subSample, &colorSpace) < 0) return false; - - if (copy) { - this->data = (unsigned char *) malloc(size); - if (!this->data) return false; - memcpy((unsigned char *)this->data, data, size); - freeData = true; - } else { - this->data = (unsigned char *) data; - freeData = false; - } - - w = static_cast<float>(width); - h = static_cast<float>(height); - this->size = size; - - return true; -} - - -bool JpgLoader::read() -{ - if (image) tjFree(image); - image = (unsigned char *)tjAlloc(static_cast<int>(w) * static_cast<int>(h) * tjPixelSize[TJPF_BGRX]); - if (!image) return false; - - //decompress jpg image - if (tjDecompress2(jpegDecompressor, data, size, image, static_cast<int>(w), 0, static_cast<int>(h), TJPF_BGRX, 0) < 0) { - TVGERR("JPG LOADER", "%s", tjGetErrorStr()); - tjFree(image); - image = nullptr; - return false; - } - - return true; -} - - -bool JpgLoader::close() -{ - clear(); - return true; -} - - -unique_ptr<Surface> JpgLoader::bitmap() -{ - if (!image) return nullptr; - - auto surface = static_cast<Surface*>(malloc(sizeof(Surface))); - surface->buffer = (uint32_t*)(image); - surface->stride = w; - surface->w = w; - surface->h = h; - surface->cs = SwCanvas::ARGB8888; - - return unique_ptr<Surface>(surface); -} diff --git a/thirdparty/thorvg/src/loaders/external_jpg/tvgJpgLoader.h b/thirdparty/thorvg/src/loaders/external_jpg/tvgJpgLoader.h deleted file mode 100644 index 3f82af8003..0000000000 --- a/thirdparty/thorvg/src/loaders/external_jpg/tvgJpgLoader.h +++ /dev/null @@ -1,52 +0,0 @@ -/* - * Copyright (c) 2021 - 2022 Samsung Electronics Co., Ltd. All rights reserved. - - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ -#ifndef _TVG_JPG_LOADER_H_ -#define _TVG_JPG_LOADER_H_ - -using tjhandle = void*; - -//TODO: Use Task? -class JpgLoader : public LoadModule -{ -public: - JpgLoader(); - ~JpgLoader(); - - using LoadModule::open; - bool open(const string& path) override; - bool open(const char* data, uint32_t size, bool copy) override; - bool read() override; - bool close() override; - - unique_ptr<Surface> bitmap() override; - -private: - void clear(); - - tjhandle jpegDecompressor; - unsigned char* data = nullptr; - unsigned char *image = nullptr; - unsigned long size = 0; - bool freeData = false; -}; - -#endif //_TVG_JPG_LOADER_H_ diff --git a/thirdparty/thorvg/src/loaders/png/tvgLodePng.cpp b/thirdparty/thorvg/src/loaders/png/tvgLodePng.cpp deleted file mode 100644 index eaed025c54..0000000000 --- a/thirdparty/thorvg/src/loaders/png/tvgLodePng.cpp +++ /dev/null @@ -1,2647 +0,0 @@ -/* - * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. - - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ - -/* - LodePNG version 20200306 - - Copyright (c) 2005-2020 Lode Vandevenne - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - - 3. This notice may not be removed or altered from any sourcedistribution. -*/ - -#include <cstdlib> -#include "tvgLodePng.h" - - -/************************************************************************/ -/* Internal Class Implementation */ -/************************************************************************/ - -#if defined(_MSC_VER) && (_MSC_VER >= 1310) /*Visual Studio: A few warning types are not desired here.*/ - #pragma warning( disable : 4244 ) /*implicit conversions: not warned by gcc -Wall -Wextra and requires too much casts*/ - #pragma warning( disable : 4996 ) /*VS does not like fopen, but fopen_s is not standard C so unusable here*/ -#endif /*_MSC_VER */ - - -/* convince the compiler to inline a function, for use when this measurably improves performance */ -/* inline is not available in C90, but use it when supported by the compiler */ -#if (defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L)) || (defined(__cplusplus) && (__cplusplus >= 199711L)) - #define LODEPNG_INLINE inline -#else - #define LODEPNG_INLINE /* not available */ -#endif - -/* restrict is not available in C90, but use it when supported by the compiler */ -#if (defined(__GNUC__) && (__GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1))) ||\ - (defined(_MSC_VER) && (_MSC_VER >= 1400)) || \ - (defined(__WATCOMC__) && (__WATCOMC__ >= 1250) && !defined(__cplusplus)) - #define LODEPNG_RESTRICT __restrict -#else - #define LODEPNG_RESTRICT /* not available */ -#endif - -#define LODEPNG_MAX(a, b) (((a) > (b)) ? (a) : (b)) -#define LODEPNG_MIN(a, b) (((a) < (b)) ? (a) : (b)) -#define LODEPNG_ABS(x) ((x) < 0 ? -(x) : (x)) - - -/* Replacements for C library functions such as memcpy and strlen, to support platforms -where a full C library is not available. The compiler can recognize them and compile -to something as fast. */ - -static void lodepng_memcpy(void* LODEPNG_RESTRICT dst, const void* LODEPNG_RESTRICT src, size_t size) -{ - size_t i; - for (i = 0; i < size; i++) ((char*)dst)[i] = ((const char*)src)[i]; -} - - -static void lodepng_memset(void* LODEPNG_RESTRICT dst, int value, size_t num) -{ - size_t i; - for (i = 0; i < num; i++) ((char*)dst)[i] = (char)value; -} - - -/* does not check memory out of bounds, do not use on untrusted data */ -static size_t lodepng_strlen(const char* a) -{ - const char* orig = a; - /* avoid warning about unused function in case of disabled COMPILE... macros */ - (void)(&lodepng_strlen); - while (*a) a++; - return (size_t)(a - orig); -} - - -/* Safely check if adding two integers will overflow (no undefined -behavior, compiler removing the code, etc...) and output result. */ -static int lodepng_addofl(size_t a, size_t b, size_t* result) -{ - *result = a + b; /* Unsigned addition is well defined and safe in C90 */ - return *result < a; -} - - -/* Safely check if multiplying two integers will overflow (no undefined -behavior, compiler removing the code, etc...) and output result. */ -static int lodepng_mulofl(size_t a, size_t b, size_t* result) -{ - *result = a * b; /* Unsigned multiplication is well defined and safe in C90 */ - return (a != 0 && *result / a != b); -} - - -/* Safely check if a + b > c, even if overflow could happen. */ -static int lodepng_gtofl(size_t a, size_t b, size_t c) -{ - size_t d; - if (lodepng_addofl(a, b, &d)) return 1; - return d > c; -} - - -/* - Often in case of an error a value is assigned to a variable and then it breaks - out of a loop (to go to the cleanup phase of a function). This macro does that. - It makes the error handling code shorter and more readable. - - Example: if(!uivector_resize(&lz77_encoded, datasize)) ERROR_BREAK(83); -*/ -#define CERROR_BREAK(errorvar, code){\ - errorvar = code;\ - break;\ -} - -/* version of CERROR_BREAK that assumes the common case where the error variable is named "error" */ -#define ERROR_BREAK(code) CERROR_BREAK(error, code) - -/* Set error var to the error code, and return it.*/ -#define CERROR_RETURN_ERROR(errorvar, code){\ - errorvar = code;\ - return code;\ -} - -/* Try the code, if it returns error, also return the error. */ -#define CERROR_TRY_RETURN(call){\ - unsigned error = call;\ - if(error) return error;\ -} - -/* Set error var to the error code, and return from the void function. */ -#define CERROR_RETURN(errorvar, code){\ - errorvar = code;\ - return;\ -} - - -/* dynamic vector of unsigned chars */ -struct ucvector -{ - unsigned char* data; - size_t size; /*used size*/ - size_t allocsize; /*allocated size*/ -}; - - -/* returns 1 if success, 0 if failure ==> nothing done */ -static unsigned ucvector_resize(ucvector* p, size_t size) -{ - if (size > p->allocsize) { - size_t newsize = size + (p->allocsize >> 1u); - void* data = realloc(p->data, newsize); - if(data) { - p->allocsize = newsize; - p->data = (unsigned char*)data; - } - else return 0; /*error: not enough memory*/ - } - p->size = size; - return 1; /*success*/ -} - - -static ucvector ucvector_init(unsigned char* buffer, size_t size) -{ - ucvector v; - v.data = buffer; - v.allocsize = v.size = size; - return v; -} - - -static unsigned lodepng_read32bitInt(const unsigned char* buffer) -{ - return (((unsigned)buffer[0] << 24u) | ((unsigned)buffer[1] << 16u) | ((unsigned)buffer[2] << 8u) | (unsigned)buffer[3]); -} - - -/* ////////////////////////////////////////////////////////////////////////// */ -/* ////////////////////////////////////////////////////////////////////////// */ -/* // End of common code and tools. Begin of Zlib related code. // */ -/* ////////////////////////////////////////////////////////////////////////// */ -/* ////////////////////////////////////////////////////////////////////////// */ - -struct LodePNGBitReader -{ - const unsigned char* data; - size_t size; /*size of data in bytes*/ - size_t bitsize; /*size of data in bits, end of valid bp values, should be 8*size*/ - size_t bp; - unsigned buffer; /*buffer for reading bits. NOTE: 'unsigned' must support at least 32 bits*/ -}; - - -/* data size argument is in bytes. Returns error if size too large causing overflow */ -static unsigned LodePNGBitReader_init(LodePNGBitReader* reader, const unsigned char* data, size_t size) -{ - size_t temp; - reader->data = data; - reader->size = size; - /* size in bits, return error if overflow (if size_t is 32 bit this supports up to 500MB) */ - if (lodepng_mulofl(size, 8u, &reader->bitsize)) return 105; - /*ensure incremented bp can be compared to bitsize without overflow even when it would be incremented 32 too much and - trying to ensure 32 more bits*/ - if (lodepng_addofl(reader->bitsize, 64u, &temp)) return 105; - reader->bp = 0; - reader->buffer = 0; - return 0; /*ok*/ - } - -/* - ensureBits functions: - Ensures the reader can at least read nbits bits in one or more readBits calls, - safely even if not enough bits are available. - Returns 1 if there are enough bits available, 0 if not. -*/ - -/*See ensureBits documentation above. This one ensures exactly 1 bit */ -/*static unsigned ensureBits1(LodePNGBitReader* reader) { - if(reader->bp >= reader->bitsize) return 0; - reader->buffer = (unsigned)reader->data[reader->bp >> 3u] >> (reader->bp & 7u); - return 1; -}*/ - -/*See ensureBits documentation above. This one ensures up to 9 bits */ -static unsigned ensureBits9(LodePNGBitReader* reader, size_t nbits) -{ - size_t start = reader->bp >> 3u; - size_t size = reader->size; - if (start + 1u < size) { - reader->buffer = (unsigned)reader->data[start + 0] | ((unsigned)reader->data[start + 1] << 8u); - reader->buffer >>= (reader->bp & 7u); - return 1; - } else { - reader->buffer = 0; - if (start + 0u < size) reader->buffer |= reader->data[start + 0]; - reader->buffer >>= (reader->bp & 7u); - return reader->bp + nbits <= reader->bitsize; - } -} - - -/*See ensureBits documentation above. This one ensures up to 17 bits */ -static unsigned ensureBits17(LodePNGBitReader* reader, size_t nbits) -{ - size_t start = reader->bp >> 3u; - size_t size = reader->size; - if (start + 2u < size) { - reader->buffer = (unsigned)reader->data[start + 0] | ((unsigned)reader->data[start + 1] << 8u) | ((unsigned)reader->data[start + 2] << 16u); - reader->buffer >>= (reader->bp & 7u); - return 1; - } else { - reader->buffer = 0; - if (start + 0u < size) reader->buffer |= reader->data[start + 0]; - if (start + 1u < size) reader->buffer |= ((unsigned)reader->data[start + 1] << 8u); - reader->buffer >>= (reader->bp & 7u); - return reader->bp + nbits <= reader->bitsize; - } -} - - -/*See ensureBits documentation above. This one ensures up to 25 bits */ -static LODEPNG_INLINE unsigned ensureBits25(LodePNGBitReader* reader, size_t nbits) -{ - size_t start = reader->bp >> 3u; - size_t size = reader->size; - if (start + 3u < size) { - reader->buffer = (unsigned)reader->data[start + 0] | ((unsigned)reader->data[start + 1] << 8u) | ((unsigned)reader->data[start + 2] << 16u) | ((unsigned)reader->data[start + 3] << 24u); - reader->buffer >>= (reader->bp & 7u); - return 1; - } else { - reader->buffer = 0; - if (start + 0u < size) reader->buffer |= reader->data[start + 0]; - if (start + 1u < size) reader->buffer |= ((unsigned)reader->data[start + 1] << 8u); - if (start + 2u < size) reader->buffer |= ((unsigned)reader->data[start + 2] << 16u); - reader->buffer >>= (reader->bp & 7u); - return reader->bp + nbits <= reader->bitsize; - } -} - - -/*See ensureBits documentation above. This one ensures up to 32 bits */ -static LODEPNG_INLINE unsigned ensureBits32(LodePNGBitReader* reader, size_t nbits) -{ - size_t start = reader->bp >> 3u; - size_t size = reader->size; - if(start + 4u < size) { - reader->buffer = (unsigned)reader->data[start + 0] | ((unsigned)reader->data[start + 1] << 8u) | ((unsigned)reader->data[start + 2] << 16u) | ((unsigned)reader->data[start + 3] << 24u); - reader->buffer >>= (reader->bp & 7u); - reader->buffer |= (((unsigned)reader->data[start + 4] << 24u) << (8u - (reader->bp & 7u))); - return 1; - } else { - reader->buffer = 0; - if (start + 0u < size) reader->buffer |= reader->data[start + 0]; - if (start + 1u < size) reader->buffer |= ((unsigned)reader->data[start + 1] << 8u); - if (start + 2u < size) reader->buffer |= ((unsigned)reader->data[start + 2] << 16u); - if (start + 3u < size) reader->buffer |= ((unsigned)reader->data[start + 3] << 24u); - reader->buffer >>= (reader->bp & 7u); - return reader->bp + nbits <= reader->bitsize; - } -} - - -/* Get bits without advancing the bit pointer. Must have enough bits available with ensureBits. Max nbits is 31. */ -static unsigned peekBits(LodePNGBitReader* reader, size_t nbits) -{ - /* The shift allows nbits to be only up to 31. */ - return reader->buffer & ((1u << nbits) - 1u); -} - - -/* Must have enough bits available with ensureBits */ -static void advanceBits(LodePNGBitReader* reader, size_t nbits) -{ - reader->buffer >>= nbits; - reader->bp += nbits; -} - - -/* Must have enough bits available with ensureBits */ -static unsigned readBits(LodePNGBitReader* reader, size_t nbits) -{ - unsigned result = peekBits(reader, nbits); - advanceBits(reader, nbits); - return result; -} - - -/* Public for testing only. steps and result must have numsteps values. */ -unsigned lode_png_test_bitreader(const unsigned char* data, size_t size, size_t numsteps, const size_t* steps, unsigned* result) -{ - size_t i; - LodePNGBitReader reader; - unsigned error = LodePNGBitReader_init(&reader, data, size); - if (error) return 0; - for (i = 0; i < numsteps; i++) { - size_t step = steps[i]; - unsigned ok; - if (step > 25) ok = ensureBits32(&reader, step); - else if (step > 17) ok = ensureBits25(&reader, step); - else if (step > 9) ok = ensureBits17(&reader, step); - else ok = ensureBits9(&reader, step); - if (!ok) return 0; - result[i] = readBits(&reader, step); - } - return 1; -} - - -static unsigned reverseBits(unsigned bits, unsigned num) -{ - /*TODO: implement faster lookup table based version when needed*/ - unsigned i, result = 0; - for (i = 0; i < num; i++) result |= ((bits >> (num - i - 1u)) & 1u) << i; - return result; -} - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / Deflate - Huffman / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -#define FIRST_LENGTH_CODE_INDEX 257 -#define LAST_LENGTH_CODE_INDEX 285 -/*256 literals, the end code, some length codes, and 2 unused codes*/ -#define NUM_DEFLATE_CODE_SYMBOLS 288 -/*the distance codes have their own symbols, 30 used, 2 unused*/ -#define NUM_DISTANCE_SYMBOLS 32 -/*the code length codes. 0-15: code lengths, 16: copy previous 3-6 times, 17: 3-10 zeros, 18: 11-138 zeros*/ -#define NUM_CODE_LENGTH_CODES 19 - -/*the base lengths represented by codes 257-285*/ -static const unsigned LENGTHBASE[29] - = {3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 15, 17, 19, 23, 27, 31, 35, 43, 51, 59, - 67, 83, 99, 115, 131, 163, 195, 227, 258}; - -/*the extra bits used by codes 257-285 (added to base length)*/ -static const unsigned LENGTHEXTRA[29] - = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, - 4, 4, 4, 4, 5, 5, 5, 5, 0}; - -/*the base backwards distances (the bits of distance codes appear after length codes and use their own huffman tree)*/ -static const unsigned DISTANCEBASE[30] - = {1, 2, 3, 4, 5, 7, 9, 13, 17, 25, 33, 49, 65, 97, 129, 193, 257, 385, 513, - 769, 1025, 1537, 2049, 3073, 4097, 6145, 8193, 12289, 16385, 24577}; - -/*the extra bits of backwards distances (added to base)*/ -static const unsigned DISTANCEEXTRA[30] - = {0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, - 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13}; - -/*the order in which "code length alphabet code lengths" are stored as specified by deflate, out of this the huffman -tree of the dynamic huffman tree lengths is generated*/ -static const unsigned CLCL_ORDER[NUM_CODE_LENGTH_CODES] - = {16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15}; - -/* ////////////////////////////////////////////////////////////////////////// */ - -/* -Huffman tree struct, containing multiple representations of the tree -*/ -struct HuffmanTree -{ - unsigned* codes; /*the huffman codes (bit patterns representing the symbols)*/ - unsigned* lengths; /*the lengths of the huffman codes*/ - unsigned maxbitlen; /*maximum number of bits a single code can get*/ - unsigned numcodes; /*number of symbols in the alphabet = number of codes*/ - /* for reading only */ - unsigned char* table_len; /*length of symbol from lookup table, or max length if secondary lookup needed*/ - unsigned short* table_value; /*value of symbol from lookup table, or pointer to secondary table if needed*/ -}; - - -static void HuffmanTree_init(HuffmanTree* tree) -{ - tree->codes = 0; - tree->lengths = 0; - tree->table_len = 0; - tree->table_value = 0; -} - - -static void HuffmanTree_cleanup(HuffmanTree* tree) -{ - free(tree->codes); - free(tree->lengths); - free(tree->table_len); - free(tree->table_value); -} - - -/* amount of bits for first huffman table lookup (aka root bits), see HuffmanTree_makeTable and huffmanDecodeSymbol.*/ -/* values 8u and 9u work the fastest */ -#define FIRSTBITS 9u - -/* a symbol value too big to represent any valid symbol, to indicate reading disallowed huffman bits combination, -which is possible in case of only 0 or 1 present symbols. */ -#define INVALIDSYMBOL 65535u - -/* make table for huffman decoding */ -static unsigned HuffmanTree_makeTable(HuffmanTree* tree) -{ - static const unsigned headsize = 1u << FIRSTBITS; /*size of the first table*/ - static const unsigned mask = (1u << FIRSTBITS) /*headsize*/ - 1u; - size_t i, numpresent, pointer, size; /*total table size*/ - unsigned* maxlens = (unsigned*)malloc(headsize * sizeof(unsigned)); - if (!maxlens) return 83; /*alloc fail*/ - - /* compute maxlens: max total bit length of symbols sharing prefix in the first table*/ - lodepng_memset(maxlens, 0, headsize * sizeof(*maxlens)); - for (i = 0; i < tree->numcodes; i++) { - unsigned symbol = tree->codes[i]; - unsigned l = tree->lengths[i]; - unsigned index; - if(l <= FIRSTBITS) continue; /*symbols that fit in first table don't increase secondary table size*/ - /*get the FIRSTBITS MSBs, the MSBs of the symbol are encoded first. See later comment about the reversing*/ - index = reverseBits(symbol >> (l - FIRSTBITS), FIRSTBITS); - maxlens[index] = LODEPNG_MAX(maxlens[index], l); - } - /* compute total table size: size of first table plus all secondary tables for symbols longer than FIRSTBITS */ - size = headsize; - for (i = 0; i < headsize; ++i) { - unsigned l = maxlens[i]; - if (l > FIRSTBITS) size += (1u << (l - FIRSTBITS)); - } - tree->table_len = (unsigned char*)malloc(size * sizeof(*tree->table_len)); - tree->table_value = (unsigned short*)malloc(size * sizeof(*tree->table_value)); - if (!tree->table_len || !tree->table_value) { - free(maxlens); - /* freeing tree->table values is done at a higher scope */ - return 83; /*alloc fail*/ - } - /*initialize with an invalid length to indicate unused entries*/ - for (i = 0; i < size; ++i) tree->table_len[i] = 16; - - /*fill in the first table for long symbols: max prefix size and pointer to secondary tables*/ - pointer = headsize; - for (i = 0; i < headsize; ++i) { - unsigned l = maxlens[i]; - if(l <= FIRSTBITS) continue; - tree->table_len[i] = l; - tree->table_value[i] = pointer; - pointer += (1u << (l - FIRSTBITS)); - } - free(maxlens); - - /*fill in the first table for short symbols, or secondary table for long symbols*/ - numpresent = 0; - for (i = 0; i < tree->numcodes; ++i) { - unsigned l = tree->lengths[i]; - unsigned symbol = tree->codes[i]; /*the huffman bit pattern. i itself is the value.*/ - /*reverse bits, because the huffman bits are given in MSB first order but the bit reader reads LSB first*/ - unsigned reverse = reverseBits(symbol, l); - if (l == 0) continue; - numpresent++; - - if (l <= FIRSTBITS) { - /*short symbol, fully in first table, replicated num times if l < FIRSTBITS*/ - unsigned num = 1u << (FIRSTBITS - l); - unsigned j; - for (j = 0; j < num; ++j) { - /*bit reader will read the l bits of symbol first, the remaining FIRSTBITS - l bits go to the MSB's*/ - unsigned index = reverse | (j << l); - if(tree->table_len[index] != 16) return 55; /*invalid tree: long symbol shares prefix with short symbol*/ - tree->table_len[index] = l; - tree->table_value[index] = i; - } - } else { - /*long symbol, shares prefix with other long symbols in first lookup table, needs second lookup*/ - /*the FIRSTBITS MSBs of the symbol are the first table index*/ - unsigned index = reverse & mask; - unsigned maxlen = tree->table_len[index]; - /*log2 of secondary table length, should be >= l - FIRSTBITS*/ - unsigned tablelen = maxlen - FIRSTBITS; - unsigned start = tree->table_value[index]; /*starting index in secondary table*/ - unsigned num = 1u << (tablelen - (l - FIRSTBITS)); /*amount of entries of this symbol in secondary table*/ - unsigned j; - if (maxlen < l) return 55; /*invalid tree: long symbol shares prefix with short symbol*/ - for (j = 0; j < num; ++j) { - unsigned reverse2 = reverse >> FIRSTBITS; /* l - FIRSTBITS bits */ - unsigned index2 = start + (reverse2 | (j << (l - FIRSTBITS))); - tree->table_len[index2] = l; - tree->table_value[index2] = i; - } - } - } - - if (numpresent < 2) { - /* In case of exactly 1 symbol, in theory the huffman symbol needs 0 bits, - but deflate uses 1 bit instead. In case of 0 symbols, no symbols can - appear at all, but such huffman tree could still exist (e.g. if distance - codes are never used). In both cases, not all symbols of the table will be - filled in. Fill them in with an invalid symbol value so returning them from - huffmanDecodeSymbol will cause error. */ - for (i = 0; i < size; ++i) { - if (tree->table_len[i] == 16) { - /* As length, use a value smaller than FIRSTBITS for the head table, - and a value larger than FIRSTBITS for the secondary table, to ensure - valid behavior for advanceBits when reading this symbol. */ - tree->table_len[i] = (i < headsize) ? 1 : (FIRSTBITS + 1); - tree->table_value[i] = INVALIDSYMBOL; - } - } - } else { - /* A good huffman tree has N * 2 - 1 nodes, of which N - 1 are internal nodes. - If that is not the case (due to too long length codes), the table will not - have been fully used, and this is an error (not all bit combinations can be - decoded): an oversubscribed huffman tree, indicated by error 55. */ - for (i = 0; i < size; ++i) { - if (tree->table_len[i] == 16) return 55; - } - } - return 0; -} - - -/* - Second step for the ...makeFromLengths and ...makeFromFrequencies functions. - numcodes, lengths and maxbitlen must already be filled in correctly. return - value is error. -*/ -static unsigned HuffmanTree_makeFromLengths2(HuffmanTree* tree) -{ - unsigned* blcount; - unsigned* nextcode; - unsigned error = 0; - unsigned bits, n; - - tree->codes = (unsigned*)malloc(tree->numcodes * sizeof(unsigned)); - blcount = (unsigned*)malloc((tree->maxbitlen + 1) * sizeof(unsigned)); - nextcode = (unsigned*)malloc((tree->maxbitlen + 1) * sizeof(unsigned)); - if (!tree->codes || !blcount || !nextcode) error = 83; /*alloc fail*/ - - if (!error) { - for (n = 0; n != tree->maxbitlen + 1; n++) blcount[n] = nextcode[n] = 0; - /*step 1: count number of instances of each code length*/ - for (bits = 0; bits != tree->numcodes; ++bits) ++blcount[tree->lengths[bits]]; - /*step 2: generate the nextcode values*/ - for(bits = 1; bits <= tree->maxbitlen; ++bits) { - nextcode[bits] = (nextcode[bits - 1] + blcount[bits - 1]) << 1u; - } - /*step 3: generate all the codes*/ - for (n = 0; n != tree->numcodes; ++n) { - if (tree->lengths[n] != 0) { - tree->codes[n] = nextcode[tree->lengths[n]]++; - /*remove superfluous bits from the code*/ - tree->codes[n] &= ((1u << tree->lengths[n]) - 1u); - } - } - } - - free(blcount); - free(nextcode); - - if (!error) error = HuffmanTree_makeTable(tree); - return error; -} - - -/* - given the code lengths (as stored in the PNG file), generate the tree as defined - by Deflate. maxbitlen is the maximum bits that a code in the tree can have. - return value is error. -*/ -static unsigned HuffmanTree_makeFromLengths(HuffmanTree* tree, const unsigned* bitlen, size_t numcodes, unsigned maxbitlen) -{ - unsigned i; - tree->lengths = (unsigned*)malloc(numcodes * sizeof(unsigned)); - if (!tree->lengths) return 83; /*alloc fail*/ - for (i = 0; i != numcodes; ++i) tree->lengths[i] = bitlen[i]; - tree->numcodes = (unsigned)numcodes; /*number of symbols*/ - tree->maxbitlen = maxbitlen; - return HuffmanTree_makeFromLengths2(tree); -} - - -/*get the literal and length code tree of a deflated block with fixed tree, as per the deflate specification*/ -static unsigned generateFixedLitLenTree(HuffmanTree* tree) -{ - unsigned i, error = 0; - unsigned* bitlen = (unsigned*)malloc(NUM_DEFLATE_CODE_SYMBOLS * sizeof(unsigned)); - if (!bitlen) return 83; /*alloc fail*/ - - /*288 possible codes: 0-255=literals, 256=endcode, 257-285=lengthcodes, 286-287=unused*/ - for (i = 0; i <= 143; ++i) bitlen[i] = 8; - for (i = 144; i <= 255; ++i) bitlen[i] = 9; - for (i = 256; i <= 279; ++i) bitlen[i] = 7; - for (i = 280; i <= 287; ++i) bitlen[i] = 8; - - error = HuffmanTree_makeFromLengths(tree, bitlen, NUM_DEFLATE_CODE_SYMBOLS, 15); - - free(bitlen); - return error; -} - - -/*get the distance code tree of a deflated block with fixed tree, as specified in the deflate specification*/ -static unsigned generateFixedDistanceTree(HuffmanTree* tree) -{ - unsigned i, error = 0; - unsigned* bitlen = (unsigned*)malloc(NUM_DISTANCE_SYMBOLS * sizeof(unsigned)); - if (!bitlen) return 83; /*alloc fail*/ - - /*there are 32 distance codes, but 30-31 are unused*/ - for (i = 0; i != NUM_DISTANCE_SYMBOLS; ++i) bitlen[i] = 5; - error = HuffmanTree_makeFromLengths(tree, bitlen, NUM_DISTANCE_SYMBOLS, 15); - - free(bitlen); - return error; -} - - -/* - returns the code. The bit reader must already have been ensured at least 15 bits -*/ -static unsigned huffmanDecodeSymbol(LodePNGBitReader* reader, const HuffmanTree* codetree) -{ - unsigned short code = peekBits(reader, FIRSTBITS); - unsigned short l = codetree->table_len[code]; - unsigned short value = codetree->table_value[code]; - if (l <= FIRSTBITS) { - advanceBits(reader, l); - return value; - } else { - unsigned index2; - advanceBits(reader, FIRSTBITS); - index2 = value + peekBits(reader, l - FIRSTBITS); - advanceBits(reader, codetree->table_len[index2] - FIRSTBITS); - return codetree->table_value[index2]; - } -} - - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / Inflator (Decompressor) / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -/*get the tree of a deflated block with fixed tree, as specified in the deflate specification -Returns error code.*/ -static unsigned getTreeInflateFixed(HuffmanTree* tree_ll, HuffmanTree* tree_d) -{ - unsigned error = generateFixedLitLenTree(tree_ll); - if (error) return error; - return generateFixedDistanceTree(tree_d); -} - - -/*get the tree of a deflated block with dynamic tree, the tree itself is also Huffman compressed with a known tree*/ -static unsigned getTreeInflateDynamic(HuffmanTree* tree_ll, HuffmanTree* tree_d, LodePNGBitReader* reader) -{ - /*make sure that length values that aren't filled in will be 0, or a wrong tree will be generated*/ - unsigned error = 0; - unsigned n, HLIT, HDIST, HCLEN, i; - - /*see comments in deflateDynamic for explanation of the context and these variables, it is analogous*/ - unsigned* bitlen_ll = 0; /*lit,len code lengths*/ - unsigned* bitlen_d = 0; /*dist code lengths*/ - /*code length code lengths ("clcl"), the bit lengths of the huffman tree used to compress bitlen_ll and bitlen_d*/ - unsigned* bitlen_cl = 0; - HuffmanTree tree_cl; /*the code tree for code length codes (the huffman tree for compressed huffman trees)*/ - - if (!ensureBits17(reader, 14)) return 49; /*error: the bit pointer is or will go past the memory*/ - - /*number of literal/length codes + 257. Unlike the spec, the value 257 is added to it here already*/ - HLIT = readBits(reader, 5) + 257; - /*number of distance codes. Unlike the spec, the value 1 is added to it here already*/ - HDIST = readBits(reader, 5) + 1; - /*number of code length codes. Unlike the spec, the value 4 is added to it here already*/ - HCLEN = readBits(reader, 4) + 4; - - bitlen_cl = (unsigned*)malloc(NUM_CODE_LENGTH_CODES * sizeof(unsigned)); - if(!bitlen_cl) return 83 /*alloc fail*/; - - HuffmanTree_init(&tree_cl); - - while (!error) { - /*read the code length codes out of 3 * (amount of code length codes) bits*/ - if (lodepng_gtofl(reader->bp, HCLEN * 3, reader->bitsize)) { - ERROR_BREAK(50); /*error: the bit pointer is or will go past the memory*/ - } - for (i = 0; i != HCLEN; ++i) { - ensureBits9(reader, 3); /*out of bounds already checked above */ - bitlen_cl[CLCL_ORDER[i]] = readBits(reader, 3); - } - for (i = HCLEN; i != NUM_CODE_LENGTH_CODES; ++i) { - bitlen_cl[CLCL_ORDER[i]] = 0; - } - - error = HuffmanTree_makeFromLengths(&tree_cl, bitlen_cl, NUM_CODE_LENGTH_CODES, 7); - if(error) break; - - /*now we can use this tree to read the lengths for the tree that this function will return*/ - bitlen_ll = (unsigned*)malloc(NUM_DEFLATE_CODE_SYMBOLS * sizeof(unsigned)); - bitlen_d = (unsigned*)malloc(NUM_DISTANCE_SYMBOLS * sizeof(unsigned)); - if (!bitlen_ll || !bitlen_d) ERROR_BREAK(83 /*alloc fail*/); - lodepng_memset(bitlen_ll, 0, NUM_DEFLATE_CODE_SYMBOLS * sizeof(*bitlen_ll)); - lodepng_memset(bitlen_d, 0, NUM_DISTANCE_SYMBOLS * sizeof(*bitlen_d)); - - /*i is the current symbol we're reading in the part that contains the code lengths of lit/len and dist codes*/ - i = 0; - while (i < HLIT + HDIST) { - unsigned code; - ensureBits25(reader, 22); /* up to 15 bits for huffman code, up to 7 extra bits below*/ - code = huffmanDecodeSymbol(reader, &tree_cl); - if (code <= 15) /*a length code*/ { - if (i < HLIT) bitlen_ll[i] = code; - else bitlen_d[i - HLIT] = code; - ++i; - } else if (code == 16) /*repeat previous*/ { - unsigned replength = 3; /*read in the 2 bits that indicate repeat length (3-6)*/ - unsigned value; /*set value to the previous code*/ - - if (i == 0) ERROR_BREAK(54); /*can't repeat previous if i is 0*/ - - replength += readBits(reader, 2); - - if (i < HLIT + 1) value = bitlen_ll[i - 1]; - else value = bitlen_d[i - HLIT - 1]; - /*repeat this value in the next lengths*/ - for (n = 0; n < replength; ++n) { - if (i >= HLIT + HDIST) ERROR_BREAK(13); /*error: i is larger than the amount of codes*/ - if (i < HLIT) bitlen_ll[i] = value; - else bitlen_d[i - HLIT] = value; - ++i; - } - } else if(code == 17) /*repeat "0" 3-10 times*/ { - unsigned replength = 3; /*read in the bits that indicate repeat length*/ - replength += readBits(reader, 3); - - /*repeat this value in the next lengths*/ - for (n = 0; n < replength; ++n) { - if (i >= HLIT + HDIST) ERROR_BREAK(14); /*error: i is larger than the amount of codes*/ - - if (i < HLIT) bitlen_ll[i] = 0; - else bitlen_d[i - HLIT] = 0; - ++i; - } - } else if(code == 18) /*repeat "0" 11-138 times*/ { - unsigned replength = 11; /*read in the bits that indicate repeat length*/ - replength += readBits(reader, 7); - - /*repeat this value in the next lengths*/ - for (n = 0; n < replength; ++n) { - if(i >= HLIT + HDIST) ERROR_BREAK(15); /*error: i is larger than the amount of codes*/ - - if(i < HLIT) bitlen_ll[i] = 0; - else bitlen_d[i - HLIT] = 0; - ++i; - } - } else /*if(code == INVALIDSYMBOL)*/ { - ERROR_BREAK(16); /*error: tried to read disallowed huffman symbol*/ - } - /*check if any of the ensureBits above went out of bounds*/ - if (reader->bp > reader->bitsize) { - /*return error code 10 or 11 depending on the situation that happened in huffmanDecodeSymbol - (10=no endcode, 11=wrong jump outside of tree)*/ - /* TODO: revise error codes 10,11,50: the above comment is no longer valid */ - ERROR_BREAK(50); /*error, bit pointer jumps past memory*/ - } - } - if (error) break; - - if (bitlen_ll[256] == 0) ERROR_BREAK(64); /*the length of the end code 256 must be larger than 0*/ - - /*now we've finally got HLIT and HDIST, so generate the code trees, and the function is done*/ - error = HuffmanTree_makeFromLengths(tree_ll, bitlen_ll, NUM_DEFLATE_CODE_SYMBOLS, 15); - if (error) break; - error = HuffmanTree_makeFromLengths(tree_d, bitlen_d, NUM_DISTANCE_SYMBOLS, 15); - - break; /*end of error-while*/ - } - - free(bitlen_cl); - free(bitlen_ll); - free(bitlen_d); - HuffmanTree_cleanup(&tree_cl); - - return error; -} - - -/*inflate a block with dynamic of fixed Huffman tree. btype must be 1 or 2.*/ -static unsigned inflateHuffmanBlock(ucvector* out, LodePNGBitReader* reader, unsigned btype) -{ - unsigned error = 0; - HuffmanTree tree_ll; /*the huffman tree for literal and length codes*/ - HuffmanTree tree_d; /*the huffman tree for distance codes*/ - - HuffmanTree_init(&tree_ll); - HuffmanTree_init(&tree_d); - - if (btype == 1) error = getTreeInflateFixed(&tree_ll, &tree_d); - else /*if(btype == 2)*/ error = getTreeInflateDynamic(&tree_ll, &tree_d, reader); - - while (!error) /*decode all symbols until end reached, breaks at end code*/ { - /*code_ll is literal, length or end code*/ - unsigned code_ll; - ensureBits25(reader, 20); /* up to 15 for the huffman symbol, up to 5 for the length extra bits */ - code_ll = huffmanDecodeSymbol(reader, &tree_ll); - if (code_ll <= 255) /*literal symbol*/ { - if (!ucvector_resize(out, out->size + 1)) ERROR_BREAK(83 /*alloc fail*/); - out->data[out->size - 1] = (unsigned char)code_ll; - } else if (code_ll >= FIRST_LENGTH_CODE_INDEX && code_ll <= LAST_LENGTH_CODE_INDEX) /*length code*/ { - unsigned code_d, distance; - unsigned numextrabits_l, numextrabits_d; /*extra bits for length and distance*/ - size_t start, backward, length; - - /*part 1: get length base*/ - length = LENGTHBASE[code_ll - FIRST_LENGTH_CODE_INDEX]; - - /*part 2: get extra bits and add the value of that to length*/ - numextrabits_l = LENGTHEXTRA[code_ll - FIRST_LENGTH_CODE_INDEX]; - if (numextrabits_l != 0) { - /* bits already ensured above */ - length += readBits(reader, numextrabits_l); - } - - /*part 3: get distance code*/ - ensureBits32(reader, 28); /* up to 15 for the huffman symbol, up to 13 for the extra bits */ - code_d = huffmanDecodeSymbol(reader, &tree_d); - if (code_d > 29) { - if (code_d <= 31) { - ERROR_BREAK(18); /*error: invalid distance code (30-31 are never used)*/ - } else /* if(code_d == INVALIDSYMBOL) */{ - ERROR_BREAK(16); /*error: tried to read disallowed huffman symbol*/ - } - } - distance = DISTANCEBASE[code_d]; - - /*part 4: get extra bits from distance*/ - numextrabits_d = DISTANCEEXTRA[code_d]; - if (numextrabits_d != 0) { - /* bits already ensured above */ - distance += readBits(reader, numextrabits_d); - } - - /*part 5: fill in all the out[n] values based on the length and dist*/ - start = out->size; - if (distance > start) ERROR_BREAK(52); /*too long backward distance*/ - backward = start - distance; - - if (!ucvector_resize(out, out->size + length)) ERROR_BREAK(83 /*alloc fail*/); - if (distance < length) { - size_t forward; - lodepng_memcpy(out->data + start, out->data + backward, distance); - start += distance; - for (forward = distance; forward < length; ++forward) { - out->data[start++] = out->data[backward++]; - } - } else { - lodepng_memcpy(out->data + start, out->data + backward, length); - } - } else if (code_ll == 256) { - break; /*end code, break the loop*/ - } else /*if(code_ll == INVALIDSYMBOL)*/ { - ERROR_BREAK(16); /*error: tried to read disallowed huffman symbol*/ - } - /*check if any of the ensureBits above went out of bounds*/ - if (reader->bp > reader->bitsize) { - /*return error code 10 or 11 depending on the situation that happened in huffmanDecodeSymbol - (10=no endcode, 11=wrong jump outside of tree)*/ - /* TODO: revise error codes 10,11,50: the above comment is no longer valid */ - ERROR_BREAK(51); /*error, bit pointer jumps past memory*/ - } - } - - HuffmanTree_cleanup(&tree_ll); - HuffmanTree_cleanup(&tree_d); - - return error; -} - - -static unsigned inflateNoCompression(ucvector* out, LodePNGBitReader* reader, const LodePNGDecompressSettings* settings) -{ - size_t bytepos; - size_t size = reader->size; - unsigned LEN, NLEN, error = 0; - - /*go to first boundary of byte*/ - bytepos = (reader->bp + 7u) >> 3u; - - /*read LEN (2 bytes) and NLEN (2 bytes)*/ - if (bytepos + 4 >= size) return 52; /*error, bit pointer will jump past memory*/ - LEN = (unsigned)reader->data[bytepos] + ((unsigned)reader->data[bytepos + 1] << 8u); bytepos += 2; - NLEN = (unsigned)reader->data[bytepos] + ((unsigned)reader->data[bytepos + 1] << 8u); bytepos += 2; - - /*check if 16-bit NLEN is really the one's complement of LEN*/ - if (!settings->ignore_nlen && LEN + NLEN != 65535) { - return 21; /*error: NLEN is not one's complement of LEN*/ - } - - if (!ucvector_resize(out, out->size + LEN)) return 83; /*alloc fail*/ - - /*read the literal data: LEN bytes are now stored in the out buffer*/ - if (bytepos + LEN > size) return 23; /*error: reading outside of in buffer*/ - - lodepng_memcpy(out->data + out->size - LEN, reader->data + bytepos, LEN); - bytepos += LEN; - - reader->bp = bytepos << 3u; - - return error; -} - - -static unsigned lodepng_inflatev(ucvector* out, const unsigned char* in, size_t insize, const LodePNGDecompressSettings* settings) -{ - unsigned BFINAL = 0; - LodePNGBitReader reader; - unsigned error = LodePNGBitReader_init(&reader, in, insize); - - if (error) return error; - - while (!BFINAL) { - unsigned BTYPE; - if (!ensureBits9(&reader, 3)) return 52; /*error, bit pointer will jump past memory*/ - BFINAL = readBits(&reader, 1); - BTYPE = readBits(&reader, 2); - - if (BTYPE == 3) return 20; /*error: invalid BTYPE*/ - else if (BTYPE == 0) error = inflateNoCompression(out, &reader, settings); /*no compression*/ - else error = inflateHuffmanBlock(out, &reader, BTYPE); /*compression, BTYPE 01 or 10*/ - - if (error) return error; - } - - return error; -} - - -static unsigned inflatev(ucvector* out, const unsigned char* in, size_t insize, const LodePNGDecompressSettings* settings) -{ - if (settings->custom_inflate) { - unsigned error = settings->custom_inflate(&out->data, &out->size, in, insize, settings); - out->allocsize = out->size; - return error; - } else { - return lodepng_inflatev(out, in, insize, settings); - } -} - - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / Adler32 / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -static unsigned update_adler32(unsigned adler, const unsigned char* data, unsigned len) -{ - unsigned s1 = adler & 0xffffu; - unsigned s2 = (adler >> 16u) & 0xffffu; - - while (len != 0u) { - unsigned i; - /*at least 5552 sums can be done before the sums overflow, saving a lot of module divisions*/ - unsigned amount = len > 5552u ? 5552u : len; - len -= amount; - for (i = 0; i != amount; ++i) { - s1 += (*data++); - s2 += s1; - } - s1 %= 65521u; - s2 %= 65521u; - } - - return (s2 << 16u) | s1; -} - -/*Return the adler32 of the bytes data[0..len-1]*/ -static unsigned adler32(const unsigned char* data, unsigned len) -{ - return update_adler32(1u, data, len); -} - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / Zlib / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -static unsigned lodepng_zlib_decompressv(ucvector* out, const unsigned char* in, size_t insize, const LodePNGDecompressSettings* settings) -{ - unsigned error = 0; - unsigned CM, CINFO, FDICT; - - if (insize < 2) return 53; /*error, size of zlib data too small*/ - /*read information from zlib header*/ - if ((in[0] * 256 + in[1]) % 31 != 0) { - /*error: 256 * in[0] + in[1] must be a multiple of 31, the FCHECK value is supposed to be made that way*/ - return 24; - } - - CM = in[0] & 15; - CINFO = (in[0] >> 4) & 15; - /*FCHECK = in[1] & 31;*/ /*FCHECK is already tested above*/ - FDICT = (in[1] >> 5) & 1; - /*FLEVEL = (in[1] >> 6) & 3;*/ /*FLEVEL is not used here*/ - - if (CM != 8 || CINFO > 7) { - /*error: only compression method 8: inflate with sliding window of 32k is supported by the PNG spec*/ - return 25; - } - if (FDICT != 0) { - /*error: the specification of PNG says about the zlib stream: - "The additional flags shall not specify a preset dictionary."*/ - return 26; - } - - error = inflatev(out, in + 2, insize - 2, settings); - if (error) return error; - - if (!settings->ignore_adler32) { - unsigned ADLER32 = lodepng_read32bitInt(&in[insize - 4]); - unsigned checksum = adler32(out->data, (unsigned)(out->size)); - if(checksum != ADLER32) return 58; /*error, adler checksum not correct, data must be corrupted*/ - } - - return 0; /*no error*/ -} - - -/*expected_size is expected output size, to avoid intermediate allocations. Set to 0 if not known. */ -static unsigned zlib_decompress(unsigned char** out, size_t* outsize, size_t expected_size, const unsigned char* in, size_t insize, const LodePNGDecompressSettings* settings) -{ - if(settings->custom_zlib) { - return settings->custom_zlib(out, outsize, in, insize, settings); - } else { - unsigned error; - ucvector v = ucvector_init(*out, *outsize); - if (expected_size) { - /*reserve the memory to avoid intermediate reallocations*/ - ucvector_resize(&v, *outsize + expected_size); - v.size = *outsize; - } - error = lodepng_zlib_decompressv(&v, in, insize, settings); - *out = v.data; - *outsize = v.size; - return error; - } -} - - -static void lodepng_decompress_settings_init(LodePNGDecompressSettings* settings) -{ - settings->ignore_adler32 = 0; - settings->ignore_nlen = 0; - settings->custom_zlib = 0; - settings->custom_inflate = 0; - settings->custom_context = 0; -} - - -/* ////////////////////////////////////////////////////////////////////////// */ -/* ////////////////////////////////////////////////////////////////////////// */ -/* // End of Zlib related code. Begin of PNG related code. // */ -/* ////////////////////////////////////////////////////////////////////////// */ -/* ////////////////////////////////////////////////////////////////////////// */ - - -#if 0 //thorvg don't use crc -/* CRC polynomial: 0xedb88320 */ -static unsigned lodepng_crc32_table[256] = { - 0u, 1996959894u, 3993919788u, 2567524794u, 124634137u, 1886057615u, 3915621685u, 2657392035u, - 249268274u, 2044508324u, 3772115230u, 2547177864u, 162941995u, 2125561021u, 3887607047u, 2428444049u, - 498536548u, 1789927666u, 4089016648u, 2227061214u, 450548861u, 1843258603u, 4107580753u, 2211677639u, - 325883990u, 1684777152u, 4251122042u, 2321926636u, 335633487u, 1661365465u, 4195302755u, 2366115317u, - 997073096u, 1281953886u, 3579855332u, 2724688242u, 1006888145u, 1258607687u, 3524101629u, 2768942443u, - 901097722u, 1119000684u, 3686517206u, 2898065728u, 853044451u, 1172266101u, 3705015759u, 2882616665u, - 651767980u, 1373503546u, 3369554304u, 3218104598u, 565507253u, 1454621731u, 3485111705u, 3099436303u, - 671266974u, 1594198024u, 3322730930u, 2970347812u, 795835527u, 1483230225u, 3244367275u, 3060149565u, - 1994146192u, 31158534u, 2563907772u, 4023717930u, 1907459465u, 112637215u, 2680153253u, 3904427059u, - 2013776290u, 251722036u, 2517215374u, 3775830040u, 2137656763u, 141376813u, 2439277719u, 3865271297u, - 1802195444u, 476864866u, 2238001368u, 4066508878u, 1812370925u, 453092731u, 2181625025u, 4111451223u, - 1706088902u, 314042704u, 2344532202u, 4240017532u, 1658658271u, 366619977u, 2362670323u, 4224994405u, - 1303535960u, 984961486u, 2747007092u, 3569037538u, 1256170817u, 1037604311u, 2765210733u, 3554079995u, - 1131014506u, 879679996u, 2909243462u, 3663771856u, 1141124467u, 855842277u, 2852801631u, 3708648649u, - 1342533948u, 654459306u, 3188396048u, 3373015174u, 1466479909u, 544179635u, 3110523913u, 3462522015u, - 1591671054u, 702138776u, 2966460450u, 3352799412u, 1504918807u, 783551873u, 3082640443u, 3233442989u, - 3988292384u, 2596254646u, 62317068u, 1957810842u, 3939845945u, 2647816111u, 81470997u, 1943803523u, - 3814918930u, 2489596804u, 225274430u, 2053790376u, 3826175755u, 2466906013u, 167816743u, 2097651377u, - 4027552580u, 2265490386u, 503444072u, 1762050814u, 4150417245u, 2154129355u, 426522225u, 1852507879u, - 4275313526u, 2312317920u, 282753626u, 1742555852u, 4189708143u, 2394877945u, 397917763u, 1622183637u, - 3604390888u, 2714866558u, 953729732u, 1340076626u, 3518719985u, 2797360999u, 1068828381u, 1219638859u, - 3624741850u, 2936675148u, 906185462u, 1090812512u, 3747672003u, 2825379669u, 829329135u, 1181335161u, - 3412177804u, 3160834842u, 628085408u, 1382605366u, 3423369109u, 3138078467u, 570562233u, 1426400815u, - 3317316542u, 2998733608u, 733239954u, 1555261956u, 3268935591u, 3050360625u, 752459403u, 1541320221u, - 2607071920u, 3965973030u, 1969922972u, 40735498u, 2617837225u, 3943577151u, 1913087877u, 83908371u, - 2512341634u, 3803740692u, 2075208622u, 213261112u, 2463272603u, 3855990285u, 2094854071u, 198958881u, - 2262029012u, 4057260610u, 1759359992u, 534414190u, 2176718541u, 4139329115u, 1873836001u, 414664567u, - 2282248934u, 4279200368u, 1711684554u, 285281116u, 2405801727u, 4167216745u, 1634467795u, 376229701u, - 2685067896u, 3608007406u, 1308918612u, 956543938u, 2808555105u, 3495958263u, 1231636301u, 1047427035u, - 2932959818u, 3654703836u, 1088359270u, 936918000u, 2847714899u, 3736837829u, 1202900863u, 817233897u, - 3183342108u, 3401237130u, 1404277552u, 615818150u, 3134207493u, 3453421203u, 1423857449u, 601450431u, - 3009837614u, 3294710456u, 1567103746u, 711928724u, 3020668471u, 3272380065u, 1510334235u, 755167117u -}; - - -/* Calculate CRC32 of buffer - Return the CRC of the bytes buf[0..len-1]. */ -static unsigned lodepng_crc32(const unsigned char* data, size_t length) -{ - unsigned r = 0xffffffffu; - size_t i; - for (i = 0; i < length; ++i) { - r = lodepng_crc32_table[(r ^ data[i]) & 0xffu] ^ (r >> 8u); - } - return r ^ 0xffffffffu; -} -#endif - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / Reading and writing PNG color channel bits / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -/* The color channel bits of less-than-8-bit pixels are read with the MSB of bytes first, -so LodePNGBitWriter and LodePNGBitReader can't be used for those. */ - -static unsigned char readBitFromReversedStream(size_t* bitpointer, const unsigned char* bitstream) -{ - unsigned char result = (unsigned char)((bitstream[(*bitpointer) >> 3] >> (7 - ((*bitpointer) & 0x7))) & 1); - ++(*bitpointer); - return result; -} - - -/* TODO: make this faster */ -static unsigned readBitsFromReversedStream(size_t* bitpointer, const unsigned char* bitstream, size_t nbits) -{ - unsigned result = 0; - size_t i; - for (i = 0 ; i < nbits; ++i) { - result <<= 1u; - result |= (unsigned)readBitFromReversedStream(bitpointer, bitstream); - } - return result; -} - - -static void setBitOfReversedStream(size_t* bitpointer, unsigned char* bitstream, unsigned char bit) -{ - /*the current bit in bitstream may be 0 or 1 for this to work*/ - if (bit == 0) bitstream[(*bitpointer) >> 3u] &= (unsigned char)(~(1u << (7u - ((*bitpointer) & 7u)))); - else bitstream[(*bitpointer) >> 3u] |= (1u << (7u - ((*bitpointer) & 7u))); - ++(*bitpointer); -} - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / PNG chunks / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -/* - The lodepng_chunk functions are normally not needed, except to traverse the - unknown chunks stored in the LodePNGInfo struct, or add new ones to it. - It also allows traversing the chunks of an encoded PNG file yourself. - - The chunk pointer always points to the beginning of the chunk itself, that is - the first byte of the 4 length bytes. - - In the PNG file format, chunks have the following format: - -4 bytes length: length of the data of the chunk in bytes (chunk itself is 12 bytes longer) - -4 bytes chunk type (ASCII a-z,A-Z only, see below) - -length bytes of data (may be 0 bytes if length was 0) - -4 bytes of CRC, computed on chunk name + data - - The first chunk starts at the 8th byte of the PNG file, the entire rest of the file - exists out of concatenated chunks with the above format. - - PNG standard chunk ASCII naming conventions: - -First byte: uppercase = critical, lowercase = ancillary - -Second byte: uppercase = public, lowercase = private - -Third byte: must be uppercase - -Fourth byte: uppercase = unsafe to copy, lowercase = safe to copy -*/ - - -/* - Gets the length of the data of the chunk. Total chunk length has 12 bytes more. - There must be at least 4 bytes to read from. If the result value is too large, - it may be corrupt data. -*/ -static unsigned lodepng_chunk_length(const unsigned char* chunk) -{ - return lodepng_read32bitInt(&chunk[0]); -} - - -/* check if the type is the given type */ -static unsigned char lodepng_chunk_type_equals(const unsigned char* chunk, const char* type) -{ - if (lodepng_strlen(type) != 4) return 0; - return (chunk[4] == type[0] && chunk[5] == type[1] && chunk[6] == type[2] && chunk[7] == type[3]); -} - - -/* 0: it's one of the critical chunk types, 1: it's an ancillary chunk (see PNG standard) */ -static unsigned char lodepng_chunk_ancillary(const unsigned char* chunk) -{ - return ((chunk[4] & 32) != 0); -} - - -static const unsigned char* lodepng_chunk_data_const(const unsigned char* chunk) -{ - return &chunk[8]; -} - -#if 0 //thorvg don't use crc -/* returns 0 if the crc is correct, 1 if it's incorrect (0 for OK as usual!) */ -static unsigned lodepng_chunk_check_crc(const unsigned char* chunk) -{ - unsigned length = lodepng_chunk_length(chunk); - unsigned CRC = lodepng_read32bitInt(&chunk[length + 8]); - /*the CRC is taken of the data and the 4 chunk type letters, not the length*/ - unsigned checksum = lodepng_crc32(&chunk[4], length + 4); - if (CRC != checksum) return 1; - else return 0; -} -#endif - -static const unsigned char* lodepng_chunk_next_const(const unsigned char* chunk, const unsigned char* end) -{ - if (chunk >= end || end - chunk < 12) return end; /*too small to contain a chunk*/ - if (chunk[0] == 0x89 && chunk[1] == 0x50 && chunk[2] == 0x4e && chunk[3] == 0x47 - && chunk[4] == 0x0d && chunk[5] == 0x0a && chunk[6] == 0x1a && chunk[7] == 0x0a) { - /* Is PNG magic header at start of PNG file. Jump to first actual chunk. */ - return chunk + 8; - } else { - size_t total_chunk_length; - const unsigned char* result; - if (lodepng_addofl(lodepng_chunk_length(chunk), 12, &total_chunk_length)) return end; - result = chunk + total_chunk_length; - if (result < chunk) return end; /*pointer overflow*/ - return result; - } -} - - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / Color types, channels, bits / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -/*checks if the colortype is valid and the bitdepth bd is allowed for this colortype. -Return value is a LodePNG error code.*/ -static unsigned checkColorValidity(LodePNGColorType colortype, unsigned bd) -{ - switch(colortype) { - case LCT_GREY: if(!(bd == 1 || bd == 2 || bd == 4 || bd == 8 || bd == 16)) return 37; break; - case LCT_RGB: if(!( bd == 8 || bd == 16)) return 37; break; - case LCT_PALETTE: if(!(bd == 1 || bd == 2 || bd == 4 || bd == 8 )) return 37; break; - case LCT_GREY_ALPHA: if(!( bd == 8 || bd == 16)) return 37; break; - case LCT_RGBA: if(!( bd == 8 || bd == 16)) return 37; break; - case LCT_MAX_OCTET_VALUE: return 31; /* invalid color type */ - default: return 31; /* invalid color type */ - } - return 0; /*allowed color type / bits combination*/ -} - - -static unsigned getNumColorChannels(LodePNGColorType colortype) -{ - switch(colortype) { - case LCT_GREY: return 1; - case LCT_RGB: return 3; - case LCT_PALETTE: return 1; - case LCT_GREY_ALPHA: return 2; - case LCT_RGBA: return 4; - case LCT_MAX_OCTET_VALUE: return 0; /* invalid color type */ - default: return 0; /*invalid color type*/ - } -} - - -static unsigned lodepng_get_bpp_lct(LodePNGColorType colortype, unsigned bitdepth) -{ - /*bits per pixel is amount of channels * bits per channel*/ - return getNumColorChannels(colortype) * bitdepth; -} - - -static void lodepng_color_mode_init(LodePNGColorMode* info) -{ - info->key_defined = 0; - info->key_r = info->key_g = info->key_b = 0; - info->colortype = LCT_RGBA; - info->bitdepth = 8; - info->palette = 0; - info->palettesize = 0; -} - - -/*allocates palette memory if needed, and initializes all colors to black*/ -static void lodepng_color_mode_alloc_palette(LodePNGColorMode* info) -{ - size_t i; - /*if the palette is already allocated, it will have size 1024 so no reallocation needed in that case*/ - /*the palette must have room for up to 256 colors with 4 bytes each.*/ - if (!info->palette) info->palette = (unsigned char*)malloc(1024); - if (!info->palette) return; /*alloc fail*/ - for (i = 0; i != 256; ++i) { - /*Initialize all unused colors with black, the value used for invalid palette indices. - This is an error according to the PNG spec, but common PNG decoders make it black instead. - That makes color conversion slightly faster due to no error handling needed.*/ - info->palette[i * 4 + 0] = 0; - info->palette[i * 4 + 1] = 0; - info->palette[i * 4 + 2] = 0; - info->palette[i * 4 + 3] = 255; - } -} - -static void lodepng_palette_clear(LodePNGColorMode* info) -{ - if (info->palette) free(info->palette); - info->palette = 0; - info->palettesize = 0; -} - - -static void lodepng_color_mode_cleanup(LodePNGColorMode* info) -{ - lodepng_palette_clear(info); -} - - -/*return value is error code (0 means no error)*/ -static unsigned lodepng_color_mode_copy(LodePNGColorMode* dest, const LodePNGColorMode* source) -{ - lodepng_color_mode_cleanup(dest); - lodepng_memcpy(dest, source, sizeof(LodePNGColorMode)); - if (source->palette) { - dest->palette = (unsigned char*)malloc(1024); - if (!dest->palette && source->palettesize) return 83; /*alloc fail*/ - lodepng_memcpy(dest->palette, source->palette, source->palettesize * 4); - } - return 0; -} - - -static int lodepng_color_mode_equal(const LodePNGColorMode* a, const LodePNGColorMode* b) -{ - size_t i; - if (a->colortype != b->colortype) return 0; - if (a->bitdepth != b->bitdepth) return 0; - if (a->key_defined != b->key_defined) return 0; - if (a->key_defined) { - if(a->key_r != b->key_r) return 0; - if(a->key_g != b->key_g) return 0; - if(a->key_b != b->key_b) return 0; - } - if (a->palettesize != b->palettesize) return 0; - for (i = 0; i != a->palettesize * 4; ++i) { - if (a->palette[i] != b->palette[i]) return 0; - } - return 1; -} - - -static size_t lodepng_get_raw_size_lct(unsigned w, unsigned h, LodePNGColorType colortype, unsigned bitdepth) -{ - size_t bpp = lodepng_get_bpp_lct(colortype, bitdepth); - size_t n = (size_t)w * (size_t)h; - return ((n / 8u) * bpp) + ((n & 7u) * bpp + 7u) / 8u; -} - - -/* Returns the byte size of a raw image buffer with given width, height and color mode */ -static size_t lodepng_get_raw_size(unsigned w, unsigned h, const LodePNGColorMode* color) -{ - return lodepng_get_raw_size_lct(w, h, color->colortype, color->bitdepth); -} - - -/*in an idat chunk, each scanline is a multiple of 8 bits, unlike the lodepng output buffer, -and in addition has one extra byte per line: the filter byte. So this gives a larger -result than lodepng_get_raw_size. Set h to 1 to get the size of 1 row including filter byte. */ -static size_t lodepng_get_raw_size_idat(unsigned w, unsigned h, unsigned bpp) -{ - /* + 1 for the filter byte, and possibly plus padding bits per line. */ - /* Ignoring casts, the expression is equal to (w * bpp + 7) / 8 + 1, but avoids overflow of w * bpp */ - size_t line = ((size_t)(w / 8u) * bpp) + 1u + ((w & 7u) * bpp + 7u) / 8u; - return (size_t)h * line; -} - - -/* Safely checks whether size_t overflow can be caused due to amount of pixels. - This check is overcautious rather than precise. If this check indicates no overflow, - you can safely compute in a size_t (but not an unsigned): - -(size_t)w * (size_t)h * 8 - -amount of bytes in IDAT (including filter, padding and Adam7 bytes) - -amount of bytes in raw color model - Returns 1 if overflow possible, 0 if not. */ -static int lodepng_pixel_overflow(unsigned w, unsigned h, const LodePNGColorMode* pngcolor, const LodePNGColorMode* rawcolor) -{ - size_t bpp = LODEPNG_MAX(lodepng_get_bpp_lct(pngcolor->colortype, pngcolor->bitdepth), lodepng_get_bpp_lct(rawcolor->colortype, rawcolor->bitdepth)); - size_t numpixels, total; - size_t line; /* bytes per line in worst case */ - - if (lodepng_mulofl((size_t)w, (size_t)h, &numpixels)) return 1; - if (lodepng_mulofl(numpixels, 8, &total)) return 1; /* bit pointer with 8-bit color, or 8 bytes per channel color */ - - /* Bytes per scanline with the expression "(w / 8u) * bpp) + ((w & 7u) * bpp + 7u) / 8u" */ - if (lodepng_mulofl((size_t)(w / 8u), bpp, &line)) return 1; - if (lodepng_addofl(line, ((w & 7u) * bpp + 7u) / 8u, &line)) return 1; - - if (lodepng_addofl(line, 5, &line)) return 1; /* 5 bytes overhead per line: 1 filterbyte, 4 for Adam7 worst case */ - if (lodepng_mulofl(line, h, &total)) return 1; /* Total bytes in worst case */ - - return 0; /* no overflow */ -} - - -static void lodepng_info_init(LodePNGInfo* info) -{ - lodepng_color_mode_init(&info->color); - info->interlace_method = 0; - info->compression_method = 0; - info->filter_method = 0; -} - - -static void lodepng_info_cleanup(LodePNGInfo* info) -{ - lodepng_color_mode_cleanup(&info->color); -} - - -/* index: bitgroup index, bits: bitgroup size(1, 2 or 4), in: bitgroup value, out: octet array to add bits to */ -static void addColorBits(unsigned char* out, size_t index, unsigned bits, unsigned in) -{ - unsigned m = bits == 1 ? 7 : bits == 2 ? 3 : 1; /*8 / bits - 1*/ - /*p = the partial index in the byte, e.g. with 4 palettebits it is 0 for first half or 1 for second half*/ - unsigned p = index & m; - in &= (1u << bits) - 1u; /*filter out any other bits of the input value*/ - in = in << (bits * (m - p)); - if(p == 0) out[index * bits / 8u] = in; - else out[index * bits / 8u] |= in; -} - -/* - One node of a color tree - This is the data structure used to count the number of unique colors and to get a palette - index for a color. It's like an octree, but because the alpha channel is used too, each - node has 16 instead of 8 children. -*/ -struct ColorTree -{ - ColorTree* children[16]; /* up to 16 pointers to ColorTree of next level */ - int index; /* the payload. Only has a meaningful value if this is in the last level */ -}; - -static void color_tree_init(ColorTree* tree) -{ - lodepng_memset(tree->children, 0, 16 * sizeof(*tree->children)); - tree->index = -1; -} - -static void color_tree_cleanup(ColorTree* tree) -{ - int i; - for (i = 0; i != 16; ++i) { - if(tree->children[i]) { - color_tree_cleanup(tree->children[i]); - free(tree->children[i]); - } - } -} - - -/* returns -1 if color not present, its index otherwise */ -static int color_tree_get(ColorTree* tree, unsigned char r, unsigned char g, unsigned char b, unsigned char a) -{ - int bit = 0; - for (bit = 0; bit < 8; ++bit) { - int i = 8 * ((r >> bit) & 1) + 4 * ((g >> bit) & 1) + 2 * ((b >> bit) & 1) + 1 * ((a >> bit) & 1); - if (!tree->children[i]) return -1; - else tree = tree->children[i]; - } - return tree ? tree->index : -1; -} - - -/* color is not allowed to already exist. - Index should be >= 0 (it's signed to be compatible with using -1 for "doesn't exist") - Returns error code, or 0 if ok */ -static unsigned color_tree_add(ColorTree* tree, unsigned char r, unsigned char g, unsigned char b, unsigned char a, unsigned index) -{ - int bit; - for (bit = 0; bit < 8; ++bit) { - int i = 8 * ((r >> bit) & 1) + 4 * ((g >> bit) & 1) + 2 * ((b >> bit) & 1) + 1 * ((a >> bit) & 1); - if (!tree->children[i]) { - tree->children[i] = (ColorTree*)malloc(sizeof(ColorTree)); - if (!tree->children[i]) return 83; /*alloc fail*/ - color_tree_init(tree->children[i]); - } - tree = tree->children[i]; - } - tree->index = (int)index; - return 0; -} - -/* put a pixel, given its RGBA color, into image of any color type */ -static unsigned rgba8ToPixel(unsigned char* out, size_t i, const LodePNGColorMode* mode, ColorTree* tree /*for palette*/, unsigned char r, unsigned char g, unsigned char b, unsigned char a) -{ - if (mode->colortype == LCT_GREY) { - unsigned char gray = r; /*((unsigned short)r + g + b) / 3u;*/ - if (mode->bitdepth == 8) out[i] = gray; - else if (mode->bitdepth == 16) out[i * 2 + 0] = out[i * 2 + 1] = gray; - else { - /*take the most significant bits of gray*/ - gray = ((unsigned)gray >> (8u - mode->bitdepth)) & ((1u << mode->bitdepth) - 1u); - addColorBits(out, i, mode->bitdepth, gray); - } - } else if (mode->colortype == LCT_RGB) { - if (mode->bitdepth == 8) { - out[i * 3 + 0] = r; - out[i * 3 + 1] = g; - out[i * 3 + 2] = b; - } else { - out[i * 6 + 0] = out[i * 6 + 1] = r; - out[i * 6 + 2] = out[i * 6 + 3] = g; - out[i * 6 + 4] = out[i * 6 + 5] = b; - } - } else if(mode->colortype == LCT_PALETTE) { - int index = color_tree_get(tree, r, g, b, a); - if (index < 0) return 82; /*color not in palette*/ - if (mode->bitdepth == 8) out[i] = index; - else addColorBits(out, i, mode->bitdepth, (unsigned)index); - } else if (mode->colortype == LCT_GREY_ALPHA) { - unsigned char gray = r; /*((unsigned short)r + g + b) / 3u;*/ - if (mode->bitdepth == 8) { - out[i * 2 + 0] = gray; - out[i * 2 + 1] = a; - } else if (mode->bitdepth == 16) { - out[i * 4 + 0] = out[i * 4 + 1] = gray; - out[i * 4 + 2] = out[i * 4 + 3] = a; - } - } else if (mode->colortype == LCT_RGBA) { - if (mode->bitdepth == 8) { - out[i * 4 + 0] = r; - out[i * 4 + 1] = g; - out[i * 4 + 2] = b; - out[i * 4 + 3] = a; - } else { - out[i * 8 + 0] = out[i * 8 + 1] = r; - out[i * 8 + 2] = out[i * 8 + 3] = g; - out[i * 8 + 4] = out[i * 8 + 5] = b; - out[i * 8 + 6] = out[i * 8 + 7] = a; - } - } - return 0; /*no error*/ -} - - -/* put a pixel, given its RGBA16 color, into image of any color 16-bitdepth type */ -static void rgba16ToPixel(unsigned char* out, size_t i, const LodePNGColorMode* mode, unsigned short r, unsigned short g, unsigned short b, unsigned short a) -{ - if (mode->colortype == LCT_GREY) { - unsigned short gray = r; /*((unsigned)r + g + b) / 3u;*/ - out[i * 2 + 0] = (gray >> 8) & 255; - out[i * 2 + 1] = gray & 255; - } else if (mode->colortype == LCT_RGB) { - out[i * 6 + 0] = (r >> 8) & 255; - out[i * 6 + 1] = r & 255; - out[i * 6 + 2] = (g >> 8) & 255; - out[i * 6 + 3] = g & 255; - out[i * 6 + 4] = (b >> 8) & 255; - out[i * 6 + 5] = b & 255; - } else if (mode->colortype == LCT_GREY_ALPHA) { - unsigned short gray = r; /*((unsigned)r + g + b) / 3u;*/ - out[i * 4 + 0] = (gray >> 8) & 255; - out[i * 4 + 1] = gray & 255; - out[i * 4 + 2] = (a >> 8) & 255; - out[i * 4 + 3] = a & 255; - } else if (mode->colortype == LCT_RGBA) { - out[i * 8 + 0] = (r >> 8) & 255; - out[i * 8 + 1] = r & 255; - out[i * 8 + 2] = (g >> 8) & 255; - out[i * 8 + 3] = g & 255; - out[i * 8 + 4] = (b >> 8) & 255; - out[i * 8 + 5] = b & 255; - out[i * 8 + 6] = (a >> 8) & 255; - out[i * 8 + 7] = a & 255; - } -} - - -/* Get RGBA8 color of pixel with index i (y * width + x) from the raw image with given color type. */ -static void getPixelColorRGBA8(unsigned char* r, unsigned char* g, unsigned char* b, unsigned char* a, const unsigned char* in, size_t i, const LodePNGColorMode* mode) -{ - if (mode->colortype == LCT_GREY) { - if (mode->bitdepth == 8) { - *r = *g = *b = in[i]; - if (mode->key_defined && *r == mode->key_r) *a = 0; - else *a = 255; - } else if (mode->bitdepth == 16) { - *r = *g = *b = in[i * 2 + 0]; - if (mode->key_defined && 256U * in[i * 2 + 0] + in[i * 2 + 1] == mode->key_r) *a = 0; - else *a = 255; - } else { - unsigned highest = ((1U << mode->bitdepth) - 1U); /* highest possible value for this bit depth */ - size_t j = i * mode->bitdepth; - unsigned value = readBitsFromReversedStream(&j, in, mode->bitdepth); - *r = *g = *b = (value * 255) / highest; - if (mode->key_defined && value == mode->key_r) *a = 0; - else *a = 255; - } - } else if (mode->colortype == LCT_RGB) { - if (mode->bitdepth == 8) { - *r = in[i * 3 + 0]; *g = in[i * 3 + 1]; *b = in[i * 3 + 2]; - if (mode->key_defined && *r == mode->key_r && *g == mode->key_g && *b == mode->key_b) *a = 0; - else *a = 255; - } else { - *r = in[i * 6 + 0]; - *g = in[i * 6 + 2]; - *b = in[i * 6 + 4]; - if (mode->key_defined && 256U * in[i * 6 + 0] + in[i * 6 + 1] == mode->key_r - && 256U * in[i * 6 + 2] + in[i * 6 + 3] == mode->key_g - && 256U * in[i * 6 + 4] + in[i * 6 + 5] == mode->key_b) *a = 0; - else *a = 255; - } - } else if (mode->colortype == LCT_PALETTE) { - unsigned index; - if (mode->bitdepth == 8) index = in[i]; - else { - size_t j = i * mode->bitdepth; - index = readBitsFromReversedStream(&j, in, mode->bitdepth); - } - /* out of bounds of palette not checked: see lodepng_color_mode_alloc_palette. */ - *r = mode->palette[index * 4 + 0]; - *g = mode->palette[index * 4 + 1]; - *b = mode->palette[index * 4 + 2]; - *a = mode->palette[index * 4 + 3]; - } else if (mode->colortype == LCT_GREY_ALPHA) { - if (mode->bitdepth == 8) { - *r = *g = *b = in[i * 2 + 0]; - *a = in[i * 2 + 1]; - } else { - *r = *g = *b = in[i * 4 + 0]; - *a = in[i * 4 + 2]; - } - } else if (mode->colortype == LCT_RGBA) { - if (mode->bitdepth == 8) { - *r = in[i * 4 + 0]; - *g = in[i * 4 + 1]; - *b = in[i * 4 + 2]; - *a = in[i * 4 + 3]; - } else { - *r = in[i * 8 + 0]; - *g = in[i * 8 + 2]; - *b = in[i * 8 + 4]; - *a = in[i * 8 + 6]; - } - } -} - - -/* Similar to getPixelColorRGBA8, but with all the for loops inside of the color - mode test cases, optimized to convert the colors much faster, when converting - to the common case of RGBA with 8 bit per channel. buffer must be RGBA with - enough memory.*/ -static void getPixelColorsRGBA8(unsigned char* LODEPNG_RESTRICT buffer, size_t numpixels, const unsigned char* LODEPNG_RESTRICT in, const LodePNGColorMode* mode) -{ - unsigned num_channels = 4; - size_t i; - if (mode->colortype == LCT_GREY) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i]; - buffer[3] = 255; - } - if (mode->key_defined) { - buffer -= numpixels * num_channels; - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - if(buffer[0] == mode->key_r) buffer[3] = 0; - } - } - } else if (mode->bitdepth == 16) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i * 2]; - buffer[3] = mode->key_defined && 256U * in[i * 2 + 0] + in[i * 2 + 1] == mode->key_r ? 0 : 255; - } - } else { - unsigned highest = ((1U << mode->bitdepth) - 1U); /* highest possible value for this bit depth */ - size_t j = 0; - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - unsigned value = readBitsFromReversedStream(&j, in, mode->bitdepth); - buffer[0] = buffer[1] = buffer[2] = (value * 255) / highest; - buffer[3] = mode->key_defined && value == mode->key_r ? 0 : 255; - } - } - } else if (mode->colortype == LCT_RGB) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - //lodepng_memcpy(buffer, &in[i * 3], 3); - //Convert colortype to LCT_BGR? - buffer[0] = in[i * 3 + 2]; - buffer[1] = in[i * 3 + 1]; - buffer[2] = in[i * 3 + 0]; - buffer[3] = 255; - } - if (mode->key_defined) { - buffer -= numpixels * num_channels; - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - if (buffer[0] == mode->key_r && buffer[1]== mode->key_g && buffer[2] == mode->key_b) buffer[3] = 0; - } - } - } else { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = in[i * 6 + 0]; - buffer[1] = in[i * 6 + 2]; - buffer[2] = in[i * 6 + 4]; - buffer[3] = mode->key_defined - && 256U * in[i * 6 + 0] + in[i * 6 + 1] == mode->key_r - && 256U * in[i * 6 + 2] + in[i * 6 + 3] == mode->key_g - && 256U * in[i * 6 + 4] + in[i * 6 + 5] == mode->key_b ? 0 : 255; - } - } - } else if (mode->colortype == LCT_PALETTE) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - unsigned index = in[i]; - /* out of bounds of palette not checked: see lodepng_color_mode_alloc_palette. */ - lodepng_memcpy(buffer, &mode->palette[index * 4], 4); - } - } else { - size_t j = 0; - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - unsigned index = readBitsFromReversedStream(&j, in, mode->bitdepth); - /* out of bounds of palette not checked: see lodepng_color_mode_alloc_palette. */ - lodepng_memcpy(buffer, &mode->palette[index * 4], 4); - } - } - } else if (mode->colortype == LCT_GREY_ALPHA) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i * 2 + 0]; - buffer[3] = in[i * 2 + 1]; - } - } else { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i * 4 + 0]; - buffer[3] = in[i * 4 + 2]; - } - } - } else if (mode->colortype == LCT_RGBA) { - if (mode->bitdepth == 8) { - lodepng_memcpy(buffer, in, numpixels * 4); - } else { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = in[i * 8 + 0]; - buffer[1] = in[i * 8 + 2]; - buffer[2] = in[i * 8 + 4]; - buffer[3] = in[i * 8 + 6]; - } - } - } -} - - -/* Similar to getPixelColorsRGBA8, but with 3-channel RGB output. */ -static void getPixelColorsRGB8(unsigned char* LODEPNG_RESTRICT buffer, size_t numpixels, const unsigned char* LODEPNG_RESTRICT in, const LodePNGColorMode* mode) -{ - const unsigned num_channels = 3; - size_t i; - if (mode->colortype == LCT_GREY) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i]; - } - } else if (mode->bitdepth == 16) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i * 2]; - } - } else { - unsigned highest = ((1U << mode->bitdepth) - 1U); /* highest possible value for this bit depth */ - size_t j = 0; - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - unsigned value = readBitsFromReversedStream(&j, in, mode->bitdepth); - buffer[0] = buffer[1] = buffer[2] = (value * 255) / highest; - } - } - } else if (mode->colortype == LCT_RGB) { - if (mode->bitdepth == 8) { - lodepng_memcpy(buffer, in, numpixels * 3); - } else { - for(i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = in[i * 6 + 0]; - buffer[1] = in[i * 6 + 2]; - buffer[2] = in[i * 6 + 4]; - } - } - } else if (mode->colortype == LCT_PALETTE) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - unsigned index = in[i]; - /* out of bounds of palette not checked: see lodepng_color_mode_alloc_palette. */ - lodepng_memcpy(buffer, &mode->palette[index * 4], 3); - } - } else { - size_t j = 0; - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - unsigned index = readBitsFromReversedStream(&j, in, mode->bitdepth); - /* out of bounds of palette not checked: see lodepng_color_mode_alloc_palette. */ - lodepng_memcpy(buffer, &mode->palette[index * 4], 3); - } - } - } else if (mode->colortype == LCT_GREY_ALPHA) { - if (mode->bitdepth == 8) { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i * 2 + 0]; - } - } else { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = buffer[1] = buffer[2] = in[i * 4 + 0]; - } - } - } else if (mode->colortype == LCT_RGBA) { - if (mode->bitdepth == 8) { - for(i = 0; i != numpixels; ++i, buffer += num_channels) { - lodepng_memcpy(buffer, &in[i * 4], 3); - } - } else { - for (i = 0; i != numpixels; ++i, buffer += num_channels) { - buffer[0] = in[i * 8 + 0]; - buffer[1] = in[i * 8 + 2]; - buffer[2] = in[i * 8 + 4]; - } - } - } -} - - -/* Get RGBA16 color of pixel with index i (y * width + x) from the raw image with - given color type, but the given color type must be 16-bit itself. */ -static void getPixelColorRGBA16(unsigned short* r, unsigned short* g, unsigned short* b, unsigned short* a, const unsigned char* in, size_t i, const LodePNGColorMode* mode) -{ - if (mode->colortype == LCT_GREY) { - *r = *g = *b = 256 * in[i * 2 + 0] + in[i * 2 + 1]; - if (mode->key_defined && 256U * in[i * 2 + 0] + in[i * 2 + 1] == mode->key_r) *a = 0; - else *a = 65535; - } else if (mode->colortype == LCT_RGB) { - *r = 256u * in[i * 6 + 0] + in[i * 6 + 1]; - *g = 256u * in[i * 6 + 2] + in[i * 6 + 3]; - *b = 256u * in[i * 6 + 4] + in[i * 6 + 5]; - if (mode->key_defined - && 256u * in[i * 6 + 0] + in[i * 6 + 1] == mode->key_r - && 256u * in[i * 6 + 2] + in[i * 6 + 3] == mode->key_g - && 256u * in[i * 6 + 4] + in[i * 6 + 5] == mode->key_b) *a = 0; - else *a = 65535; - } else if (mode->colortype == LCT_GREY_ALPHA) { - *r = *g = *b = 256u * in[i * 4 + 0] + in[i * 4 + 1]; - *a = 256u * in[i * 4 + 2] + in[i * 4 + 3]; - } else if (mode->colortype == LCT_RGBA) { - *r = 256u * in[i * 8 + 0] + in[i * 8 + 1]; - *g = 256u * in[i * 8 + 2] + in[i * 8 + 3]; - *b = 256u * in[i * 8 + 4] + in[i * 8 + 5]; - *a = 256u * in[i * 8 + 6] + in[i * 8 + 7]; - } -} - -/* - Converts raw buffer from one color type to another color type, based on - LodePNGColorMode structs to describe the input and output color type. - See the reference manual at the end of this header file to see which color conversions are supported. - return value = LodePNG error code (0 if all went ok, an error if the conversion isn't supported) - The out buffer must have size (w * h * bpp + 7) / 8, where bpp is the bits per pixel - of the output color type (lodepng_get_bpp). - For < 8 bpp images, there should not be padding bits at the end of scanlines. - For 16-bit per channel colors, uses big endian format like PNG does. - Return value is LodePNG error code -*/ -static unsigned lodepng_convert(unsigned char* out, const unsigned char* in, const LodePNGColorMode* mode_out, const LodePNGColorMode* mode_in, unsigned w, unsigned h) -{ - size_t i; - ColorTree tree; - size_t numpixels = (size_t)w * (size_t)h; - unsigned error = 0; - - if (mode_in->colortype == LCT_PALETTE && !mode_in->palette) { - return 107; /* error: must provide palette if input mode is palette */ - } - - if (lodepng_color_mode_equal(mode_out, mode_in)) { - size_t numbytes = lodepng_get_raw_size(w, h, mode_in); - lodepng_memcpy(out, in, numbytes); - return 0; - } - - if (mode_out->colortype == LCT_PALETTE) { - size_t palettesize = mode_out->palettesize; - const unsigned char* palette = mode_out->palette; - size_t palsize = (size_t)1u << mode_out->bitdepth; - /* if the user specified output palette but did not give the values, assume - they want the values of the input color type (assuming that one is palette). - Note that we never create a new palette ourselves.*/ - if (palettesize == 0) { - palettesize = mode_in->palettesize; - palette = mode_in->palette; - /* if the input was also palette with same bitdepth, then the color types are also - equal, so copy literally. This to preserve the exact indices that were in the PNG - even in case there are duplicate colors in the palette.*/ - if (mode_in->colortype == LCT_PALETTE && mode_in->bitdepth == mode_out->bitdepth) { - size_t numbytes = lodepng_get_raw_size(w, h, mode_in); - lodepng_memcpy(out, in, numbytes); - return 0; - } - } - if (palettesize < palsize) palsize = palettesize; - color_tree_init(&tree); - for (i = 0; i != palsize; ++i) { - const unsigned char* p = &palette[i * 4]; - error = color_tree_add(&tree, p[0], p[1], p[2], p[3], (unsigned)i); - if (error) break; - } - } - - if (!error) { - if (mode_in->bitdepth == 16 && mode_out->bitdepth == 16) { - for (i = 0; i != numpixels; ++i) { - unsigned short r = 0, g = 0, b = 0, a = 0; - getPixelColorRGBA16(&r, &g, &b, &a, in, i, mode_in); - rgba16ToPixel(out, i, mode_out, r, g, b, a); - } - } else if (mode_out->bitdepth == 8 && mode_out->colortype == LCT_RGBA) { - getPixelColorsRGBA8(out, numpixels, in, mode_in); - } else if(mode_out->bitdepth == 8 && mode_out->colortype == LCT_RGB) { - getPixelColorsRGB8(out, numpixels, in, mode_in); - } else { - unsigned char r = 0, g = 0, b = 0, a = 0; - for (i = 0; i != numpixels; ++i) { - getPixelColorRGBA8(&r, &g, &b, &a, in, i, mode_in); - error = rgba8ToPixel(out, i, mode_out, &tree, r, g, b, a); - if (error) break; - } - } - } - - if (mode_out->colortype == LCT_PALETTE) { - color_tree_cleanup(&tree); - } - - return error; -} - - -/* Paeth predictor, used by PNG filter type 4 - The parameters are of type short, but should come from unsigned chars, the shorts - are only needed to make the paeth calculation correct. -*/ -static unsigned char paethPredictor(short a, short b, short c) -{ - short pa = LODEPNG_ABS(b - c); - short pb = LODEPNG_ABS(a - c); - short pc = LODEPNG_ABS(a + b - c - c); - /* return input value associated with smallest of pa, pb, pc (with certain priority if equal) */ - if (pb < pa) { a = b; pa = pb; } - return (pc < pa) ? c : a; -} - - -/*shared values used by multiple Adam7 related functions*/ -static const unsigned ADAM7_IX[7] = { 0, 4, 0, 2, 0, 1, 0 }; /*x start values*/ -static const unsigned ADAM7_IY[7] = { 0, 0, 4, 0, 2, 0, 1 }; /*y start values*/ -static const unsigned ADAM7_DX[7] = { 8, 8, 4, 4, 2, 2, 1 }; /*x delta values*/ -static const unsigned ADAM7_DY[7] = { 8, 8, 8, 4, 4, 2, 2 }; /*y delta values*/ - -/* Outputs various dimensions and positions in the image related to the Adam7 reduced images. - passw: output containing the width of the 7 passes - passh: output containing the height of the 7 passes - filter_passstart: output containing the index of the start and end of each - reduced image with filter bytes - padded_passstart output containing the index of the start and end of each - reduced image when without filter bytes but with padded scanlines - passstart: output containing the index of the start and end of each reduced - image without padding between scanlines, but still padding between the images - w, h: width and height of non-interlaced image - bpp: bits per pixel - "padded" is only relevant if bpp is less than 8 and a scanline or image does not - end at a full byte */ -static void Adam7_getpassvalues(unsigned passw[7], unsigned passh[7], size_t filter_passstart[8], size_t padded_passstart[8], size_t passstart[8], unsigned w, unsigned h, unsigned bpp) -{ - /* the passstart values have 8 values: the 8th one indicates the byte after the end of the 7th (= last) pass */ - unsigned i; - - /* calculate width and height in pixels of each pass */ - for (i = 0; i != 7; ++i) { - passw[i] = (w + ADAM7_DX[i] - ADAM7_IX[i] - 1) / ADAM7_DX[i]; - passh[i] = (h + ADAM7_DY[i] - ADAM7_IY[i] - 1) / ADAM7_DY[i]; - if(passw[i] == 0) passh[i] = 0; - if(passh[i] == 0) passw[i] = 0; - } - - filter_passstart[0] = padded_passstart[0] = passstart[0] = 0; - for (i = 0; i != 7; ++i) { - /* if passw[i] is 0, it's 0 bytes, not 1 (no filtertype-byte) */ - filter_passstart[i + 1] = filter_passstart[i] - + ((passw[i] && passh[i]) ? passh[i] * (1u + (passw[i] * bpp + 7u) / 8u) : 0); - /* bits padded if needed to fill full byte at end of each scanline */ - padded_passstart[i + 1] = padded_passstart[i] + passh[i] * ((passw[i] * bpp + 7u) / 8u); - /* only padded at end of reduced image */ - passstart[i + 1] = passstart[i] + (passh[i] * passw[i] * bpp + 7u) / 8u; - } -} - - -/* ////////////////////////////////////////////////////////////////////////// */ -/* / PNG Decoder / */ -/* ////////////////////////////////////////////////////////////////////////// */ - -static unsigned unfilterScanline(unsigned char* recon, const unsigned char* scanline, const unsigned char* precon, size_t bytewidth, unsigned char filterType, size_t length) -{ - /* For PNG filter method 0 - unfilter a PNG image scanline by scanline. when the pixels are smaller than 1 byte, - the filter works byte per byte (bytewidth = 1) - precon is the previous unfiltered scanline, recon the result, scanline the current one - the incoming scanlines do NOT include the filtertype byte, that one is given in the parameter filterType instead - recon and scanline MAY be the same memory address! precon must be disjoint. */ - - size_t i; - switch (filterType) { - case 0: { - if (bytewidth == 4) { - for (i = 0; i < length; i += 4) { - //RGBA -> BGRA - recon[i + 0] = scanline[i + 2]; - recon[i + 1] = scanline[i + 1]; - recon[i + 2] = scanline[i + 0]; - recon[i + 3] = scanline[i + 3]; - } - } else { - for (i = 0; i != length; ++i) recon[i] = scanline[i]; - } - break; - } - case 1: { - for (i = 0; i != bytewidth; ++i) recon[i] = scanline[i]; - for (i = bytewidth; i < length; ++i) recon[i] = scanline[i] + recon[i - bytewidth]; - break; - } - case 2: { - if (precon) { - for (i = 0; i != length; ++i) recon[i] = scanline[i] + precon[i]; - } else { - for (i = 0; i != length; ++i) recon[i] = scanline[i]; - } - break; - } - case 3: { - if (precon) { - for (i = 0; i != bytewidth; ++i) recon[i] = scanline[i] + (precon[i] >> 1u); - for (i = bytewidth; i < length; ++i) recon[i] = scanline[i] + ((recon[i - bytewidth] + precon[i]) >> 1u); - } else { - for (i = 0; i != bytewidth; ++i) recon[i] = scanline[i]; - for (i = bytewidth; i < length; ++i) recon[i] = scanline[i] + (recon[i - bytewidth] >> 1u); - } - break; - } - case 4: { - if (precon) { - for (i = 0; i != bytewidth; ++i) { - recon[i] = (scanline[i] + precon[i]); /*paethPredictor(0, precon[i], 0) is always precon[i]*/ - } - - /* Unroll independent paths of the paeth predictor. A 6x and 8x version would also be possible but that - adds too much code. Whether this actually speeds anything up at all depends on compiler and settings. */ - if (bytewidth >= 4) { - for (; i + 3 < length; i += 4) { - size_t j = i - bytewidth; - unsigned char s0 = scanline[i + 0], s1 = scanline[i + 1], s2 = scanline[i + 2], s3 = scanline[i + 3]; - unsigned char r0 = recon[j + 0], r1 = recon[j + 1], r2 = recon[j + 2], r3 = recon[j + 3]; - unsigned char p0 = precon[i + 0], p1 = precon[i + 1], p2 = precon[i + 2], p3 = precon[i + 3]; - unsigned char q0 = precon[j + 0], q1 = precon[j + 1], q2 = precon[j + 2], q3 = precon[j + 3]; - recon[i + 0] = s0 + paethPredictor(r0, p0, q0); - recon[i + 1] = s1 + paethPredictor(r1, p1, q1); - recon[i + 2] = s2 + paethPredictor(r2, p2, q2); - recon[i + 3] = s3 + paethPredictor(r3, p3, q3); - } - } else if (bytewidth >= 3) { - for (; i + 2 < length; i += 3) { - size_t j = i - bytewidth; - unsigned char s0 = scanline[i + 0], s1 = scanline[i + 1], s2 = scanline[i + 2]; - unsigned char r0 = recon[j + 0], r1 = recon[j + 1], r2 = recon[j + 2]; - unsigned char p0 = precon[i + 0], p1 = precon[i + 1], p2 = precon[i + 2]; - unsigned char q0 = precon[j + 0], q1 = precon[j + 1], q2 = precon[j + 2]; - recon[i + 0] = s0 + paethPredictor(r0, p0, q0); - recon[i + 1] = s1 + paethPredictor(r1, p1, q1); - recon[i + 2] = s2 + paethPredictor(r2, p2, q2); - } - } else if (bytewidth >= 2) { - for (; i + 1 < length; i += 2) { - size_t j = i - bytewidth; - unsigned char s0 = scanline[i + 0], s1 = scanline[i + 1]; - unsigned char r0 = recon[j + 0], r1 = recon[j + 1]; - unsigned char p0 = precon[i + 0], p1 = precon[i + 1]; - unsigned char q0 = precon[j + 0], q1 = precon[j + 1]; - recon[i + 0] = s0 + paethPredictor(r0, p0, q0); - recon[i + 1] = s1 + paethPredictor(r1, p1, q1); - } - } - - for (; i != length; ++i) { - recon[i] = (scanline[i] + paethPredictor(recon[i - bytewidth], precon[i], precon[i - bytewidth])); - } - } else { - for (i = 0; i != bytewidth; ++i) { - recon[i] = scanline[i]; - } - for (i = bytewidth; i < length; ++i) { - /* paethPredictor(recon[i - bytewidth], 0, 0) is always recon[i - bytewidth] */ - recon[i] = (scanline[i] + recon[i - bytewidth]); - } - } - break; - } - default: return 36; /* error: invalid filter type given */ - } - return 0; -} - - -static unsigned unfilter(unsigned char* out, const unsigned char* in, unsigned w, unsigned h, unsigned bpp) -{ - /* For PNG filter method 0 - this function unfilters a single image (e.g. without interlacing this is called once, with Adam7 seven times) - out must have enough bytes allocated already, in must have the scanlines + 1 filtertype byte per scanline - w and h are image dimensions or dimensions of reduced image, bpp is bits per pixel - in and out are allowed to be the same memory address (but aren't the same size since in has the extra filter bytes) */ - - unsigned y; - unsigned char* prevline = 0; - - /* bytewidth is used for filtering, is 1 when bpp < 8, number of bytes per pixel otherwise */ - size_t bytewidth = (bpp + 7u) / 8u; - /* the width of a scanline in bytes, not including the filter type */ - size_t linebytes = lodepng_get_raw_size_idat(w, 1, bpp) - 1u; - - for (y = 0; y < h; ++y) { - size_t outindex = linebytes * y; - size_t inindex = (1 + linebytes) * y; /* the extra filterbyte added to each row */ - unsigned char filterType = in[inindex]; - CERROR_TRY_RETURN(unfilterScanline(&out[outindex], &in[inindex + 1], prevline, bytewidth, filterType, linebytes)); - prevline = &out[outindex]; - } - - return 0; -} - -/* in: Adam7 interlaced image, with no padding bits between scanlines, but between - reduced images so that each reduced image starts at a byte. - out: the same pixels, but re-ordered so that they're now a non-interlaced image with size w*h - bpp: bits per pixel - out has the following size in bits: w * h * bpp. - in is possibly bigger due to padding bits between reduced images. - out must be big enough AND must be 0 everywhere if bpp < 8 in the current implementation - (because that's likely a little bit faster) - NOTE: comments about padding bits are only relevant if bpp < 8 */ -static void Adam7_deinterlace(unsigned char* out, const unsigned char* in, unsigned w, unsigned h, unsigned bpp) -{ - unsigned passw[7], passh[7]; - size_t filter_passstart[8], padded_passstart[8], passstart[8]; - unsigned i; - - Adam7_getpassvalues(passw, passh, filter_passstart, padded_passstart, passstart, w, h, bpp); - - if (bpp >= 8) { - for(i = 0; i != 7; ++i) { - unsigned x, y, b; - size_t bytewidth = bpp / 8u; - for (y = 0; y < passh[i]; ++y) - for (x = 0; x < passw[i]; ++x) { - size_t pixelinstart = passstart[i] + (y * passw[i] + x) * bytewidth; - size_t pixeloutstart = ((ADAM7_IY[i] + (size_t)y * ADAM7_DY[i]) * (size_t)w + ADAM7_IX[i] + (size_t)x * ADAM7_DX[i]) * bytewidth; - for (b = 0; b < bytewidth; ++b) { - out[pixeloutstart + b] = in[pixelinstart + b]; - } - } - } - } else /* bpp < 8: Adam7 with pixels < 8 bit is a bit trickier: with bit pointers */ { - for (i = 0; i != 7; ++i) { - unsigned x, y, b; - unsigned ilinebits = bpp * passw[i]; - unsigned olinebits = bpp * w; - size_t obp, ibp; /* bit pointers (for out and in buffer) */ - for (y = 0; y < passh[i]; ++y) - for (x = 0; x < passw[i]; ++x) { - ibp = (8 * passstart[i]) + (y * ilinebits + x * bpp); - obp = (ADAM7_IY[i] + (size_t)y * ADAM7_DY[i]) * olinebits + (ADAM7_IX[i] + (size_t)x * ADAM7_DX[i]) * bpp; - for (b = 0; b < bpp; ++b) { - unsigned char bit = readBitFromReversedStream(&ibp, in); - setBitOfReversedStream(&obp, out, bit); - } - } - } - } -} - - -static void removePaddingBits(unsigned char* out, const unsigned char* in, size_t olinebits, size_t ilinebits, unsigned h) -{ - /* After filtering there are still padding bits if scanlines have non multiple of 8 bit amounts. They need - to be removed (except at last scanline of (Adam7-reduced) image) before working with pure image buffers - for the Adam7 code, the color convert code and the output to the user. - in and out are allowed to be the same buffer, in may also be higher but still overlapping; in must - have >= ilinebits*h bits, out must have >= olinebits*h bits, olinebits must be <= ilinebits - also used to move bits after earlier such operations happened, e.g. in a sequence of reduced images from Adam7 - only useful if (ilinebits - olinebits) is a value in the range 1..7 */ - unsigned y; - size_t diff = ilinebits - olinebits; - size_t ibp = 0, obp = 0; /*input and output bit pointers*/ - for (y = 0; y < h; ++y) { - size_t x; - for (x = 0; x < olinebits; ++x) { - unsigned char bit = readBitFromReversedStream(&ibp, in); - setBitOfReversedStream(&obp, out, bit); - } - ibp += diff; - } -} - - -/* out must be buffer big enough to contain full image, and in must contain the full decompressed data from - the IDAT chunks (with filter index bytes and possible padding bits) - return value is error */ -static unsigned postProcessScanlines(unsigned char* out, unsigned char* in, unsigned w, unsigned h, const LodePNGInfo* info_png) -{ - /* This function converts the filtered-padded-interlaced data into pure 2D image buffer with the PNG's colortype. - Steps: - *) if no Adam7: 1) unfilter 2) remove padding bits (= possible extra bits per scanline if bpp < 8) - *) if adam7: 1) 7x unfilter 2) 7x remove padding bits 3) Adam7_deinterlace - NOTE: the in buffer will be overwritten with intermediate data! */ - unsigned bpp = lodepng_get_bpp_lct(info_png->color.colortype, info_png->color.bitdepth); - if (bpp == 0) return 31; /* error: invalid colortype */ - - if (info_png->interlace_method == 0) { - if (bpp < 8 && w * bpp != ((w * bpp + 7u) / 8u) * 8u) { - CERROR_TRY_RETURN(unfilter(in, in, w, h, bpp)); - removePaddingBits(out, in, w * bpp, ((w * bpp + 7u) / 8u) * 8u, h); - } - /* we can immediately filter into the out buffer, no other steps needed */ - else CERROR_TRY_RETURN(unfilter(out, in, w, h, bpp)); - } else /* interlace_method is 1 (Adam7) */ { - unsigned passw[7], passh[7]; size_t filter_passstart[8], padded_passstart[8], passstart[8]; - unsigned i; - - Adam7_getpassvalues(passw, passh, filter_passstart, padded_passstart, passstart, w, h, bpp); - - for (i = 0; i != 7; ++i) { - CERROR_TRY_RETURN(unfilter(&in[padded_passstart[i]], &in[filter_passstart[i]], passw[i], passh[i], bpp)); - /* TODO: possible efficiency improvement: if in this reduced image the bits fit nicely in 1 scanline, - move bytes instead of bits or move not at all */ - if (bpp < 8) { - /* remove padding bits in scanlines; after this there still may be padding - bits between the different reduced images: each reduced image still starts nicely at a byte */ - removePaddingBits(&in[passstart[i]], &in[padded_passstart[i]], passw[i] * bpp, ((passw[i] * bpp + 7u) / 8u) * 8u, passh[i]); - } - } - Adam7_deinterlace(out, in, w, h, bpp); - } - return 0; -} - - -static unsigned readChunk_PLTE(LodePNGColorMode* color, const unsigned char* data, size_t chunkLength) -{ - unsigned pos = 0, i; - color->palettesize = chunkLength / 3u; - if (color->palettesize == 0 || color->palettesize > 256) return 38; /* error: palette too small or big */ - lodepng_color_mode_alloc_palette(color); - if (!color->palette && color->palettesize) { - color->palettesize = 0; - return 83; /* alloc fail */ - } - - for (i = 0; i != color->palettesize; ++i) { - color->palette[4 * i + 0] = data[pos++]; /*R*/ - color->palette[4 * i + 1] = data[pos++]; /*G*/ - color->palette[4 * i + 2] = data[pos++]; /*B*/ - color->palette[4 * i + 3] = 255; /*alpha*/ - } - - return 0; /* OK */ -} - - -static unsigned readChunk_tRNS(LodePNGColorMode* color, const unsigned char* data, size_t chunkLength) -{ - unsigned i; - if (color->colortype == LCT_PALETTE) { - /* error: more alpha values given than there are palette entries */ - if (chunkLength > color->palettesize) return 39; - - for (i = 0; i != chunkLength; ++i) color->palette[4 * i + 3] = data[i]; - } else if (color->colortype == LCT_GREY) { - /* error: this chunk must be 2 bytes for grayscale image */ - if (chunkLength != 2) return 30; - - color->key_defined = 1; - color->key_r = color->key_g = color->key_b = 256u * data[0] + data[1]; - } else if (color->colortype == LCT_RGB) { - /* error: this chunk must be 6 bytes for RGB image */ - if (chunkLength != 6) return 41; - - color->key_defined = 1; - color->key_r = 256u * data[0] + data[1]; - color->key_g = 256u * data[2] + data[3]; - color->key_b = 256u * data[4] + data[5]; - } - else return 42; /* error: tRNS chunk not allowed for other color models */ - - return 0; /* OK */ -} - - -/* read a PNG, the result will be in the same color type as the PNG (hence "generic") */ -static void decodeGeneric(unsigned char** out, unsigned* w, unsigned* h, LodePNGState* state, const unsigned char* in, size_t insize) -{ - unsigned char IEND = 0; - const unsigned char* chunk; - unsigned char* idat; /*the data from idat chunks, zlib compressed*/ - size_t idatsize = 0; - unsigned char* scanlines = 0; - size_t scanlines_size = 0, expected_size = 0; - size_t outsize = 0; - - /* safe output values in case error happens */ - *out = 0; - *w = *h = 0; - - state->error = lodepng_inspect(w, h, state, in, insize); /*reads header and resets other parameters in state->info_png*/ - if (state->error) return; - - if (lodepng_pixel_overflow(*w, *h, &state->info_png.color, &state->info_raw)) { - CERROR_RETURN(state->error, 92); /*overflow possible due to amount of pixels*/ - } - - /*the input filesize is a safe upper bound for the sum of idat chunks size*/ - idat = (unsigned char*)malloc(insize); - if (!idat) CERROR_RETURN(state->error, 83); /*alloc fail*/ - - chunk = &in[33]; /*first byte of the first chunk after the header*/ - - /*loop through the chunks, ignoring unknown chunks and stopping at IEND chunk. - IDAT data is put at the start of the in buffer*/ - while (!IEND && !state->error) { - unsigned chunkLength; - const unsigned char* data; /*the data in the chunk*/ - - /*error: size of the in buffer too small to contain next chunk*/ - if ((size_t)((chunk - in) + 12) > insize || chunk < in) { - if (state->decoder.ignore_end) break; /*other errors may still happen though*/ - CERROR_BREAK(state->error, 30); - } - - /*length of the data of the chunk, excluding the length bytes, chunk type and CRC bytes*/ - chunkLength = lodepng_chunk_length(chunk); - /*error: chunk length larger than the max PNG chunk size*/ - if (chunkLength > 2147483647) { - if (state->decoder.ignore_end) break; /*other errors may still happen though*/ - CERROR_BREAK(state->error, 63); - } - - if ((size_t)((chunk - in) + chunkLength + 12) > insize || (chunk + chunkLength + 12) < in) { - CERROR_BREAK(state->error, 64); /*error: size of the in buffer too small to contain next chunk*/ - } - - data = lodepng_chunk_data_const(chunk); - - /*for unknown chunk order*/ - //unsigned unknown = 0; - - /*IDAT chunk, containing compressed image data*/ - if (lodepng_chunk_type_equals(chunk, "IDAT")) { - size_t newsize; - if (lodepng_addofl(idatsize, chunkLength, &newsize)) CERROR_BREAK(state->error, 95); - if (newsize > insize) CERROR_BREAK(state->error, 95); - lodepng_memcpy(idat + idatsize, data, chunkLength); - idatsize += chunkLength; - } else if (lodepng_chunk_type_equals(chunk, "IEND")) { - /*IEND chunk*/ - IEND = 1; - } else if (lodepng_chunk_type_equals(chunk, "PLTE")) { - /*palette chunk (PLTE)*/ - state->error = readChunk_PLTE(&state->info_png.color, data, chunkLength); - if (state->error) break; - } else if (lodepng_chunk_type_equals(chunk, "tRNS")) { - /*palette transparency chunk (tRNS). Even though this one is an ancillary chunk , it is still compiled - in without 'LODEPNG_COMPILE_ANCILLARY_CHUNKS' because it contains essential color information that - affects the alpha channel of pixels. */ - state->error = readChunk_tRNS(&state->info_png.color, data, chunkLength); - if (state->error) break; - } else /*it's not an implemented chunk type, so ignore it: skip over the data*/ { - /*error: unknown critical chunk (5th bit of first byte of chunk type is 0)*/ - if (!state->decoder.ignore_critical && !lodepng_chunk_ancillary(chunk)) { - CERROR_BREAK(state->error, 69); - } - //unknown = 1; - } - -#if 0 //We don't use CRC - if (!state->decoder.ignore_crc && !unknown) /*check CRC if wanted, only on known chunk types*/ { - if (lodepng_chunk_check_crc(chunk)) CERROR_BREAK(state->error, 57); /*invalid CRC*/ - } -#endif - if (!IEND) chunk = lodepng_chunk_next_const(chunk, in + insize); - } - - if (state->info_png.color.colortype == LCT_PALETTE && !state->info_png.color.palette) { - state->error = 106; /* error: PNG file must have PLTE chunk if color type is palette */ - } - - if (!state->error) { - /*predict output size, to allocate exact size for output buffer to avoid more dynamic allocation. - If the decompressed size does not match the prediction, the image must be corrupt.*/ - if (state->info_png.interlace_method == 0) { - size_t bpp = lodepng_get_bpp_lct(state->info_png.color.colortype, state->info_png.color.bitdepth); - expected_size = lodepng_get_raw_size_idat(*w, *h, bpp); - } else { - size_t bpp = lodepng_get_bpp_lct(state->info_png.color.colortype, state->info_png.color.bitdepth); - /*Adam-7 interlaced: expected size is the sum of the 7 sub-images sizes*/ - expected_size = 0; - expected_size += lodepng_get_raw_size_idat((*w + 7) >> 3, (*h + 7) >> 3, bpp); - if (*w > 4) expected_size += lodepng_get_raw_size_idat((*w + 3) >> 3, (*h + 7) >> 3, bpp); - expected_size += lodepng_get_raw_size_idat((*w + 3) >> 2, (*h + 3) >> 3, bpp); - if (*w > 2) expected_size += lodepng_get_raw_size_idat((*w + 1) >> 2, (*h + 3) >> 2, bpp); - expected_size += lodepng_get_raw_size_idat((*w + 1) >> 1, (*h + 1) >> 2, bpp); - if (*w > 1) expected_size += lodepng_get_raw_size_idat((*w + 0) >> 1, (*h + 1) >> 1, bpp); - expected_size += lodepng_get_raw_size_idat((*w + 0), (*h + 0) >> 1, bpp); - } - state->error = zlib_decompress(&scanlines, &scanlines_size, expected_size, idat, idatsize, &state->decoder.zlibsettings); - } - - if (!state->error && scanlines_size != expected_size) state->error = 91; /*decompressed size doesn't match prediction*/ - free(idat); - - if (!state->error) { - outsize = lodepng_get_raw_size(*w, *h, &state->info_png.color); - *out = (unsigned char*)malloc(outsize); - if (!*out) state->error = 83; /*alloc fail*/ - } - if (!state->error) { - lodepng_memset(*out, 0, outsize); - state->error = postProcessScanlines(*out, scanlines, *w, *h, &state->info_png); - } - free(scanlines); -} - - -static void lodepng_decoder_settings_init(LodePNGDecoderSettings* settings) -{ - settings->color_convert = 1; - settings->ignore_crc = 0; - settings->ignore_critical = 0; - settings->ignore_end = 0; - lodepng_decompress_settings_init(&settings->zlibsettings); -} - - -/************************************************************************/ -/* External Class Implementation */ -/************************************************************************/ - -/*read the information from the header and store it in the LodePNGInfo. return value is error*/ -unsigned lodepng_inspect(unsigned* w, unsigned* h, LodePNGState* state, const unsigned char* in, size_t insize) -{ - unsigned width, height; - LodePNGInfo* info = &state->info_png; - if (insize == 0 || in == 0) { - CERROR_RETURN_ERROR(state->error, 48); /*error: the given data is empty*/ - } - if (insize < 33) { - CERROR_RETURN_ERROR(state->error, 27); /*error: the data length is smaller than the length of a PNG header*/ - } - - /* when decoding a new PNG image, make sure all parameters created after previous decoding are reset */ - /* TODO: remove this. One should use a new LodePNGState for new sessions */ - lodepng_info_cleanup(info); - lodepng_info_init(info); - - if (in[0] != 137 || in[1] != 80 || in[2] != 78 || in[3] != 71 || in[4] != 13 || in[5] != 10 || in[6] != 26 || in[7] != 10) { - CERROR_RETURN_ERROR(state->error, 28); /*error: the first 8 bytes are not the correct PNG signature*/ - } - if (lodepng_chunk_length(in + 8) != 13) { - CERROR_RETURN_ERROR(state->error, 94); /*error: header size must be 13 bytes*/ - } - if (!lodepng_chunk_type_equals(in + 8, "IHDR")) { - CERROR_RETURN_ERROR(state->error, 29); /*error: it doesn't start with a IHDR chunk!*/ - } - - /*read the values given in the header*/ - width = lodepng_read32bitInt(&in[16]); - height = lodepng_read32bitInt(&in[20]); - /*TODO: remove the undocumented feature that allows to give null pointers to width or height*/ - if (w) *w = width; - if (h) *h = height; - info->color.bitdepth = in[24]; - info->color.colortype = (LodePNGColorType)in[25]; - info->compression_method = in[26]; - info->filter_method = in[27]; - info->interlace_method = in[28]; - - /*errors returned only after the parsing so other values are still output*/ - - /*error: invalid image size*/ - if (width == 0 || height == 0) CERROR_RETURN_ERROR(state->error, 93); - /*error: invalid colortype or bitdepth combination*/ - state->error = checkColorValidity(info->color.colortype, info->color.bitdepth); - if (state->error) return state->error; - /*error: only compression method 0 is allowed in the specification*/ - if (info->compression_method != 0) CERROR_RETURN_ERROR(state->error, 32); - /*error: only filter method 0 is allowed in the specification*/ - if (info->filter_method != 0) CERROR_RETURN_ERROR(state->error, 33); - /*error: only interlace methods 0 and 1 exist in the specification*/ - if (info->interlace_method > 1) CERROR_RETURN_ERROR(state->error, 34); - -#if 0 //thorvg don't use crc - if (!state->decoder.ignore_crc) { - unsigned CRC = lodepng_read32bitInt(&in[29]); - unsigned checksum = lodepng_crc32(&in[12], 17); - if (CRC != checksum) { - CERROR_RETURN_ERROR(state->error, 57); /*invalid CRC*/ - } - } -#endif - return state->error; -} - - -unsigned lodepng_decode(unsigned char** out, unsigned* w, unsigned* h, LodePNGState* state, const unsigned char* in, size_t insize) -{ - *out = 0; - decodeGeneric(out, w, h, state, in, insize); - if (state->error) return state->error; - if (!state->decoder.color_convert || lodepng_color_mode_equal(&state->info_raw, &state->info_png.color)) { - /*same color type, no copying or converting of data needed*/ - /*store the info_png color settings on the info_raw so that the info_raw still reflects what colortype - the raw image has to the end user*/ - if (!state->decoder.color_convert) { - state->error = lodepng_color_mode_copy(&state->info_raw, &state->info_png.color); - if (state->error) return state->error; - } - } else { /*color conversion needed*/ - unsigned char* data = *out; - size_t outsize; - - /*TODO: check if this works according to the statement in the documentation: "The converter can convert - from grayscale input color type, to 8-bit grayscale or grayscale with alpha"*/ - if (!(state->info_raw.colortype == LCT_RGB || state->info_raw.colortype == LCT_RGBA) && !(state->info_raw.bitdepth == 8)) { - return 56; /*unsupported color mode conversion*/ - } - - outsize = lodepng_get_raw_size(*w, *h, &state->info_raw); - *out = (unsigned char*)malloc(outsize); - if (!(*out)) { - state->error = 83; /*alloc fail*/ - } - else state->error = lodepng_convert(*out, data, &state->info_raw, &state->info_png.color, *w, *h); - free(data); - } - return state->error; -} - - -void lodepng_state_init(LodePNGState* state) -{ - lodepng_decoder_settings_init(&state->decoder); - lodepng_color_mode_init(&state->info_raw); - lodepng_info_init(&state->info_png); - state->error = 1; -} - - -void lodepng_state_cleanup(LodePNGState* state) -{ - lodepng_color_mode_cleanup(&state->info_raw); - lodepng_info_cleanup(&state->info_png); -} diff --git a/thirdparty/thorvg/src/loaders/png/tvgLodePng.h b/thirdparty/thorvg/src/loaders/png/tvgLodePng.h deleted file mode 100644 index 0cdac7cbea..0000000000 --- a/thirdparty/thorvg/src/loaders/png/tvgLodePng.h +++ /dev/null @@ -1,174 +0,0 @@ -/* - * Copyright (c) 2020 - 2022 Samsung Electronics Co., Ltd. All rights reserved. - - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ - -/* - LodePNG version 20200306 - - Copyright (c) 2005-2020 Lode Vandevenne - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - - 3. This notice may not be removed or altered from any source - distribution. -*/ - -#ifndef _TVG_LODEPNG_H_ -#define _TVG_LODEPNG_H_ - -#include <stddef.h> - -/*The PNG color types (also used for raw image).*/ -enum LodePNGColorType -{ - LCT_GREY = 0, /*grayscale: 1,2,4,8,16 bit*/ - LCT_RGB = 2, /*RGB: 8,16 bit*/ - LCT_PALETTE = 3, /*palette: 1,2,4,8 bit*/ - LCT_GREY_ALPHA = 4, /*grayscale with alpha: 8,16 bit*/ - LCT_RGBA = 6, /*RGB with alpha: 8,16 bit*/ - /*LCT_MAX_OCTET_VALUE lets the compiler allow this enum to represent any invalid - byte value from 0 to 255 that could be present in an invalid PNG file header. Do - not use, compare with or set the name LCT_MAX_OCTET_VALUE, instead either use - the valid color type names above, or numeric values like 1 or 7 when checking for - particular disallowed color type byte values, or cast to integer to print it.*/ - LCT_MAX_OCTET_VALUE = 255 -}; - -/*Settings for zlib decompression*/ -struct LodePNGDecompressSettings -{ - /* Check LodePNGDecoderSettings for more ignorable errors such as ignore_crc */ - unsigned ignore_adler32; /*if 1, continue and don't give an error message if the Adler32 checksum is corrupted*/ - unsigned ignore_nlen; /*ignore complement of len checksum in uncompressed blocks*/ - - /*use custom zlib decoder instead of built in one (default: null)*/ - unsigned (*custom_zlib)(unsigned char**, size_t*, const unsigned char*, size_t, const LodePNGDecompressSettings*); - /*use custom deflate decoder instead of built in one (default: null) if custom_zlib is not null, custom_inflate is ignored (the zlib format uses deflate)*/ - unsigned (*custom_inflate)(unsigned char**, size_t*, const unsigned char*, size_t, const LodePNGDecompressSettings*); - - const void* custom_context; /*optional custom settings for custom functions*/ -}; - -/* - Color mode of an image. Contains all information required to decode the pixel - bits to RGBA colors. This information is the same as used in the PNG file - format, and is used both for PNG and raw image data in LodePNG. -*/ -struct LodePNGColorMode -{ - /*header (IHDR)*/ - LodePNGColorType colortype; /*color type, see PNG standard or documentation further in this header file*/ - unsigned bitdepth; /*bits per sample, see PNG standard or documentation further in this header file*/ - - /* - palette (PLTE and tRNS) - - Dynamically allocated with the colors of the palette, including alpha. - This field may not be allocated directly, use lodepng_color_mode_init first, - then lodepng_palette_add per color to correctly initialize it (to ensure size - of exactly 1024 bytes). - - The alpha channels must be set as well, set them to 255 for opaque images. - - When decoding, by default you can ignore this palette, since LodePNG already - fills the palette colors in the pixels of the raw RGBA output. - - The palette is only supported for color type 3. - */ - unsigned char* palette; /*palette in RGBARGBA... order. Must be either 0, or when allocated must have 1024 bytes*/ - size_t palettesize; /*palette size in number of colors (amount of used bytes is 4 * palettesize)*/ - - /* - transparent color key (tRNS) - - This color uses the same bit depth as the bitdepth value in this struct, which can be 1-bit to 16-bit. - For grayscale PNGs, r, g and b will all 3 be set to the same. - - When decoding, by default you can ignore this information, since LodePNG sets - pixels with this key to transparent already in the raw RGBA output. - - The color key is only supported for color types 0 and 2. - */ - unsigned key_defined; /*is a transparent color key given? 0 = false, 1 = true*/ - unsigned key_r; /*red/grayscale component of color key*/ - unsigned key_g; /*green component of color key*/ - unsigned key_b; /*blue component of color key*/ -}; - -/*Information about the PNG image, except pixels, width and height.*/ -struct LodePNGInfo -{ - /*header (IHDR), palette (PLTE) and transparency (tRNS) chunks*/ - unsigned compression_method;/*compression method of the original file. Always 0.*/ - unsigned filter_method; /*filter method of the original file*/ - unsigned interlace_method; /*interlace method of the original file: 0=none, 1=Adam7*/ - LodePNGColorMode color; /*color type and bits, palette and transparency of the PNG file*/ -}; - -/* - Settings for the decoder. This contains settings for the PNG and the Zlib - decoder, but not the Info settings from the Info structs. -*/ -struct LodePNGDecoderSettings -{ - LodePNGDecompressSettings zlibsettings; /*in here is the setting to ignore Adler32 checksums*/ - - /* Check LodePNGDecompressSettings for more ignorable errors such as ignore_adler32 */ - unsigned ignore_crc; /*ignore CRC checksums*/ - unsigned ignore_critical; /*ignore unknown critical chunks*/ - unsigned ignore_end; /*ignore issues at end of file if possible (missing IEND chunk, too large chunk, ...)*/ - /* TODO: make a system involving warnings with levels and a strict mode instead. Other potentially recoverable - errors: srgb rendering intent value, size of content of ancillary chunks, more than 79 characters for some - strings, placement/combination rules for ancillary chunks, crc of unknown chunks, allowed characters - in string keys, etc... */ - - unsigned color_convert; /*whether to convert the PNG to the color type you want. Default: yes*/ -}; - -/*The settings, state and information for extended encoding and decoding.*/ -struct LodePNGState -{ - LodePNGDecoderSettings decoder; /*the decoding settings*/ - LodePNGColorMode info_raw; /*specifies the format in which you would like to get the raw pixel buffer*/ - LodePNGInfo info_png; /*info of the PNG image obtained after decoding*/ - unsigned error; -}; - -void lodepng_state_init(LodePNGState* state); -void lodepng_state_cleanup(LodePNGState* state); -unsigned lodepng_decode(unsigned char** out, unsigned* w, unsigned* h, LodePNGState* state, const unsigned char* in, size_t insize); -unsigned lodepng_inspect(unsigned* w, unsigned* h, LodePNGState* state, const unsigned char* in, size_t insize); - -#endif //_TVG_LODEPNG_H_ diff --git a/thirdparty/thorvg/src/loaders/png/tvgPngLoader.cpp b/thirdparty/thorvg/src/loaders/png/tvgPngLoader.cpp deleted file mode 100644 index 3e293176b7..0000000000 --- a/thirdparty/thorvg/src/loaders/png/tvgPngLoader.cpp +++ /dev/null @@ -1,194 +0,0 @@ -/* - * Copyright (c) 2021 - 2022 Samsung Electronics Co., Ltd. All rights reserved. - - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ -#include <memory.h> -#include "tvgLoader.h" -#include "tvgPngLoader.h" - - -/************************************************************************/ -/* Internal Class Implementation */ -/************************************************************************/ - - -static inline uint32_t PREMULTIPLY(uint32_t c) -{ - auto a = (c >> 24); - return (c & 0xff000000) + ((((c >> 8) & 0xff) * a) & 0xff00) + ((((c & 0x00ff00ff) * a) >> 8) & 0x00ff00ff); -} - - -static void _premultiply(uint32_t* data, uint32_t w, uint32_t h) -{ - auto buffer = data; - for (uint32_t y = 0; y < h; ++y, buffer += w) { - auto src = buffer; - for (uint32_t x = 0; x < w; ++x, ++src) { - *src = PREMULTIPLY(*src); - } - } -} - - -void PngLoader::clear() -{ - lodepng_state_cleanup(&state); - - if (freeData) free(data); - data = nullptr; - size = 0; - freeData = false; -} - - -/************************************************************************/ -/* External Class Implementation */ -/************************************************************************/ - -PngLoader::PngLoader() -{ - lodepng_state_init(&state); -} - - -PngLoader::~PngLoader() -{ - if (freeData) free(data); - free(image); -} - - -bool PngLoader::open(const string& path) -{ - clear(); - - auto pngFile = fopen(path.c_str(), "rb"); - if (!pngFile) return false; - - auto ret = false; - - //determine size - if (fseek(pngFile, 0, SEEK_END) < 0) goto finalize; - if (((size = ftell(pngFile)) < 1)) goto finalize; - if (fseek(pngFile, 0, SEEK_SET)) goto finalize; - - data = (unsigned char *) malloc(size); - if (!data) goto finalize; - - freeData = true; - - if (fread(data, size, 1, pngFile) < 1) goto failure; - - lodepng_state_init(&state); - - unsigned int width, height; - if (lodepng_inspect(&width, &height, &state, data, size) > 0) goto failure; - - w = static_cast<float>(width); - h = static_cast<float>(height); - ret = true; - - goto finalize; - -failure: - clear(); - -finalize: - fclose(pngFile); - return ret; -} - - -bool PngLoader::open(const char* data, uint32_t size, bool copy) -{ - clear(); - - lodepng_state_init(&state); - - unsigned int width, height; - if (lodepng_inspect(&width, &height, &state, (unsigned char*)(data), size) > 0) return false; - - if (copy) { - this->data = (unsigned char *) malloc(size); - if (!this->data) return false; - memcpy((unsigned char *)this->data, data, size); - freeData = true; - } else { - this->data = (unsigned char *) data; - freeData = false; - } - - w = static_cast<float>(width); - h = static_cast<float>(height); - this->size = size; - - return true; -} - - -bool PngLoader::read() -{ - if (!data || w <= 0 || h <= 0) return false; - - TaskScheduler::request(this); - - return true; -} - - -bool PngLoader::close() -{ - this->done(); - clear(); - return true; -} - - -unique_ptr<Surface> PngLoader::bitmap() -{ - this->done(); - - if (!image) return nullptr; - - auto surface = static_cast<Surface*>(malloc(sizeof(Surface))); - surface->buffer = (uint32_t*)(image); - surface->stride = w; - surface->w = w; - surface->h = h; - surface->cs = SwCanvas::ARGB8888; - - return unique_ptr<Surface>(surface); -} - - -void PngLoader::run(unsigned tid) -{ - if (image) { - free(image); - image = nullptr; - } - auto width = static_cast<unsigned>(w); - auto height = static_cast<unsigned>(h); - - lodepng_decode(&image, &width, &height, &state, data, size); - - _premultiply((uint32_t*)(image), width, height); -} diff --git a/thirdparty/thorvg/src/loaders/png/tvgPngLoader.h b/thirdparty/thorvg/src/loaders/png/tvgPngLoader.h deleted file mode 100644 index 8f07f6418f..0000000000 --- a/thirdparty/thorvg/src/loaders/png/tvgPngLoader.h +++ /dev/null @@ -1,54 +0,0 @@ -/* - * Copyright (c) 2021 - 2022 Samsung Electronics Co., Ltd. All rights reserved. - - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ -#ifndef _TVG_PNG_LOADER_H_ -#define _TVG_PNG_LOADER_H_ - -#include "tvgLodePng.h" -#include "tvgTaskScheduler.h" - - -class PngLoader : public LoadModule, public Task -{ -private: - LodePNGState state; - unsigned char* data = nullptr; - unsigned char *image = nullptr; - unsigned long size = 0; - bool freeData = false; - - void clear(); - -public: - PngLoader(); - ~PngLoader(); - - using LoadModule::open; - bool open(const string& path) override; - bool open(const char* data, uint32_t size, bool copy) override; - bool read() override; - bool close() override; - - unique_ptr<Surface> bitmap() override; - void run(unsigned tid) override; -}; - -#endif //_TVG_PNG_LOADER_H_ diff --git a/thirdparty/thorvg/src/loaders/svg/tvgXmlParser.cpp b/thirdparty/thorvg/src/loaders/svg/tvgXmlParser.cpp index d7c51bdc30..c373da2dd5 100644 --- a/thirdparty/thorvg/src/loaders/svg/tvgXmlParser.cpp +++ b/thirdparty/thorvg/src/loaders/svg/tvgXmlParser.cpp @@ -26,8 +26,8 @@ #ifdef _WIN32 #include <malloc.h> -#elif defined(__FreeBSD__) - #include <stdlib.h> +#elif __FreeBSD__ + #include<stdlib.h> #else #include <alloca.h> #endif @@ -390,7 +390,7 @@ bool simpleXmlParse(const char* buf, unsigned bufLength, bool strip, simpleXMLCb if (p) { //Invalid case: '<' nested - if (*p == '<') return false; + if (*p == '<' && type != SimpleXMLType::Doctype) return false; const char *start, *end; start = itr + 1 + toff; diff --git a/thirdparty/thorvg/src/loaders/tvg/tvgTvgBinInterpreter.cpp b/thirdparty/thorvg/src/loaders/tvg/tvgTvgBinInterpreter.cpp index 66de860aaa..62a75ecd3d 100644 --- a/thirdparty/thorvg/src/loaders/tvg/tvgTvgBinInterpreter.cpp +++ b/thirdparty/thorvg/src/loaders/tvg/tvgTvgBinInterpreter.cpp @@ -23,8 +23,8 @@ #ifdef _WIN32 #include <malloc.h> -#elif defined(__FreeBSD__) - #include <stdlib.h> +#elif __FreeBSD__ + #include<stdlib.h> #else #include <alloca.h> #endif diff --git a/thirdparty/thorvg/src/savers/tvg/tvgTvgSaver.cpp b/thirdparty/thorvg/src/savers/tvg/tvgTvgSaver.cpp index fca313b430..adf85836c3 100644 --- a/thirdparty/thorvg/src/savers/tvg/tvgTvgSaver.cpp +++ b/thirdparty/thorvg/src/savers/tvg/tvgTvgSaver.cpp @@ -28,8 +28,8 @@ #ifdef _WIN32 #include <malloc.h> -#elif defined(__FreeBSD__) - #include <stdlib.h> +#elif __FreeBSD__ + #include<stdlib.h> #else #include <alloca.h> #endif diff --git a/thirdparty/thorvg/update-thorvg.sh b/thirdparty/thorvg/update-thorvg.sh index a3b73a7135..f2fd2a80e4 100755 --- a/thirdparty/thorvg/update-thorvg.sh +++ b/thirdparty/thorvg/update-thorvg.sh @@ -1,12 +1,12 @@ -VERSION=0.8.1 +VERSION=0.8.2 rm -rf AUTHORS inc LICENSE src *.zip -curl -L -O https://github.com/Samsung/thorvg/archive/$VERSION.zip +curl -L -O https://github.com/Samsung/thorvg/archive/v$VERSION.zip bsdtar --strip-components=1 -xvf *.zip rm *.zip -rm -rf .github docs pc res test tools .git* *.md *.txt wasm_build.sh +rm -rf .github docs pc res test tools tvgcompat .git* *.md *.txt wasm_build.sh find . -type f -name 'meson.build' -delete rm -rf src/bin src/bindings src/examples src/wasm -rm -rf src/lib/gl_engine tvgcompat +rm -rf src/lib/gl_engine src/loaders/external_jpg src/loaders/png cat << EOF > inc/config.h #ifndef THORVG_CONFIG_H #define THORVG_CONFIG_H |