summaryrefslogtreecommitdiff
path: root/macros/luatex/generic/luaotfload
diff options
context:
space:
mode:
Diffstat (limited to 'macros/luatex/generic/luaotfload')
-rw-r--r--macros/luatex/generic/luaotfload/COPYING350
-rw-r--r--macros/luatex/generic/luaotfload/NEWS343
-rw-r--r--macros/luatex/generic/luaotfload/README.md103
-rw-r--r--macros/luatex/generic/luaotfload/filegraph.pdfbin0 -> 39715 bytes
-rw-r--r--macros/luatex/generic/luaotfload/filegraph.tex266
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-2019-08-11.lua34169
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-basics-chr.lua3619
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-basics-gen.lua479
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-basics-nod.lua263
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-data-con.lua138
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-afk.lua200
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-cff.lua2483
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-cid.lua177
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-con.lua1711
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-def.lua536
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-dsp.lua3902
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-imp-effects.lua414
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-imp-italics.lua147
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-imp-ligatures.lua136
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-imp-tex.lua144
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-ini.lua54
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-lua.lua46
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-map.lua693
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-ocl.lua670
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-one.lua842
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-onr.lua550
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-osd.lua2859
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-ota.lua448
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-otc.lua875
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-oti.lua262
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-otj.lua1755
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-otl.lua857
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-oto.lua542
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-otr.lua2553
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-ots.lua4492
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-ott.lua1234
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-oup.lua3067
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-ttf.lua1379
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-font-vfc.lua123
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-def.lua98
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-enc.lua75
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-ext.lua244
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-gbn.lua300
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-lig.lua2067
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-mis.lua35
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-syn.lua104
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-fonts-tfm.lua654
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-boolean.lua69
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-file.lua738
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-function.lua11
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-io.lua473
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-lpeg.lua1196
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-lua.lua259
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-math.lua149
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-string.lua244
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-table.lua1471
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-l-unicode.lua1405
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-reference-load-order.lua349
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-reference-load-order.tex140
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-reference.lua38728
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-util-fil.lua452
-rw-r--r--macros/luatex/generic/luaotfload/fontloader-util-str.lua1461
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-auxiliary.lua851
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-blacklist.cnf4
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-characters.lua203947
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-colors.lua414
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-conf.pdfbin0 -> 77672 bytes
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-configuration.lua1034
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-database.lua3764
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-diagnostics.lua698
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-embolden.lua42
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-features.lua596
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-filelist.lua430
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-glyphlist.lua4313
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-init.lua781
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-latex.pdfbin0 -> 347111 bytes
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-latex.tex530
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-letterspace.lua578
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-loaders.lua240
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-log.lua394
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-main.lua313
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-main.tex2035
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-notdef.lua105
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-parsers.lua799
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-resolvers.lua303
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-status.lua90
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-tool.1442
-rwxr-xr-xmacros/luatex/generic/luaotfload/luaotfload-tool.lua1661
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-tool.pdfbin0 -> 76919 bytes
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-tool.rst328
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload-unicode.lua109
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload.conf.5632
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload.conf.example30
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload.conf.rst409
-rw-r--r--macros/luatex/generic/luaotfload/luaotfload.sty53
95 files changed, 349528 insertions, 0 deletions
diff --git a/macros/luatex/generic/luaotfload/COPYING b/macros/luatex/generic/luaotfload/COPYING
new file mode 100644
index 0000000000..d769b3faa1
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/COPYING
@@ -0,0 +1,350 @@
+Context, where the fontloader Luaotfload is built around originates, is
+licensed under the GPL version 2.0 (exactly). As a derived work, anything
+Luaotflaod adds to that is also subject to the same license at the same
+version. The “any later version” clause as used by the FSF in the license text
+*does not apply* to either Context or Luaotfload, despite being kept around in
+the license text given below.
+
+-------------------------------------------------------------------------------
+ LICENSE TEXT BELOW
+-------------------------------------------------------------------------------
+
+ GNU GENERAL PUBLIC LICENSE
+ Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
+ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+ Preamble
+
+ The licenses for most software are designed to take away your
+freedom to share and change it. By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users. This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it. (Some other Free Software Foundation software is covered by
+the GNU Lesser General Public License instead.) You can apply it to
+your programs, too.
+
+ When we speak of free software, we are referring to freedom, not
+price. Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+ To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+ For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have. You must make sure that they, too, receive or can get the
+source code. And you must show them these terms so they know their
+rights.
+
+ We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+ Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software. If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+ Finally, any free program is threatened constantly by software
+patents. We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary. To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+ The precise terms and conditions for copying, distribution and
+modification follow.
+
+ GNU GENERAL PUBLIC LICENSE
+ TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+ 0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License. The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language. (Hereinafter, translation is included without limitation in
+the term "modification".) Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope. The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+ 1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+ 2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+ a) You must cause the modified files to carry prominent notices
+ stating that you changed the files and the date of any change.
+
+ b) You must cause any work that you distribute or publish, that in
+ whole or in part contains or is derived from the Program or any
+ part thereof, to be licensed as a whole at no charge to all third
+ parties under the terms of this License.
+
+ c) If the modified program normally reads commands interactively
+ when run, you must cause it, when started running for such
+ interactive use in the most ordinary way, to print or display an
+ announcement including an appropriate copyright notice and a
+ notice that there is no warranty (or else, saying that you provide
+ a warranty) and that users may redistribute the program under
+ these conditions, and telling the user how to view a copy of this
+ License. (Exception: if the Program itself is interactive but
+ does not normally print such an announcement, your work based on
+ the Program is not required to print an announcement.)
+
+These requirements apply to the modified work as a whole. If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works. But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+ 3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+ a) Accompany it with the complete corresponding machine-readable
+ source code, which must be distributed under the terms of Sections
+ 1 and 2 above on a medium customarily used for software interchange; or,
+
+ b) Accompany it with a written offer, valid for at least three
+ years, to give any third party, for a charge no more than your
+ cost of physically performing source distribution, a complete
+ machine-readable copy of the corresponding source code, to be
+ distributed under the terms of Sections 1 and 2 above on a medium
+ customarily used for software interchange; or,
+
+ c) Accompany it with the information you received as to the offer
+ to distribute corresponding source code. (This alternative is
+ allowed only for noncommercial distribution and only if you
+ received the program in object code or executable form with such
+ an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it. For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable. However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+
+ 4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License. Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+ 5. You are not required to accept this License, since you have not
+signed it. However, nothing else grants you permission to modify or
+distribute the Program or its derivative works. These actions are
+prohibited by law if you do not accept this License. Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+ 6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions. You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+ 7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License. If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all. For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices. Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+
+ 8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded. In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+ 9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time. Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number. If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation. If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+ 10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission. For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this. Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+ NO WARRANTY
+
+ 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+ 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+ END OF TERMS AND CONDITIONS
+
+ How to Apply These Terms to Your New Programs
+
+ If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+ To do so, attach the following notices to the program. It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+ <one line to give the program's name and a brief idea of what it does.>
+ Copyright (C) <year> <name of author>
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License along
+ with this program; if not, write to the Free Software Foundation, Inc.,
+ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+ Gnomovision version 69, Copyright (C) year name of author
+ Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+ This is free software, and you are welcome to redistribute it
+ under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License. Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary. Here is a sample; alter the names:
+
+ Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+ `Gnomovision' (which makes passes at compilers) written by James Hacker.
+
+ <signature of Ty Coon>, 1 April 1989
+ Ty Coon, President of Vice
+
+This General Public License does not permit incorporating your program into
+proprietary programs. If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library. If this is what you want to do, use the GNU Lesser General
+Public License instead of this License.
diff --git a/macros/luatex/generic/luaotfload/NEWS b/macros/luatex/generic/luaotfload/NEWS
new file mode 100644
index 0000000000..aa6b4ca7d7
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/NEWS
@@ -0,0 +1,343 @@
+Change History
+--------------
+2019-08-11 luaotfload v2.991
+ * fix issue #88
+
+2019-08-11 luaotfload v2.99
+ * some clean up
+ * fix a bug in luaotfload.aux.resolve_fontname() (issue #76)
+ * removed dependency on slnunicode (PR#72)
+ * sync with context files from 2019-08-11
+
+2019-06-20 luaotfload v2.98
+ * add embolden key
+ * add missing char detection issue #65
+ * sync with context files from 2019-07-04
+
+2019-05-18 luaotfload v2.97
+ * fix issue #47
+ * fix whatsits interfering with letterspacing (issue #53)
+ * fix luaotfload-tool switches version and find not working correctly (PR#59)
+ * fix luaotfload-tool support of ttc fonts (PR#58)
+ * sync with context files from 2019-05-18 (improves handling of large fonts, see e.g. issue #55 and PR#58)
+
+2019-01-28 luaotfload v2.96
+ * repaired broken letterspace (issue #38)
+ * changed handling of spaces in letterspacing
+ * changed handling of ligatures in letterspacing
+ * corrected detection of bold fonts (issue #41)
+
+2019-01-28 luaotfload v2.95
+ * imported context files of 2019-01-28
+ * changed bold indification (for lucida demi bold) (issue #33)
+ * changed handling of tex file (issue #35)
+ * changed resolver code (pr #36)
+
+2019-01-14 luaotfload v2.94
+ * imported context files of 2018-12-19
+ * removed luaotfload-characters from init - use the basics-chr instead.
+ * allow custom fontloaders through the mode-key https://github.com/u-fischer/luaotfload/pull/25
+ * resolved issue #29
+
+2018-10-28 luaotfload v2.93
+ * reinserted forgotten man files
+ * unified and improved version/module info for automatic tagging
+
+
+2018-10-21 luaotfload v2.92
+ * better deva support, issue #9
+ * test for --safer and abort, issue #12
+ * newest context files
+ * correct file: syntax for tfm files, issue #11.
+
+2018-10-03 luaotfload v2.91
+ * solved copy & paste of variant glyphs, https://tex.stackexchange.com/questions/451442/localized-glyphs-locl-have-unicode-value-ufffd
+ * solved problem with PUA no longer accessible with \char, see https://github.com/u-fischer/luaotfload/issues/7
+
+2018-09-21 luaotfload v2.9
+ * added various testfiles for the l3build system/travis tests to the github repository
+ * solved a bug regarding directions https://github.com/u-fischer/lua-font-pond/issues/12
+ * adapted luaotfload-letterspace to new fontloader
+ * solved the case problem see https://github.com/u-fischer/lua-font-pond/issues/6
+ * Fix parsing of font.conf see https://github.com/lualatex/luaotfload/pull/420
+ * imported new versions of the context files - fontloader is compatible with luatex 1.08 again
+ * adapted the files list
+ * created a luaotfload-filelist.lua which describes the files of the package
+ * removed some not functional files
+ * adapted mkstatus to use the new file list.
+
+2017-01-29, luaotfload v2.8:
+ * Latest fontloader code.
+ * Support for Luatex 1.0.
+ * Integration of the extended AFM handler.
+ * Fixes to font family assignment.
+ * Skip initialization if Luaotfload is already loaded.
+ * Optical sizes advertised by fonts treated as big points.
+
+2016/04/21, luaotfload v2.7:
+ * Rework lookup chaining.
+ * Combining glyphs from different fonts (``combo: ...`` requests).
+ * Glyph fallbacks.
+ * Latest fontloader code.
+ * Adapt packaging to changed upstream file layout.
+ * Remove support for builtin Fontforge libraries (this includes the PFA,
+ PFB, DFONT, and feature file readers).
+ * Allow configuration of anonymous lookups.
+
+2015/12/09, luaotfload v2.6
+ * Add ``sign`` target to makefile for automated package signing.
+ * Add ``--dumpconf`` option to luaotfload-tool for generating configuration
+ files.
+ * Move fontloader files to subtree src/fontloader.
+ * New script ``mkimport`` facilitates maintainance of code imported from
+ Context.
+ * Revised letterspacing, now utilizing the ``node.direct`` interface.
+ * Revized colorization of fonts, utilizing ``node.direct`` (Dohyun Kim).
+ * Colorization was moved to the ``post_linebreak_filter`` stage.
+ * Move remaining functionality from ``luaotfload-override`` into
+ initialization.
+ * Write names index if fonts were removed.
+ * Separate module loading from initialization.
+ * Custom fontloader package with the files from Lualibs removed.
+ * Swappable fontloader via configuration option.
+ * Lualibs are now a dependency when used in a TeX run as well.
+ * Respect interword spaces when letterspacing.
+
+2014/07/13, luaotfload v2.5
+ * Remove legacy code.
+ * Remove compatibility with the old mkluatexfontdb script.
+ * Remove test directory. Use https://bitbucket.org/phg/lua-la-tex-tests
+ instead.
+ * Remove luaotfload.lua from luaotfload.dtx; it is now a separate file
+ luaotfload-main.lua.
+ * Standard source tree structure: the code is now located in the ./doc,
+ ./scripts, ./src, ./build, and ./misc directories.
+ * Move the heavier LPEG parsers from luaotfload-features (syntax) and
+ luaotfload-database (fontconfig) into the new file
+ luaotfload-parsers.lua.
+ * Move logging routines from luaotfload-override in to luaotfload-log.
+ * Scan local font files (``--local`` flag to luaotfload-tool, flag
+ ``scan_local`` during TeX run).
+ * Add bisection mode (``--bisect``) to luaotfload-tool.
+ * Add functions for accessing the database: ``aux.font_index()`` and
+ ``aux.read_font_index()``.
+ * Distinguish XDG configuration paths (Reuben Thomas)
+ * Optional configuration via rc files.
+ * Configure default features via configuration file.
+
+2013/12/31, luaotfload v2.4
+ * Additional self-tests, now in separate file (luaotfload-diagnostics.lua)
+ * Better path and directory handling, especially on Windows
+ * database now indexes Type1 fonts (PFA, PFB) and makes them accessible
+ with style modifiers (requires --format=+pfa,pfb option to luaotfload-tool)
+ * Test runner (script mktests)
+ * New luaotfload-tool option: ``--no-reload``
+ * ``luaotfload-tool --find`` now understands request syntax
+ * text (Lua script) version of the font index is filtered through gzip by
+ default, the ``--no-compress`` option of luaotfload-tool will prevent
+ this
+ * rename ``luaotfload-merged.lua`` (the fontloader package from Context)
+ to ``luaotfload-fontloader.lua``
+ * Treat arguments of the ``letterspace`` option as percentages; add
+ ``kernfactor`` option that behaves as before.
+ * Remove imported version of typo-krn.lua. Xetex-style per-font
+ letterspacing is now the canonical method.
+ * Merge functionality from extralibs (fake Context layer) into
+ luaotfload-letterspace.lua as it is only needed there anyways.
+
+2013/07/10, luaotfload v2.3a
+ * Detect LuaJIT interpreter (LuaJITTeX)
+ * Self-test functionality for luaotfload-tool.lua (option ``--diagnose``)
+
+2013/07/03, luaotfload v2.3:
+ * New experimental lookups: ``kpse`` (kpathsea), ``my`` (callback)
+ * Precedence of texmf over system fonts can be requested
+ using the ``--prefer-texmf`` option of luaotfload-tool
+ * Resolve file names to full paths at later stage
+ * Rewrite the output of ``\fontname`` via ``patch_font`` callback
+ * Allow blacklisting directories
+ * Drop compatibility layer
+ * Remove dependency on luaotfload-lib-dir (references to dir.glob() and
+ dir.mkdirs())
+ * luaotfload-tool now displays extensive information about a font if given
+ the argument --inspect
+
+2013/05/20, luaotfload v2.2:
+ * There is now a central, non-personal dev repo on github:
+ https://github.com/lualatex/luaotfload
+ * Synchronisation with ConTeXt from TeXLive 2013, inducing
+ backward-incompatible changes in the font structure. A
+ backward-compatibility layer has been added for the current
+ versions of fontspec, unicode-math and microtype, but it should
+ disapear in a future version.
+ * Synchronisation with ConTeXt is now easier and can be done by just
+ updating luaotfload-merged.lua (<= luatex-fonts-merged.lua from
+ the LuaTeX-Plain format)
+ * Improved and extended documentation
+ * Font filenames are stored in the database (file: lookups more efficient)
+ * Optional caching of name: lookups (uses separate cache file)
+ * Rewriting and increased fidelity of XeTeX emulation
+ * Renaming mkluatexfontdb into luaotfload-tool (the old behavior is kept if
+ the script is symlinked or renamed mkluatexfontdb)
+ * Added options to luaotfload-tool for simple database queries
+ * Logging facilities have been rewritten and allow for more granularity
+ * All files have been renamed, abandoning cryptic acronyms; also
+ the new prefix is "luaotfload" (<= "otfl")
+ * The Adobe Glyph List (font-age.lua) is now built via script (mkglyphlist)
+ * Hans adapted the font loader to several of our requests (attribute
+ allocation, custom merged package name etc.)
+ * Auxiliary functions for package authors
+ * Man page for luaotfload-tool
+ * Unsupported v1.3 codebase is included in the luaotfload-*lua files. Crude,
+ but effective way to support older Luatex binaries
+ * implemented basic cache control/stats option for luaotfload-tool
+ * Character list is generated from char-def.lua (mkcharacters)
+
+2013/04/27, luaotfload v1.3:
+ * blacklisting lingoes.ttf (segfaults)
+ * unblacklisting ttc fonts (warning: may break LuaTeX < 0.65)
+ * fixing font cache file name with non-ascii characters
+
+2013/04/25, luaotfload v1.29:
+ * Reverting the unified resolver, as the database was rebuilt too often
+ which made the compilation longer. This will come back improved
+ in the next version, hopefully for TeXLive 2013.
+ * Fix resolving of Libertine Mono
+ * Fix a bug that made fontconfig files not parsed when OSFONTDIR is set
+
+2013/04/11, luaotfload v1.28:
+ * Adapting to LuaTeX 0.75
+ * Fix small documentation issues in mkluatexfontdb
+ * Fix possible infite loop with fontconfig config files references
+ * Adding semibold synonym for bold
+ * file:xxx syntax now uses the same search function as name: which
+ make more fonts recognized
+
+2012/05/28, luaotfload v1.27:
+ * Fix "endless loop in charlist" with some OpenType math fonts
+
+2012/03/27, luaotfload v1.26:
+ * Enable setting italic correction values by default
+ * Fix finding demibold italic fonts
+
+2011/04/21, luaotfload v1.25:
+ * Fix bug loading *.dfont fonts
+ * Misc. documentation fixes
+ * Fix the need to manually delete font cache when feature file is changed
+ * Hack to support Demi fonts
+
+2011/02/16, luaotfload v1.24:
+ * Fix infinite loop first time creating a name list
+
+2011/02/04, luaotfload v1.23:
+ * Fix a typo breaking fonts.names.scan()
+
+2011/01/25, luaotfload v1.22:
+ * Remove --database-dir and --sys options from mkluatexfontdb
+ * Provide a "luaotfload.patch_font" callback for on the fly patching of fonts
+ * Some documentation improvements
+
+2010/11/11, luaotfload v1.21:
+ * Adapt to luatexbase v3.0
+
+2010/10/16, luaotfload v1.20:
+ * Make cache directory creation more robust
+ * Fix GPOS mark placement in left-to-right direction
+ * Reject fonts missing 'names' table
+ * Sanitize color value before attempting to use it
+
+2010/09/12, luaotfload v1.19:
+ * fix LaTeX's detection (made Tikz fail under a non-LaTeX format)
+
+2010/07/15, luaotfload v1.18:
+ * fix for \overwithdelims and brothers
+
+2010/07/14, luaotfload v1.17:
+ * allow stylistic sets features in base mode
+ * don't scale percent math constants
+
+2010/07/12, luaotfload v1.16:
+ * support keys prefixed by "+", for compatibility with XeTeX
+ * remove the progress bar from mkluatexfontdb, it is of little use now
+ * minor code a documentation cleanups
+
+2010/06/28, luaotfload v1.15:
+ * anum feature did not work as advertised
+ * add system shipped TTC fonts on Mac OS X to the blacklist, until the
+ culprit ones are isolated
+
+2010/06/25, luaotfload v1.14:
+ * fix mkluatexfontdb which was broken in the last version
+ * support general font blacklisting feature
+ * temporally re-enable ttc fonts on Mac OS X
+ * make sure mkluatexfontdb in verbose mode prints font filename before
+ attempting to load it
+
+2010/06/24, luaotfload v1.13:
+ * fix typo in font cache path
+
+2010/06/18, luaotfload v1.12:
+ * populate MathConstants table for OpenType math fonts, now such fonts
+ can be really used in math mode.
+ * sync with ConTeXt beta 2010.06.18
+ * change cache dir to $TEXMFCACHE/luatex-cache/generic
+
+2010/06/09, luaotfload v1.11:
+ * when asking for a font with style that doesn't exist, we would return
+ nothing, now we fallback to the regular font
+
+2010/06/07, luaotfload v1.10:
+ * provide a fonts.names.scan(dir) function that temporally loads fonts
+ from the specified dir into the names database
+ * Log loaded font file before attempting to open it
+ * fix XeTeX's square brackets syntax so that it doesn't trigger database
+ update
+ * fix loading fonts with absolute path
+ * add \fontdimen8 support, for XeTeX compatibility
+ * be more verbose when updating the font database
+ * improve fonts.conf parsing
+ * make sure when a TFM font is requested we don't end up loading a non-TFM
+ font with a similar name instead
+ * Remove --fc-cache option from mkluatexfontdb.lua, since we no longer use
+ fontconfig tools
+ * misc. bug fixes
+
+2010/05/30, luaotfload v1.09:
+ * the last release didn't even load
+ * fix passing --destdir to mkluatexfontdb
+
+2010/05/28, luaotfload v1.08a:
+ * revert experimental code that was committed by mistake
+
+2010/05/28, luaotfload v1.08:
+ * fix misc. bugs with system fonts scanning
+ * parse fontconfig configuration directly, no longer dependant on 'fc-list'
+ * now if no font names database is found, luaotfload will generate it, also
+ it will force an update of the database if the asked font can not be
+ found
+ * avoid loading non-tfm fonts when the user asks for tfm font
+ * update the documentation
+ * blacklist .ttc and LastResort font on mac.
+ * sync with ConTeXt beta 2010.05.22
+ * fix attribute handling
+ * clarify license
+ * misc. bug fixes
+
+2010/05/10, luaotfload v1.07:
+ * using the new luatexbase package
+ * synchronizing with latest ConTeXt stable 2010.05.08
+ * adding support for microtypography
+ * adding support for color and transparency
+ * adding a script to generate a font database with TeX and system fonts
+ * more verbose log file
+
+2010/02/07, luaotfload v1.06a:
+ * more complete tlig and trep
+ * defaults options changed to "+ccmp;+locl;+rlig;+liga;+clig;+kern;
+ +mark;+mkmk;"
+ * supporting windows absolute path
+
+2009/12/01, luaotfload v1.06:
+ * synchronizing with ConTeXt stable 2009.11.26
+ * adding backward compatibility with LuaTeX 0.40.6
+
diff --git a/macros/luatex/generic/luaotfload/README.md b/macros/luatex/generic/luaotfload/README.md
new file mode 100644
index 0000000000..e59852f294
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/README.md
@@ -0,0 +1,103 @@
+# The Luaotfload Package
+
+VERSION: 2.991
+
+DATE: 2019-08-11
+
+
+## Description
+
+Luaotfload is an adaptation of the ConTeXt font loading system for the Plain
+and LaTeX formats. It allows OpenType fonts to be loaded with font features
+accessible using an extended font request syntax while providing compatibility
+with XeTeX. By indexing metadata in a database it facilitates loading fonts by
+their proper names instead of file names.
+
+Luaotfload may be loaded in Plain LuaTeX with "\input luaotfload.sty" and in
+LuaLaTeX with "\usepackage{luaotfload}". LuaLaTeX users may be interested in
+the fontspec package which provides a high-level interface to the functionality
+provided by this package.
+
+Please see the documentation luaotfload.pdf for more information.
+
+## Maintenance
+
+This package is currently maintained at
+<https://github.com/u-fischer/luaotfload>.
+
+Issues can be reported at the issue tracker or at the old issue tracker on
+<http://github.com/lualatex/luaotfload>.
+
+The development for LuaLaTeX is discussed on the lualatex-dev mailing list. See
+<http://www.tug.org/mailman/listinfo/lualatex-dev> for details.
+
+
+## Responsible Persons
+
+The following people have contributed to this package.
+
+- Khaled Hosny <khaledhosny@eglug.org>
+- Elie Roux <elie.roux@telecom-bretagne.eu>
+- Will Robertson <will.robertson@latex-project.org>
+- Philipp Gesang <phg@phi-gamma.net>
+- Dohyun Kim <nomosnomos@gmail.com>
+- Reuben Thomas <https://github.com/rrthomas>
+- Joseph Wright <joseph.wright@morningstar2.co.uk>
+- Manuel Pégourié-Gonnard <mpg@elzevir.fr>
+- Olof-Joachim Frahm <olof@macrolet.net>
+- Patrick Gundlach <gundlach@speedata.de>
+- Philipp Stephani <st_philipp@yahoo.de>
+- David Carlisle <d.p.carlisle@gmail.com>
+- Yan Zhou @zhouyan
+- Ulrike Fischer <fischer@troubleshooting-tex.de>
+- Marcel Krüger <https://github.com/zauguin>
+
+## Installation
+
+1. Install the current version with the package management tools of your TeX system.
+ If you want to install manually: there is a tds-zip file which can be unpacked in a texmf tree.
+
+2. If you want to try the development version download the texmf folder in the development branch.
+ at <https://github.com/u-fischer/luaotfload>
+
+3. Manual installation:
+ * luaotfload-tool.lua belongs in scripts/luatex/luaotfload
+ * fontloader-reference-load-order.tex and fontloader-reference-load-order.lua are source files and can got in source or doc
+ * the other lua-files and the sty belong in tex/luatex/luaotfload
+ * luaotfload.conf.5 and luaotfload-tool.1 belong in doc/man
+ * the rest in doc/luatex/luaotfload
+
+## Documentation
+
+* The main documentation is luaotfload-latex.pdf.
+* luaotfload.conf.5 and luaotfload-tool.1 are man-files, their sources are the rst-files.
+* README.md, NEWS and COPYING contain what their name says.
+* The rest are input files.
+
+
+
+
+## License
+
+The luaotfload bundle, as a derived work of ConTeXt, is distributed under the
+GNU GPLv2 license:
+
+ <http://www.gnu.org/licenses/old-licenses/gpl-2.0.html>
+
+This license requires the license itself to be distributed with the work. For
+its full text see the documentation in luaotfload.pdf.
+
+
+## DISCLAIMER
+
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License
+ as published by the Free Software Foundation; version 2.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ See headers of each source file for copyright details.
+
diff --git a/macros/luatex/generic/luaotfload/filegraph.pdf b/macros/luatex/generic/luaotfload/filegraph.pdf
new file mode 100644
index 0000000000..e5807ca3ca
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/filegraph.pdf
Binary files differ
diff --git a/macros/luatex/generic/luaotfload/filegraph.tex b/macros/luatex/generic/luaotfload/filegraph.tex
new file mode 100644
index 0000000000..297816671a
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/filegraph.tex
@@ -0,0 +1,266 @@
+% !Mode:: "TeX:EN:UTF-8:Main"
+%created with by @marmot 14.09.2018
+%
+\documentclass[border=3.14mm,tikz]{standalone}
+\usetikzlibrary{fit,matrix,positioning,arrows.meta,decorations.text,shapes.callouts}
+\pgfdeclarelayer{background}
+\pgfdeclarelayer{container}
+\pgfdeclarelayer{foreground}
+\pgfsetlayers{container,background,main,foreground}
+\usepackage {fontspec}
+\usepackage {unicode-math}
+\usepackage{tikzmarmots,tikzducks}
+
+\setmainfont[
+% Numbers = OldStyle, %% buggy with font cache
+ Ligatures = TeX,
+ BoldFont = {Linux Libertine O Bold},
+ ItalicFont = {Linux Libertine O Italic},
+ SlantedFont = {Linux Libertine O Italic},
+]{Linux Libertine O}
+\setmonofont[Ligatures=TeX,Scale=MatchLowercase]{InconsolataN-Regular.otf}
+%setsansfont[Ligatures=TeX]{Linux Biolinum O}
+\setsansfont[Ligatures=TeX,Scale=MatchLowercase]{Iwona Medium}
+
+\usepackage{luacode}
+\begin{luacode}
+require("luaotfload-filelist.lua")
+
+function printctxfontlist ()
+ t= luaotfload.filelist.selectctxfontentries (luaotfload.filelist.data)
+ for i,v in ipairs (t) do
+ tex.sprint("\\mbox{"..v.name..v.ext.."} ")
+ end
+end
+
+function printctxlibslist ()
+ t= luaotfload.filelist.selectctxlibsentries (luaotfload.filelist.data)
+ local rowcnt = 0
+ local sep = "&"
+ for i,v in ipairs (t) do
+ rowcnt = rowcnt + 1
+ if rowcnt % 4 == 0 then sep = "\\\\" else sep = "&" end
+ tex.sprint("\\mbox{"..v.name..v.ext.."}".. sep)
+ end
+end
+
+function printctxgenericlist ()
+ t= luaotfload.filelist.selectctxgeneusedentries (luaotfload.filelist.data)
+ local rowcnt = 0
+ local sep = "&"
+ for i,v in ipairs (t) do
+ rowcnt = rowcnt + 1
+ if rowcnt % 2 == 0 then sep = "\\\\" else sep = "&" end
+ tex.sprint("\\mbox{"..v.ctxpref..v.name..v.ext.."}".. sep)
+ end
+end
+
+
+function printlibrarylist ()
+ t = luaotfload.filelist.selectlollibentries (luaotfload.filelist.data)
+ local rowcnt = 0
+ local sep = "&"
+ for i,v in ipairs (t) do
+ rowcnt = rowcnt + 1
+ if rowcnt % 2 == 0 then sep = "\\\\" else sep = "&" end
+ tex.sprint("\\mbox{"..v.gitpref..v.name..v.ext.."}".. sep)
+ end
+ if rowcnt % 2 == 1 then tex.sprint("\\\\") end -- if odd number we must end the matrix
+end
+
+function printscriptlist ()
+ t = luaotfload.filelist.selectlolscrentries (luaotfload.filelist.data)
+ for i,v in ipairs ( t ) do
+ if v.kind == 8 then
+ tex.sprint( v.name .."\\\\")
+ end
+ end
+end
+
+\end{luacode}
+\begin{document}
+\begin{tikzpicture}[rounded corners,basic/.style={inner
+sep=9pt,font=\ttfamily,align=center}]
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+% text nodes
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+% m1
+\matrix [matrix of nodes,font=\ttfamily,nodes={anchor=base west},
+label={[name=mL1,font=\itshape]above:Luaotfload Libraries}] (m1)
+{%
+%<<<<<<<<<<<<<<<<
+\directlua{printlibrarylist()}
+%>>>>>>>>>>>>>>>>
+};
+% m2
+\node[right=4.2cm of m1,fill=gray!20,draw=gray!30,dashed,basic] (m2) {luaotfload-blacklist.cnf};
+% m3
+\matrix [below=2cm of m1,matrix of nodes,font=\ttfamily,nodes={anchor=base west},
+label={[name=mL3,font=\itshape,anchor=south]above:Lualibs -- Lua Libraries from Context}] (m3)
+{%
+%<<<<<<<<<<<<<<<<
+\directlua{printctxlibslist ()}
+%>>>>>>>>>>>>>>>>
+};
+% m4
+\node[left=2cm of m3,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm] (m4) {luaotfload-main.lua};
+% m5
+\node[fill=gray!20,draw=gray!30,dashed,basic,inner sep=6mm,anchor=south west] at (m3.south -|
+m2.west)(m5){%
+%<<<<<<<<<<<<<<<<
+luaotfload-names.lua.gz\\
+luaotfload-names.luc
+%>>>>>>>>>>>>>>>>
+};
+% m6
+\node[below=3cm of m3,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm] (m6){luaotfload-init.lua};
+% m7
+\node[above right=0.5cm and 2.5cm of m6,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm] (m7){luaotfload-log.lua};
+% m8
+\matrix [below left=1cm and 2cm of m6,matrix of nodes,font=\ttfamily,
+row sep=5mm,
+nodes={inner sep=3mm,fill=orange!10,rounded corners},
+label={[name=mL8,font=\it]above:Fontloader}] (m8)
+{%
+%<<<<<<<<<<<<<<<<
+fontloader-basics-gen.lua\\
+fontloader-YY-MM-DD.lua\\
+%<<<<<<<<<<<<<<<<
+};
+% m9
+\node [below right=1cm and 2cm of m6,font=\ttfamily,
+inner sep=3mm,text width=7.3cm,align=left,
+label={[name=mL9,font=\itshape]Font and Node Libraries from Context}] (m9)
+{\spaceskip=1.5em \raggedright
+%%<<<<<<<<<<<<<<<<
+\directlua{printctxfontlist()}
+%>>>>>>>>>>>>>>>>
+};
+% m10
+\node [below=1cm of m9,font=\ttfamily,
+inner sep=3mm,text width=7.3cm,align=center,
+label={[name=mL10,font=\itshape]Font Loader (LuaTeX-Fonts)}] (m10)
+{\tabcolsep=0.5em
+ \begin{tabular}{@{}ll@{}}
+%<<<<<<<<<<<<<<<<
+\directlua{printctxgenericlist ()}
+%>>>>>>>>>>>>>>>>
+ \end{tabular}
+};
+% m11
+\node [above=1cm of m9] (m11) {Merged libraries};
+% m12
+\matrix [below=4cm of m6,xshift=-1cm,matrix of nodes,font=\ttfamily,
+row sep=5mm,
+nodes={inner sep=3mm,fill=gray!10,rounded corners,text width=3cm,align=center},
+label={[name=mL12,font=\sffamily]above:Standalone scripts}] (m12)
+{%
+%<<<<<<<<<<<<<<<<
+\directlua{printscriptlist ()}
+%>>>>>>>>>>>>>>>>
+};
+% m13
+\node[below=1.2cm of m10,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm] (m13)
+{%
+%<<<<<<<<<<<<<<<<
+luaotfload-glyphlist.lua
+%>>>>>>>>>>>>>>>>
+};
+% m14
+\node[below=0.8cm of m13,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm] (m14)
+{%
+%<<<<<<<<<<<<<<<<
+luaotfload-characters.lua
+%>>>>>>>>>>>>>>>>
+};
+% m15
+\node[below=3cm of m8,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm]
+(m15) {%
+%<<<<<<<<<<<<<<<<
+luaotfload-tool.lua
+%>>>>>>>>>>>>>>>>
+};
+% m16
+\node[below=1cm of m15,fill=gray!20,draw=gray!30,thick,basic,inner sep=6mm]
+(m16) {%
+%<<<<<<<<<<<<<<<<
+luaotfload-diagnostics.lua
+%>>>>>>>>>>>>>>>>
+};
+% m17
+\node[below=2cm of m16,xshift=3cm,fill=gray!20,draw=gray!30,dashed,basic,inner sep=6pt]
+(m17) {%
+%<<<<<<<<<<<<<<<<
+luaotfload-status.lua
+%>>>>>>>>>>>>>>>>
+};
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+% envelopes
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\begin{pgfonlayer}{background}
+%M1
+\node[fill=gray!10,fit=(m1)(mL1),rounded corners=0](mF1){};
+%M3
+\node[fill=blue!10,fit=(m3)(mL3),rounded corners=0](mF3){};
+%M9
+\node[fill=purple!10,fit=(m9)(mL9)](mF9){};
+%M10
+\node[fill=purple!10,fit=(m10)(mL10)](mF10){};
+\end{pgfonlayer}
+\begin{pgfonlayer}{container}
+%M1
+\node[fill=gray!20,fit=(mF1)](M1){};
+%M3
+\node[fill=blue!20,fit=(mF3)](M3){};
+%M8
+\node[fill=orange!20,fit=(m8)(mL8)](mF8){};
+%M11
+\node[fill=purple!20,fit=(m11)(mF9)(mF10)](M11){};
+%M11
+\node[top color=gray!40,bottom color=red!60!black,fit=(mL12)(m12)](M12){};
+\end{pgfonlayer}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+% arrows
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\begin{scope}[font=\sffamily,>={Triangle[open]},annotate/.style={postaction={decorate,decoration={text along path,text
+align=center,raise=2pt,text={|\sffamily| #1}}}}]
+\draw[->,annotate=luaotfload-database.lua] (M1) -- (m2);
+\draw[->,annotate=main()] (m4) -- (M1);
+\draw[->] (m4) -- (M3);
+\draw[->,annotate=luaotfload-database.lua] (M1.-15) to[out=0,in=90] (m5);
+\draw[->,annotate=main()] (m4) to[out=-70,in=120] (m6);
+\draw[->,annotate=init{{\_}}early()] (m6) to[out=45,in=190] (m7);
+\draw[<-,annotate=init{{\_}}early()] (m8-1-1) to[in=-150,out=0] (m6);
+\draw[<-,annotate=init{{\_}}main()] (m8-2-1) to[in=-100,out=4] (m6);
+\draw[->,annotate=unmerged] (m6) to[out=0,in=180] (mF9.150);
+\draw[->,dashed,annotate=merged] (m8-2-1) to[out=0,in=180] (mF9.170);
+\draw[->,dashed,annotate=pulls] (m12-1-1) to[out=0,in=180] (mF9);
+\draw[->,dashed,annotate=pulls] (m12-1-1) to[out=0,in=180] (mF10);
+\draw[<-,dashed,annotate=merges] (m8-2-1) to[out=-45,in=180] (m12-1-1);
+\draw[->] (mF10) to node[midway,left]{luatex-fonts-enc.lua} (m13);
+\draw[->] (mF10.-30) to[out=-60,in=50]node[pos=0.3,right]{ luaotfload-auxiliary.lua} (m14.15);
+\draw[->,dashed,annotate=generates from glyphlist.txt] (m12-2-1) to[out=0,in=180] (m13);
+\draw[->,dashed,annotate=generates from Context's char-def.lua] (m12-3-1) to[out=0,in=180] (m14);
+\draw[->,dashed,annotate={{-}{-}update}] (m15) to[out=130,in=-80] ++ (-3.5,4)
+to[out=100,in=-110] ++ (0,2)
+to[out=70,in=-165] (m5);
+\draw[->,annotate=version information] (m15) to[out=-170,in=90] ++(-3.5,-3)
+to[out=-90,in=180] (m17);
+\draw[->] (m15) -- node[midway,right]{-\,-diagnose} (m16);
+\draw[->,annotate=hash files] (m16) -- (m17);
+\draw[<-,dashed,annotate=generates from distribution files] (m17)
+to[out=0,in=-135] ++(5,1) to[out=45,in=0] (m12-4-1);
+\end{scope}
+
+\begin{scope}[shift={([xshift=2cm,yshift=-3cm]current bounding box.north west)},sharp corners]
+\marmot;
+\duck[invisible];
+\node[anchor=south,draw,text width=3cm,shape=rectangle callout,font=\sffamily\scriptsize,align=center]
+at ([yshift=1cm,xshift=-0.5cm]bill)
+{It looks complicated\\ because it is complicated!};
+%
+\end{scope}
+
+\end{tikzpicture}
+\end{document} \ No newline at end of file
diff --git a/macros/luatex/generic/luaotfload/fontloader-2019-08-11.lua b/macros/luatex/generic/luaotfload/fontloader-2019-08-11.lua
new file mode 100644
index 0000000000..b4d3f3ce12
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-2019-08-11.lua
@@ -0,0 +1,34169 @@
+--[[info-----------------------------------------------------------------------
+ Luaotfload fontloader package
+ build 2019-08-13 18:34:34
+-------------------------------------------------------------------------------
+
+ © 2019 PRAGMA ADE / ConTeXt Development Team
+
+ The code in this file is provided under the GPL v2.0 license. See the
+ file COPYING in the Luaotfload repository for details.
+
+ Report bugs to github.com/u-fischer/luaotfload
+
+ This file has been assembled from components taken from Context. See
+ the Luaotfload documentation for details:
+
+ $ texdoc luaotfload
+ $ man 1 luaotfload-tool
+ $ man 5 luaotfload.conf
+
+ Included files:
+
+ · fontloader-data-con.lua
+ · fontloader-basics-nod.lua
+ · fontloader-basics-chr.lua
+ · fontloader-font-ini.lua
+ · fontloader-fonts-mis.lua
+ · fontloader-font-con.lua
+ · fontloader-fonts-enc.lua
+ · fontloader-font-cid.lua
+ · fontloader-font-map.lua
+ · fontloader-font-vfc.lua
+ · fontloader-font-otr.lua
+ · fontloader-font-oti.lua
+ · fontloader-font-ott.lua
+ · fontloader-font-cff.lua
+ · fontloader-font-ttf.lua
+ · fontloader-font-dsp.lua
+ · fontloader-font-oup.lua
+ · fontloader-font-otl.lua
+ · fontloader-font-oto.lua
+ · fontloader-font-otj.lua
+ · fontloader-font-ota.lua
+ · fontloader-font-ots.lua
+ · fontloader-font-osd.lua
+ · fontloader-font-ocl.lua
+ · fontloader-font-otc.lua
+ · fontloader-font-onr.lua
+ · fontloader-font-one.lua
+ · fontloader-font-afk.lua
+ · fontloader-fonts-tfm.lua
+ · fontloader-font-lua.lua
+ · fontloader-font-def.lua
+ · fontloader-fonts-def.lua
+ · fontloader-fonts-ext.lua
+ · fontloader-font-imp-tex.lua
+ · fontloader-font-imp-ligatures.lua
+ · fontloader-font-imp-italics.lua
+ · fontloader-font-imp-effects.lua
+ · fontloader-fonts-lig.lua
+ · fontloader-fonts-gbn.lua
+
+--info]]-----------------------------------------------------------------------
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “data-con” 7ce546725b1550f655c78ac9d69419ca] ---
+
+if not modules then modules={} end modules ['data-con']={
+ version=1.100,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local format,lower,gsub=string.format,string.lower,string.gsub
+local trace_cache=false trackers.register("resolvers.cache",function(v) trace_cache=v end)
+local trace_containers=false trackers.register("resolvers.containers",function(v) trace_containers=v end)
+local trace_storage=false trackers.register("resolvers.storage",function(v) trace_storage=v end)
+containers=containers or {}
+local containers=containers
+containers.usecache=true
+local report_containers=logs.reporter("resolvers","containers")
+local allocated={}
+local mt={
+ __index=function(t,k)
+ if k=="writable" then
+ local writable=caches.getwritablepath(t.category,t.subcategory) or { "." }
+ t.writable=writable
+ return writable
+ elseif k=="readables" then
+ local readables=caches.getreadablepaths(t.category,t.subcategory) or { "." }
+ t.readables=readables
+ return readables
+ end
+ end,
+ __storage__=true
+}
+function containers.define(category,subcategory,version,enabled)
+ if category and subcategory then
+ local c=allocated[category]
+ if not c then
+ c={}
+ allocated[category]=c
+ end
+ local s=c[subcategory]
+ if not s then
+ s={
+ category=category,
+ subcategory=subcategory,
+ storage={},
+ enabled=enabled,
+ version=version or math.pi,
+ trace=false,
+ }
+ setmetatable(s,mt)
+ c[subcategory]=s
+ end
+ return s
+ end
+end
+function containers.is_usable(container,name)
+ return container.enabled and caches and caches.is_writable(container.writable,name)
+end
+function containers.is_valid(container,name)
+ if name and name~="" then
+ local storage=container.storage[name]
+ return storage and storage.cache_version==container.version
+ else
+ return false
+ end
+end
+function containers.read(container,name)
+ local storage=container.storage
+ local stored=storage[name]
+ if not stored and container.enabled and caches and containers.usecache then
+ stored=caches.loaddata(container.readables,name,container.writable)
+ if stored and stored.cache_version==container.version then
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","load",container.subcategory,name)
+ end
+ else
+ stored=nil
+ end
+ storage[name]=stored
+ elseif stored then
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","reuse",container.subcategory,name)
+ end
+ end
+ return stored
+end
+function containers.write(container,name,data)
+ if data then
+ data.cache_version=container.version
+ if container.enabled and caches then
+ local unique,shared=data.unique,data.shared
+ data.unique,data.shared=nil,nil
+ caches.savedata(container.writable,name,data)
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","save",container.subcategory,name)
+ end
+ data.unique,data.shared=unique,shared
+ end
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","store",container.subcategory,name)
+ end
+ container.storage[name]=data
+ end
+ return data
+end
+function containers.content(container,name)
+ return container.storage[name]
+end
+function containers.cleanname(name)
+ return (gsub(lower(name),"[^%w\128-\255]+","-"))
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “data-con”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “basics-nod” 65064d03c2650a1761ee13ebd9e1400a] ---
+
+if not modules then modules={} end modules ['luatex-fonts-nod']={
+ version=1.001,
+ comment="companion to luatex-fonts.lua",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+ os.exit()
+end
+if tex.attribute[0]~=0 then
+ texio.write_nl("log","!")
+ texio.write_nl("log","! Attribute 0 is reserved for ConTeXt's font feature management and has to be")
+ texio.write_nl("log","! set to zero. Also, some attributes in the range 1-255 are used for special")
+ texio.write_nl("log","! purposes so setting them at the TeX end might break the font handler.")
+ texio.write_nl("log","!")
+ tex.attribute[0]=0
+end
+attributes=attributes or {}
+attributes.unsetvalue=-0x7FFFFFFF
+local numbers,last={},127
+attributes.private=attributes.private or function(name)
+ local number=numbers[name]
+ if not number then
+ if last<255 then
+ last=last+1
+ end
+ number=last
+ numbers[name]=number
+ end
+ return number
+end
+nodes={}
+nodes.handlers={}
+local nodecodes={}
+local glyphcodes=node.subtypes("glyph")
+local disccodes=node.subtypes("disc")
+for k,v in next,node.types() do
+ v=string.gsub(v,"_","")
+ nodecodes[k]=v
+ nodecodes[v]=k
+end
+for k,v in next,glyphcodes do
+ glyphcodes[v]=k
+end
+for k,v in next,disccodes do
+ disccodes[v]=k
+end
+nodes.nodecodes=nodecodes
+nodes.glyphcodes=glyphcodes
+nodes.disccodes=disccodes
+nodes.handlers.protectglyphs=node.protect_glyphs
+nodes.handlers.unprotectglyphs=node.unprotect_glyphs
+local direct=node.direct
+local nuts={}
+nodes.nuts=nuts
+local tonode=direct.tonode
+local tonut=direct.todirect
+nodes.tonode=tonode
+nodes.tonut=tonut
+nuts.tonode=tonode
+nuts.tonut=tonut
+nuts.getattr=direct.get_attribute
+nuts.getboth=direct.getboth
+nuts.getchar=direct.getchar
+nuts.getcomponents=direct.getcomponents
+nuts.getdirection=direct.getdirection
+nuts.getdisc=direct.getdisc
+nuts.getfield=direct.getfield
+nuts.getfont=direct.getfont
+nuts.getid=direct.getid
+nuts.getkern=direct.getkern
+nuts.getlist=direct.getlist
+nuts.getnext=direct.getnext
+nuts.getoffsets=direct.getoffsets
+nuts.getprev=direct.getprev
+nuts.getsubtype=direct.getsubtype
+nuts.getwidth=direct.getwidth
+nuts.setattr=direct.setfield
+nuts.setboth=direct.setboth
+nuts.setchar=direct.setchar
+nuts.setcomponents=direct.setcomponents
+nuts.setdirection=direct.setdirection
+nuts.setdisc=direct.setdisc
+nuts.setfield=setfield
+nuts.setkern=direct.setkern
+nuts.setlink=direct.setlink
+nuts.setlist=direct.setlist
+nuts.setnext=direct.setnext
+nuts.setoffsets=direct.setoffsets
+nuts.setprev=direct.setprev
+nuts.setsplit=direct.setsplit
+nuts.setsubtype=direct.setsubtype
+nuts.setwidth=direct.setwidth
+nuts.getglyphdata=nuts.getattr
+nuts.setglyphdata=nuts.setattr
+nuts.ischar=direct.is_char
+nuts.isglyph=direct.is_glyph
+nuts.copy=direct.copy
+nuts.copy_list=direct.copy_list
+nuts.copy_node=direct.copy
+nuts.delete=direct.delete
+nuts.end_of_math=direct.end_of_math
+nuts.flush=direct.flush
+nuts.flush_list=direct.flush_list
+nuts.flush_node=direct.flush_node
+nuts.free=direct.free
+nuts.insert_after=direct.insert_after
+nuts.insert_before=direct.insert_before
+nuts.is_node=direct.is_node
+nuts.kerning=direct.kerning
+nuts.ligaturing=direct.ligaturing
+nuts.new=direct.new
+nuts.remove=direct.remove
+nuts.tail=direct.tail
+nuts.traverse=direct.traverse
+nuts.traverse_char=direct.traverse_char
+nuts.traverse_glyph=direct.traverse_glyph
+nuts.traverse_id=direct.traverse_id
+local propertydata=direct.get_properties_table()
+nodes.properties={ data=propertydata }
+if direct.set_properties_mode then
+ direct.set_properties_mode(true,true)
+ function direct.set_properties_mode() end
+end
+nuts.getprop=function(n,k)
+ local p=propertydata[n]
+ if p then
+ return p[k]
+ end
+end
+nuts.setprop=function(n,k,v)
+ if v then
+ local p=propertydata[n]
+ if p then
+ p[k]=v
+ else
+ propertydata[n]={ [k]=v }
+ end
+ end
+end
+nodes.setprop=nodes.setproperty
+nodes.getprop=nodes.getproperty
+local setprev=nuts.setprev
+local setnext=nuts.setnext
+local getnext=nuts.getnext
+local setlink=nuts.setlink
+local getfield=nuts.getfield
+local setfield=nuts.setfield
+local getcomponents=nuts.getcomponents
+local setcomponents=nuts.setcomponents
+local find_tail=nuts.tail
+local flush_list=nuts.flush_list
+local flush_node=nuts.flush_node
+local traverse_id=nuts.traverse_id
+local copy_node=nuts.copy_node
+local glyph_code=nodes.nodecodes.glyph
+function nuts.copy_no_components(g,copyinjection)
+ local components=getcomponents(g)
+ if components then
+ setcomponents(g)
+ local n=copy_node(g)
+ if copyinjection then
+ copyinjection(n,g)
+ end
+ setcomponents(g,components)
+ return n
+ else
+ local n=copy_node(g)
+ if copyinjection then
+ copyinjection(n,g)
+ end
+ return n
+ end
+end
+function nuts.copy_only_glyphs(current)
+ local head=nil
+ local previous=nil
+ for n in traverse_id(glyph_code,current) do
+ n=copy_node(n)
+ if head then
+ setlink(previous,n)
+ else
+ head=n
+ end
+ previous=n
+ end
+ return head
+end
+nuts.uses_font=direct.uses_font
+do
+ local dummy=tonut(node.new("glyph"))
+ nuts.traversers={
+ glyph=nuts.traverse_id(nodecodes.glyph,dummy),
+ glue=nuts.traverse_id(nodecodes.glue,dummy),
+ disc=nuts.traverse_id(nodecodes.disc,dummy),
+ boundary=nuts.traverse_id(nodecodes.boundary,dummy),
+ char=nuts.traverse_char(dummy),
+ node=nuts.traverse(dummy),
+ }
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “basics-nod”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “basics-chr” 58b7ef0c486e06090b362971b9f85e27] ---
+
+
+characters=characters or {}
+characters.blockrange={}
+characters.classifiers={
+ [768]=5,
+ [769]=5,
+ [770]=5,
+ [771]=5,
+ [772]=5,
+ [773]=5,
+ [774]=5,
+ [775]=5,
+ [776]=5,
+ [777]=5,
+ [778]=5,
+ [779]=5,
+ [780]=5,
+ [781]=5,
+ [782]=5,
+ [783]=5,
+ [784]=5,
+ [785]=5,
+ [786]=5,
+ [787]=5,
+ [788]=5,
+ [789]=5,
+ [790]=5,
+ [791]=5,
+ [792]=5,
+ [793]=5,
+ [794]=5,
+ [795]=5,
+ [796]=5,
+ [797]=5,
+ [798]=5,
+ [799]=5,
+ [800]=5,
+ [801]=5,
+ [802]=5,
+ [803]=5,
+ [804]=5,
+ [805]=5,
+ [806]=5,
+ [807]=5,
+ [808]=5,
+ [809]=5,
+ [810]=5,
+ [811]=5,
+ [812]=5,
+ [813]=5,
+ [814]=5,
+ [815]=5,
+ [816]=5,
+ [817]=5,
+ [818]=5,
+ [819]=5,
+ [820]=5,
+ [821]=5,
+ [822]=5,
+ [823]=5,
+ [824]=5,
+ [825]=5,
+ [826]=5,
+ [827]=5,
+ [828]=5,
+ [829]=5,
+ [830]=5,
+ [831]=5,
+ [832]=5,
+ [833]=5,
+ [834]=5,
+ [835]=5,
+ [836]=5,
+ [837]=5,
+ [838]=5,
+ [839]=5,
+ [840]=5,
+ [841]=5,
+ [842]=5,
+ [843]=5,
+ [844]=5,
+ [845]=5,
+ [846]=5,
+ [847]=5,
+ [848]=5,
+ [849]=5,
+ [850]=5,
+ [851]=5,
+ [852]=5,
+ [853]=5,
+ [854]=5,
+ [855]=5,
+ [856]=5,
+ [857]=5,
+ [858]=5,
+ [859]=5,
+ [860]=5,
+ [861]=5,
+ [862]=5,
+ [863]=5,
+ [864]=5,
+ [865]=5,
+ [866]=5,
+ [867]=5,
+ [868]=5,
+ [869]=5,
+ [870]=5,
+ [871]=5,
+ [872]=5,
+ [873]=5,
+ [874]=5,
+ [875]=5,
+ [876]=5,
+ [877]=5,
+ [878]=5,
+ [879]=5,
+ [1155]=5,
+ [1156]=5,
+ [1157]=5,
+ [1158]=5,
+ [1159]=5,
+ [1425]=5,
+ [1426]=5,
+ [1427]=5,
+ [1428]=5,
+ [1429]=5,
+ [1430]=5,
+ [1431]=5,
+ [1432]=5,
+ [1433]=5,
+ [1434]=5,
+ [1435]=5,
+ [1436]=5,
+ [1437]=5,
+ [1438]=5,
+ [1439]=5,
+ [1440]=5,
+ [1441]=5,
+ [1442]=5,
+ [1443]=5,
+ [1444]=5,
+ [1445]=5,
+ [1446]=5,
+ [1447]=5,
+ [1448]=5,
+ [1449]=5,
+ [1450]=5,
+ [1451]=5,
+ [1452]=5,
+ [1453]=5,
+ [1454]=5,
+ [1455]=5,
+ [1456]=5,
+ [1457]=5,
+ [1458]=5,
+ [1459]=5,
+ [1460]=5,
+ [1461]=5,
+ [1462]=5,
+ [1463]=5,
+ [1464]=5,
+ [1465]=5,
+ [1466]=5,
+ [1467]=5,
+ [1468]=5,
+ [1469]=5,
+ [1471]=5,
+ [1473]=5,
+ [1474]=5,
+ [1476]=5,
+ [1477]=5,
+ [1479]=5,
+ [1536]=4,
+ [1537]=4,
+ [1538]=4,
+ [1539]=4,
+ [1540]=4,
+ [1541]=4,
+ [1542]=6,
+ [1543]=6,
+ [1544]=4,
+ [1545]=6,
+ [1546]=6,
+ [1547]=4,
+ [1548]=6,
+ [1549]=6,
+ [1550]=6,
+ [1551]=6,
+ [1552]=5,
+ [1553]=5,
+ [1554]=5,
+ [1555]=5,
+ [1556]=5,
+ [1557]=5,
+ [1558]=5,
+ [1559]=5,
+ [1560]=5,
+ [1561]=5,
+ [1562]=5,
+ [1563]=6,
+ [1564]=6,
+ [1566]=6,
+ [1567]=6,
+ [1568]=2,
+ [1569]=4,
+ [1570]=3,
+ [1571]=3,
+ [1572]=3,
+ [1573]=3,
+ [1574]=2,
+ [1575]=3,
+ [1576]=2,
+ [1577]=3,
+ [1578]=2,
+ [1579]=2,
+ [1580]=2,
+ [1581]=2,
+ [1582]=2,
+ [1583]=3,
+ [1584]=3,
+ [1585]=3,
+ [1586]=3,
+ [1587]=2,
+ [1588]=2,
+ [1589]=2,
+ [1590]=2,
+ [1591]=2,
+ [1592]=2,
+ [1593]=2,
+ [1594]=2,
+ [1595]=2,
+ [1596]=2,
+ [1597]=2,
+ [1598]=2,
+ [1599]=2,
+ [1600]=2,
+ [1601]=2,
+ [1602]=2,
+ [1603]=2,
+ [1604]=2,
+ [1605]=2,
+ [1606]=2,
+ [1607]=2,
+ [1608]=3,
+ [1609]=2,
+ [1610]=2,
+ [1611]=5,
+ [1612]=5,
+ [1613]=5,
+ [1614]=5,
+ [1615]=5,
+ [1616]=5,
+ [1617]=5,
+ [1618]=5,
+ [1619]=5,
+ [1620]=5,
+ [1621]=5,
+ [1622]=5,
+ [1623]=5,
+ [1624]=5,
+ [1625]=5,
+ [1626]=5,
+ [1627]=5,
+ [1628]=5,
+ [1629]=5,
+ [1630]=5,
+ [1631]=5,
+ [1632]=6,
+ [1633]=6,
+ [1634]=6,
+ [1635]=6,
+ [1636]=6,
+ [1637]=6,
+ [1638]=6,
+ [1639]=6,
+ [1640]=6,
+ [1641]=6,
+ [1642]=6,
+ [1643]=6,
+ [1644]=6,
+ [1645]=6,
+ [1646]=2,
+ [1647]=2,
+ [1648]=5,
+ [1649]=3,
+ [1650]=3,
+ [1651]=3,
+ [1652]=4,
+ [1653]=3,
+ [1654]=3,
+ [1655]=3,
+ [1656]=2,
+ [1657]=2,
+ [1658]=2,
+ [1659]=2,
+ [1660]=2,
+ [1661]=2,
+ [1662]=2,
+ [1663]=2,
+ [1664]=2,
+ [1665]=2,
+ [1666]=2,
+ [1667]=2,
+ [1668]=2,
+ [1669]=2,
+ [1670]=2,
+ [1671]=2,
+ [1672]=3,
+ [1673]=3,
+ [1674]=3,
+ [1675]=3,
+ [1676]=3,
+ [1677]=3,
+ [1678]=3,
+ [1679]=3,
+ [1680]=3,
+ [1681]=3,
+ [1682]=3,
+ [1683]=3,
+ [1684]=3,
+ [1685]=3,
+ [1686]=3,
+ [1687]=3,
+ [1688]=3,
+ [1689]=3,
+ [1690]=2,
+ [1691]=2,
+ [1692]=2,
+ [1693]=2,
+ [1694]=2,
+ [1695]=2,
+ [1696]=2,
+ [1697]=2,
+ [1698]=2,
+ [1699]=2,
+ [1700]=2,
+ [1701]=2,
+ [1702]=2,
+ [1703]=2,
+ [1704]=2,
+ [1705]=2,
+ [1706]=2,
+ [1707]=2,
+ [1708]=2,
+ [1709]=2,
+ [1710]=2,
+ [1711]=2,
+ [1712]=2,
+ [1713]=2,
+ [1714]=2,
+ [1715]=2,
+ [1716]=2,
+ [1717]=2,
+ [1718]=2,
+ [1719]=2,
+ [1720]=2,
+ [1721]=2,
+ [1722]=2,
+ [1723]=2,
+ [1724]=2,
+ [1725]=2,
+ [1726]=2,
+ [1727]=2,
+ [1728]=3,
+ [1729]=2,
+ [1730]=2,
+ [1731]=3,
+ [1732]=3,
+ [1733]=3,
+ [1734]=3,
+ [1735]=3,
+ [1736]=3,
+ [1737]=3,
+ [1738]=3,
+ [1739]=3,
+ [1740]=2,
+ [1741]=3,
+ [1742]=2,
+ [1743]=3,
+ [1744]=2,
+ [1745]=2,
+ [1746]=3,
+ [1747]=3,
+ [1748]=6,
+ [1749]=3,
+ [1750]=5,
+ [1751]=5,
+ [1752]=5,
+ [1753]=5,
+ [1754]=5,
+ [1755]=5,
+ [1756]=5,
+ [1757]=4,
+ [1758]=6,
+ [1759]=5,
+ [1760]=5,
+ [1761]=5,
+ [1762]=5,
+ [1763]=5,
+ [1764]=5,
+ [1765]=6,
+ [1766]=6,
+ [1767]=5,
+ [1768]=5,
+ [1769]=6,
+ [1770]=5,
+ [1771]=5,
+ [1772]=5,
+ [1773]=5,
+ [1774]=3,
+ [1775]=3,
+ [1776]=6,
+ [1777]=6,
+ [1778]=6,
+ [1779]=6,
+ [1780]=6,
+ [1781]=6,
+ [1782]=6,
+ [1783]=6,
+ [1784]=6,
+ [1785]=6,
+ [1786]=2,
+ [1787]=2,
+ [1788]=2,
+ [1789]=6,
+ [1790]=6,
+ [1791]=2,
+ [1792]=6,
+ [1793]=6,
+ [1794]=6,
+ [1795]=6,
+ [1796]=6,
+ [1797]=6,
+ [1798]=6,
+ [1799]=6,
+ [1800]=6,
+ [1801]=6,
+ [1802]=6,
+ [1803]=6,
+ [1804]=6,
+ [1805]=6,
+ [1808]=3,
+ [1809]=5,
+ [1810]=2,
+ [1811]=2,
+ [1812]=2,
+ [1813]=3,
+ [1814]=3,
+ [1815]=3,
+ [1816]=3,
+ [1817]=3,
+ [1818]=2,
+ [1819]=2,
+ [1820]=2,
+ [1821]=2,
+ [1822]=3,
+ [1823]=2,
+ [1824]=2,
+ [1825]=2,
+ [1826]=2,
+ [1827]=2,
+ [1828]=2,
+ [1829]=2,
+ [1830]=2,
+ [1831]=2,
+ [1832]=3,
+ [1833]=2,
+ [1834]=3,
+ [1835]=2,
+ [1836]=3,
+ [1837]=2,
+ [1838]=2,
+ [1839]=3,
+ [1840]=5,
+ [1841]=5,
+ [1842]=5,
+ [1843]=5,
+ [1844]=5,
+ [1845]=5,
+ [1846]=5,
+ [1847]=5,
+ [1848]=5,
+ [1849]=5,
+ [1850]=5,
+ [1851]=5,
+ [1852]=5,
+ [1853]=5,
+ [1854]=5,
+ [1855]=5,
+ [1856]=5,
+ [1857]=5,
+ [1858]=5,
+ [1859]=5,
+ [1860]=5,
+ [1861]=5,
+ [1862]=5,
+ [1863]=5,
+ [1864]=5,
+ [1865]=5,
+ [1866]=5,
+ [1869]=3,
+ [1870]=2,
+ [1871]=2,
+ [1872]=2,
+ [1873]=2,
+ [1874]=2,
+ [1875]=2,
+ [1876]=2,
+ [1877]=2,
+ [1878]=2,
+ [1879]=2,
+ [1880]=2,
+ [1881]=3,
+ [1882]=3,
+ [1883]=3,
+ [1884]=2,
+ [1885]=2,
+ [1886]=2,
+ [1887]=2,
+ [1888]=2,
+ [1889]=2,
+ [1890]=2,
+ [1891]=2,
+ [1892]=2,
+ [1893]=2,
+ [1894]=2,
+ [1895]=2,
+ [1896]=2,
+ [1897]=2,
+ [1898]=2,
+ [1899]=3,
+ [1900]=3,
+ [1901]=2,
+ [1902]=2,
+ [1903]=2,
+ [1904]=2,
+ [1905]=3,
+ [1906]=2,
+ [1907]=3,
+ [1908]=3,
+ [1909]=2,
+ [1910]=2,
+ [1911]=2,
+ [1912]=3,
+ [1913]=3,
+ [1914]=2,
+ [1915]=2,
+ [1916]=2,
+ [1917]=2,
+ [1918]=2,
+ [1919]=2,
+ [1958]=5,
+ [1959]=5,
+ [1960]=5,
+ [1961]=5,
+ [1962]=5,
+ [1963]=5,
+ [1964]=5,
+ [1965]=5,
+ [1966]=5,
+ [1967]=5,
+ [1968]=5,
+ [1984]=6,
+ [1985]=6,
+ [1986]=6,
+ [1987]=6,
+ [1988]=6,
+ [1989]=6,
+ [1990]=6,
+ [1991]=6,
+ [1992]=6,
+ [1993]=6,
+ [1994]=2,
+ [1995]=2,
+ [1996]=2,
+ [1997]=2,
+ [1998]=2,
+ [1999]=2,
+ [2000]=2,
+ [2001]=2,
+ [2002]=2,
+ [2003]=2,
+ [2004]=2,
+ [2005]=2,
+ [2006]=2,
+ [2007]=2,
+ [2008]=2,
+ [2009]=2,
+ [2010]=2,
+ [2011]=2,
+ [2012]=2,
+ [2013]=2,
+ [2014]=2,
+ [2015]=2,
+ [2016]=2,
+ [2017]=2,
+ [2018]=2,
+ [2019]=2,
+ [2020]=2,
+ [2021]=2,
+ [2022]=2,
+ [2023]=2,
+ [2024]=2,
+ [2025]=2,
+ [2026]=2,
+ [2027]=5,
+ [2028]=5,
+ [2029]=5,
+ [2030]=5,
+ [2031]=5,
+ [2032]=5,
+ [2033]=5,
+ [2034]=5,
+ [2035]=5,
+ [2036]=6,
+ [2037]=6,
+ [2038]=6,
+ [2039]=6,
+ [2040]=6,
+ [2041]=6,
+ [2042]=2,
+ [2045]=5,
+ [2046]=6,
+ [2047]=6,
+ [2070]=5,
+ [2071]=5,
+ [2072]=5,
+ [2073]=5,
+ [2075]=5,
+ [2076]=5,
+ [2077]=5,
+ [2078]=5,
+ [2079]=5,
+ [2080]=5,
+ [2081]=5,
+ [2082]=5,
+ [2083]=5,
+ [2085]=5,
+ [2086]=5,
+ [2087]=5,
+ [2089]=5,
+ [2090]=5,
+ [2091]=5,
+ [2092]=5,
+ [2093]=5,
+ [2112]=3,
+ [2113]=2,
+ [2114]=2,
+ [2115]=2,
+ [2116]=2,
+ [2117]=2,
+ [2118]=3,
+ [2119]=3,
+ [2120]=2,
+ [2121]=3,
+ [2122]=2,
+ [2123]=2,
+ [2124]=2,
+ [2125]=2,
+ [2126]=2,
+ [2127]=2,
+ [2128]=2,
+ [2129]=2,
+ [2130]=2,
+ [2131]=2,
+ [2132]=3,
+ [2133]=2,
+ [2134]=4,
+ [2135]=4,
+ [2136]=4,
+ [2137]=5,
+ [2138]=5,
+ [2139]=5,
+ [2144]=2,
+ [2145]=4,
+ [2146]=2,
+ [2147]=2,
+ [2148]=2,
+ [2149]=2,
+ [2150]=4,
+ [2151]=3,
+ [2152]=2,
+ [2153]=3,
+ [2154]=3,
+ [2208]=2,
+ [2209]=2,
+ [2210]=2,
+ [2211]=2,
+ [2212]=2,
+ [2213]=2,
+ [2214]=2,
+ [2215]=2,
+ [2216]=2,
+ [2217]=2,
+ [2218]=3,
+ [2219]=3,
+ [2220]=3,
+ [2221]=4,
+ [2222]=3,
+ [2223]=2,
+ [2224]=2,
+ [2225]=3,
+ [2226]=3,
+ [2227]=2,
+ [2228]=2,
+ [2230]=2,
+ [2231]=2,
+ [2232]=2,
+ [2233]=3,
+ [2234]=2,
+ [2235]=2,
+ [2236]=2,
+ [2237]=2,
+ [2259]=5,
+ [2260]=5,
+ [2261]=5,
+ [2262]=5,
+ [2263]=5,
+ [2264]=5,
+ [2265]=5,
+ [2266]=5,
+ [2267]=5,
+ [2268]=5,
+ [2269]=5,
+ [2270]=5,
+ [2271]=5,
+ [2272]=5,
+ [2273]=5,
+ [2274]=4,
+ [2275]=5,
+ [2276]=5,
+ [2277]=5,
+ [2278]=5,
+ [2279]=5,
+ [2280]=5,
+ [2281]=5,
+ [2282]=5,
+ [2283]=5,
+ [2284]=5,
+ [2285]=5,
+ [2286]=5,
+ [2287]=5,
+ [2288]=5,
+ [2289]=5,
+ [2290]=5,
+ [2291]=5,
+ [2292]=5,
+ [2293]=5,
+ [2294]=5,
+ [2295]=5,
+ [2296]=5,
+ [2297]=5,
+ [2298]=5,
+ [2299]=5,
+ [2300]=5,
+ [2301]=5,
+ [2302]=5,
+ [2303]=5,
+ [2304]=5,
+ [2305]=5,
+ [2306]=5,
+ [2362]=5,
+ [2364]=5,
+ [2369]=5,
+ [2370]=5,
+ [2371]=5,
+ [2372]=5,
+ [2373]=5,
+ [2374]=5,
+ [2375]=5,
+ [2376]=5,
+ [2381]=5,
+ [2385]=5,
+ [2386]=5,
+ [2387]=5,
+ [2388]=5,
+ [2389]=5,
+ [2390]=5,
+ [2391]=5,
+ [2402]=5,
+ [2403]=5,
+ [2433]=5,
+ [2492]=5,
+ [2497]=5,
+ [2498]=5,
+ [2499]=5,
+ [2500]=5,
+ [2509]=5,
+ [2530]=5,
+ [2531]=5,
+ [2558]=5,
+ [2561]=5,
+ [2562]=5,
+ [2620]=5,
+ [2625]=5,
+ [2626]=5,
+ [2631]=5,
+ [2632]=5,
+ [2635]=5,
+ [2636]=5,
+ [2637]=5,
+ [2641]=5,
+ [2672]=5,
+ [2673]=5,
+ [2677]=5,
+ [2689]=5,
+ [2690]=5,
+ [2748]=5,
+ [2753]=5,
+ [2754]=5,
+ [2755]=5,
+ [2756]=5,
+ [2757]=5,
+ [2759]=5,
+ [2760]=5,
+ [2765]=5,
+ [2786]=5,
+ [2787]=5,
+ [2810]=5,
+ [2811]=5,
+ [2812]=5,
+ [2813]=5,
+ [2814]=5,
+ [2815]=5,
+ [2817]=5,
+ [2876]=5,
+ [2879]=5,
+ [2881]=5,
+ [2882]=5,
+ [2883]=5,
+ [2884]=5,
+ [2893]=5,
+ [2902]=5,
+ [2914]=5,
+ [2915]=5,
+ [2946]=5,
+ [3008]=5,
+ [3021]=5,
+ [3072]=5,
+ [3076]=5,
+ [3134]=5,
+ [3135]=5,
+ [3136]=5,
+ [3142]=5,
+ [3143]=5,
+ [3144]=5,
+ [3146]=5,
+ [3147]=5,
+ [3148]=5,
+ [3149]=5,
+ [3157]=5,
+ [3158]=5,
+ [3170]=5,
+ [3171]=5,
+ [3201]=5,
+ [3260]=5,
+ [3263]=5,
+ [3270]=5,
+ [3276]=5,
+ [3277]=5,
+ [3298]=5,
+ [3299]=5,
+ [3328]=5,
+ [3329]=5,
+ [3387]=5,
+ [3388]=5,
+ [3393]=5,
+ [3394]=5,
+ [3395]=5,
+ [3396]=5,
+ [3405]=5,
+ [3426]=5,
+ [3427]=5,
+ [3530]=5,
+ [3538]=5,
+ [3539]=5,
+ [3540]=5,
+ [3542]=5,
+ [3633]=5,
+ [3636]=5,
+ [3637]=5,
+ [3638]=5,
+ [3639]=5,
+ [3640]=5,
+ [3641]=5,
+ [3642]=5,
+ [3655]=5,
+ [3656]=5,
+ [3657]=5,
+ [3658]=5,
+ [3659]=5,
+ [3660]=5,
+ [3661]=5,
+ [3662]=5,
+ [3761]=5,
+ [3764]=5,
+ [3765]=5,
+ [3766]=5,
+ [3767]=5,
+ [3768]=5,
+ [3769]=5,
+ [3770]=5,
+ [3771]=5,
+ [3772]=5,
+ [3784]=5,
+ [3785]=5,
+ [3786]=5,
+ [3787]=5,
+ [3788]=5,
+ [3789]=5,
+ [3864]=5,
+ [3865]=5,
+ [3893]=5,
+ [3895]=5,
+ [3897]=5,
+ [3953]=5,
+ [3954]=5,
+ [3955]=5,
+ [3956]=5,
+ [3957]=5,
+ [3958]=5,
+ [3959]=5,
+ [3960]=5,
+ [3961]=5,
+ [3962]=5,
+ [3963]=5,
+ [3964]=5,
+ [3965]=5,
+ [3966]=5,
+ [3968]=5,
+ [3969]=5,
+ [3970]=5,
+ [3971]=5,
+ [3972]=5,
+ [3974]=5,
+ [3975]=5,
+ [3981]=5,
+ [3982]=5,
+ [3983]=5,
+ [3984]=5,
+ [3985]=5,
+ [3986]=5,
+ [3987]=5,
+ [3988]=5,
+ [3989]=5,
+ [3990]=5,
+ [3991]=5,
+ [3993]=5,
+ [3994]=5,
+ [3995]=5,
+ [3996]=5,
+ [3997]=5,
+ [3998]=5,
+ [3999]=5,
+ [4000]=5,
+ [4001]=5,
+ [4002]=5,
+ [4003]=5,
+ [4004]=5,
+ [4005]=5,
+ [4006]=5,
+ [4007]=5,
+ [4008]=5,
+ [4009]=5,
+ [4010]=5,
+ [4011]=5,
+ [4012]=5,
+ [4013]=5,
+ [4014]=5,
+ [4015]=5,
+ [4016]=5,
+ [4017]=5,
+ [4018]=5,
+ [4019]=5,
+ [4020]=5,
+ [4021]=5,
+ [4022]=5,
+ [4023]=5,
+ [4024]=5,
+ [4025]=5,
+ [4026]=5,
+ [4027]=5,
+ [4028]=5,
+ [4038]=5,
+ [4141]=5,
+ [4142]=5,
+ [4143]=5,
+ [4144]=5,
+ [4146]=5,
+ [4147]=5,
+ [4148]=5,
+ [4149]=5,
+ [4150]=5,
+ [4151]=5,
+ [4153]=5,
+ [4154]=5,
+ [4157]=5,
+ [4158]=5,
+ [4184]=5,
+ [4185]=5,
+ [4190]=5,
+ [4191]=5,
+ [4192]=5,
+ [4209]=5,
+ [4210]=5,
+ [4211]=5,
+ [4212]=5,
+ [4226]=5,
+ [4229]=5,
+ [4230]=5,
+ [4237]=5,
+ [4253]=5,
+ [4957]=5,
+ [4958]=5,
+ [4959]=5,
+ [5906]=5,
+ [5907]=5,
+ [5908]=5,
+ [5938]=5,
+ [5939]=5,
+ [5940]=5,
+ [5970]=5,
+ [5971]=5,
+ [6002]=5,
+ [6003]=5,
+ [6071]=5,
+ [6072]=5,
+ [6073]=5,
+ [6074]=5,
+ [6075]=5,
+ [6076]=5,
+ [6077]=5,
+ [6086]=5,
+ [6089]=5,
+ [6090]=5,
+ [6091]=5,
+ [6092]=5,
+ [6093]=5,
+ [6094]=5,
+ [6095]=5,
+ [6096]=5,
+ [6097]=5,
+ [6098]=5,
+ [6099]=5,
+ [6109]=5,
+ [6150]=4,
+ [6151]=2,
+ [6154]=2,
+ [6155]=5,
+ [6156]=5,
+ [6157]=5,
+ [6158]=4,
+ [6176]=2,
+ [6177]=2,
+ [6178]=2,
+ [6179]=2,
+ [6180]=2,
+ [6181]=2,
+ [6182]=2,
+ [6183]=2,
+ [6184]=2,
+ [6185]=2,
+ [6186]=2,
+ [6187]=2,
+ [6188]=2,
+ [6189]=2,
+ [6190]=2,
+ [6191]=2,
+ [6192]=2,
+ [6193]=2,
+ [6194]=2,
+ [6195]=2,
+ [6196]=2,
+ [6197]=2,
+ [6198]=2,
+ [6199]=2,
+ [6200]=2,
+ [6201]=2,
+ [6202]=2,
+ [6203]=2,
+ [6204]=2,
+ [6205]=2,
+ [6206]=2,
+ [6207]=2,
+ [6208]=2,
+ [6209]=2,
+ [6210]=2,
+ [6211]=2,
+ [6212]=2,
+ [6213]=2,
+ [6214]=2,
+ [6215]=2,
+ [6216]=2,
+ [6217]=2,
+ [6218]=2,
+ [6219]=2,
+ [6220]=2,
+ [6221]=2,
+ [6222]=2,
+ [6223]=2,
+ [6224]=2,
+ [6225]=2,
+ [6226]=2,
+ [6227]=2,
+ [6228]=2,
+ [6229]=2,
+ [6230]=2,
+ [6231]=2,
+ [6232]=2,
+ [6233]=2,
+ [6234]=2,
+ [6235]=2,
+ [6236]=2,
+ [6237]=2,
+ [6238]=2,
+ [6239]=2,
+ [6240]=2,
+ [6241]=2,
+ [6242]=2,
+ [6243]=2,
+ [6244]=2,
+ [6245]=2,
+ [6246]=2,
+ [6247]=2,
+ [6248]=2,
+ [6249]=2,
+ [6250]=2,
+ [6251]=2,
+ [6252]=2,
+ [6253]=2,
+ [6254]=2,
+ [6255]=2,
+ [6256]=2,
+ [6257]=2,
+ [6258]=2,
+ [6259]=2,
+ [6260]=2,
+ [6261]=2,
+ [6262]=2,
+ [6263]=2,
+ [6264]=2,
+ [6272]=4,
+ [6273]=4,
+ [6274]=4,
+ [6275]=4,
+ [6276]=4,
+ [6279]=2,
+ [6280]=2,
+ [6281]=2,
+ [6282]=2,
+ [6283]=2,
+ [6284]=2,
+ [6285]=2,
+ [6286]=2,
+ [6287]=2,
+ [6288]=2,
+ [6289]=2,
+ [6290]=2,
+ [6291]=2,
+ [6292]=2,
+ [6293]=2,
+ [6294]=2,
+ [6295]=2,
+ [6296]=2,
+ [6297]=2,
+ [6298]=2,
+ [6299]=2,
+ [6300]=2,
+ [6301]=2,
+ [6302]=2,
+ [6303]=2,
+ [6304]=2,
+ [6305]=2,
+ [6306]=2,
+ [6307]=2,
+ [6308]=2,
+ [6309]=2,
+ [6310]=2,
+ [6311]=2,
+ [6312]=2,
+ [6313]=5,
+ [6314]=2,
+ [6432]=5,
+ [6433]=5,
+ [6434]=5,
+ [6439]=5,
+ [6440]=5,
+ [6450]=5,
+ [6457]=5,
+ [6458]=5,
+ [6459]=5,
+ [6679]=5,
+ [6680]=5,
+ [6742]=5,
+ [6744]=5,
+ [6745]=5,
+ [6746]=5,
+ [6747]=5,
+ [6748]=5,
+ [6749]=5,
+ [6750]=5,
+ [6752]=5,
+ [6754]=5,
+ [6757]=5,
+ [6758]=5,
+ [6759]=5,
+ [6760]=5,
+ [6761]=5,
+ [6762]=5,
+ [6763]=5,
+ [6764]=5,
+ [6771]=5,
+ [6772]=5,
+ [6773]=5,
+ [6774]=5,
+ [6775]=5,
+ [6776]=5,
+ [6777]=5,
+ [6778]=5,
+ [6779]=5,
+ [6780]=5,
+ [6783]=5,
+ [6832]=5,
+ [6833]=5,
+ [6834]=5,
+ [6835]=5,
+ [6836]=5,
+ [6837]=5,
+ [6838]=5,
+ [6839]=5,
+ [6840]=5,
+ [6841]=5,
+ [6842]=5,
+ [6843]=5,
+ [6844]=5,
+ [6845]=5,
+ [6912]=5,
+ [6913]=5,
+ [6914]=5,
+ [6915]=5,
+ [6964]=5,
+ [6966]=5,
+ [6967]=5,
+ [6968]=5,
+ [6969]=5,
+ [6970]=5,
+ [6972]=5,
+ [6978]=5,
+ [7019]=5,
+ [7020]=5,
+ [7021]=5,
+ [7022]=5,
+ [7023]=5,
+ [7024]=5,
+ [7025]=5,
+ [7026]=5,
+ [7027]=5,
+ [7040]=5,
+ [7041]=5,
+ [7074]=5,
+ [7075]=5,
+ [7076]=5,
+ [7077]=5,
+ [7080]=5,
+ [7081]=5,
+ [7083]=5,
+ [7142]=5,
+ [7144]=5,
+ [7145]=5,
+ [7149]=5,
+ [7151]=5,
+ [7152]=5,
+ [7153]=5,
+ [7212]=5,
+ [7213]=5,
+ [7214]=5,
+ [7215]=5,
+ [7216]=5,
+ [7217]=5,
+ [7218]=5,
+ [7219]=5,
+ [7222]=5,
+ [7223]=5,
+ [7376]=5,
+ [7377]=5,
+ [7378]=5,
+ [7380]=5,
+ [7381]=5,
+ [7382]=5,
+ [7383]=5,
+ [7384]=5,
+ [7385]=5,
+ [7386]=5,
+ [7387]=5,
+ [7388]=5,
+ [7389]=5,
+ [7390]=5,
+ [7391]=5,
+ [7392]=5,
+ [7394]=5,
+ [7395]=5,
+ [7396]=5,
+ [7397]=5,
+ [7398]=5,
+ [7399]=5,
+ [7400]=5,
+ [7405]=5,
+ [7412]=5,
+ [7416]=5,
+ [7417]=5,
+ [7616]=5,
+ [7617]=5,
+ [7618]=5,
+ [7619]=5,
+ [7620]=5,
+ [7621]=5,
+ [7622]=5,
+ [7623]=5,
+ [7624]=5,
+ [7625]=5,
+ [7626]=5,
+ [7627]=5,
+ [7628]=5,
+ [7629]=5,
+ [7630]=5,
+ [7631]=5,
+ [7632]=5,
+ [7633]=5,
+ [7634]=5,
+ [7635]=5,
+ [7636]=5,
+ [7637]=5,
+ [7638]=5,
+ [7639]=5,
+ [7640]=5,
+ [7641]=5,
+ [7642]=5,
+ [7643]=5,
+ [7644]=5,
+ [7645]=5,
+ [7646]=5,
+ [7647]=5,
+ [7648]=5,
+ [7649]=5,
+ [7650]=5,
+ [7651]=5,
+ [7652]=5,
+ [7653]=5,
+ [7654]=5,
+ [7655]=5,
+ [7656]=5,
+ [7657]=5,
+ [7658]=5,
+ [7659]=5,
+ [7660]=5,
+ [7661]=5,
+ [7662]=5,
+ [7663]=5,
+ [7664]=5,
+ [7665]=5,
+ [7666]=5,
+ [7667]=5,
+ [7668]=5,
+ [7669]=5,
+ [7670]=5,
+ [7671]=5,
+ [7672]=5,
+ [7673]=5,
+ [7675]=5,
+ [7676]=5,
+ [7677]=5,
+ [7678]=5,
+ [7679]=5,
+ [8204]=4,
+ [8205]=2,
+ [8239]=4,
+ [8294]=4,
+ [8295]=4,
+ [8296]=4,
+ [8297]=4,
+ [8400]=5,
+ [8401]=5,
+ [8402]=5,
+ [8403]=5,
+ [8404]=5,
+ [8405]=5,
+ [8406]=5,
+ [8407]=5,
+ [8408]=5,
+ [8409]=5,
+ [8410]=5,
+ [8411]=5,
+ [8412]=5,
+ [8417]=5,
+ [8421]=5,
+ [8422]=5,
+ [8423]=5,
+ [8424]=5,
+ [8425]=5,
+ [8426]=5,
+ [8427]=5,
+ [8428]=5,
+ [8429]=5,
+ [8430]=5,
+ [8431]=5,
+ [8432]=5,
+ [11503]=5,
+ [11504]=5,
+ [11505]=5,
+ [11647]=5,
+ [11744]=5,
+ [11745]=5,
+ [11746]=5,
+ [11747]=5,
+ [11748]=5,
+ [11749]=5,
+ [11750]=5,
+ [11751]=5,
+ [11752]=5,
+ [11753]=5,
+ [11754]=5,
+ [11755]=5,
+ [11756]=5,
+ [11757]=5,
+ [11758]=5,
+ [11759]=5,
+ [11760]=5,
+ [11761]=5,
+ [11762]=5,
+ [11763]=5,
+ [11764]=5,
+ [11765]=5,
+ [11766]=5,
+ [11767]=5,
+ [11768]=5,
+ [11769]=5,
+ [11770]=5,
+ [11771]=5,
+ [11772]=5,
+ [11773]=5,
+ [11774]=5,
+ [11775]=5,
+ [12330]=5,
+ [12331]=5,
+ [12332]=5,
+ [12333]=5,
+ [12334]=5,
+ [12335]=5,
+ [12441]=5,
+ [12442]=5,
+ [42607]=5,
+ [42612]=5,
+ [42613]=5,
+ [42614]=5,
+ [42615]=5,
+ [42616]=5,
+ [42617]=5,
+ [42618]=5,
+ [42619]=5,
+ [42620]=5,
+ [42621]=5,
+ [42654]=5,
+ [42655]=5,
+ [42736]=5,
+ [42737]=5,
+ [43014]=5,
+ [43019]=5,
+ [43045]=5,
+ [43046]=5,
+ [43072]=2,
+ [43073]=2,
+ [43074]=2,
+ [43075]=2,
+ [43076]=2,
+ [43077]=2,
+ [43078]=2,
+ [43079]=2,
+ [43080]=2,
+ [43081]=2,
+ [43082]=2,
+ [43083]=2,
+ [43084]=2,
+ [43085]=2,
+ [43086]=2,
+ [43087]=2,
+ [43088]=2,
+ [43089]=2,
+ [43090]=2,
+ [43091]=2,
+ [43092]=2,
+ [43093]=2,
+ [43094]=2,
+ [43095]=2,
+ [43096]=2,
+ [43097]=2,
+ [43098]=2,
+ [43099]=2,
+ [43100]=2,
+ [43101]=2,
+ [43102]=2,
+ [43103]=2,
+ [43104]=2,
+ [43105]=2,
+ [43106]=2,
+ [43107]=2,
+ [43108]=2,
+ [43109]=2,
+ [43110]=2,
+ [43111]=2,
+ [43112]=2,
+ [43113]=2,
+ [43114]=2,
+ [43115]=2,
+ [43116]=2,
+ [43117]=2,
+ [43118]=2,
+ [43119]=2,
+ [43120]=2,
+ [43121]=2,
+ [43122]=1,
+ [43123]=4,
+ [43204]=5,
+ [43205]=5,
+ [43232]=5,
+ [43233]=5,
+ [43234]=5,
+ [43235]=5,
+ [43236]=5,
+ [43237]=5,
+ [43238]=5,
+ [43239]=5,
+ [43240]=5,
+ [43241]=5,
+ [43242]=5,
+ [43243]=5,
+ [43244]=5,
+ [43245]=5,
+ [43246]=5,
+ [43247]=5,
+ [43248]=5,
+ [43249]=5,
+ [43263]=5,
+ [43302]=5,
+ [43303]=5,
+ [43304]=5,
+ [43305]=5,
+ [43306]=5,
+ [43307]=5,
+ [43308]=5,
+ [43309]=5,
+ [43335]=5,
+ [43336]=5,
+ [43337]=5,
+ [43338]=5,
+ [43339]=5,
+ [43340]=5,
+ [43341]=5,
+ [43342]=5,
+ [43343]=5,
+ [43344]=5,
+ [43345]=5,
+ [43392]=5,
+ [43393]=5,
+ [43394]=5,
+ [43443]=5,
+ [43446]=5,
+ [43447]=5,
+ [43448]=5,
+ [43449]=5,
+ [43452]=5,
+ [43493]=5,
+ [43561]=5,
+ [43562]=5,
+ [43563]=5,
+ [43564]=5,
+ [43565]=5,
+ [43566]=5,
+ [43569]=5,
+ [43570]=5,
+ [43573]=5,
+ [43574]=5,
+ [43587]=5,
+ [43596]=5,
+ [43644]=5,
+ [43696]=5,
+ [43698]=5,
+ [43699]=5,
+ [43700]=5,
+ [43703]=5,
+ [43704]=5,
+ [43710]=5,
+ [43711]=5,
+ [43713]=5,
+ [43756]=5,
+ [43757]=5,
+ [43766]=5,
+ [44005]=5,
+ [44008]=5,
+ [44013]=5,
+ [64286]=5,
+ [65056]=5,
+ [65057]=5,
+ [65058]=5,
+ [65059]=5,
+ [65060]=5,
+ [65061]=5,
+ [65062]=5,
+ [65063]=5,
+ [65064]=5,
+ [65065]=5,
+ [65066]=5,
+ [65067]=5,
+ [65068]=5,
+ [65069]=5,
+ [65070]=5,
+ [65071]=5,
+ [66045]=5,
+ [66272]=5,
+ [66422]=5,
+ [66423]=5,
+ [66424]=5,
+ [66425]=5,
+ [66426]=5,
+ [68097]=5,
+ [68098]=5,
+ [68099]=5,
+ [68101]=5,
+ [68102]=5,
+ [68108]=5,
+ [68109]=5,
+ [68110]=5,
+ [68111]=5,
+ [68152]=5,
+ [68153]=5,
+ [68154]=5,
+ [68159]=5,
+ [68288]=2,
+ [68289]=2,
+ [68290]=2,
+ [68291]=2,
+ [68292]=2,
+ [68293]=3,
+ [68294]=4,
+ [68295]=3,
+ [68296]=4,
+ [68297]=3,
+ [68298]=3,
+ [68299]=4,
+ [68300]=4,
+ [68301]=1,
+ [68302]=3,
+ [68303]=3,
+ [68304]=3,
+ [68305]=3,
+ [68306]=3,
+ [68307]=2,
+ [68308]=2,
+ [68309]=2,
+ [68310]=2,
+ [68311]=1,
+ [68312]=2,
+ [68313]=2,
+ [68314]=2,
+ [68315]=2,
+ [68316]=2,
+ [68317]=3,
+ [68318]=2,
+ [68319]=2,
+ [68320]=2,
+ [68321]=3,
+ [68322]=4,
+ [68323]=4,
+ [68324]=3,
+ [68325]=5,
+ [68326]=5,
+ [68331]=2,
+ [68332]=2,
+ [68333]=2,
+ [68334]=2,
+ [68335]=3,
+ [68480]=2,
+ [68481]=3,
+ [68482]=2,
+ [68483]=3,
+ [68484]=3,
+ [68485]=3,
+ [68486]=2,
+ [68487]=2,
+ [68488]=2,
+ [68489]=3,
+ [68490]=2,
+ [68491]=2,
+ [68492]=3,
+ [68493]=2,
+ [68494]=3,
+ [68495]=3,
+ [68496]=2,
+ [68497]=3,
+ [68521]=3,
+ [68522]=3,
+ [68523]=3,
+ [68524]=3,
+ [68525]=2,
+ [68526]=2,
+ [68527]=4,
+ [68864]=1,
+ [68865]=2,
+ [68866]=2,
+ [68867]=2,
+ [68868]=2,
+ [68869]=2,
+ [68870]=2,
+ [68871]=2,
+ [68872]=2,
+ [68873]=2,
+ [68874]=2,
+ [68875]=2,
+ [68876]=2,
+ [68877]=2,
+ [68878]=2,
+ [68879]=2,
+ [68880]=2,
+ [68881]=2,
+ [68882]=2,
+ [68883]=2,
+ [68884]=2,
+ [68885]=2,
+ [68886]=2,
+ [68887]=2,
+ [68888]=2,
+ [68889]=2,
+ [68890]=2,
+ [68891]=2,
+ [68892]=2,
+ [68893]=2,
+ [68894]=2,
+ [68895]=2,
+ [68896]=2,
+ [68897]=2,
+ [68898]=3,
+ [68899]=2,
+ [68900]=5,
+ [68901]=5,
+ [68902]=5,
+ [68903]=5,
+ [69424]=2,
+ [69425]=2,
+ [69426]=2,
+ [69427]=3,
+ [69428]=2,
+ [69429]=2,
+ [69430]=2,
+ [69431]=2,
+ [69432]=2,
+ [69433]=2,
+ [69434]=2,
+ [69435]=2,
+ [69436]=2,
+ [69437]=2,
+ [69438]=2,
+ [69439]=2,
+ [69440]=2,
+ [69441]=2,
+ [69442]=2,
+ [69443]=2,
+ [69444]=2,
+ [69445]=4,
+ [69446]=5,
+ [69447]=5,
+ [69448]=5,
+ [69449]=5,
+ [69450]=5,
+ [69451]=5,
+ [69452]=5,
+ [69453]=5,
+ [69454]=5,
+ [69455]=5,
+ [69456]=5,
+ [69457]=2,
+ [69458]=2,
+ [69459]=2,
+ [69460]=3,
+ [69633]=5,
+ [69688]=5,
+ [69689]=5,
+ [69690]=5,
+ [69691]=5,
+ [69692]=5,
+ [69693]=5,
+ [69694]=5,
+ [69695]=5,
+ [69696]=5,
+ [69697]=5,
+ [69698]=5,
+ [69699]=5,
+ [69700]=5,
+ [69701]=5,
+ [69702]=5,
+ [69759]=5,
+ [69760]=5,
+ [69761]=5,
+ [69811]=5,
+ [69812]=5,
+ [69813]=5,
+ [69814]=5,
+ [69817]=5,
+ [69818]=5,
+ [69821]=4,
+ [69837]=4,
+ [69888]=5,
+ [69889]=5,
+ [69890]=5,
+ [69927]=5,
+ [69928]=5,
+ [69929]=5,
+ [69930]=5,
+ [69931]=5,
+ [69933]=5,
+ [69934]=5,
+ [69935]=5,
+ [69936]=5,
+ [69937]=5,
+ [69938]=5,
+ [69939]=5,
+ [69940]=5,
+ [70003]=5,
+ [70016]=5,
+ [70017]=5,
+ [70070]=5,
+ [70071]=5,
+ [70072]=5,
+ [70073]=5,
+ [70074]=5,
+ [70075]=5,
+ [70076]=5,
+ [70077]=5,
+ [70078]=5,
+ [70090]=5,
+ [70091]=5,
+ [70092]=5,
+ [70191]=5,
+ [70192]=5,
+ [70193]=5,
+ [70196]=5,
+ [70198]=5,
+ [70199]=5,
+ [70206]=5,
+ [70367]=5,
+ [70371]=5,
+ [70372]=5,
+ [70373]=5,
+ [70374]=5,
+ [70375]=5,
+ [70376]=5,
+ [70377]=5,
+ [70378]=5,
+ [70400]=5,
+ [70401]=5,
+ [70459]=5,
+ [70460]=5,
+ [70464]=5,
+ [70502]=5,
+ [70503]=5,
+ [70504]=5,
+ [70505]=5,
+ [70506]=5,
+ [70507]=5,
+ [70508]=5,
+ [70512]=5,
+ [70513]=5,
+ [70514]=5,
+ [70515]=5,
+ [70516]=5,
+ [70712]=5,
+ [70713]=5,
+ [70714]=5,
+ [70715]=5,
+ [70716]=5,
+ [70717]=5,
+ [70718]=5,
+ [70719]=5,
+ [70722]=5,
+ [70723]=5,
+ [70724]=5,
+ [70726]=5,
+ [70750]=5,
+ [70835]=5,
+ [70836]=5,
+ [70837]=5,
+ [70838]=5,
+ [70839]=5,
+ [70840]=5,
+ [70842]=5,
+ [70847]=5,
+ [70848]=5,
+ [70850]=5,
+ [70851]=5,
+ [71090]=5,
+ [71091]=5,
+ [71092]=5,
+ [71093]=5,
+ [71100]=5,
+ [71101]=5,
+ [71103]=5,
+ [71104]=5,
+ [71132]=5,
+ [71133]=5,
+ [71219]=5,
+ [71220]=5,
+ [71221]=5,
+ [71222]=5,
+ [71223]=5,
+ [71224]=5,
+ [71225]=5,
+ [71226]=5,
+ [71229]=5,
+ [71231]=5,
+ [71232]=5,
+ [71339]=5,
+ [71341]=5,
+ [71344]=5,
+ [71345]=5,
+ [71346]=5,
+ [71347]=5,
+ [71348]=5,
+ [71349]=5,
+ [71351]=5,
+ [71453]=5,
+ [71454]=5,
+ [71455]=5,
+ [71458]=5,
+ [71459]=5,
+ [71460]=5,
+ [71461]=5,
+ [71463]=5,
+ [71464]=5,
+ [71465]=5,
+ [71466]=5,
+ [71467]=5,
+ [71727]=5,
+ [71728]=5,
+ [71729]=5,
+ [71730]=5,
+ [71731]=5,
+ [71732]=5,
+ [71733]=5,
+ [71734]=5,
+ [71735]=5,
+ [71737]=5,
+ [71738]=5,
+ [72148]=5,
+ [72149]=5,
+ [72150]=5,
+ [72151]=5,
+ [72154]=5,
+ [72155]=5,
+ [72160]=5,
+ [72193]=5,
+ [72194]=5,
+ [72195]=5,
+ [72196]=5,
+ [72197]=5,
+ [72198]=5,
+ [72201]=5,
+ [72202]=5,
+ [72243]=5,
+ [72244]=5,
+ [72245]=5,
+ [72246]=5,
+ [72247]=5,
+ [72248]=5,
+ [72251]=5,
+ [72252]=5,
+ [72253]=5,
+ [72254]=5,
+ [72263]=5,
+ [72273]=5,
+ [72274]=5,
+ [72275]=5,
+ [72276]=5,
+ [72277]=5,
+ [72278]=5,
+ [72281]=5,
+ [72282]=5,
+ [72283]=5,
+ [72330]=5,
+ [72331]=5,
+ [72332]=5,
+ [72333]=5,
+ [72334]=5,
+ [72335]=5,
+ [72336]=5,
+ [72337]=5,
+ [72338]=5,
+ [72339]=5,
+ [72340]=5,
+ [72341]=5,
+ [72342]=5,
+ [72344]=5,
+ [72345]=5,
+ [72752]=5,
+ [72753]=5,
+ [72754]=5,
+ [72755]=5,
+ [72756]=5,
+ [72757]=5,
+ [72758]=5,
+ [72760]=5,
+ [72761]=5,
+ [72762]=5,
+ [72763]=5,
+ [72764]=5,
+ [72765]=5,
+ [72767]=5,
+ [72850]=5,
+ [72851]=5,
+ [72852]=5,
+ [72853]=5,
+ [72854]=5,
+ [72855]=5,
+ [72856]=5,
+ [72857]=5,
+ [72858]=5,
+ [72859]=5,
+ [72860]=5,
+ [72861]=5,
+ [72862]=5,
+ [72863]=5,
+ [72864]=5,
+ [72865]=5,
+ [72866]=5,
+ [72867]=5,
+ [72868]=5,
+ [72869]=5,
+ [72870]=5,
+ [72871]=5,
+ [72874]=5,
+ [72875]=5,
+ [72876]=5,
+ [72877]=5,
+ [72878]=5,
+ [72879]=5,
+ [72880]=5,
+ [72882]=5,
+ [72883]=5,
+ [72885]=5,
+ [72886]=5,
+ [73009]=5,
+ [73010]=5,
+ [73011]=5,
+ [73012]=5,
+ [73013]=5,
+ [73014]=5,
+ [73018]=5,
+ [73020]=5,
+ [73021]=5,
+ [73023]=5,
+ [73024]=5,
+ [73025]=5,
+ [73026]=5,
+ [73027]=5,
+ [73028]=5,
+ [73029]=5,
+ [73031]=5,
+ [73104]=5,
+ [73105]=5,
+ [73109]=5,
+ [73111]=5,
+ [73459]=5,
+ [73460]=5,
+ [92912]=5,
+ [92913]=5,
+ [92914]=5,
+ [92915]=5,
+ [92916]=5,
+ [92976]=5,
+ [92977]=5,
+ [92978]=5,
+ [92979]=5,
+ [92980]=5,
+ [92981]=5,
+ [92982]=5,
+ [94031]=5,
+ [94095]=5,
+ [94096]=5,
+ [94097]=5,
+ [94098]=5,
+ [113821]=5,
+ [113822]=5,
+ [119143]=5,
+ [119144]=5,
+ [119145]=5,
+ [119163]=5,
+ [119164]=5,
+ [119165]=5,
+ [119166]=5,
+ [119167]=5,
+ [119168]=5,
+ [119169]=5,
+ [119170]=5,
+ [119173]=5,
+ [119174]=5,
+ [119175]=5,
+ [119176]=5,
+ [119177]=5,
+ [119178]=5,
+ [119179]=5,
+ [119210]=5,
+ [119211]=5,
+ [119212]=5,
+ [119213]=5,
+ [119362]=5,
+ [119363]=5,
+ [119364]=5,
+ [121344]=5,
+ [121345]=5,
+ [121346]=5,
+ [121347]=5,
+ [121348]=5,
+ [121349]=5,
+ [121350]=5,
+ [121351]=5,
+ [121352]=5,
+ [121353]=5,
+ [121354]=5,
+ [121355]=5,
+ [121356]=5,
+ [121357]=5,
+ [121358]=5,
+ [121359]=5,
+ [121360]=5,
+ [121361]=5,
+ [121362]=5,
+ [121363]=5,
+ [121364]=5,
+ [121365]=5,
+ [121366]=5,
+ [121367]=5,
+ [121368]=5,
+ [121369]=5,
+ [121370]=5,
+ [121371]=5,
+ [121372]=5,
+ [121373]=5,
+ [121374]=5,
+ [121375]=5,
+ [121376]=5,
+ [121377]=5,
+ [121378]=5,
+ [121379]=5,
+ [121380]=5,
+ [121381]=5,
+ [121382]=5,
+ [121383]=5,
+ [121384]=5,
+ [121385]=5,
+ [121386]=5,
+ [121387]=5,
+ [121388]=5,
+ [121389]=5,
+ [121390]=5,
+ [121391]=5,
+ [121392]=5,
+ [121393]=5,
+ [121394]=5,
+ [121395]=5,
+ [121396]=5,
+ [121397]=5,
+ [121398]=5,
+ [121403]=5,
+ [121404]=5,
+ [121405]=5,
+ [121406]=5,
+ [121407]=5,
+ [121408]=5,
+ [121409]=5,
+ [121410]=5,
+ [121411]=5,
+ [121412]=5,
+ [121413]=5,
+ [121414]=5,
+ [121415]=5,
+ [121416]=5,
+ [121417]=5,
+ [121418]=5,
+ [121419]=5,
+ [121420]=5,
+ [121421]=5,
+ [121422]=5,
+ [121423]=5,
+ [121424]=5,
+ [121425]=5,
+ [121426]=5,
+ [121427]=5,
+ [121428]=5,
+ [121429]=5,
+ [121430]=5,
+ [121431]=5,
+ [121432]=5,
+ [121433]=5,
+ [121434]=5,
+ [121435]=5,
+ [121436]=5,
+ [121437]=5,
+ [121438]=5,
+ [121439]=5,
+ [121440]=5,
+ [121441]=5,
+ [121442]=5,
+ [121443]=5,
+ [121444]=5,
+ [121445]=5,
+ [121446]=5,
+ [121447]=5,
+ [121448]=5,
+ [121449]=5,
+ [121450]=5,
+ [121451]=5,
+ [121452]=5,
+ [121461]=5,
+ [121476]=5,
+ [121499]=5,
+ [121500]=5,
+ [121501]=5,
+ [121502]=5,
+ [121503]=5,
+ [121505]=5,
+ [121506]=5,
+ [121507]=5,
+ [121508]=5,
+ [121509]=5,
+ [121510]=5,
+ [121511]=5,
+ [121512]=5,
+ [121513]=5,
+ [121514]=5,
+ [121515]=5,
+ [121516]=5,
+ [121517]=5,
+ [121518]=5,
+ [121519]=5,
+ [122880]=5,
+ [122881]=5,
+ [122882]=5,
+ [122883]=5,
+ [122884]=5,
+ [122885]=5,
+ [122886]=5,
+ [122888]=5,
+ [122889]=5,
+ [122890]=5,
+ [122891]=5,
+ [122892]=5,
+ [122893]=5,
+ [122894]=5,
+ [122895]=5,
+ [122896]=5,
+ [122897]=5,
+ [122898]=5,
+ [122899]=5,
+ [122900]=5,
+ [122901]=5,
+ [122902]=5,
+ [122903]=5,
+ [122904]=5,
+ [122907]=5,
+ [122908]=5,
+ [122909]=5,
+ [122910]=5,
+ [122911]=5,
+ [122912]=5,
+ [122913]=5,
+ [122915]=5,
+ [122916]=5,
+ [122918]=5,
+ [122919]=5,
+ [122920]=5,
+ [122921]=5,
+ [122922]=5,
+ [123184]=5,
+ [123185]=5,
+ [123186]=5,
+ [123187]=5,
+ [123188]=5,
+ [123189]=5,
+ [123190]=5,
+ [123628]=5,
+ [123629]=5,
+ [123630]=5,
+ [123631]=5,
+ [125136]=5,
+ [125137]=5,
+ [125138]=5,
+ [125139]=5,
+ [125140]=5,
+ [125141]=5,
+ [125142]=5,
+ [125184]=2,
+ [125185]=2,
+ [125186]=2,
+ [125187]=2,
+ [125188]=2,
+ [125189]=2,
+ [125190]=2,
+ [125191]=2,
+ [125192]=2,
+ [125193]=2,
+ [125194]=2,
+ [125195]=2,
+ [125196]=2,
+ [125197]=2,
+ [125198]=2,
+ [125199]=2,
+ [125200]=2,
+ [125201]=2,
+ [125202]=2,
+ [125203]=2,
+ [125204]=2,
+ [125205]=2,
+ [125206]=2,
+ [125207]=2,
+ [125208]=2,
+ [125209]=2,
+ [125210]=2,
+ [125211]=2,
+ [125212]=2,
+ [125213]=2,
+ [125214]=2,
+ [125215]=2,
+ [125216]=2,
+ [125217]=2,
+ [125218]=2,
+ [125219]=2,
+ [125220]=2,
+ [125221]=2,
+ [125222]=2,
+ [125223]=2,
+ [125224]=2,
+ [125225]=2,
+ [125226]=2,
+ [125227]=2,
+ [125228]=2,
+ [125229]=2,
+ [125230]=2,
+ [125231]=2,
+ [125232]=2,
+ [125233]=2,
+ [125234]=2,
+ [125235]=2,
+ [125236]=2,
+ [125237]=2,
+ [125238]=2,
+ [125239]=2,
+ [125240]=2,
+ [125241]=2,
+ [125242]=2,
+ [125243]=2,
+ [125244]=2,
+ [125245]=2,
+ [125246]=2,
+ [125247]=2,
+ [125248]=2,
+ [125249]=2,
+ [125250]=2,
+ [125251]=2,
+ [125252]=5,
+ [125253]=5,
+ [125254]=5,
+ [125255]=5,
+ [125256]=5,
+ [125257]=5,
+ [125258]=5,
+ [1042752]=5,
+}
+characters.indicgroups={
+ ["above_mark"]={
+ [2304]=true,
+ [2305]=true,
+ [2306]=true,
+ [2362]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2385]=true,
+ [2387]=true,
+ [2388]=true,
+ [2389]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2690]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2879]=true,
+ [3008]=true,
+ [3021]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3142]=true,
+ [3143]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3149]=true,
+ [3263]=true,
+ [3270]=true,
+ [3406]=true,
+ [4141]=true,
+ [4142]=true,
+ [4146]=true,
+ [4147]=true,
+ [4148]=true,
+ [4149]=true,
+ [4150]=true,
+ [4154]=true,
+ [4209]=true,
+ [4210]=true,
+ [4211]=true,
+ [4212]=true,
+ [4229]=true,
+ [4230]=true,
+ [4253]=true,
+ [43232]=true,
+ [43233]=true,
+ [43234]=true,
+ [43235]=true,
+ [43236]=true,
+ [43237]=true,
+ [43238]=true,
+ [43239]=true,
+ [43240]=true,
+ [43241]=true,
+ [43242]=true,
+ [43243]=true,
+ [43244]=true,
+ [43245]=true,
+ [43246]=true,
+ [43247]=true,
+ [43248]=true,
+ [43249]=true,
+ [43493]=true,
+ [43644]=true,
+ },
+ ["after_half"]={},
+ ["after_main"]={
+ [2864]=true,
+ [2879]=true,
+ [2902]=true,
+ [3376]=true,
+ },
+ ["after_postscript"]={
+ [2433]=true,
+ [2494]=true,
+ [2496]=true,
+ [2519]=true,
+ [2561]=true,
+ [2562]=true,
+ [2622]=true,
+ [2624]=true,
+ [2625]=true,
+ [2626]=true,
+ [2672]=true,
+ [2673]=true,
+ [2735]=true,
+ [2750]=true,
+ [2752]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2786]=true,
+ [2787]=true,
+ [2878]=true,
+ [2880]=true,
+ [2903]=true,
+ [2992]=true,
+ [3006]=true,
+ [3007]=true,
+ [3009]=true,
+ [3010]=true,
+ [3031]=true,
+ [3120]=true,
+ [3248]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3415]=true,
+ },
+ ["after_subscript"]={
+ [2366]=true,
+ [2368]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2402]=true,
+ [2403]=true,
+ [2480]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2530]=true,
+ [2531]=true,
+ [2544]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [3008]=true,
+ [3139]=true,
+ [3140]=true,
+ [3267]=true,
+ [3268]=true,
+ [3285]=true,
+ [3286]=true,
+ },
+ ["anudatta"]={
+ [2386]=true,
+ },
+ ["before_half"]={
+ [2367]=true,
+ [2382]=true,
+ [2495]=true,
+ [2503]=true,
+ [2504]=true,
+ [2623]=true,
+ [2751]=true,
+ [2887]=true,
+ },
+ ["before_main"]={
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ },
+ ["before_postscript"]={
+ [2352]=true,
+ [2736]=true,
+ },
+ ["before_subscript"]={
+ [2608]=true,
+ [2817]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3137]=true,
+ [3138]=true,
+ [3142]=true,
+ [3143]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3157]=true,
+ [3158]=true,
+ [3262]=true,
+ [3263]=true,
+ [3265]=true,
+ [3266]=true,
+ [3270]=true,
+ [3276]=true,
+ [3298]=true,
+ [3299]=true,
+ },
+ ["below_mark"]={
+ [2364]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2381]=true,
+ [2386]=true,
+ [2390]=true,
+ [2391]=true,
+ [2402]=true,
+ [2403]=true,
+ [2492]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2509]=true,
+ [2620]=true,
+ [2625]=true,
+ [2626]=true,
+ [2637]=true,
+ [2748]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2765]=true,
+ [2876]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [2884]=true,
+ [2893]=true,
+ [2914]=true,
+ [2915]=true,
+ [3009]=true,
+ [3010]=true,
+ [3170]=true,
+ [3171]=true,
+ [3260]=true,
+ [3286]=true,
+ [3298]=true,
+ [3299]=true,
+ [3426]=true,
+ [3427]=true,
+ [4143]=true,
+ [4144]=true,
+ [4151]=true,
+ [4153]=true,
+ [4157]=true,
+ [4158]=true,
+ [4184]=true,
+ [4185]=true,
+ [4190]=true,
+ [4191]=true,
+ [4192]=true,
+ [4226]=true,
+ [4237]=true,
+ },
+ ["consonant"]={
+ [2325]=true,
+ [2326]=true,
+ [2327]=true,
+ [2328]=true,
+ [2329]=true,
+ [2330]=true,
+ [2331]=true,
+ [2332]=true,
+ [2333]=true,
+ [2334]=true,
+ [2335]=true,
+ [2336]=true,
+ [2337]=true,
+ [2338]=true,
+ [2339]=true,
+ [2340]=true,
+ [2341]=true,
+ [2342]=true,
+ [2343]=true,
+ [2344]=true,
+ [2345]=true,
+ [2346]=true,
+ [2347]=true,
+ [2348]=true,
+ [2349]=true,
+ [2350]=true,
+ [2351]=true,
+ [2352]=true,
+ [2353]=true,
+ [2354]=true,
+ [2355]=true,
+ [2356]=true,
+ [2357]=true,
+ [2358]=true,
+ [2359]=true,
+ [2360]=true,
+ [2361]=true,
+ [2392]=true,
+ [2393]=true,
+ [2394]=true,
+ [2395]=true,
+ [2396]=true,
+ [2397]=true,
+ [2398]=true,
+ [2399]=true,
+ [2424]=true,
+ [2425]=true,
+ [2426]=true,
+ [2453]=true,
+ [2454]=true,
+ [2455]=true,
+ [2456]=true,
+ [2457]=true,
+ [2458]=true,
+ [2459]=true,
+ [2460]=true,
+ [2461]=true,
+ [2462]=true,
+ [2463]=true,
+ [2464]=true,
+ [2465]=true,
+ [2466]=true,
+ [2467]=true,
+ [2468]=true,
+ [2469]=true,
+ [2470]=true,
+ [2471]=true,
+ [2472]=true,
+ [2474]=true,
+ [2475]=true,
+ [2476]=true,
+ [2477]=true,
+ [2478]=true,
+ [2479]=true,
+ [2480]=true,
+ [2482]=true,
+ [2486]=true,
+ [2487]=true,
+ [2488]=true,
+ [2489]=true,
+ [2510]=true,
+ [2524]=true,
+ [2525]=true,
+ [2527]=true,
+ [2581]=true,
+ [2582]=true,
+ [2583]=true,
+ [2584]=true,
+ [2585]=true,
+ [2586]=true,
+ [2587]=true,
+ [2588]=true,
+ [2589]=true,
+ [2590]=true,
+ [2591]=true,
+ [2592]=true,
+ [2593]=true,
+ [2594]=true,
+ [2595]=true,
+ [2596]=true,
+ [2597]=true,
+ [2598]=true,
+ [2599]=true,
+ [2600]=true,
+ [2602]=true,
+ [2603]=true,
+ [2604]=true,
+ [2605]=true,
+ [2606]=true,
+ [2607]=true,
+ [2608]=true,
+ [2610]=true,
+ [2611]=true,
+ [2613]=true,
+ [2614]=true,
+ [2616]=true,
+ [2617]=true,
+ [2649]=true,
+ [2650]=true,
+ [2651]=true,
+ [2652]=true,
+ [2654]=true,
+ [2709]=true,
+ [2710]=true,
+ [2711]=true,
+ [2712]=true,
+ [2713]=true,
+ [2714]=true,
+ [2715]=true,
+ [2716]=true,
+ [2717]=true,
+ [2718]=true,
+ [2719]=true,
+ [2720]=true,
+ [2721]=true,
+ [2722]=true,
+ [2723]=true,
+ [2724]=true,
+ [2725]=true,
+ [2726]=true,
+ [2727]=true,
+ [2728]=true,
+ [2730]=true,
+ [2731]=true,
+ [2732]=true,
+ [2733]=true,
+ [2734]=true,
+ [2735]=true,
+ [2736]=true,
+ [2738]=true,
+ [2739]=true,
+ [2741]=true,
+ [2742]=true,
+ [2743]=true,
+ [2744]=true,
+ [2745]=true,
+ [2837]=true,
+ [2838]=true,
+ [2839]=true,
+ [2840]=true,
+ [2841]=true,
+ [2842]=true,
+ [2843]=true,
+ [2844]=true,
+ [2845]=true,
+ [2846]=true,
+ [2847]=true,
+ [2848]=true,
+ [2849]=true,
+ [2850]=true,
+ [2851]=true,
+ [2852]=true,
+ [2853]=true,
+ [2854]=true,
+ [2855]=true,
+ [2856]=true,
+ [2858]=true,
+ [2859]=true,
+ [2860]=true,
+ [2861]=true,
+ [2862]=true,
+ [2863]=true,
+ [2864]=true,
+ [2866]=true,
+ [2867]=true,
+ [2869]=true,
+ [2870]=true,
+ [2871]=true,
+ [2872]=true,
+ [2873]=true,
+ [2908]=true,
+ [2909]=true,
+ [2929]=true,
+ [2965]=true,
+ [2969]=true,
+ [2970]=true,
+ [2972]=true,
+ [2974]=true,
+ [2975]=true,
+ [2979]=true,
+ [2980]=true,
+ [2984]=true,
+ [2985]=true,
+ [2986]=true,
+ [2990]=true,
+ [2991]=true,
+ [2992]=true,
+ [2993]=true,
+ [2994]=true,
+ [2995]=true,
+ [2996]=true,
+ [2997]=true,
+ [2998]=true,
+ [2999]=true,
+ [3000]=true,
+ [3001]=true,
+ [3093]=true,
+ [3094]=true,
+ [3095]=true,
+ [3096]=true,
+ [3097]=true,
+ [3098]=true,
+ [3099]=true,
+ [3100]=true,
+ [3101]=true,
+ [3102]=true,
+ [3103]=true,
+ [3104]=true,
+ [3105]=true,
+ [3106]=true,
+ [3107]=true,
+ [3108]=true,
+ [3109]=true,
+ [3110]=true,
+ [3111]=true,
+ [3112]=true,
+ [3114]=true,
+ [3115]=true,
+ [3116]=true,
+ [3117]=true,
+ [3118]=true,
+ [3119]=true,
+ [3120]=true,
+ [3121]=true,
+ [3122]=true,
+ [3123]=true,
+ [3124]=true,
+ [3125]=true,
+ [3126]=true,
+ [3127]=true,
+ [3128]=true,
+ [3129]=true,
+ [3133]=true,
+ [3221]=true,
+ [3222]=true,
+ [3223]=true,
+ [3224]=true,
+ [3225]=true,
+ [3226]=true,
+ [3227]=true,
+ [3228]=true,
+ [3229]=true,
+ [3230]=true,
+ [3231]=true,
+ [3232]=true,
+ [3233]=true,
+ [3234]=true,
+ [3235]=true,
+ [3236]=true,
+ [3237]=true,
+ [3238]=true,
+ [3239]=true,
+ [3240]=true,
+ [3242]=true,
+ [3243]=true,
+ [3244]=true,
+ [3245]=true,
+ [3246]=true,
+ [3247]=true,
+ [3248]=true,
+ [3249]=true,
+ [3250]=true,
+ [3251]=true,
+ [3253]=true,
+ [3254]=true,
+ [3255]=true,
+ [3256]=true,
+ [3257]=true,
+ [3294]=true,
+ [3349]=true,
+ [3350]=true,
+ [3351]=true,
+ [3352]=true,
+ [3353]=true,
+ [3354]=true,
+ [3355]=true,
+ [3356]=true,
+ [3357]=true,
+ [3358]=true,
+ [3359]=true,
+ [3360]=true,
+ [3361]=true,
+ [3362]=true,
+ [3363]=true,
+ [3364]=true,
+ [3365]=true,
+ [3366]=true,
+ [3367]=true,
+ [3368]=true,
+ [3369]=true,
+ [3370]=true,
+ [3371]=true,
+ [3372]=true,
+ [3373]=true,
+ [3374]=true,
+ [3375]=true,
+ [3376]=true,
+ [3377]=true,
+ [3378]=true,
+ [3379]=true,
+ [3380]=true,
+ [3381]=true,
+ [3382]=true,
+ [3383]=true,
+ [3384]=true,
+ [3385]=true,
+ [3386]=true,
+ [4096]=true,
+ [4097]=true,
+ [4098]=true,
+ [4099]=true,
+ [4100]=true,
+ [4101]=true,
+ [4102]=true,
+ [4103]=true,
+ [4104]=true,
+ [4105]=true,
+ [4106]=true,
+ [4107]=true,
+ [4108]=true,
+ [4109]=true,
+ [4110]=true,
+ [4111]=true,
+ [4112]=true,
+ [4113]=true,
+ [4114]=true,
+ [4115]=true,
+ [4116]=true,
+ [4117]=true,
+ [4118]=true,
+ [4119]=true,
+ [4120]=true,
+ [4121]=true,
+ [4122]=true,
+ [4123]=true,
+ [4124]=true,
+ [4125]=true,
+ [4126]=true,
+ [4127]=true,
+ [4128]=true,
+ [4155]=true,
+ [4156]=true,
+ [4157]=true,
+ [4158]=true,
+ [4159]=true,
+ [4176]=true,
+ [4177]=true,
+ [4186]=true,
+ [4187]=true,
+ [4188]=true,
+ [4189]=true,
+ [4190]=true,
+ [4191]=true,
+ [4192]=true,
+ [4193]=true,
+ [4197]=true,
+ [4198]=true,
+ [4206]=true,
+ [4207]=true,
+ [4208]=true,
+ [4213]=true,
+ [4214]=true,
+ [4215]=true,
+ [4216]=true,
+ [4217]=true,
+ [4218]=true,
+ [4219]=true,
+ [4220]=true,
+ [4221]=true,
+ [4222]=true,
+ [4223]=true,
+ [4224]=true,
+ [4225]=true,
+ [4226]=true,
+ [4238]=true,
+ [43488]=true,
+ [43489]=true,
+ [43490]=true,
+ [43491]=true,
+ [43492]=true,
+ [43495]=true,
+ [43496]=true,
+ [43497]=true,
+ [43498]=true,
+ [43499]=true,
+ [43500]=true,
+ [43501]=true,
+ [43502]=true,
+ [43503]=true,
+ [43514]=true,
+ [43515]=true,
+ [43516]=true,
+ [43517]=true,
+ [43518]=true,
+ [43616]=true,
+ [43617]=true,
+ [43618]=true,
+ [43619]=true,
+ [43620]=true,
+ [43621]=true,
+ [43622]=true,
+ [43623]=true,
+ [43624]=true,
+ [43625]=true,
+ [43626]=true,
+ [43628]=true,
+ [43629]=true,
+ [43630]=true,
+ [43631]=true,
+ [43633]=true,
+ [43634]=true,
+ [43635]=true,
+ [43636]=true,
+ [43637]=true,
+ [43638]=true,
+ [43642]=true,
+ [43646]=true,
+ [43647]=true,
+ },
+ ["dependent_vowel"]={
+ [2362]=true,
+ [2363]=true,
+ [2366]=true,
+ [2367]=true,
+ [2368]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2382]=true,
+ [2383]=true,
+ [2389]=true,
+ [2390]=true,
+ [2391]=true,
+ [2402]=true,
+ [2403]=true,
+ [2494]=true,
+ [2495]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2503]=true,
+ [2504]=true,
+ [2507]=true,
+ [2508]=true,
+ [2622]=true,
+ [2623]=true,
+ [2624]=true,
+ [2625]=true,
+ [2626]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2750]=true,
+ [2751]=true,
+ [2752]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2878]=true,
+ [2879]=true,
+ [2880]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [2884]=true,
+ [2887]=true,
+ [2888]=true,
+ [2891]=true,
+ [2892]=true,
+ [2914]=true,
+ [2915]=true,
+ [3006]=true,
+ [3007]=true,
+ [3008]=true,
+ [3009]=true,
+ [3010]=true,
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3018]=true,
+ [3019]=true,
+ [3020]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3137]=true,
+ [3138]=true,
+ [3139]=true,
+ [3140]=true,
+ [3142]=true,
+ [3143]=true,
+ [3144]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3170]=true,
+ [3171]=true,
+ [3262]=true,
+ [3263]=true,
+ [3264]=true,
+ [3265]=true,
+ [3266]=true,
+ [3267]=true,
+ [3268]=true,
+ [3270]=true,
+ [3271]=true,
+ [3272]=true,
+ [3274]=true,
+ [3275]=true,
+ [3276]=true,
+ [3285]=true,
+ [3286]=true,
+ [3298]=true,
+ [3299]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3396]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ [3402]=true,
+ [3403]=true,
+ [3404]=true,
+ [3415]=true,
+ [3426]=true,
+ [3427]=true,
+ [4139]=true,
+ [4140]=true,
+ [4141]=true,
+ [4142]=true,
+ [4143]=true,
+ [4144]=true,
+ [4145]=true,
+ [4146]=true,
+ [4147]=true,
+ [4148]=true,
+ [4149]=true,
+ [4182]=true,
+ [4183]=true,
+ [4184]=true,
+ [4185]=true,
+ [4194]=true,
+ [4199]=true,
+ [4200]=true,
+ [4209]=true,
+ [4210]=true,
+ [4211]=true,
+ [4212]=true,
+ [4227]=true,
+ [4228]=true,
+ [4229]=true,
+ [4230]=true,
+ [4252]=true,
+ [4253]=true,
+ [43493]=true,
+ },
+ ["halant"]={
+ [2381]=true,
+ [2509]=true,
+ [2637]=true,
+ [2765]=true,
+ [2893]=true,
+ [3021]=true,
+ [3149]=true,
+ [3277]=true,
+ [3405]=true,
+ },
+ ["independent_vowel"]={
+ [2308]=true,
+ [2309]=true,
+ [2310]=true,
+ [2311]=true,
+ [2312]=true,
+ [2313]=true,
+ [2314]=true,
+ [2315]=true,
+ [2316]=true,
+ [2317]=true,
+ [2318]=true,
+ [2319]=true,
+ [2320]=true,
+ [2321]=true,
+ [2322]=true,
+ [2323]=true,
+ [2324]=true,
+ [2400]=true,
+ [2401]=true,
+ [2418]=true,
+ [2419]=true,
+ [2420]=true,
+ [2421]=true,
+ [2422]=true,
+ [2423]=true,
+ [2437]=true,
+ [2438]=true,
+ [2439]=true,
+ [2440]=true,
+ [2441]=true,
+ [2442]=true,
+ [2443]=true,
+ [2444]=true,
+ [2447]=true,
+ [2448]=true,
+ [2451]=true,
+ [2452]=true,
+ [2528]=true,
+ [2529]=true,
+ [2530]=true,
+ [2531]=true,
+ [2565]=true,
+ [2566]=true,
+ [2567]=true,
+ [2568]=true,
+ [2569]=true,
+ [2570]=true,
+ [2575]=true,
+ [2576]=true,
+ [2579]=true,
+ [2580]=true,
+ [2693]=true,
+ [2694]=true,
+ [2695]=true,
+ [2696]=true,
+ [2697]=true,
+ [2698]=true,
+ [2699]=true,
+ [2700]=true,
+ [2701]=true,
+ [2703]=true,
+ [2704]=true,
+ [2705]=true,
+ [2707]=true,
+ [2708]=true,
+ [2784]=true,
+ [2785]=true,
+ [2786]=true,
+ [2787]=true,
+ [2821]=true,
+ [2822]=true,
+ [2823]=true,
+ [2824]=true,
+ [2825]=true,
+ [2826]=true,
+ [2827]=true,
+ [2828]=true,
+ [2831]=true,
+ [2832]=true,
+ [2835]=true,
+ [2836]=true,
+ [2912]=true,
+ [2913]=true,
+ [2949]=true,
+ [2950]=true,
+ [2951]=true,
+ [2952]=true,
+ [2953]=true,
+ [2954]=true,
+ [2958]=true,
+ [2959]=true,
+ [2960]=true,
+ [2962]=true,
+ [2963]=true,
+ [2964]=true,
+ [3077]=true,
+ [3078]=true,
+ [3079]=true,
+ [3080]=true,
+ [3081]=true,
+ [3082]=true,
+ [3083]=true,
+ [3084]=true,
+ [3086]=true,
+ [3087]=true,
+ [3088]=true,
+ [3090]=true,
+ [3091]=true,
+ [3092]=true,
+ [3168]=true,
+ [3169]=true,
+ [3205]=true,
+ [3206]=true,
+ [3207]=true,
+ [3208]=true,
+ [3209]=true,
+ [3210]=true,
+ [3211]=true,
+ [3212]=true,
+ [3214]=true,
+ [3215]=true,
+ [3216]=true,
+ [3218]=true,
+ [3219]=true,
+ [3220]=true,
+ [3296]=true,
+ [3297]=true,
+ [3333]=true,
+ [3334]=true,
+ [3335]=true,
+ [3336]=true,
+ [3337]=true,
+ [3338]=true,
+ [3339]=true,
+ [3340]=true,
+ [3342]=true,
+ [3343]=true,
+ [3344]=true,
+ [3346]=true,
+ [3347]=true,
+ [3348]=true,
+ [3423]=true,
+ [3424]=true,
+ [3425]=true,
+ [4129]=true,
+ [4130]=true,
+ [4131]=true,
+ [4132]=true,
+ [4133]=true,
+ [4134]=true,
+ [4135]=true,
+ [4136]=true,
+ [4137]=true,
+ [4138]=true,
+ [4178]=true,
+ [4179]=true,
+ [4180]=true,
+ [4181]=true,
+ },
+ ["nukta"]={
+ [2364]=true,
+ [2492]=true,
+ [2620]=true,
+ [2748]=true,
+ [2876]=true,
+ [3260]=true,
+ },
+ ["post_mark"]={
+ [2307]=true,
+ [2363]=true,
+ [2366]=true,
+ [2368]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2383]=true,
+ [2494]=true,
+ [2496]=true,
+ [2622]=true,
+ [2624]=true,
+ [2750]=true,
+ [2752]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2878]=true,
+ [2880]=true,
+ [3006]=true,
+ [3007]=true,
+ [3137]=true,
+ [3138]=true,
+ [3139]=true,
+ [3140]=true,
+ [3262]=true,
+ [3265]=true,
+ [3266]=true,
+ [3267]=true,
+ [3268]=true,
+ [3276]=true,
+ [3285]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3396]=true,
+ [3415]=true,
+ [4139]=true,
+ [4140]=true,
+ [4152]=true,
+ [4155]=true,
+ [4182]=true,
+ [4183]=true,
+ [4194]=true,
+ [4195]=true,
+ [4196]=true,
+ [4199]=true,
+ [4200]=true,
+ [4201]=true,
+ [4202]=true,
+ [4203]=true,
+ [4204]=true,
+ [4205]=true,
+ [4227]=true,
+ [4231]=true,
+ [4232]=true,
+ [4233]=true,
+ [4234]=true,
+ [4235]=true,
+ [4236]=true,
+ [4239]=true,
+ [4250]=true,
+ [4251]=true,
+ [4252]=true,
+ [43643]=true,
+ [43645]=true,
+ },
+ ["pre_mark"]={
+ [2367]=true,
+ [2382]=true,
+ [2495]=true,
+ [2503]=true,
+ [2504]=true,
+ [2623]=true,
+ [2751]=true,
+ [2887]=true,
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ [4145]=true,
+ [4228]=true,
+ },
+ ["ra"]={
+ [2352]=true,
+ [2480]=true,
+ [2544]=true,
+ [2608]=true,
+ [2736]=true,
+ [2864]=true,
+ [2992]=true,
+ [3120]=true,
+ [3248]=true,
+ [3376]=true,
+ },
+ ["stress_tone_mark"]={
+ [2385]=true,
+ [2386]=true,
+ [2387]=true,
+ [2388]=true,
+ [4151]=true,
+ [4195]=true,
+ [4196]=true,
+ [4201]=true,
+ [4202]=true,
+ [4203]=true,
+ [4204]=true,
+ [4205]=true,
+ [4231]=true,
+ [4232]=true,
+ [4233]=true,
+ [4234]=true,
+ [4235]=true,
+ [4236]=true,
+ [4237]=true,
+ [4239]=true,
+ [4250]=true,
+ [4251]=true,
+ [43643]=true,
+ [43644]=true,
+ [43645]=true,
+ },
+ ["twopart_mark"]={
+ [2507]={ 2503,2494 },
+ [2508]={ 2503,2519 },
+ [2888]={ 2887,2902 },
+ [2891]={ 2887,2878 },
+ [2892]={ 2887,2903 },
+ [3018]={ 3014,3006 },
+ [3019]={ 3015,3006 },
+ [3020]={ 3014,3031 },
+ [3144]={ 3142,3158 },
+ [3264]={ 3263,3285 },
+ [3271]={ 3270,3285 },
+ [3272]={ 3270,3286 },
+ [3274]={ 3270,3266 },
+ [3275]={ 3274,3285 },
+ [3402]={ 3398,3390 },
+ [3403]={ 3399,3390 },
+ [3404]={ 3398,3415 },
+ },
+ ["vowel_modifier"]={
+ [2304]=true,
+ [2305]=true,
+ [2306]=true,
+ [2307]=true,
+ [2433]=true,
+ [3330]=true,
+ [3331]=true,
+ [4150]=true,
+ [4152]=true,
+ [4153]=true,
+ [4154]=true,
+ [43232]=true,
+ [43233]=true,
+ [43234]=true,
+ [43235]=true,
+ [43236]=true,
+ [43237]=true,
+ [43238]=true,
+ [43239]=true,
+ [43240]=true,
+ [43241]=true,
+ [43242]=true,
+ [43243]=true,
+ [43244]=true,
+ [43245]=true,
+ [43246]=true,
+ [43247]=true,
+ [43249]=true,
+ },
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “basics-chr”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ini” 4299a02110bbd7c0d27e131235c5319d] ---
+
+if not modules then modules={} end modules ['font-ini']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local allocate=utilities.storage.allocate
+local sortedhash=table.sortedhash
+fonts=fonts or {}
+local fonts=fonts
+local identifiers=allocate()
+fonts.hashes=fonts.hashes or { identifiers=identifiers }
+fonts.tables=fonts.tables or {}
+fonts.helpers=fonts.helpers or {}
+fonts.tracers=fonts.tracers or {}
+fonts.specifiers=fonts.specifiers or {}
+fonts.analyzers={}
+fonts.readers={}
+fonts.definers={ methods={} }
+fonts.loggers={ register=function() end }
+if context then
+ font.originaleach=font.each
+ function font.each()
+ return sortedhash(identifiers)
+ end
+ fontloader=nil
+end
+fonts.privateoffsets={
+ textbase=0xF0000,
+ textextrabase=0xFD000,
+ mathextrabase=0xFE000,
+ mathbase=0xFF000,
+ keepnames=false,
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ini”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-mis” bc9eb43c27f63ce9d0fff67e104fe1c6] ---
+
+if not modules then modules={} end modules ['luatex-font-mis']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+ os.exit()
+end
+local currentfont=font.current
+local hashes=fonts.hashes
+local identifiers=hashes.identifiers or {}
+local marks=hashes.marks or {}
+hashes.identifiers=identifiers
+hashes.marks=marks
+table.setmetatableindex(marks,function(t,k)
+ if k==true then
+ return marks[currentfont()]
+ else
+ local resources=identifiers[k].resources or {}
+ local marks=resources.marks or {}
+ t[k]=marks
+ return marks
+ end
+end)
+function font.each()
+ return table.sortedhash(fonts.hashes.identifiers)
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-mis”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-con” ca733211a0555d9a93b1e2f7ebc937d3] ---
+
+if not modules then modules={} end modules ['font-con']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,tostring,tonumber,rawget=next,tostring,tonumber,rawget
+local format,match,lower,gsub,find=string.format,string.match,string.lower,string.gsub,string.find
+local sort,insert,concat=table.sort,table.insert,table.concat
+local sortedkeys,sortedhash,serialize,fastcopy=table.sortedkeys,table.sortedhash,table.serialize,table.fastcopy
+local derivetable=table.derive
+local ioflush=io.flush
+local round=math.round
+local setmetatable,getmetatable,rawget,rawset=setmetatable,getmetatable,rawget,rawset
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local trace_scaling=false trackers.register("fonts.scaling",function(v) trace_scaling=v end)
+local report_defining=logs.reporter("fonts","defining")
+local fonts=fonts
+local constructors=fonts.constructors or {}
+fonts.constructors=constructors
+local handlers=fonts.handlers or {}
+fonts.handlers=handlers
+local allocate=utilities.storage.allocate
+local setmetatableindex=table.setmetatableindex
+constructors.dontembed=allocate()
+constructors.autocleanup=true
+constructors.namemode="fullpath"
+constructors.version=1.01
+constructors.cache=containers.define("fonts","constructors",constructors.version,false)
+constructors.privateoffset=fonts.privateoffsets.textbase or 0xF0000
+constructors.cacheintex=true
+constructors.addtounicode=true
+local designsizes=allocate()
+constructors.designsizes=designsizes
+local loadedfonts=allocate()
+constructors.loadedfonts=loadedfonts
+local factors={
+ pt=65536.0,
+ bp=65781.8,
+}
+function constructors.setfactor(f)
+ constructors.factor=factors[f or 'pt'] or factors.pt
+end
+constructors.setfactor()
+function constructors.scaled(scaledpoints,designsize)
+ if scaledpoints<0 then
+ local factor=constructors.factor
+ if designsize then
+ if designsize>factor then
+ return (- scaledpoints/1000)*designsize
+ else
+ return (- scaledpoints/1000)*designsize*factor
+ end
+ else
+ return (- scaledpoints/1000)*10*factor
+ end
+ else
+ return scaledpoints
+ end
+end
+function constructors.getprivate(tfmdata)
+ local properties=tfmdata.properties
+ local private=properties.private
+ properties.private=private+1
+ return private
+end
+function constructors.setmathparameter(tfmdata,name,value)
+ local m=tfmdata.mathparameters
+ local c=tfmdata.MathConstants
+ if m then
+ m[name]=value
+ end
+ if c and c~=m then
+ c[name]=value
+ end
+end
+function constructors.getmathparameter(tfmdata,name)
+ local p=tfmdata.mathparameters or tfmdata.MathConstants
+ if p then
+ return p[name]
+ end
+end
+function constructors.cleanuptable(tfmdata)
+ if constructors.autocleanup and tfmdata.properties.virtualized then
+ for k,v in next,tfmdata.characters do
+ if v.commands then v.commands=nil end
+ end
+ end
+end
+function constructors.calculatescale(tfmdata,scaledpoints)
+ local parameters=tfmdata.parameters
+ if scaledpoints<0 then
+ scaledpoints=(- scaledpoints/1000)*(tfmdata.designsize or parameters.designsize)
+ end
+ return scaledpoints,scaledpoints/(parameters.units or 1000)
+end
+local unscaled={
+ ScriptPercentScaleDown=true,
+ ScriptScriptPercentScaleDown=true,
+ RadicalDegreeBottomRaisePercent=true,
+ NoLimitSupFactor=true,
+ NoLimitSubFactor=true,
+}
+function constructors.assignmathparameters(target,original)
+ local mathparameters=original.mathparameters
+ if mathparameters and next(mathparameters) then
+ local targetparameters=target.parameters
+ local targetproperties=target.properties
+ local targetmathparameters={}
+ local factor=targetproperties.math_is_scaled and 1 or targetparameters.factor
+ for name,value in next,mathparameters do
+ if unscaled[name] then
+ targetmathparameters[name]=value
+ else
+ targetmathparameters[name]=value*factor
+ end
+ end
+ if not targetmathparameters.FractionDelimiterSize then
+ targetmathparameters.FractionDelimiterSize=1.01*targetparameters.size
+ end
+ if not mathparameters.FractionDelimiterDisplayStyleSize then
+ targetmathparameters.FractionDelimiterDisplayStyleSize=2.40*targetparameters.size
+ end
+ target.mathparameters=targetmathparameters
+ end
+end
+function constructors.beforecopyingcharacters(target,original)
+end
+function constructors.aftercopyingcharacters(target,original)
+end
+constructors.sharefonts=false
+constructors.nofsharedfonts=0
+local sharednames={}
+function constructors.trytosharefont(target,tfmdata)
+ if constructors.sharefonts then
+ local characters=target.characters
+ local n=1
+ local t={ target.psname }
+ local u=sortedkeys(characters)
+ for i=1,#u do
+ local k=u[i]
+ n=n+1;t[n]=k
+ n=n+1;t[n]=characters[k].index or k
+ end
+ local h=md5.HEX(concat(t," "))
+ local s=sharednames[h]
+ if s then
+ if trace_defining then
+ report_defining("font %a uses backend resources of font %a",target.fullname,s)
+ end
+ target.fullname=s
+ constructors.nofsharedfonts=constructors.nofsharedfonts+1
+ target.properties.sharedwith=s
+ else
+ sharednames[h]=target.fullname
+ end
+ end
+end
+local synonyms={
+ exheight="x_height",
+ xheight="x_height",
+ ex="x_height",
+ emwidth="quad",
+ em="quad",
+ spacestretch="space_stretch",
+ stretch="space_stretch",
+ spaceshrink="space_shrink",
+ shrink="space_shrink",
+ extraspace="extra_space",
+ xspace="extra_space",
+ slantperpoint="slant",
+}
+function constructors.enhanceparameters(parameters)
+ local mt=getmetatable(parameters)
+ local getter=function(t,k)
+ if not k then
+ return nil
+ end
+ local s=synonyms[k]
+ if s then
+ return rawget(t,s) or (mt and mt[s]) or nil
+ end
+ if k=="spacing" then
+ return {
+ width=t.space,
+ stretch=t.space_stretch,
+ shrink=t.space_shrink,
+ extra=t.extra_space,
+ }
+ end
+ return mt and mt[k] or nil
+ end
+ local setter=function(t,k,v)
+ if not k then
+ return 0
+ end
+ local s=synonyms[k]
+ if s then
+ rawset(t,s,v)
+ elseif k=="spacing" then
+ if type(v)=="table" then
+ rawset(t,"space",v.width or 0)
+ rawset(t,"space_stretch",v.stretch or 0)
+ rawset(t,"space_shrink",v.shrink or 0)
+ rawset(t,"extra_space",v.extra or 0)
+ end
+ else
+ rawset(t,k,v)
+ end
+ end
+ setmetatable(parameters,{
+ __index=getter,
+ __newindex=setter,
+ })
+end
+local function mathkerns(v,vdelta)
+ local k={}
+ for i=1,#v do
+ local entry=v[i]
+ local height=entry.height
+ local kern=entry.kern
+ k[i]={
+ height=height and vdelta*height or 0,
+ kern=kern and vdelta*kern or 0,
+ }
+ end
+ return k
+end
+local psfake=0
+local function fixedpsname(psname,fallback)
+ local usedname=psname
+ if psname and psname~="" then
+ if find(psname," ",1,true) then
+ usedname=gsub(psname,"[%s]+","-")
+ else
+ end
+ elseif not fallback or fallback=="" then
+ psfake=psfake+1
+ psname="fakename-"..psfake
+ else
+ psname=fallback
+ usedname=gsub(psname,"[^a-zA-Z0-9]+","-")
+ end
+ return usedname,psname~=usedname
+end
+function constructors.scale(tfmdata,specification)
+ local target={}
+ if tonumber(specification) then
+ specification={ size=specification }
+ end
+ target.specification=specification
+ local scaledpoints=specification.size
+ local relativeid=specification.relativeid
+ local properties=tfmdata.properties or {}
+ local goodies=tfmdata.goodies or {}
+ local resources=tfmdata.resources or {}
+ local descriptions=tfmdata.descriptions or {}
+ local characters=tfmdata.characters or {}
+ local changed=tfmdata.changed or {}
+ local shared=tfmdata.shared or {}
+ local parameters=tfmdata.parameters or {}
+ local mathparameters=tfmdata.mathparameters or {}
+ local targetcharacters={}
+ local targetdescriptions=derivetable(descriptions)
+ local targetparameters=derivetable(parameters)
+ local targetproperties=derivetable(properties)
+ local targetgoodies=goodies
+ target.characters=targetcharacters
+ target.descriptions=targetdescriptions
+ target.parameters=targetparameters
+ target.properties=targetproperties
+ target.goodies=targetgoodies
+ target.shared=shared
+ target.resources=resources
+ target.unscaled=tfmdata
+ local mathsize=tonumber(specification.mathsize) or 0
+ local textsize=tonumber(specification.textsize) or scaledpoints
+ local forcedsize=tonumber(parameters.mathsize ) or 0
+ local extrafactor=tonumber(specification.factor ) or 1
+ if (mathsize==2 or forcedsize==2) and parameters.scriptpercentage then
+ scaledpoints=parameters.scriptpercentage*textsize/100
+ elseif (mathsize==3 or forcedsize==3) and parameters.scriptscriptpercentage then
+ scaledpoints=parameters.scriptscriptpercentage*textsize/100
+ elseif forcedsize>1000 then
+ scaledpoints=forcedsize
+ else
+ end
+ targetparameters.mathsize=mathsize
+ targetparameters.textsize=textsize
+ targetparameters.forcedsize=forcedsize
+ targetparameters.extrafactor=extrafactor
+ local addtounicode=constructors.addtounicode
+ local tounicode=fonts.mappings.tounicode
+ local unknowncode=tounicode(0xFFFD)
+ local defaultwidth=resources.defaultwidth or 0
+ local defaultheight=resources.defaultheight or 0
+ local defaultdepth=resources.defaultdepth or 0
+ local units=parameters.units or 1000
+ targetproperties.language=properties.language or "dflt"
+ targetproperties.script=properties.script or "dflt"
+ targetproperties.mode=properties.mode or "base"
+ local askedscaledpoints=scaledpoints
+ local scaledpoints,delta=constructors.calculatescale(tfmdata,scaledpoints,nil,specification)
+ local hdelta=delta
+ local vdelta=delta
+ target.designsize=parameters.designsize
+ target.units=units
+ target.units_per_em=units
+ local direction=properties.direction or tfmdata.direction or 0
+ target.direction=direction
+ properties.direction=direction
+ target.size=scaledpoints
+ target.encodingbytes=properties.encodingbytes or 1
+ target.embedding=properties.embedding or "subset"
+ target.tounicode=1
+ target.cidinfo=properties.cidinfo
+ target.format=properties.format
+ target.cache=constructors.cacheintex and "yes" or "renew"
+ local fontname=properties.fontname or tfmdata.fontname
+ local fullname=properties.fullname or tfmdata.fullname
+ local filename=properties.filename or tfmdata.filename
+ local psname=properties.psname or tfmdata.psname
+ local name=properties.name or tfmdata.name
+ local psname,psfixed=fixedpsname(psname,fontname or fullname or file.nameonly(filename))
+ target.fontname=fontname
+ target.fullname=fullname
+ target.filename=filename
+ target.psname=psname
+ target.name=name
+ properties.fontname=fontname
+ properties.fullname=fullname
+ properties.filename=filename
+ properties.psname=psname
+ properties.name=name
+ local expansion=parameters.expansion
+ if expansion then
+ target.stretch=expansion.stretch
+ target.shrink=expansion.shrink
+ target.step=expansion.step
+ end
+ local slantfactor=parameters.slantfactor or 0
+ if slantfactor~=0 then
+ target.slant=slantfactor*1000
+ else
+ target.slant=0
+ end
+ local extendfactor=parameters.extendfactor or 0
+ if extendfactor~=0 and extendfactor~=1 then
+ hdelta=hdelta*extendfactor
+ target.extend=extendfactor*1000
+ else
+ target.extend=1000
+ end
+ local squeezefactor=parameters.squeezefactor or 0
+ if squeezefactor~=0 and squeezefactor~=1 then
+ vdelta=vdelta*squeezefactor
+ target.squeeze=squeezefactor*1000
+ else
+ target.squeeze=1000
+ end
+ local mode=parameters.mode or 0
+ if mode~=0 then
+ target.mode=mode
+ end
+ local width=parameters.width or 0
+ if width~=0 then
+ target.width=width*delta*1000/655360
+ end
+ targetparameters.factor=delta
+ targetparameters.hfactor=hdelta
+ targetparameters.vfactor=vdelta
+ targetparameters.size=scaledpoints
+ targetparameters.units=units
+ targetparameters.scaledpoints=askedscaledpoints
+ targetparameters.mode=mode
+ targetparameters.width=width
+ local isvirtual=properties.virtualized or tfmdata.type=="virtual"
+ local hasquality=parameters.expansion or parameters.protrusion
+ local hasitalics=properties.hasitalics
+ local autoitalicamount=properties.autoitalicamount
+ local stackmath=not properties.nostackmath
+ local haskerns=properties.haskerns or properties.mode=="base"
+ local hasligatures=properties.hasligatures or properties.mode=="base"
+ local realdimensions=properties.realdimensions
+ local writingmode=properties.writingmode or "horizontal"
+ local identity=properties.identity or "horizontal"
+ local vfonts=target.fonts
+ if vfonts and #vfonts>0 then
+ target.fonts=fastcopy(vfonts)
+ elseif isvirtual then
+ target.fonts={ { id=0 } }
+ end
+ if changed and not next(changed) then
+ changed=false
+ end
+ target.type=isvirtual and "virtual" or "real"
+ target.writingmode=writingmode=="vertical" and "vertical" or "horizontal"
+ target.identity=identity=="vertical" and "vertical" or "horizontal"
+ target.postprocessors=tfmdata.postprocessors
+ local targetslant=(parameters.slant or parameters[1] or 0)*factors.pt
+ local targetspace=(parameters.space or parameters[2] or 0)*hdelta
+ local targetspace_stretch=(parameters.space_stretch or parameters[3] or 0)*hdelta
+ local targetspace_shrink=(parameters.space_shrink or parameters[4] or 0)*hdelta
+ local targetx_height=(parameters.x_height or parameters[5] or 0)*vdelta
+ local targetquad=(parameters.quad or parameters[6] or 0)*hdelta
+ local targetextra_space=(parameters.extra_space or parameters[7] or 0)*hdelta
+ targetparameters.slant=targetslant
+ targetparameters.space=targetspace
+ targetparameters.space_stretch=targetspace_stretch
+ targetparameters.space_shrink=targetspace_shrink
+ targetparameters.x_height=targetx_height
+ targetparameters.quad=targetquad
+ targetparameters.extra_space=targetextra_space
+ local ascender=parameters.ascender
+ if ascender then
+ targetparameters.ascender=delta*ascender
+ end
+ local descender=parameters.descender
+ if descender then
+ targetparameters.descender=delta*descender
+ end
+ constructors.enhanceparameters(targetparameters)
+ local protrusionfactor=(targetquad~=0 and 1000/targetquad) or 0
+ local scaledwidth=defaultwidth*hdelta
+ local scaledheight=defaultheight*vdelta
+ local scaleddepth=defaultdepth*vdelta
+ local hasmath=(properties.hasmath or next(mathparameters)) and true
+ if hasmath then
+ constructors.assignmathparameters(target,tfmdata)
+ properties.hasmath=true
+ target.nomath=false
+ target.MathConstants=target.mathparameters
+ else
+ properties.hasmath=false
+ target.nomath=true
+ target.mathparameters=nil
+ end
+ if hasmath then
+ local mathitalics=properties.mathitalics
+ if mathitalics==false then
+ if trace_defining then
+ report_defining("%s italics %s for font %a, fullname %a, filename %a","math",hasitalics and "ignored" or "disabled",name,fullname,filename)
+ end
+ hasitalics=false
+ autoitalicamount=false
+ end
+ else
+ local textitalics=properties.textitalics
+ if textitalics==false then
+ if trace_defining then
+ report_defining("%s italics %s for font %a, fullname %a, filename %a","text",hasitalics and "ignored" or "disabled",name,fullname,filename)
+ end
+ hasitalics=false
+ autoitalicamount=false
+ end
+ end
+ if trace_defining then
+ report_defining("defining tfm, name %a, fullname %a, filename %a, %spsname %a, hscale %a, vscale %a, math %a, italics %a",
+ name,fullname,filename,psfixed and "(fixed) " or "",psname,hdelta,vdelta,
+ hasmath and "enabled" or "disabled",hasitalics and "enabled" or "disabled")
+ end
+ constructors.beforecopyingcharacters(target,tfmdata)
+ local sharedkerns={}
+ for unicode,character in next,characters do
+ local chr,description,index
+ if changed then
+ local c=changed[unicode]
+ if c and c~=unicode then
+ if c then
+ description=descriptions[c] or descriptions[unicode] or character
+ character=characters[c] or character
+ index=description.index or c
+ else
+ description=descriptions[unicode] or character
+ index=description.index or unicode
+ end
+ else
+ description=descriptions[unicode] or character
+ index=description.index or unicode
+ end
+ else
+ description=descriptions[unicode] or character
+ index=description.index or unicode
+ end
+ local width=description.width
+ local height=description.height
+ local depth=description.depth
+ local isunicode=description.unicode
+ if realdimensions then
+ if not height or height==0 then
+ local bb=description.boundingbox
+ local ht=bb[4]
+ if ht~=0 then
+ height=ht
+ end
+ if not depth or depth==0 then
+ local dp=-bb[2]
+ if dp~=0 then
+ depth=dp
+ end
+ end
+ elseif not depth or depth==0 then
+ local dp=-description.boundingbox[2]
+ if dp~=0 then
+ depth=dp
+ end
+ end
+ end
+ if width then width=hdelta*width else width=scaledwidth end
+ if height then height=vdelta*height else height=scaledheight end
+ if depth and depth~=0 then
+ depth=delta*depth
+ if isunicode then
+ chr={
+ index=index,
+ height=height,
+ depth=depth,
+ width=width,
+ unicode=isunicode,
+ }
+ else
+ chr={
+ index=index,
+ height=height,
+ depth=depth,
+ width=width,
+ }
+ end
+ else
+ if isunicode then
+ chr={
+ index=index,
+ height=height,
+ width=width,
+ unicode=isunicode,
+ }
+ else
+ chr={
+ index=index,
+ height=height,
+ width=width,
+ }
+ end
+ end
+ if addtounicode then
+ chr.tounicode=isunicode and tounicode(isunicode) or unknowncode
+ end
+ if hasquality then
+ local ve=character.expansion_factor
+ if ve then
+ chr.expansion_factor=ve*1000
+ end
+ local vl=character.left_protruding
+ if vl then
+ chr.left_protruding=protrusionfactor*width*vl
+ end
+ local vr=character.right_protruding
+ if vr then
+ chr.right_protruding=protrusionfactor*width*vr
+ end
+ end
+ if hasmath then
+ local vn=character.next
+ if vn then
+ chr.next=vn
+ else
+ local vv=character.vert_variants
+ if vv then
+ local t={}
+ for i=1,#vv do
+ local vvi=vv[i]
+ local s=vvi["start"] or 0
+ local e=vvi["end"] or 0
+ local a=vvi["advance"] or 0
+ t[i]={
+ ["start"]=s==0 and 0 or s*vdelta,
+ ["end"]=e==0 and 0 or e*vdelta,
+ ["advance"]=a==0 and 0 or a*vdelta,
+ ["extender"]=vvi["extender"],
+ ["glyph"]=vvi["glyph"],
+ }
+ end
+ chr.vert_variants=t
+ else
+ local hv=character.horiz_variants
+ if hv then
+ local t={}
+ for i=1,#hv do
+ local hvi=hv[i]
+ local s=hvi["start"] or 0
+ local e=hvi["end"] or 0
+ local a=hvi["advance"] or 0
+ t[i]={
+ ["start"]=s==0 and 0 or s*hdelta,
+ ["end"]=e==0 and 0 or e*hdelta,
+ ["advance"]=a==0 and 0 or a*hdelta,
+ ["extender"]=hvi["extender"],
+ ["glyph"]=hvi["glyph"],
+ }
+ end
+ chr.horiz_variants=t
+ end
+ end
+ end
+ local vi=character.vert_italic
+ if vi and vi~=0 then
+ chr.vert_italic=vi*hdelta
+ end
+ local va=character.accent
+ if va then
+ chr.top_accent=vdelta*va
+ end
+ if stackmath then
+ local mk=character.mathkerns
+ if mk then
+ local tr=mk.topright
+ local tl=mk.topleft
+ local br=mk.bottomright
+ local bl=mk.bottomleft
+ chr.mathkern={
+ top_right=tr and mathkerns(tr,vdelta) or nil,
+ top_left=tl and mathkerns(tl,vdelta) or nil,
+ bottom_right=br and mathkerns(br,vdelta) or nil,
+ bottom_left=bl and mathkerns(bl,vdelta) or nil,
+ }
+ end
+ end
+ if hasitalics then
+ local vi=character.italic
+ if vi and vi~=0 then
+ chr.italic=vi*hdelta
+ end
+ end
+ elseif autoitalicamount then
+ local vi=description.italic
+ if not vi then
+ local bb=description.boundingbox
+ if bb then
+ local vi=bb[3]-description.width+autoitalicamount
+ if vi>0 then
+ chr.italic=vi*hdelta
+ end
+ else
+ end
+ elseif vi~=0 then
+ chr.italic=vi*hdelta
+ end
+ elseif hasitalics then
+ local vi=character.italic
+ if vi and vi~=0 then
+ chr.italic=vi*hdelta
+ end
+ end
+ if haskerns then
+ local vk=character.kerns
+ if vk then
+ local s=sharedkerns[vk]
+ if not s then
+ s={}
+ for k,v in next,vk do s[k]=v*hdelta end
+ sharedkerns[vk]=s
+ end
+ chr.kerns=s
+ end
+ end
+ if hasligatures then
+ local vl=character.ligatures
+ if vl then
+ if true then
+ chr.ligatures=vl
+ else
+ local tt={}
+ for i,l in next,vl do
+ tt[i]=l
+ end
+ chr.ligatures=tt
+ end
+ end
+ end
+ if isvirtual then
+ local vc=character.commands
+ if vc then
+ local ok=false
+ for i=1,#vc do
+ local key=vc[i][1]
+ if key=="right" or key=="down" or key=="rule" then
+ ok=true
+ break
+ end
+ end
+ if ok then
+ local tt={}
+ for i=1,#vc do
+ local ivc=vc[i]
+ local key=ivc[1]
+ if key=="right" then
+ tt[i]={ key,ivc[2]*hdelta }
+ elseif key=="down" then
+ tt[i]={ key,ivc[2]*vdelta }
+ elseif key=="rule" then
+ tt[i]={ key,ivc[2]*vdelta,ivc[3]*hdelta }
+ else
+ tt[i]=ivc
+ end
+ end
+ chr.commands=tt
+ else
+ chr.commands=vc
+ end
+ end
+ end
+ targetcharacters[unicode]=chr
+ end
+ properties.setitalics=hasitalics
+ constructors.aftercopyingcharacters(target,tfmdata)
+ constructors.trytosharefont(target,tfmdata)
+ local vfonts=target.fonts
+ if isvirtual or target.type=="virtual" or properties.virtualized then
+ properties.virtualized=true
+ target.type="virtual"
+ if not vfonts or #vfonts==0 then
+ target.fonts={ { id=0 } }
+ end
+ elseif vfonts then
+ properties.virtualized=true
+ target.type="virtual"
+ if #vfonts==0 then
+ target.fonts={ { id=0 } }
+ end
+ end
+ return target
+end
+function constructors.finalize(tfmdata)
+ if tfmdata.properties and tfmdata.properties.finalized then
+ return
+ end
+ if not tfmdata.characters then
+ return nil
+ end
+ if not tfmdata.goodies then
+ tfmdata.goodies={}
+ end
+ local parameters=tfmdata.parameters
+ if not parameters then
+ return nil
+ end
+ if not parameters.expansion then
+ parameters.expansion={
+ stretch=tfmdata.stretch or 0,
+ shrink=tfmdata.shrink or 0,
+ step=tfmdata.step or 0,
+ }
+ end
+ if not parameters.size then
+ parameters.size=tfmdata.size
+ end
+ if not parameters.mode then
+ parameters.mode=0
+ end
+ if not parameters.width then
+ parameters.width=0
+ end
+ if not parameters.slantfactor then
+ parameters.slantfactor=(tfmdata.slant or 0)/1000
+ end
+ if not parameters.extendfactor then
+ parameters.extendfactor=(tfmdata.extend or 1000)/1000
+ end
+ if not parameters.squeezefactor then
+ parameters.squeezefactor=(tfmdata.squeeze or 1000)/1000
+ end
+ local designsize=parameters.designsize
+ if designsize then
+ parameters.minsize=tfmdata.minsize or designsize
+ parameters.maxsize=tfmdata.maxsize or designsize
+ else
+ designsize=factors.pt*10
+ parameters.designsize=designsize
+ parameters.minsize=designsize
+ parameters.maxsize=designsize
+ end
+ parameters.minsize=tfmdata.minsize or parameters.designsize
+ parameters.maxsize=tfmdata.maxsize or parameters.designsize
+ if not parameters.units then
+ parameters.units=tfmdata.units or tfmdata.units_per_em or 1000
+ end
+ if not tfmdata.descriptions then
+ local descriptions={}
+ setmetatableindex(descriptions,function(t,k) local v={} t[k]=v return v end)
+ tfmdata.descriptions=descriptions
+ end
+ local properties=tfmdata.properties
+ if not properties then
+ properties={}
+ tfmdata.properties=properties
+ end
+ if not properties.virtualized then
+ properties.virtualized=tfmdata.type=="virtual"
+ end
+ properties.fontname=properties.fontname or tfmdata.fontname
+ properties.filename=properties.filename or tfmdata.filename
+ properties.fullname=properties.fullname or tfmdata.fullname
+ properties.name=properties.name or tfmdata.name
+ properties.psname=properties.psname or tfmdata.psname
+ properties.encodingbytes=tfmdata.encodingbytes or 1
+ properties.embedding=tfmdata.embedding or "subset"
+ properties.tounicode=tfmdata.tounicode or 1
+ properties.cidinfo=tfmdata.cidinfo or nil
+ properties.format=tfmdata.format or "type1"
+ properties.direction=tfmdata.direction or 0
+ properties.writingmode=tfmdata.writingmode or "horizontal"
+ properties.identity=tfmdata.identity or "horizontal"
+ properties.usedbitmap=tfmdata.usedbitmap
+ if not tfmdata.resources then
+ tfmdata.resources={}
+ end
+ if not tfmdata.shared then
+ tfmdata.shared={}
+ end
+ if not properties.hasmath then
+ properties.hasmath=not tfmdata.nomath
+ end
+ tfmdata.MathConstants=nil
+ tfmdata.postprocessors=nil
+ tfmdata.fontname=nil
+ tfmdata.filename=nil
+ tfmdata.fullname=nil
+ tfmdata.name=nil
+ tfmdata.psname=nil
+ tfmdata.encodingbytes=nil
+ tfmdata.embedding=nil
+ tfmdata.tounicode=nil
+ tfmdata.cidinfo=nil
+ tfmdata.format=nil
+ tfmdata.direction=nil
+ tfmdata.type=nil
+ tfmdata.nomath=nil
+ tfmdata.designsize=nil
+ tfmdata.size=nil
+ tfmdata.stretch=nil
+ tfmdata.shrink=nil
+ tfmdata.step=nil
+ tfmdata.slant=nil
+ tfmdata.extend=nil
+ tfmdata.squeeze=nil
+ tfmdata.mode=nil
+ tfmdata.width=nil
+ tfmdata.units=nil
+ tfmdata.units_per_em=nil
+ tfmdata.cache=nil
+ properties.finalized=true
+ return tfmdata
+end
+local hashmethods={}
+constructors.hashmethods=hashmethods
+function constructors.hashfeatures(specification)
+ local features=specification.features
+ if features then
+ local t,n={},0
+ for category,list in sortedhash(features) do
+ if next(list) then
+ local hasher=hashmethods[category]
+ if hasher then
+ local hash=hasher(list)
+ if hash then
+ n=n+1
+ t[n]=category..":"..hash
+ end
+ end
+ end
+ end
+ if n>0 then
+ return concat(t," & ")
+ end
+ end
+ return "unknown"
+end
+hashmethods.normal=function(list)
+ local s={}
+ local n=0
+ for k,v in next,list do
+ if not k then
+ elseif k=="number" or k=="features" then
+ else
+ n=n+1
+ if type(v)=="table" then
+ local t={}
+ local m=0
+ for k,v in next,v do
+ m=m+1
+ t[m]=k..'='..tostring(v)
+ end
+ s[n]=k..'={'..concat(t,",").."}"
+ else
+ s[n]=k..'='..tostring(v)
+ end
+ end
+ end
+ if n>0 then
+ sort(s)
+ return concat(s,"+")
+ end
+end
+function constructors.hashinstance(specification,force)
+ local hash=specification.hash
+ local size=specification.size
+ local fallbacks=specification.fallbacks
+ if force or not hash then
+ hash=constructors.hashfeatures(specification)
+ specification.hash=hash
+ end
+ if size<1000 and designsizes[hash] then
+ size=round(constructors.scaled(size,designsizes[hash]))
+ else
+ size=round(size)
+ end
+ specification.size=size
+ if fallbacks then
+ return hash..' @ '..size..' @ '..fallbacks
+ else
+ return hash..' @ '..size
+ end
+end
+function constructors.setname(tfmdata,specification)
+ if constructors.namemode=="specification" then
+ local specname=specification.specification
+ if specname then
+ tfmdata.properties.name=specname
+ if trace_defining then
+ report_otf("overloaded fontname %a",specname)
+ end
+ end
+ end
+end
+function constructors.checkedfilename(data)
+ local foundfilename=data.foundfilename
+ if not foundfilename then
+ local askedfilename=data.filename or ""
+ if askedfilename~="" then
+ askedfilename=resolvers.resolve(askedfilename)
+ foundfilename=resolvers.findbinfile(askedfilename,"") or ""
+ if foundfilename=="" then
+ report_defining("source file %a is not found",askedfilename)
+ foundfilename=resolvers.findbinfile(file.basename(askedfilename),"") or ""
+ if foundfilename~="" then
+ report_defining("using source file %a due to cache mismatch",foundfilename)
+ end
+ end
+ end
+ data.foundfilename=foundfilename
+ end
+ return foundfilename
+end
+local formats=allocate()
+fonts.formats=formats
+setmetatableindex(formats,function(t,k)
+ local l=lower(k)
+ if rawget(t,k) then
+ t[k]=l
+ return l
+ end
+ return rawget(t,file.suffix(l))
+end)
+do
+ local function setindeed(mode,source,target,group,name,position)
+ local action=source[mode]
+ if not action then
+ return
+ end
+ local t=target[mode]
+ if not t then
+ report_defining("fatal error in setting feature %a, group %a, mode %a",name,group,mode)
+ os.exit()
+ elseif position then
+ insert(t,position,{ name=name,action=action })
+ else
+ for i=1,#t do
+ local ti=t[i]
+ if ti.name==name then
+ ti.action=action
+ return
+ end
+ end
+ insert(t,{ name=name,action=action })
+ end
+ end
+ local function set(group,name,target,source)
+ target=target[group]
+ if not target then
+ report_defining("fatal target error in setting feature %a, group %a",name,group)
+ os.exit()
+ end
+ local source=source[group]
+ if not source then
+ report_defining("fatal source error in setting feature %a, group %a",name,group)
+ os.exit()
+ end
+ local position=source.position
+ setindeed("node",source,target,group,name,position)
+ setindeed("base",source,target,group,name,position)
+ setindeed("plug",source,target,group,name,position)
+ end
+ local function register(where,specification)
+ local name=specification.name
+ if name and name~="" then
+ local default=specification.default
+ local description=specification.description
+ local initializers=specification.initializers
+ local processors=specification.processors
+ local manipulators=specification.manipulators
+ local modechecker=specification.modechecker
+ if default then
+ where.defaults[name]=default
+ end
+ if description and description~="" then
+ where.descriptions[name]=description
+ end
+ if initializers then
+ set('initializers',name,where,specification)
+ end
+ if processors then
+ set('processors',name,where,specification)
+ end
+ if manipulators then
+ set('manipulators',name,where,specification)
+ end
+ if modechecker then
+ where.modechecker=modechecker
+ end
+ end
+ end
+ constructors.registerfeature=register
+ function constructors.getfeatureaction(what,where,mode,name)
+ what=handlers[what].features
+ if what then
+ where=what[where]
+ if where then
+ mode=where[mode]
+ if mode then
+ for i=1,#mode do
+ local m=mode[i]
+ if m.name==name then
+ return m.action
+ end
+ end
+ end
+ end
+ end
+ end
+ local newfeatures={}
+ constructors.newfeatures=newfeatures
+ constructors.features=newfeatures
+ local function setnewfeatures(what)
+ local handler=handlers[what]
+ local features=handler.features
+ if not features then
+ local tables=handler.tables
+ local statistics=handler.statistics
+ features=allocate {
+ defaults={},
+ descriptions=tables and tables.features or {},
+ used=statistics and statistics.usedfeatures or {},
+ initializers={ base={},node={},plug={} },
+ processors={ base={},node={},plug={} },
+ manipulators={ base={},node={},plug={} },
+ }
+ features.register=function(specification) return register(features,specification) end
+ handler.features=features
+ end
+ return features
+ end
+ setmetatable(newfeatures,{
+ __call=function(t,k) local v=t[k] return v end,
+ __index=function(t,k) local v=setnewfeatures(k) t[k]=v return v end,
+ })
+end
+do
+ local newhandler={}
+ constructors.handlers=newhandler
+ constructors.newhandler=newhandler
+ local function setnewhandler(what)
+ local handler=handlers[what]
+ if not handler then
+ handler={}
+ handlers[what]=handler
+ end
+ return handler
+ end
+ setmetatable(newhandler,{
+ __call=function(t,k) local v=t[k] return v end,
+ __index=function(t,k) local v=setnewhandler(k) t[k]=v return v end,
+ })
+end
+do
+ local newenhancer={}
+ constructors.enhancers=newenhancer
+ constructors.newenhancer=newenhancer
+ local function setnewenhancer(format)
+ local handler=handlers[format]
+ local enhancers=handler.enhancers
+ if not enhancers then
+ local actions=allocate()
+ local before=allocate()
+ local after=allocate()
+ local order=allocate()
+ local known={}
+ local nofsteps=0
+ local patches={ before=before,after=after }
+ local trace=false
+ local report=logs.reporter("fonts",format.." enhancing")
+ trackers.register(format..".loading",function(v) trace=v end)
+ local function enhance(name,data,filename,raw)
+ local enhancer=actions[name]
+ if enhancer then
+ if trace then
+ report("apply enhancement %a to file %a",name,filename)
+ ioflush()
+ end
+ enhancer(data,filename,raw)
+ else
+ end
+ end
+ local function apply(data,filename,raw)
+ local basename=file.basename(lower(filename))
+ if trace then
+ report("%s enhancing file %a","start",filename)
+ end
+ ioflush()
+ for e=1,nofsteps do
+ local enhancer=order[e]
+ local b=before[enhancer]
+ if b then
+ for pattern,action in next,b do
+ if find(basename,pattern) then
+ action(data,filename,raw)
+ end
+ end
+ end
+ enhance(enhancer,data,filename,raw)
+ local a=after[enhancer]
+ if a then
+ for pattern,action in next,a do
+ if find(basename,pattern) then
+ action(data,filename,raw)
+ end
+ end
+ end
+ ioflush()
+ end
+ if trace then
+ report("%s enhancing file %a","stop",filename)
+ end
+ ioflush()
+ end
+ local function register(what,action)
+ if action then
+ if actions[what] then
+ else
+ nofsteps=nofsteps+1
+ order[nofsteps]=what
+ known[what]=nofsteps
+ end
+ actions[what]=action
+ else
+ report("bad enhancer %a",what)
+ end
+ end
+ local function patch(what,where,pattern,action)
+ local pw=patches[what]
+ if pw then
+ local ww=pw[where]
+ if ww then
+ ww[pattern]=action
+ else
+ pw[where]={ [pattern]=action }
+ if not known[where] then
+ nofsteps=nofsteps+1
+ order[nofsteps]=where
+ known[where]=nofsteps
+ end
+ end
+ end
+ end
+ enhancers={
+ register=register,
+ apply=apply,
+ patch=patch,
+ report=report,
+ patches={
+ register=patch,
+ report=report,
+ },
+ }
+ handler.enhancers=enhancers
+ end
+ return enhancers
+ end
+ setmetatable(newenhancer,{
+ __call=function(t,k) local v=t[k] return v end,
+ __index=function(t,k) local v=setnewenhancer(k) t[k]=v return v end,
+ })
+end
+function constructors.checkedfeatures(what,features)
+ local defaults=handlers[what].features.defaults
+ if features and next(features) then
+ features=fastcopy(features)
+ for key,value in next,defaults do
+ if features[key]==nil then
+ features[key]=value
+ end
+ end
+ return features
+ else
+ return fastcopy(defaults)
+ end
+end
+function constructors.initializefeatures(what,tfmdata,features,trace,report)
+ if features and next(features) then
+ local properties=tfmdata.properties or {}
+ local whathandler=handlers[what]
+ local whatfeatures=whathandler.features
+ local whatmodechecker=whatfeatures.modechecker
+ local mode=properties.mode or (whatmodechecker and whatmodechecker(tfmdata,features,features.mode)) or features.mode or "base"
+ properties.mode=mode
+ features.mode=mode
+ local done={}
+ while true do
+ local redo=false
+ local initializers=whatfeatures.initializers[mode]
+ if initializers then
+ for i=1,#initializers do
+ local step=initializers[i]
+ local feature=step.name
+ local value=features[feature]
+ if not value then
+ elseif done[feature] then
+ else
+ local action=step.action
+ if trace then
+ report("initializing feature %a to %a for mode %a for font %a",feature,
+ value,mode,tfmdata.properties.fullname)
+ end
+ action(tfmdata,value,features)
+ if mode~=properties.mode or mode~=features.mode then
+ if whatmodechecker then
+ properties.mode=whatmodechecker(tfmdata,features,properties.mode)
+ features.mode=properties.mode
+ end
+ if mode~=properties.mode then
+ mode=properties.mode
+ redo=true
+ end
+ end
+ done[feature]=true
+ end
+ if redo then
+ break
+ end
+ end
+ if not redo then
+ break
+ end
+ else
+ break
+ end
+ end
+ properties.mode=mode
+ return true
+ else
+ return false
+ end
+end
+function constructors.collectprocessors(what,tfmdata,features,trace,report)
+ local processes={}
+ local nofprocesses=0
+ if features and next(features) then
+ local properties=tfmdata.properties
+ local whathandler=handlers[what]
+ local whatfeatures=whathandler.features
+ local whatprocessors=whatfeatures.processors
+ local mode=properties.mode
+ local processors=whatprocessors[mode]
+ if processors then
+ for i=1,#processors do
+ local step=processors[i]
+ local feature=step.name
+ if features[feature] then
+ local action=step.action
+ if trace then
+ report("installing feature processor %a for mode %a for font %a",feature,mode,tfmdata.properties.fullname)
+ end
+ if action then
+ nofprocesses=nofprocesses+1
+ processes[nofprocesses]=action
+ end
+ end
+ end
+ elseif trace then
+ report("no feature processors for mode %a for font %a",mode,properties.fullname)
+ end
+ end
+ return processes
+end
+function constructors.applymanipulators(what,tfmdata,features,trace,report)
+ if features and next(features) then
+ local properties=tfmdata.properties
+ local whathandler=handlers[what]
+ local whatfeatures=whathandler.features
+ local whatmanipulators=whatfeatures.manipulators
+ local mode=properties.mode
+ local manipulators=whatmanipulators[mode]
+ if manipulators then
+ for i=1,#manipulators do
+ local step=manipulators[i]
+ local feature=step.name
+ local value=features[feature]
+ if value then
+ local action=step.action
+ if trace then
+ report("applying feature manipulator %a for mode %a for font %a",feature,mode,properties.fullname)
+ end
+ if action then
+ action(tfmdata,feature,value)
+ end
+ end
+ end
+ end
+ end
+end
+function constructors.addcoreunicodes(unicodes)
+ if not unicodes then
+ unicodes={}
+ end
+ unicodes.space=0x0020
+ unicodes.hyphen=0x002D
+ unicodes.zwj=0x200D
+ unicodes.zwnj=0x200C
+ return unicodes
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-con”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-enc” 3e71a54297e8f85a1ac438bb0f20dd79] ---
+
+if not modules then modules={} end modules ['luatex-font-enc']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+ os.exit()
+end
+local fonts=fonts
+local encodings={}
+fonts.encodings=encodings
+encodings.agl={}
+encodings.known={}
+setmetatable(encodings.agl,{ __index=function(t,k)
+ if k=="unicodes" then
+ logs.report("fonts","loading (extended) adobe glyph list")
+ local unicodes=dofile(resolvers.findfile("font-age.lua"))
+ encodings.agl={ unicodes=unicodes }
+ return unicodes
+ else
+ return nil
+ end
+end })
+encodings.cache=containers.define("fonts","enc",encodings.version,true)
+function encodings.load(filename)
+ local name=file.removesuffix(filename)
+ local data=containers.read(encodings.cache,name)
+ if data then
+ return data
+ end
+ local vector,tag,hash,unicodes={},"",{},{}
+ local foundname=resolvers.findfile(filename,'enc')
+ if foundname and foundname~="" then
+ local ok,encoding,size=resolvers.loadbinfile(foundname)
+ if ok and encoding then
+ encoding=string.gsub(encoding,"%%(.-)\n","")
+ local unicoding=encodings.agl.unicodes
+ local tag,vec=string.match(encoding,"/(%w+)%s*%[(.*)%]%s*def")
+ local i=0
+ for ch in string.gmatch(vec,"/([%a%d%.]+)") do
+ if ch~=".notdef" then
+ vector[i]=ch
+ if not hash[ch] then
+ hash[ch]=i
+ else
+ end
+ local u=unicoding[ch]
+ if u then
+ unicodes[u]=i
+ end
+ end
+ i=i+1
+ end
+ end
+ end
+ local data={
+ name=name,
+ tag=tag,
+ vector=vector,
+ hash=hash,
+ unicodes=unicodes
+ }
+ return containers.write(encodings.cache,name,data)
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-enc”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-cid” 4d87988efa86020a14708ee03c23415f] ---
+
+if not modules then modules={} end modules ['font-cid']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local format,match,lower=string.format,string.match,string.lower
+local tonumber=tonumber
+local P,S,R,C,V,lpegmatch=lpeg.P,lpeg.S,lpeg.R,lpeg.C,lpeg.V,lpeg.match
+local fonts,logs,trackers=fonts,logs,trackers
+local trace_loading=false trackers.register("otf.loading",function(v) trace_loading=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local cid={}
+fonts.cid=cid
+local cidmap={}
+local cidmax=10
+local number=C(R("09","af","AF")^1)
+local space=S(" \n\r\t")
+local spaces=space^0
+local period=P(".")
+local periods=period*period
+local name=P("/")*C((1-space)^1)
+local unicodes,names={},{}
+local function do_one(a,b)
+ unicodes[tonumber(a)]=tonumber(b,16)
+end
+local function do_range(a,b,c)
+ c=tonumber(c,16)
+ for i=tonumber(a),tonumber(b) do
+ unicodes[i]=c
+ c=c+1
+ end
+end
+local function do_name(a,b)
+ names[tonumber(a)]=b
+end
+local grammar=P { "start",
+ start=number*spaces*number*V("series"),
+ series=(spaces*(V("one")+V("range")+V("named")))^1,
+ one=(number*spaces*number)/do_one,
+ range=(number*periods*number*spaces*number)/do_range,
+ named=(number*spaces*name)/do_name
+}
+local function loadcidfile(filename)
+ local data=io.loaddata(filename)
+ if data then
+ unicodes,names={},{}
+ lpegmatch(grammar,data)
+ local supplement,registry,ordering=match(filename,"^(.-)%-(.-)%-()%.(.-)$")
+ return {
+ supplement=supplement,
+ registry=registry,
+ ordering=ordering,
+ filename=filename,
+ unicodes=unicodes,
+ names=names,
+ }
+ end
+end
+cid.loadfile=loadcidfile
+local template="%s-%s-%s.cidmap"
+local function locate(registry,ordering,supplement)
+ local filename=format(template,registry,ordering,supplement)
+ local hashname=lower(filename)
+ local found=cidmap[hashname]
+ if not found then
+ if trace_loading then
+ report_otf("checking cidmap, registry %a, ordering %a, supplement %a, filename %a",registry,ordering,supplement,filename)
+ end
+ local fullname=resolvers.findfile(filename,'cid') or ""
+ if fullname~="" then
+ found=loadcidfile(fullname)
+ if found then
+ if trace_loading then
+ report_otf("using cidmap file %a",filename)
+ end
+ cidmap[hashname]=found
+ found.usedname=file.basename(filename)
+ end
+ end
+ end
+ return found
+end
+function cid.getmap(specification)
+ if not specification then
+ report_otf("invalid cidinfo specification, table expected")
+ return
+ end
+ local registry=specification.registry
+ local ordering=specification.ordering
+ local supplement=specification.supplement
+ local filename=format(registry,ordering,supplement)
+ local lowername=lower(filename)
+ local found=cidmap[lowername]
+ if found then
+ return found
+ end
+ if ordering=="Identity" then
+ local found={
+ supplement=supplement,
+ registry=registry,
+ ordering=ordering,
+ filename=filename,
+ unicodes={},
+ names={},
+ }
+ cidmap[lowername]=found
+ return found
+ end
+ if trace_loading then
+ report_otf("cidmap needed, registry %a, ordering %a, supplement %a",registry,ordering,supplement)
+ end
+ found=locate(registry,ordering,supplement)
+ if not found then
+ local supnum=tonumber(supplement)
+ local cidnum=nil
+ if supnum<cidmax then
+ for s=supnum+1,cidmax do
+ local c=locate(registry,ordering,s)
+ if c then
+ found,cidnum=c,s
+ break
+ end
+ end
+ end
+ if not found and supnum>0 then
+ for s=supnum-1,0,-1 do
+ local c=locate(registry,ordering,s)
+ if c then
+ found,cidnum=c,s
+ break
+ end
+ end
+ end
+ registry=lower(registry)
+ ordering=lower(ordering)
+ if found and cidnum>0 then
+ for s=0,cidnum-1 do
+ local filename=format(template,registry,ordering,s)
+ if not cidmap[filename] then
+ cidmap[filename]=found
+ end
+ end
+ end
+ end
+ return found
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-cid”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-map” f486746e90fe972de4b73e208ac7cbb2] ---
+
+if not modules then modules={} end modules ['font-map']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local tonumber,next,type=tonumber,next,type
+local match,format,find,concat,gsub,lower=string.match,string.format,string.find,table.concat,string.gsub,string.lower
+local P,R,S,C,Ct,Cc,lpegmatch=lpeg.P,lpeg.R,lpeg.S,lpeg.C,lpeg.Ct,lpeg.Cc,lpeg.match
+local formatters=string.formatters
+local sortedhash,sortedkeys=table.sortedhash,table.sortedkeys
+local rshift=bit32.rshift
+local trace_loading=false trackers.register("fonts.loading",function(v) trace_loading=v end)
+local trace_mapping=false trackers.register("fonts.mapping",function(v) trace_mapping=v end)
+local report_fonts=logs.reporter("fonts","loading")
+local force_ligatures=false directives.register("fonts.mapping.forceligatures",function(v) force_ligatures=v end)
+local fonts=fonts or {}
+local mappings=fonts.mappings or {}
+fonts.mappings=mappings
+local allocate=utilities.storage.allocate
+local hex=R("AF","af","09")
+local hexfour=(hex*hex*hex^-2)/function(s) return tonumber(s,16) end
+local hexsix=(hex*hex*hex^-4)/function(s) return tonumber(s,16) end
+local dec=(R("09")^1)/tonumber
+local period=P(".")
+local unicode=(P("uni")+P("UNI"))*(hexfour*(period+P(-1))*Cc(false)+Ct(hexfour^1)*Cc(true))
+local ucode=(P("u")+P("U") )*(hexsix*(period+P(-1))*Cc(false)+Ct(hexsix^1)*Cc(true))
+local index=P("index")*dec*Cc(false)
+local parser=unicode+ucode+index
+local parsers={}
+local function makenameparser(str)
+ if not str or str=="" then
+ return parser
+ else
+ local p=parsers[str]
+ if not p then
+ p=P(str)*period*dec*Cc(false)
+ parsers[str]=p
+ end
+ return p
+ end
+end
+local f_single=formatters["%04X"]
+local f_double=formatters["%04X%04X"]
+local function tounicode16(unicode)
+ if unicode<0xD7FF or (unicode>0xDFFF and unicode<=0xFFFF) then
+ return f_single(unicode)
+ else
+ unicode=unicode-0x10000
+ return f_double(rshift(unicode,10)+0xD800,unicode%1024+0xDC00)
+ end
+end
+local function tounicode16sequence(unicodes)
+ local t={}
+ for l=1,#unicodes do
+ local u=unicodes[l]
+ if u<0xD7FF or (u>0xDFFF and u<=0xFFFF) then
+ t[l]=f_single(u)
+ else
+ u=u-0x10000
+ t[l]=f_double(rshift(u,10)+0xD800,u%1024+0xDC00)
+ end
+ end
+ return concat(t)
+end
+local unknown=f_single(0xFFFD)
+local hash={}
+local conc={}
+table.setmetatableindex(hash,function(t,k)
+ if k<0xD7FF or (k>0xDFFF and k<=0xFFFF) then
+ v=f_single(k)
+ else
+ local k=k-0x10000
+ v=f_double(rshift(k,10)+0xD800,k%1024+0xDC00)
+ end
+ t[k]=v
+ return v
+end)
+local function tounicode(k)
+ if type(k)=="table" then
+ local n=#k
+ for l=1,n do
+ conc[l]=hash[k[l]]
+ end
+ return concat(conc,"",1,n)
+ elseif k>=0x00E000 and k<=0x00F8FF then
+ return unknown
+ elseif k>=0x0F0000 and k<=0x0FFFFF then
+ return unknown
+ elseif k>=0x100000 and k<=0x10FFFF then
+ return unknown
+ else
+ return hash[k]
+ end
+end
+local function fromunicode16(str)
+ if #str==4 then
+ return tonumber(str,16)
+ else
+ local l,r=match(str,"(....)(....)")
+ return 0x10000+(tonumber(l,16)-0xD800)*0x400+tonumber(r,16)-0xDC00
+ end
+end
+mappings.makenameparser=makenameparser
+mappings.tounicode=tounicode
+mappings.tounicode16=tounicode16
+mappings.tounicode16sequence=tounicode16sequence
+mappings.fromunicode16=fromunicode16
+local ligseparator=P("_")
+local varseparator=P(".")
+local namesplitter=Ct(C((1-ligseparator-varseparator)^1)*(ligseparator*C((1-ligseparator-varseparator)^1))^0)
+do
+ local overloads={
+ IJ={ name="I_J",unicode={ 0x49,0x4A },mess=0x0132 },
+ ij={ name="i_j",unicode={ 0x69,0x6A },mess=0x0133 },
+ ff={ name="f_f",unicode={ 0x66,0x66 },mess=0xFB00 },
+ fi={ name="f_i",unicode={ 0x66,0x69 },mess=0xFB01 },
+ fl={ name="f_l",unicode={ 0x66,0x6C },mess=0xFB02 },
+ ffi={ name="f_f_i",unicode={ 0x66,0x66,0x69 },mess=0xFB03 },
+ ffl={ name="f_f_l",unicode={ 0x66,0x66,0x6C },mess=0xFB04 },
+ fj={ name="f_j",unicode={ 0x66,0x6A } },
+ fk={ name="f_k",unicode={ 0x66,0x6B } },
+ }
+ local o=allocate {}
+ for k,v in next,overloads do
+ local name=v.name
+ local mess=v.mess
+ if name then
+ o[name]=v
+ end
+ if mess then
+ o[mess]=v
+ end
+ o[k]=v
+ end
+ mappings.overloads=o
+end
+function mappings.addtounicode(data,filename,checklookups,forceligatures)
+ local resources=data.resources
+ local unicodes=resources.unicodes
+ if not unicodes then
+ if trace_mapping then
+ report_fonts("no unicode list, quitting tounicode for %a",filename)
+ end
+ return
+ end
+ local properties=data.properties
+ local descriptions=data.descriptions
+ local overloads=mappings.overloads
+ unicodes['space']=unicodes['space'] or 32
+ unicodes['hyphen']=unicodes['hyphen'] or 45
+ unicodes['zwj']=unicodes['zwj'] or 0x200D
+ unicodes['zwnj']=unicodes['zwnj'] or 0x200C
+ local private=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+ local unicodevector=fonts.encodings.agl.unicodes or {}
+ local contextvector=fonts.encodings.agl.ctxcodes or {}
+ local missing={}
+ local nofmissing=0
+ local oparser=nil
+ local cidnames=nil
+ local cidcodes=nil
+ local cidinfo=properties.cidinfo
+ local usedmap=cidinfo and fonts.cid.getmap(cidinfo)
+ local uparser=makenameparser()
+ if usedmap then
+ oparser=usedmap and makenameparser(cidinfo.ordering)
+ cidnames=usedmap.names
+ cidcodes=usedmap.unicodes
+ end
+ local ns=0
+ local nl=0
+ local dlist=sortedkeys(descriptions)
+ for i=1,#dlist do
+ local du=dlist[i]
+ local glyph=descriptions[du]
+ local name=glyph.name
+ if name then
+ local overload=overloads[name] or overloads[du]
+ if overload then
+ glyph.unicode=overload.unicode
+ else
+ local gu=glyph.unicode
+ if not gu or gu==-1 or du>=private or (du>=0xE000 and du<=0xF8FF) or du==0xFFFE or du==0xFFFF then
+ local unicode=unicodevector[name] or contextvector[name]
+ if unicode then
+ glyph.unicode=unicode
+ ns=ns+1
+ end
+ if (not unicode) and usedmap then
+ local foundindex=lpegmatch(oparser,name)
+ if foundindex then
+ unicode=cidcodes[foundindex]
+ if unicode then
+ glyph.unicode=unicode
+ ns=ns+1
+ else
+ local reference=cidnames[foundindex]
+ if reference then
+ local foundindex=lpegmatch(oparser,reference)
+ if foundindex then
+ unicode=cidcodes[foundindex]
+ if unicode then
+ glyph.unicode=unicode
+ ns=ns+1
+ end
+ end
+ if not unicode or unicode=="" then
+ local foundcodes,multiple=lpegmatch(uparser,reference)
+ if foundcodes then
+ glyph.unicode=foundcodes
+ if multiple then
+ nl=nl+1
+ unicode=true
+ else
+ ns=ns+1
+ unicode=foundcodes
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if not unicode or unicode=="" then
+ local split=lpegmatch(namesplitter,name)
+ local nsplit=split and #split or 0
+ if nsplit==0 then
+ elseif nsplit==1 then
+ local base=split[1]
+ local u=unicodes[base] or unicodevector[base] or contextvector[name]
+ if not u then
+ elseif type(u)=="table" then
+ if u[1]<private then
+ unicode=u
+ glyph.unicode=unicode
+ end
+ elseif u<private then
+ unicode=u
+ glyph.unicode=unicode
+ end
+ else
+ local t={}
+ local n=0
+ for l=1,nsplit do
+ local base=split[l]
+ local u=unicodes[base] or unicodevector[base] or contextvector[name]
+ if not u then
+ break
+ elseif type(u)=="table" then
+ if u[1]>=private then
+ break
+ end
+ n=n+1
+ t[n]=u[1]
+ else
+ if u>=private then
+ break
+ end
+ n=n+1
+ t[n]=u
+ end
+ end
+ if n>0 then
+ if n==1 then
+ unicode=t[1]
+ else
+ unicode=t
+ end
+ glyph.unicode=unicode
+ end
+ end
+ nl=nl+1
+ end
+ if not unicode or unicode=="" then
+ local foundcodes,multiple=lpegmatch(uparser,name)
+ if foundcodes then
+ glyph.unicode=foundcodes
+ if multiple then
+ nl=nl+1
+ unicode=true
+ else
+ ns=ns+1
+ unicode=foundcodes
+ end
+ end
+ end
+ local r=overloads[unicode]
+ if r then
+ unicode=r.unicode
+ glyph.unicode=unicode
+ end
+ if not unicode then
+ missing[du]=true
+ nofmissing=nofmissing+1
+ end
+ else
+ end
+ end
+ else
+ local overload=overloads[du]
+ if overload then
+ glyph.unicode=overload.unicode
+ elseif not glyph.unicode then
+ missing[du]=true
+ nofmissing=nofmissing+1
+ end
+ end
+ end
+ if type(checklookups)=="function" then
+ checklookups(data,missing,nofmissing)
+ end
+ local unicoded=0
+ local collected=fonts.handlers.otf.readers.getcomponents(data)
+ local function resolve(glyph,u)
+ local n=#u
+ for i=1,n do
+ if u[i]>private then
+ n=0
+ break
+ end
+ end
+ if n>0 then
+ if n>1 then
+ glyph.unicode=u
+ else
+ glyph.unicode=u[1]
+ end
+ unicoded=unicoded+1
+ end
+ end
+ if not collected then
+ elseif forceligatures or force_ligatures then
+ for i=1,#dlist do
+ local du=dlist[i]
+ if du>=private or (du>=0xE000 and du<=0xF8FF) then
+ local u=collected[du]
+ if u then
+ resolve(descriptions[du],u)
+ end
+ end
+ end
+ else
+ for i=1,#dlist do
+ local du=dlist[i]
+ if du>=private or (du>=0xE000 and du<=0xF8FF) then
+ local glyph=descriptions[du]
+ if glyph.class=="ligature" and not glyph.unicode then
+ local u=collected[du]
+ if u then
+ resolve(glyph,u)
+ end
+ end
+ end
+ end
+ end
+ if trace_mapping and unicoded>0 then
+ report_fonts("%n ligature tounicode mappings deduced from gsub ligature features",unicoded)
+ end
+ if trace_mapping then
+ for i=1,#dlist do
+ local du=dlist[i]
+ local glyph=descriptions[du]
+ local name=glyph.name or "-"
+ local index=glyph.index or 0
+ local unicode=glyph.unicode
+ if unicode then
+ if type(unicode)=="table" then
+ local unicodes={}
+ for i=1,#unicode do
+ unicodes[i]=formatters("%U",unicode[i])
+ end
+ report_fonts("internal slot %U, name %a, unicode %U, tounicode % t",index,name,du,unicodes)
+ else
+ report_fonts("internal slot %U, name %a, unicode %U, tounicode %U",index,name,du,unicode)
+ end
+ else
+ report_fonts("internal slot %U, name %a, unicode %U",index,name,du)
+ end
+ end
+ end
+ if trace_loading and (ns>0 or nl>0) then
+ report_fonts("%s tounicode entries added, ligatures %s",nl+ns,ns)
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-map”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-vfc” 94937140f2c909e9c831ba021f1ab303] ---
+
+if not modules then modules={} end modules ['font-vfc']={
+ version=1.001,
+ comment="companion to font-ini.mkiv and hand-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local select,type=select,type
+local insert=table.insert
+local fonts=fonts
+local helpers=fonts.helpers
+local setmetatableindex=table.setmetatableindex
+local makeweak=table.makeweak
+local push={ "push" }
+local pop={ "pop" }
+local dummy={ "comment" }
+function helpers.prependcommands(commands,...)
+ insert(commands,1,push)
+ for i=select("#",...),1,-1 do
+ local s=(select(i,...))
+ if s then
+ insert(commands,1,s)
+ end
+ end
+ insert(commands,pop)
+ return commands
+end
+function helpers.appendcommands(commands,...)
+ insert(commands,1,push)
+ insert(commands,pop)
+ for i=1,select("#",...) do
+ local s=(select(i,...))
+ if s then
+ insert(commands,s)
+ end
+ end
+ return commands
+end
+function helpers.prependcommandtable(commands,t)
+ insert(commands,1,push)
+ for i=#t,1,-1 do
+ local s=t[i]
+ if s then
+ insert(commands,1,s)
+ end
+ end
+ insert(commands,pop)
+ return commands
+end
+function helpers.appendcommandtable(commands,t)
+ insert(commands,1,push)
+ insert(commands,pop)
+ for i=1,#t do
+ local s=t[i]
+ if s then
+ insert(commands,s)
+ end
+ end
+ return commands
+end
+local char=setmetatableindex(function(t,k)
+ local v={ "slot",0,k }
+ t[k]=v
+ return v
+end)
+local right=setmetatableindex(function(t,k)
+ local v={ "right",k }
+ t[k]=v
+ return v
+end)
+local left=setmetatableindex(function(t,k)
+ local v={ "right",-k }
+ t[k]=v
+ return v
+end)
+local down=setmetatableindex(function(t,k)
+ local v={ "down",k }
+ t[k]=v
+ return v
+end)
+local up=setmetatableindex(function(t,k)
+ local v={ "down",-k }
+ t[k]=v
+ return v
+end)
+helpers.commands=utilities.storage.allocate {
+ char=char,
+ right=right,
+ left=left,
+ down=down,
+ up=up,
+ push=push,
+ pop=pop,
+ dummy=dummy,
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-vfc”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otr” b1c03925c949027c86f781785fa7a208] ---
+
+if not modules then modules={} end modules ['font-otr']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+local byte,lower,char,gsub=string.byte,string.lower,string.char,string.gsub
+local fullstrip=string.fullstrip
+local floor,round=math.floor,math.round
+local P,R,S,C,Cs,Cc,Ct,Carg,Cmt=lpeg.P,lpeg.R,lpeg.S,lpeg.C,lpeg.Cs,lpeg.Cc,lpeg.Ct,lpeg.Carg,lpeg.Cmt
+local lpegmatch=lpeg.match
+local rshift=bit32.rshift
+local setmetatableindex=table.setmetatableindex
+local sortedkeys=table.sortedkeys
+local sortedhash=table.sortedhash
+local stripstring=string.nospaces
+local utf16_to_utf8_be=utf.utf16_to_utf8_be
+local report=logs.reporter("otf reader")
+local report_cmap=logs.reporter("otf reader","cmap")
+local trace_cmap=false trackers.register("otf.cmap",function(v) trace_cmap=v end)
+local trace_cmap_details=false trackers.register("otf.cmap.details",function(v) trace_cmap_details=v end)
+fonts=fonts or {}
+local handlers=fonts.handlers or {}
+fonts.handlers=handlers
+local otf=handlers.otf or {}
+handlers.otf=otf
+local readers=otf.readers or {}
+otf.readers=readers
+local streamreader=utilities.files
+local streamwriter=utilities.files
+readers.streamreader=streamreader
+readers.streamwriter=streamwriter
+local openfile=streamreader.open
+local closefile=streamreader.close
+local setposition=streamreader.setposition
+local skipshort=streamreader.skipshort
+local readbytes=streamreader.readbytes
+local readstring=streamreader.readstring
+local readbyte=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readuint=streamreader.readcardinal3
+local readulong=streamreader.readcardinal4
+local readshort=streamreader.readinteger2
+local readlong=streamreader.readinteger4
+local readfixed=streamreader.readfixed4
+local read2dot14=streamreader.read2dot14
+local readfword=readshort
+local readufword=readushort
+local readoffset=readushort
+local readcardinaltable=streamreader.readcardinaltable
+local readintegertable=streamreader.readintegertable
+function streamreader.readtag(f)
+ return lower(stripstring(readstring(f,4)))
+end
+local short=2
+local ushort=2
+local ulong=4
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ openfile=streamreader.open
+ closefile=streamreader.close
+ setposition=streamreader.setposition
+ skipshort=streamreader.skipshort
+ readbytes=streamreader.readbytes
+ readstring=streamreader.readstring
+ readbyte=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readuint=streamreader.readcardinal3
+ readulong=streamreader.readcardinal4
+ readshort=streamreader.readinteger2
+ readlong=streamreader.readinteger4
+ readfixed=streamreader.readfixed4
+ read2dot14=streamreader.read2dot14
+ readfword=readshort
+ readufword=readushort
+ readoffset=readushort
+ readcardinaltable=streamreader.readcardinaltable
+ readintegertable=streamreader.readintegertable
+ function streamreader.readtag(f)
+ return lower(stripstring(readstring(f,4)))
+ end
+end)
+local function readlongdatetime(f)
+ local a,b,c,d,e,f,g,h=readbytes(f,8)
+ return 0x100000000*d+0x1000000*e+0x10000*f+0x100*g+h
+end
+local tableversion=0.004
+readers.tableversion=tableversion
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local reservednames={ [0]="copyright",
+ "family",
+ "subfamily",
+ "uniqueid",
+ "fullname",
+ "version",
+ "postscriptname",
+ "trademark",
+ "manufacturer",
+ "designer",
+ "description",
+ "vendorurl",
+ "designerurl",
+ "license",
+ "licenseurl",
+ "reserved",
+ "typographicfamily",
+ "typographicsubfamily",
+ "compatiblefullname",
+ "sampletext",
+ "cidfindfontname",
+ "wwsfamily",
+ "wwssubfamily",
+ "lightbackgroundpalette",
+ "darkbackgroundpalette",
+ "variationspostscriptnameprefix",
+}
+local platforms={ [0]="unicode",
+ "macintosh",
+ "iso",
+ "windows",
+ "custom",
+}
+local encodings={
+ unicode={ [0]="unicode 1.0 semantics",
+ "unicode 1.1 semantics",
+ "iso/iec 10646",
+ "unicode 2.0 bmp",
+ "unicode 2.0 full",
+ "unicode variation sequences",
+ "unicode full repertoire",
+ },
+ macintosh={ [0]="roman","japanese","chinese (traditional)","korean","arabic","hebrew","greek","russian",
+ "rsymbol","devanagari","gurmukhi","gujarati","oriya","bengali","tamil","telugu","kannada",
+ "malayalam","sinhalese","burmese","khmer","thai","laotian","georgian","armenian",
+ "chinese (simplified)","tibetan","mongolian","geez","slavic","vietnamese","sindhi",
+ "uninterpreted",
+ },
+ iso={ [0]="7-bit ascii",
+ "iso 10646",
+ "iso 8859-1",
+ },
+ windows={ [0]="symbol",
+ "unicode bmp",
+ "shiftjis",
+ "prc",
+ "big5",
+ "wansung",
+ "johab",
+ "reserved 7",
+ "reserved 8",
+ "reserved 9",
+ "unicode ucs-4",
+ },
+ custom={
+ }
+}
+local decoders={
+ unicode={},
+ macintosh={},
+ iso={},
+ windows={
+ ["unicode semantics"]=utf16_to_utf8_be,
+ ["unicode bmp"]=utf16_to_utf8_be,
+ ["unicode full"]=utf16_to_utf8_be,
+ ["unicode 1.0 semantics"]=utf16_to_utf8_be,
+ ["unicode 1.1 semantics"]=utf16_to_utf8_be,
+ ["unicode 2.0 bmp"]=utf16_to_utf8_be,
+ ["unicode 2.0 full"]=utf16_to_utf8_be,
+ ["unicode variation sequences"]=utf16_to_utf8_be,
+ ["unicode full repertoire"]=utf16_to_utf8_be,
+ },
+ custom={},
+}
+local languages={
+ unicode={
+ [ 0]="english",
+ },
+ macintosh={
+ [ 0]="english",
+ },
+ iso={},
+ windows={
+ [0x0409]="english - united states",
+ },
+ custom={},
+}
+local standardromanencoding={ [0]=
+ "notdef",".null","nonmarkingreturn","space","exclam","quotedbl",
+ "numbersign","dollar","percent","ampersand","quotesingle","parenleft",
+ "parenright","asterisk","plus","comma","hyphen","period","slash",
+ "zero","one","two","three","four","five","six","seven","eight",
+ "nine","colon","semicolon","less","equal","greater","question","at",
+ "A","B","C","D","E","F","G","H","I","J","K","L","M","N","O",
+ "P","Q","R","S","T","U","V","W","X","Y","Z","bracketleft",
+ "backslash","bracketright","asciicircum","underscore","grave","a","b",
+ "c","d","e","f","g","h","i","j","k","l","m","n","o","p","q",
+ "r","s","t","u","v","w","x","y","z","braceleft","bar",
+ "braceright","asciitilde","Adieresis","Aring","Ccedilla","Eacute",
+ "Ntilde","Odieresis","Udieresis","aacute","agrave","acircumflex",
+ "adieresis","atilde","aring","ccedilla","eacute","egrave",
+ "ecircumflex","edieresis","iacute","igrave","icircumflex","idieresis",
+ "ntilde","oacute","ograve","ocircumflex","odieresis","otilde","uacute",
+ "ugrave","ucircumflex","udieresis","dagger","degree","cent","sterling",
+ "section","bullet","paragraph","germandbls","registered","copyright",
+ "trademark","acute","dieresis","notequal","AE","Oslash","infinity",
+ "plusminus","lessequal","greaterequal","yen","mu","partialdiff",
+ "summation","product","pi","integral","ordfeminine","ordmasculine",
+ "Omega","ae","oslash","questiondown","exclamdown","logicalnot",
+ "radical","florin","approxequal","Delta","guillemotleft",
+ "guillemotright","ellipsis","nonbreakingspace","Agrave","Atilde",
+ "Otilde","OE","oe","endash","emdash","quotedblleft","quotedblright",
+ "quoteleft","quoteright","divide","lozenge","ydieresis","Ydieresis",
+ "fraction","currency","guilsinglleft","guilsinglright","fi","fl",
+ "daggerdbl","periodcentered","quotesinglbase","quotedblbase",
+ "perthousand","Acircumflex","Ecircumflex","Aacute","Edieresis","Egrave",
+ "Iacute","Icircumflex","Idieresis","Igrave","Oacute","Ocircumflex",
+ "apple","Ograve","Uacute","Ucircumflex","Ugrave","dotlessi",
+ "circumflex","tilde","macron","breve","dotaccent","ring","cedilla",
+ "hungarumlaut","ogonek","caron","Lslash","lslash","Scaron","scaron",
+ "Zcaron","zcaron","brokenbar","Eth","eth","Yacute","yacute","Thorn",
+ "thorn","minus","multiply","onesuperior","twosuperior","threesuperior",
+ "onehalf","onequarter","threequarters","franc","Gbreve","gbreve",
+ "Idotaccent","Scedilla","scedilla","Cacute","cacute","Ccaron","ccaron",
+ "dcroat",
+}
+local weights={
+ [100]="thin",
+ [200]="extralight",
+ [300]="light",
+ [400]="normal",
+ [500]="medium",
+ [600]="semibold",
+ [700]="bold",
+ [800]="extrabold",
+ [900]="black",
+}
+local widths={
+ [1]="ultracondensed",
+ [2]="extracondensed",
+ [3]="condensed",
+ [4]="semicondensed",
+ [5]="normal",
+ [6]="semiexpanded",
+ [7]="expanded",
+ [8]="extraexpanded",
+ [9]="ultraexpanded",
+}
+setmetatableindex(weights,function(t,k)
+ local r=floor((k+50)/100)*100
+ local v=(r>900 and "black") or rawget(t,r) or "normal"
+ return v
+end)
+setmetatableindex(widths,function(t,k)
+ return "normal"
+end)
+local panoseweights={
+ [ 0]="normal",
+ [ 1]="normal",
+ [ 2]="verylight",
+ [ 3]="light",
+ [ 4]="thin",
+ [ 5]="book",
+ [ 6]="medium",
+ [ 7]="demi",
+ [ 8]="bold",
+ [ 9]="heavy",
+ [10]="black",
+}
+local panosewidths={
+ [ 0]="normal",
+ [ 1]="normal",
+ [ 2]="normal",
+ [ 3]="normal",
+ [ 4]="normal",
+ [ 5]="expanded",
+ [ 6]="condensed",
+ [ 7]="veryexpanded",
+ [ 8]="verycondensed",
+ [ 9]="monospaced",
+}
+local helpers={}
+readers.helpers=helpers
+local function gotodatatable(f,fontdata,tag,criterium)
+ if criterium and f then
+ local tables=fontdata.tables
+ if tables then
+ local datatable=tables[tag]
+ if datatable then
+ local tableoffset=datatable.offset
+ setposition(f,tableoffset)
+ return tableoffset
+ end
+ else
+ report("no tables")
+ end
+ end
+end
+local function reportskippedtable(f,fontdata,tag,criterium)
+ if criterium and f then
+ local tables=fontdata.tables
+ if tables then
+ local datatable=tables[tag]
+ if datatable then
+ report("loading of table %a skipped",tag)
+ end
+ else
+ report("no tables")
+ end
+ end
+end
+local function setvariabledata(fontdata,tag,data)
+ local variabledata=fontdata.variabledata
+ if variabledata then
+ variabledata[tag]=data
+ else
+ fontdata.variabledata={ [tag]=data }
+ end
+end
+helpers.gotodatatable=gotodatatable
+helpers.setvariabledata=setvariabledata
+helpers.reportskippedtable=reportskippedtable
+local platformnames={
+ postscriptname=true,
+ fullname=true,
+ family=true,
+ subfamily=true,
+ typographicfamily=true,
+ typographicsubfamily=true,
+ compatiblefullname=true,
+}
+local platformextras={
+ uniqueid=true,
+ version=true,
+ copyright=true,
+ license=true,
+ licenseurl=true,
+ manufacturer=true,
+ vendorurl=true,
+}
+function readers.name(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"name",true)
+ if tableoffset then
+ local format=readushort(f)
+ local nofnames=readushort(f)
+ local offset=readushort(f)
+ local start=tableoffset+offset
+ local namelists={
+ unicode={},
+ windows={},
+ macintosh={},
+ }
+ for i=1,nofnames do
+ local platform=platforms[readushort(f)]
+ if platform then
+ local namelist=namelists[platform]
+ if namelist then
+ local encoding=readushort(f)
+ local language=readushort(f)
+ local encodings=encodings[platform]
+ local languages=languages[platform]
+ if encodings and languages then
+ local encoding=encodings[encoding]
+ local language=languages[language]
+ if encoding and language then
+ local index=readushort(f)
+ local name=reservednames[index]
+ namelist[#namelist+1]={
+ platform=platform,
+ encoding=encoding,
+ language=language,
+ name=name,
+ index=index,
+ length=readushort(f),
+ offset=start+readushort(f),
+ }
+ else
+ skipshort(f,3)
+ end
+ else
+ skipshort(f,3)
+ end
+ else
+ skipshort(f,5)
+ end
+ else
+ skipshort(f,5)
+ end
+ end
+ local names={}
+ local done={}
+ local extras={}
+ local function decoded(platform,encoding,content)
+ local decoder=decoders[platform]
+ if decoder then
+ decoder=decoder[encoding]
+ end
+ if decoder then
+ return decoder(content)
+ else
+ return content
+ end
+ end
+ local function filter(platform,e,l)
+ local namelist=namelists[platform]
+ for i=1,#namelist do
+ local name=namelist[i]
+ local nametag=name.name
+ local index=name.index
+ if not done[nametag or i] then
+ local encoding=name.encoding
+ local language=name.language
+ if (not e or encoding==e) and (not l or language==l) then
+ setposition(f,name.offset)
+ local content=decoded(platform,encoding,readstring(f,name.length))
+ if nametag then
+ names[nametag]={
+ content=content,
+ platform=platform,
+ encoding=encoding,
+ language=language,
+ }
+ end
+ extras[index]=content
+ done[nametag or i]=true
+ end
+ end
+ end
+ end
+ filter("windows","unicode bmp","english - united states")
+ filter("macintosh","roman","english")
+ filter("windows")
+ filter("macintosh")
+ filter("unicode")
+ fontdata.names=names
+ fontdata.extras=extras
+ if specification.platformnames then
+ local collected={}
+ local platformextras=specification.platformextras and platformextras
+ for platform,namelist in next,namelists do
+ local filtered=false
+ for i=1,#namelist do
+ local entry=namelist[i]
+ local name=entry.name
+ if platformnames[name] or (platformextras and platformextras[name]) then
+ setposition(f,entry.offset)
+ local content=decoded(platform,entry.encoding,readstring(f,entry.length))
+ if filtered then
+ filtered[name]=content
+ else
+ filtered={ [name]=content }
+ end
+ end
+ end
+ if filtered then
+ collected[platform]=filtered
+ end
+ end
+ fontdata.platformnames=collected
+ end
+ else
+ fontdata.names={}
+ end
+end
+local validutf=lpeg.patterns.validutf8
+local function getname(fontdata,key)
+ local names=fontdata.names
+ if names then
+ local value=names[key]
+ if value then
+ local content=value.content
+ return lpegmatch(validutf,content) and content or nil
+ end
+ end
+end
+readers["os/2"]=function(f,fontdata)
+ local tableoffset=gotodatatable(f,fontdata,"os/2",true)
+ if tableoffset then
+ local version=readushort(f)
+ local windowsmetrics={
+ version=version,
+ averagewidth=readshort(f),
+ weightclass=readushort(f),
+ widthclass=readushort(f),
+ fstype=readushort(f),
+ subscriptxsize=readshort(f),
+ subscriptysize=readshort(f),
+ subscriptxoffset=readshort(f),
+ subscriptyoffset=readshort(f),
+ superscriptxsize=readshort(f),
+ superscriptysize=readshort(f),
+ superscriptxoffset=readshort(f),
+ superscriptyoffset=readshort(f),
+ strikeoutsize=readshort(f),
+ strikeoutpos=readshort(f),
+ familyclass=readshort(f),
+ panose={ readbytes(f,10) },
+ unicoderanges={ readulong(f),readulong(f),readulong(f),readulong(f) },
+ vendor=readstring(f,4),
+ fsselection=readushort(f),
+ firstcharindex=readushort(f),
+ lastcharindex=readushort(f),
+ typoascender=readshort(f),
+ typodescender=readshort(f),
+ typolinegap=readshort(f),
+ winascent=readushort(f),
+ windescent=readushort(f),
+ }
+ if version>=1 then
+ windowsmetrics.codepageranges={ readulong(f),readulong(f) }
+ end
+ if version>=2 then
+ windowsmetrics.xheight=readshort(f)
+ windowsmetrics.capheight=readshort(f)
+ windowsmetrics.defaultchar=readushort(f)
+ windowsmetrics.breakchar=readushort(f)
+ end
+ windowsmetrics.weight=windowsmetrics.weightclass and weights[windowsmetrics.weightclass]
+ windowsmetrics.width=windowsmetrics.widthclass and widths [windowsmetrics.widthclass]
+ windowsmetrics.panoseweight=panoseweights[windowsmetrics.panose[3]]
+ windowsmetrics.panosewidth=panosewidths [windowsmetrics.panose[4]]
+ fontdata.windowsmetrics=windowsmetrics
+ else
+ fontdata.windowsmetrics={}
+ end
+end
+readers.head=function(f,fontdata)
+ local tableoffset=gotodatatable(f,fontdata,"head",true)
+ if tableoffset then
+ local version=readulong(f)
+ local fontversion=readulong(f)
+ local fontheader={
+ version=version,
+ fontversion=number.to16dot16(fontversion),
+ fontversionnumber=fontversion,
+ checksum=readushort(f)*0x10000+readushort(f),
+ magic=readulong(f),
+ flags=readushort(f),
+ units=readushort(f),
+ created=readlongdatetime(f),
+ modified=readlongdatetime(f),
+ xmin=readshort(f),
+ ymin=readshort(f),
+ xmax=readshort(f),
+ ymax=readshort(f),
+ macstyle=readushort(f),
+ smallpixels=readushort(f),
+ directionhint=readshort(f),
+ indextolocformat=readshort(f),
+ glyphformat=readshort(f),
+ }
+ fontdata.fontheader=fontheader
+ else
+ fontdata.fontheader={}
+ end
+ fontdata.nofglyphs=0
+end
+readers.hhea=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"hhea",specification.details)
+ if tableoffset then
+ fontdata.horizontalheader={
+ version=readulong(f),
+ ascender=readfword(f),
+ descender=readfword(f),
+ linegap=readfword(f),
+ maxadvancewidth=readufword(f),
+ minleftsidebearing=readfword(f),
+ minrightsidebearing=readfword(f),
+ maxextent=readfword(f),
+ caretsloperise=readshort(f),
+ caretsloperun=readshort(f),
+ caretoffset=readshort(f),
+ reserved_1=readshort(f),
+ reserved_2=readshort(f),
+ reserved_3=readshort(f),
+ reserved_4=readshort(f),
+ metricdataformat=readshort(f),
+ nofmetrics=readushort(f),
+ }
+ else
+ fontdata.horizontalheader={
+ nofmetrics=0,
+ }
+ end
+end
+readers.vhea=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"vhea",specification.details)
+ if tableoffset then
+ fontdata.verticalheader={
+ version=readulong(f),
+ ascender=readfword(f),
+ descender=readfword(f),
+ linegap=readfword(f),
+ maxadvanceheight=readufword(f),
+ mintopsidebearing=readfword(f),
+ minbottomsidebearing=readfword(f),
+ maxextent=readfword(f),
+ caretsloperise=readshort(f),
+ caretsloperun=readshort(f),
+ caretoffset=readshort(f),
+ reserved_1=readshort(f),
+ reserved_2=readshort(f),
+ reserved_3=readshort(f),
+ reserved_4=readshort(f),
+ metricdataformat=readshort(f),
+ nofmetrics=readushort(f),
+ }
+ else
+ fontdata.verticalheader={
+ nofmetrics=0,
+ }
+ end
+end
+readers.maxp=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"maxp",specification.details)
+ if tableoffset then
+ local version=readulong(f)
+ local nofglyphs=readushort(f)
+ fontdata.nofglyphs=nofglyphs
+ if version==0x00005000 then
+ fontdata.maximumprofile={
+ version=version,
+ nofglyphs=nofglyphs,
+ }
+ elseif version==0x00010000 then
+ fontdata.maximumprofile={
+ version=version,
+ nofglyphs=nofglyphs,
+ points=readushort(f),
+ contours=readushort(f),
+ compositepoints=readushort(f),
+ compositecontours=readushort(f),
+ zones=readushort(f),
+ twilightpoints=readushort(f),
+ storage=readushort(f),
+ functiondefs=readushort(f),
+ instructiondefs=readushort(f),
+ stackelements=readushort(f),
+ sizeofinstructions=readushort(f),
+ componentelements=readushort(f),
+ componentdepth=readushort(f),
+ }
+ else
+ fontdata.maximumprofile={
+ version=version,
+ nofglyphs=0,
+ }
+ end
+ end
+end
+readers.hmtx=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"hmtx",specification.glyphs)
+ if tableoffset then
+ local horizontalheader=fontdata.horizontalheader
+ local nofmetrics=horizontalheader.nofmetrics
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs
+ local width=0
+ local leftsidebearing=0
+ for i=0,nofmetrics-1 do
+ local glyph=glyphs[i]
+ width=readshort(f)
+ leftsidebearing=readshort(f)
+ if width~=0 then
+ glyph.width=width
+ end
+ end
+ for i=nofmetrics,nofglyphs-1 do
+ local glyph=glyphs[i]
+ if width~=0 then
+ glyph.width=width
+ end
+ end
+ end
+end
+readers.vmtx=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"vmtx",specification.glyphs)
+ if tableoffset then
+ local verticalheader=fontdata.verticalheader
+ local nofmetrics=verticalheader.nofmetrics
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs
+ local vheight=0
+ local vdefault=verticalheader.ascender-verticalheader.descender
+ local topsidebearing=0
+ for i=0,nofmetrics-1 do
+ local glyph=glyphs[i]
+ vheight=readushort(f)
+ topsidebearing=readshort(f)
+ if vheight~=0 and vheight~=vdefault then
+ glyph.vheight=vheight
+ end
+ if topsidebearing~=0 then
+ glyph.tsb=topsidebearing
+ end
+ end
+ for i=nofmetrics,nofglyphs-1 do
+ local glyph=glyphs[i]
+ if vheight~=0 and vheight~=vdefault then
+ glyph.vheight=vheight
+ end
+ end
+ end
+end
+readers.vorg=function(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"vorg",specification.glyphs)
+end
+readers.post=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"post",true)
+ if tableoffset then
+ local version=readulong(f)
+ fontdata.postscript={
+ version=version,
+ italicangle=round(1000*readfixed(f))/1000,
+ underlineposition=readfword(f),
+ underlinethickness=readfword(f),
+ monospaced=readulong(f),
+ minmemtype42=readulong(f),
+ maxmemtype42=readulong(f),
+ minmemtype1=readulong(f),
+ maxmemtype1=readulong(f),
+ }
+ if not specification.glyphs then
+ elseif version==0x00010000 then
+ for index=0,#standardromanencoding do
+ glyphs[index].name=standardromanencoding[index]
+ end
+ elseif version==0x00020000 then
+ local glyphs=fontdata.glyphs
+ local nofglyphs=readushort(f)
+ local indices={}
+ local names={}
+ local maxnames=0
+ for i=0,nofglyphs-1 do
+ local nameindex=readushort(f)
+ if nameindex>=258 then
+ maxnames=maxnames+1
+ nameindex=nameindex-257
+ indices[nameindex]=i
+ else
+ glyphs[i].name=standardromanencoding[nameindex]
+ end
+ end
+ for i=1,maxnames do
+ local mapping=indices[i]
+ if not mapping then
+ report("quit post name fetching at %a of %a: %s",i,maxnames,"no index")
+ break
+ else
+ local length=readbyte(f)
+ if length>0 then
+ glyphs[mapping].name=readstring(f,length)
+ else
+ report("quit post name fetching at %a of %a: %s",i,maxnames,"overflow")
+ break
+ end
+ end
+ end
+ end
+ else
+ fontdata.postscript={}
+ end
+end
+readers.cff=function(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cff",specification.glyphs)
+end
+local formatreaders={}
+local duplicatestoo=true
+local sequence={
+ { 3,1,4 },
+ { 3,10,12 },
+ { 0,3,4 },
+ { 0,3,12 },
+ { 0,1,4 },
+ { 0,1,12 },
+ { 0,0,6 },
+ { 3,0,6 },
+ { 3,0,4 },
+ { 0,5,14 },
+ { 0,4,12 },
+ { 3,10,13 },
+}
+local supported={}
+for i=1,#sequence do
+ local si=sequence[i]
+ local sp,se,sf=si[1],si[2],si[3]
+ local p=supported[sp]
+ if not p then
+ p={}
+ supported[sp]=p
+ end
+ local e=p[se]
+ if not e then
+ e={}
+ p[se]=e
+ end
+ e[sf]=true
+end
+formatreaders[4]=function(f,fontdata,offset)
+ setposition(f,offset+2)
+ local length=readushort(f)
+ local language=readushort(f)
+ local nofsegments=readushort(f)/2
+ skipshort(f,3)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local nofdone=0
+ local endchars=readcardinaltable(f,nofsegments,ushort)
+ local reserved=readushort(f)
+ local startchars=readcardinaltable(f,nofsegments,ushort)
+ local deltas=readcardinaltable(f,nofsegments,ushort)
+ local offsets=readcardinaltable(f,nofsegments,ushort)
+ local size=(length-2*2-5*2-4*2*nofsegments)/2
+ local indices=readcardinaltable(f,size-1,ushort)
+ for segment=1,nofsegments do
+ local startchar=startchars[segment]
+ local endchar=endchars[segment]
+ local offset=offsets[segment]
+ local delta=deltas[segment]
+ if startchar==0xFFFF and endchar==0xFFFF then
+ elseif startchar==0xFFFF and offset==0 then
+ elseif offset==0xFFFF then
+ elseif offset==0 then
+ if trace_cmap_details then
+ report("format 4.%i segment %2i from %C upto %C at index %H",1,segment,startchar,endchar,(startchar+delta)%65536)
+ end
+ for unicode=startchar,endchar do
+ local index=(unicode+delta)%65536
+ if index and index>0 then
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ if duplicatestoo then
+ local d=duplicates[gu]
+ if d then
+ d[unicode]=true
+ else
+ duplicates[gu]={ [unicode]=true }
+ end
+ else
+ report("duplicate case 1: %C %04i %s",unicode,index,glyphs[index].name)
+ end
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ end
+ end
+ else
+ local shift=(segment-nofsegments+offset/2)-startchar
+ if trace_cmap_details then
+ report_cmap("format 4.%i segment %2i from %C upto %C at index %H",0,segment,startchar,endchar,(startchar+delta)%65536)
+ end
+ for unicode=startchar,endchar do
+ local slot=shift+unicode
+ local index=indices[slot]
+ if index and index>0 then
+ index=(index+delta)%65536
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ if duplicatestoo then
+ local d=duplicates[gu]
+ if d then
+ d[unicode]=true
+ else
+ duplicates[gu]={ [unicode]=true }
+ end
+ else
+ report("duplicate case 2: %C %04i %s",unicode,index,glyphs[index].name)
+ end
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ end
+ end
+ end
+ end
+ return nofdone
+end
+formatreaders[6]=function(f,fontdata,offset)
+ setposition(f,offset)
+ local format=readushort(f)
+ local length=readushort(f)
+ local language=readushort(f)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local start=readushort(f)
+ local count=readushort(f)
+ local stop=start+count-1
+ local nofdone=0
+ if trace_cmap_details then
+ report_cmap("format 6 from %C to %C",2,start,stop)
+ end
+ for unicode=start,stop do
+ local index=readushort(f)
+ if index>0 then
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ end
+ end
+ return nofdone
+end
+formatreaders[12]=function(f,fontdata,offset)
+ setposition(f,offset+2+2+4+4)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local nofgroups=readulong(f)
+ local nofdone=0
+ for i=1,nofgroups do
+ local first=readulong(f)
+ local last=readulong(f)
+ local index=readulong(f)
+ if trace_cmap_details then
+ report_cmap("format 12 from %C to %C starts at index %i",first,last,index)
+ end
+ for unicode=first,last do
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ local d=duplicates[gu]
+ if d then
+ d[unicode]=true
+ else
+ duplicates[gu]={ [unicode]=true }
+ end
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ index=index+1
+ end
+ end
+ return nofdone
+end
+formatreaders[13]=function(f,fontdata,offset)
+ setposition(f,offset+2+2+4+4)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local nofgroups=readulong(f)
+ local nofdone=0
+ for i=1,nofgroups do
+ local first=readulong(f)
+ local last=readulong(f)
+ local index=readulong(f)
+ if first<privateoffset then
+ if trace_cmap_details then
+ report_cmap("format 13 from %C to %C get index %i",first,last,index)
+ end
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=first
+ glyph.unicode=unicode
+ first=first+1
+ end
+ local list=duplicates[unicode]
+ mapping[index]=unicode
+ if not list then
+ list={}
+ duplicates[unicode]=list
+ end
+ if last>=privateoffset then
+ local limit=privateoffset-1
+ report("format 13 from %C to %C pruned to %C",first,last,limit)
+ last=limit
+ end
+ for unicode=first,last do
+ list[unicode]=true
+ end
+ nofdone=nofdone+last-first+1
+ else
+ report("format 13 from %C to %C ignored",first,last)
+ end
+ end
+ return nofdone
+end
+formatreaders[14]=function(f,fontdata,offset)
+ if offset and offset~=0 then
+ setposition(f,offset)
+ local format=readushort(f)
+ local length=readulong(f)
+ local nofrecords=readulong(f)
+ local records={}
+ local variants={}
+ local nofdone=0
+ fontdata.variants=variants
+ for i=1,nofrecords do
+ records[i]={
+ selector=readuint(f),
+ default=readulong(f),
+ other=readulong(f),
+ }
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ local selector=record.selector
+ local default=record.default
+ local other=record.other
+ local other=record.other
+ if other~=0 then
+ setposition(f,offset+other)
+ local mapping={}
+ local count=readulong(f)
+ for i=1,count do
+ mapping[readuint(f)]=readushort(f)
+ end
+ nofdone=nofdone+count
+ variants[selector]=mapping
+ end
+ end
+ return nofdone
+ else
+ return 0
+ end
+end
+local function checkcmap(f,fontdata,records,platform,encoding,format)
+ local pdata=records[platform]
+ if not pdata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no platform",platform,encoding,format)
+ end
+ return 0
+ end
+ local edata=pdata[encoding]
+ if not edata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no encoding",platform,encoding,format)
+ end
+ return 0
+ end
+ local fdata=edata[format]
+ if not fdata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no format",platform,encoding,format)
+ end
+ return 0
+ elseif type(fdata)~="number" then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","already done",platform,encoding,format)
+ end
+ return 0
+ end
+ edata[format]=true
+ local reader=formatreaders[format]
+ if not reader then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","unsupported format",platform,encoding,format)
+ end
+ return 0
+ end
+ local n=reader(f,fontdata,fdata) or 0
+ if trace_cmap_details or trace_cmap then
+ local p=platforms[platform]
+ local e=encodings[p]
+ report_cmap("checked, platform %i (%s), encoding %i (%s), format %i, new unicodes %i",
+ platform,p,encoding,e and e[encoding] or "?",format,n)
+ end
+ return n
+end
+function readers.cmap(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cmap",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local noftables=readushort(f)
+ local records={}
+ local unicodecid=false
+ local variantcid=false
+ local variants={}
+ local duplicates=fontdata.duplicates or {}
+ fontdata.duplicates=duplicates
+ for i=1,noftables do
+ local platform=readushort(f)
+ local encoding=readushort(f)
+ local offset=readulong(f)
+ local record=records[platform]
+ if not record then
+ records[platform]={
+ [encoding]={
+ offsets={ offset },
+ formats={},
+ }
+ }
+ else
+ local subtables=record[encoding]
+ if not subtables then
+ record[encoding]={
+ offsets={ offset },
+ formats={},
+ }
+ else
+ local offsets=subtables.offsets
+ offsets[#offsets+1]=offset
+ end
+ end
+ end
+ if trace_cmap then
+ report("found cmaps:")
+ end
+ for platform,record in sortedhash(records) do
+ local p=platforms[platform]
+ local e=encodings[p]
+ local sp=supported[platform]
+ local ps=p or "?"
+ if trace_cmap then
+ if sp then
+ report(" platform %i: %s",platform,ps)
+ else
+ report(" platform %i: %s (unsupported)",platform,ps)
+ end
+ end
+ for encoding,subtables in sortedhash(record) do
+ local se=sp and sp[encoding]
+ local es=e and e[encoding] or "?"
+ if trace_cmap then
+ if se then
+ report(" encoding %i: %s",encoding,es)
+ else
+ report(" encoding %i: %s (unsupported)",encoding,es)
+ end
+ end
+ local offsets=subtables.offsets
+ local formats=subtables.formats
+ for i=1,#offsets do
+ local offset=tableoffset+offsets[i]
+ setposition(f,offset)
+ formats[readushort(f)]=offset
+ end
+ record[encoding]=formats
+ if trace_cmap then
+ local list=sortedkeys(formats)
+ for i=1,#list do
+ if not (se and se[list[i]]) then
+ list[i]=list[i].." (unsupported)"
+ end
+ end
+ report(" formats: % t",list)
+ end
+ end
+ end
+ local ok=false
+ for i=1,#sequence do
+ local si=sequence[i]
+ local sp,se,sf=si[1],si[2],si[3]
+ if checkcmap(f,fontdata,records,sp,se,sf)>0 then
+ ok=true
+ end
+ end
+ if not ok then
+ report("no useable unicode cmap found")
+ end
+ fontdata.cidmaps={
+ version=version,
+ noftables=noftables,
+ records=records,
+ }
+ else
+ fontdata.cidmaps={}
+ end
+end
+function readers.loca(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"loca",specification.glyphs)
+end
+function readers.glyf(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"glyf",specification.glyphs)
+end
+function readers.colr(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"colr",specification.glyphs)
+end
+function readers.cpal(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cpal",specification.glyphs)
+end
+function readers.svg(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"svg",specification.glyphs)
+end
+function readers.sbix(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"sbix",specification.glyphs)
+end
+function readers.cbdt(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cbdt",specification.glyphs)
+end
+function readers.cblc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cblc",specification.glyphs)
+end
+function readers.ebdt(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"ebdt",specification.glyphs)
+end
+function readers.ebsc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"ebsc",specification.glyphs)
+end
+function readers.eblc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"eblc",specification.glyphs)
+end
+function readers.kern(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"kern",specification.kerns)
+ if tableoffset then
+ local version=readushort(f)
+ local noftables=readushort(f)
+ for i=1,noftables do
+ local version=readushort(f)
+ local length=readushort(f)
+ local coverage=readushort(f)
+ local format=rshift(coverage,8)
+ if format==0 then
+ local nofpairs=readushort(f)
+ local searchrange=readushort(f)
+ local entryselector=readushort(f)
+ local rangeshift=readushort(f)
+ local kerns={}
+ local glyphs=fontdata.glyphs
+ for i=1,nofpairs do
+ local left=readushort(f)
+ local right=readushort(f)
+ local kern=readfword(f)
+ local glyph=glyphs[left]
+ local kerns=glyph.kerns
+ if kerns then
+ kerns[right]=kern
+ else
+ glyph.kerns={ [right]=kern }
+ end
+ end
+ elseif format==2 then
+ report("todo: kern classes")
+ else
+ report("todo: kerns")
+ end
+ end
+ end
+end
+function readers.gdef(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gdef",specification.details)
+end
+function readers.gsub(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gsub",specification.details)
+end
+function readers.gpos(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gpos",specification.details)
+end
+function readers.math(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"math",specification.details)
+end
+local function getinfo(maindata,sub,platformnames,rawfamilynames,metricstoo,instancenames)
+ local fontdata=sub and maindata.subfonts and maindata.subfonts[sub] or maindata
+ local names=fontdata.names
+ local info=nil
+ if names then
+ local metrics=fontdata.windowsmetrics or {}
+ local postscript=fontdata.postscript or {}
+ local fontheader=fontdata.fontheader or {}
+ local cffinfo=fontdata.cffinfo or {}
+ local verticalheader=fontdata.verticalheader or {}
+ local filename=fontdata.filename
+ local weight=getname(fontdata,"weight") or (cffinfo and cffinfo.weight) or (metrics and metrics.weight)
+ local width=getname(fontdata,"width") or (cffinfo and cffinfo.width ) or (metrics and metrics.width )
+ local fontname=getname(fontdata,"postscriptname")
+ local fullname=getname(fontdata,"fullname")
+ local family=getname(fontdata,"family")
+ local subfamily=getname(fontdata,"subfamily")
+ local familyname=getname(fontdata,"typographicfamily")
+ local subfamilyname=getname(fontdata,"typographicsubfamily")
+ local compatiblename=getname(fontdata,"compatiblefullname")
+ if rawfamilynames then
+ else
+ if not familyname then familyname=family end
+ if not subfamilyname then subfamilyname=subfamily end
+ end
+ if platformnames then
+ platformnames=fontdata.platformnames
+ end
+ if instancenames then
+ local variabledata=fontdata.variabledata
+ if variabledata then
+ local instances=variabledata and variabledata.instances
+ if instances then
+ instancenames={}
+ for i=1,#instances do
+ instancenames[i]=lower(stripstring(instances[i].subfamily))
+ end
+ else
+ instancenames=nil
+ end
+ else
+ instancenames=nil
+ end
+ end
+ info={
+ subfontindex=fontdata.subfontindex or sub or 0,
+ version=getname(fontdata,"version"),
+ fontname=fontname,
+ fullname=fullname,
+ family=family,
+ subfamily=subfamily,
+ familyname=familyname,
+ subfamilyname=subfamilyname,
+ compatiblename=compatiblename,
+ weight=weight and lower(weight),
+ width=width and lower(width),
+ pfmweight=metrics.weightclass or 400,
+ pfmwidth=metrics.widthclass or 5,
+ panosewidth=metrics.panosewidth,
+ panoseweight=metrics.panoseweight,
+ italicangle=postscript.italicangle or 0,
+ units=fontheader.units or 0,
+ designsize=fontdata.designsize,
+ minsize=fontdata.minsize,
+ maxsize=fontdata.maxsize,
+ boundingbox=fontheader and { fontheader.xmin or 0,fontheader.ymin or 0,fontheader.xmax or 0,fontheader.ymax or 0 } or nil,
+ monospaced=(tonumber(postscript.monospaced or 0)>0) or metrics.panosewidth=="monospaced",
+ averagewidth=metrics.averagewidth,
+ xheight=metrics.xheight,
+ capheight=metrics.capheight or fontdata.maxy,
+ ascender=metrics.typoascender,
+ descender=metrics.typodescender,
+ platformnames=platformnames or nil,
+ instancenames=instancenames or nil,
+ tableoffsets=fontdata.tableoffsets,
+ defaultvheight=(verticalheader.ascender or 0)-(verticalheader.descender or 0)
+ }
+ if metricstoo then
+ local keys={
+ "version",
+ "ascender","descender","linegap",
+ "maxadvancewidth","maxadvanceheight","maxextent",
+ "minbottomsidebearing","mintopsidebearing",
+ }
+ local h=fontdata.horizontalheader or {}
+ local v=fontdata.verticalheader or {}
+ if h then
+ local th={}
+ local tv={}
+ for i=1,#keys do
+ local key=keys[i]
+ th[key]=h[key] or 0
+ tv[key]=v[key] or 0
+ end
+ info.horizontalmetrics=th
+ info.verticalmetrics=tv
+ end
+ end
+ elseif n then
+ info={
+ filename=fontdata.filename,
+ comment="there is no info for subfont "..n,
+ }
+ else
+ info={
+ filename=fontdata.filename,
+ comment="there is no info",
+ }
+ end
+ return info
+end
+local function loadtables(f,specification,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ local tables={}
+ local basename=file.basename(specification.filename)
+ local filesize=specification.filesize
+ local filetime=specification.filetime
+ local fontdata={
+ filename=basename,
+ filesize=filesize,
+ filetime=filetime,
+ version=readstring(f,4),
+ noftables=readushort(f),
+ searchrange=readushort(f),
+ entryselector=readushort(f),
+ rangeshift=readushort(f),
+ tables=tables,
+ foundtables=false,
+ }
+ for i=1,fontdata.noftables do
+ local tag=lower(stripstring(readstring(f,4)))
+ local checksum=readushort(f)*0x10000+readushort(f)
+ local offset=readulong(f)
+ local length=readulong(f)
+ if offset+length>filesize then
+ report("bad %a table in file %a",tag,basename)
+ end
+ tables[tag]={
+ checksum=checksum,
+ offset=offset,
+ length=length,
+ }
+ end
+ fontdata.foundtables=sortedkeys(tables)
+ if tables.cff or tables.cff2 then
+ fontdata.format="opentype"
+ else
+ fontdata.format="truetype"
+ end
+ return fontdata,tables
+end
+local function prepareglyps(fontdata)
+ local glyphs=setmetatableindex(function(t,k)
+ local v={
+ index=k,
+ }
+ t[k]=v
+ return v
+ end)
+ fontdata.glyphs=glyphs
+ fontdata.mapping={}
+end
+local function readtable(tag,f,fontdata,specification,...)
+ local reader=readers[tag]
+ if reader then
+ reader(f,fontdata,specification,...)
+ end
+end
+local variablefonts_supported=(context and true) or (logs and logs.application and true) or false
+local function readdata(f,offset,specification)
+ local fontdata,tables=loadtables(f,specification,offset)
+ if specification.glyphs then
+ prepareglyps(fontdata)
+ end
+ if not variablefonts_supported then
+ specification.instance=nil
+ specification.variable=nil
+ specification.factors=nil
+ end
+ fontdata.temporary={}
+ readtable("name",f,fontdata,specification)
+ local askedname=specification.askedname
+ if askedname then
+ local fullname=getname(fontdata,"fullname") or ""
+ local cleanname=gsub(askedname,"[^a-zA-Z0-9]","")
+ local foundname=gsub(fullname,"[^a-zA-Z0-9]","")
+ if lower(cleanname)~=lower(foundname) then
+ return
+ end
+ end
+ readtable("stat",f,fontdata,specification)
+ readtable("avar",f,fontdata,specification)
+ readtable("fvar",f,fontdata,specification)
+ if variablefonts_supported then
+ local variabledata=fontdata.variabledata
+ if variabledata then
+ local instances=variabledata.instances
+ local axis=variabledata.axis
+ if axis and (not instances or #instances==0) then
+ instances={}
+ variabledata.instances=instances
+ local function add(n,subfamily,value)
+ local values={}
+ for i=1,#axis do
+ local a=axis[i]
+ values[i]={
+ axis=a.tag,
+ value=i==n and value or a.default,
+ }
+ end
+ instances[#instances+1]={
+ subfamily=subfamily,
+ values=values,
+ }
+ end
+ for i=1,#axis do
+ local a=axis[i]
+ local tag=a.tag
+ add(i,"default"..tag,a.default)
+ add(i,"minimum"..tag,a.minimum)
+ add(i,"maximum"..tag,a.maximum)
+ end
+ end
+ end
+ if not specification.factors then
+ local instance=specification.instance
+ if type(instance)=="string" then
+ local factors=helpers.getfactors(fontdata,instance)
+ if factors then
+ specification.factors=factors
+ fontdata.factors=factors
+ fontdata.instance=instance
+ report("user instance: %s, factors: % t",instance,factors)
+ else
+ report("user instance: %s, bad factors",instance)
+ end
+ end
+ end
+ if not fontdata.factors then
+ if fontdata.variabledata then
+ local factors=helpers.getfactors(fontdata,true)
+ if factors then
+ specification.factors=factors
+ fontdata.factors=factors
+ end
+ else
+ end
+ end
+ end
+ readtable("os/2",f,fontdata,specification)
+ readtable("head",f,fontdata,specification)
+ readtable("maxp",f,fontdata,specification)
+ readtable("hhea",f,fontdata,specification)
+ readtable("vhea",f,fontdata,specification)
+ readtable("hmtx",f,fontdata,specification)
+ readtable("vmtx",f,fontdata,specification)
+ readtable("vorg",f,fontdata,specification)
+ readtable("post",f,fontdata,specification)
+ readtable("mvar",f,fontdata,specification)
+ readtable("hvar",f,fontdata,specification)
+ readtable("vvar",f,fontdata,specification)
+ readtable("gdef",f,fontdata,specification)
+ readtable("cff",f,fontdata,specification)
+ readtable("cff2",f,fontdata,specification)
+ readtable("cmap",f,fontdata,specification)
+ readtable("loca",f,fontdata,specification)
+ readtable("glyf",f,fontdata,specification)
+ readtable("colr",f,fontdata,specification)
+ readtable("cpal",f,fontdata,specification)
+ readtable("svg",f,fontdata,specification)
+ readtable("sbix",f,fontdata,specification)
+ readtable("cbdt",f,fontdata,specification)
+ readtable("cblc",f,fontdata,specification)
+ readtable("ebdt",f,fontdata,specification)
+ readtable("eblc",f,fontdata,specification)
+ readtable("kern",f,fontdata,specification)
+ readtable("gsub",f,fontdata,specification)
+ readtable("gpos",f,fontdata,specification)
+ readtable("math",f,fontdata,specification)
+ fontdata.locations=nil
+ fontdata.cidmaps=nil
+ fontdata.dictionaries=nil
+ if specification.tableoffsets then
+ fontdata.tableoffsets=tables
+ setmetatableindex(tables,{
+ version=fontdata.version,
+ noftables=fontdata.noftables,
+ searchrange=fontdata.searchrange,
+ entryselector=fontdata.entryselector,
+ rangeshift=fontdata.rangeshift,
+ })
+ end
+ return fontdata
+end
+local function loadfontdata(specification)
+ local filename=specification.filename
+ local fileattr=lfs.attributes(filename)
+ local filesize=fileattr and fileattr.size or 0
+ local filetime=fileattr and fileattr.modification or 0
+ local f=openfile(filename,true)
+ if not f then
+ report("unable to open %a",filename)
+ elseif filesize==0 then
+ report("empty file %a",filename)
+ closefile(f)
+ else
+ specification.filesize=filesize
+ specification.filetime=filetime
+ local version=readstring(f,4)
+ local fontdata=nil
+ if version=="OTTO" or version=="true" or version=="\0\1\0\0" then
+ fontdata=readdata(f,0,specification)
+ elseif version=="ttcf" then
+ local subfont=tonumber(specification.subfont)
+ local ttcversion=readulong(f)
+ local nofsubfonts=readulong(f)
+ local offsets=readcardinaltable(f,nofsubfonts,ulong)
+ if subfont then
+ if subfont>=1 and subfont<=nofsubfonts then
+ fontdata=readdata(f,offsets[subfont],specification)
+ else
+ report("no subfont %a in file %a",subfont,filename)
+ end
+ else
+ subfont=specification.subfont
+ if type(subfont)=="string" and subfont~="" then
+ specification.askedname=subfont
+ for i=1,nofsubfonts do
+ fontdata=readdata(f,offsets[i],specification)
+ if fontdata then
+ fontdata.subfontindex=i
+ report("subfont named %a has index %a",subfont,i)
+ break
+ end
+ end
+ if not fontdata then
+ report("no subfont named %a",subfont)
+ end
+ else
+ local subfonts={}
+ fontdata={
+ filename=filename,
+ filesize=filesize,
+ filetime=filetime,
+ version=version,
+ subfonts=subfonts,
+ ttcversion=ttcversion,
+ nofsubfonts=nofsubfonts,
+ }
+ for i=1,nofsubfonts do
+ subfonts[i]=readdata(f,offsets[i],specification)
+ end
+ end
+ end
+ else
+ report("unknown version %a in file %a",version,filename)
+ end
+ closefile(f)
+ return fontdata or {}
+ end
+end
+local function loadfont(specification,n,instance)
+ if type(specification)=="string" then
+ specification={
+ filename=specification,
+ info=true,
+ details=true,
+ glyphs=true,
+ shapes=true,
+ kerns=true,
+ variable=true,
+ globalkerns=true,
+ lookups=true,
+ subfont=n or true,
+ tounicode=false,
+ instance=instance
+ }
+ end
+ if specification.shapes or specification.lookups or specification.kerns then
+ specification.glyphs=true
+ end
+ if specification.glyphs then
+ specification.details=true
+ end
+ if specification.details then
+ specification.info=true
+ end
+ if specification.platformnames then
+ specification.platformnames=true
+ end
+ if specification.instance or instance then
+ specification.variable=true
+ specification.instance=specification.instance or instance
+ end
+ local function message(str)
+ report("fatal error in file %a: %s\n%s",specification.filename,str,debug and debug.traceback())
+ end
+ local ok,result=xpcall(loadfontdata,message,specification)
+ if ok then
+ return result
+ end
+end
+function readers.loadshapes(filename,n,instance,streams)
+ local fontdata=loadfont {
+ filename=filename,
+ shapes=true,
+ streams=streams,
+ variable=true,
+ subfont=n,
+ instance=instance,
+ }
+ if fontdata then
+ for k,v in next,fontdata.glyphs do
+ v.class=nil
+ v.index=nil
+ v.math=nil
+ end
+ local names=fontdata.names
+ if names then
+ for k,v in next,names do
+ names[k]=fullstrip(v.content)
+ end
+ end
+ end
+ return fontdata and {
+ filename=filename,
+ format=fontdata.format,
+ glyphs=fontdata.glyphs,
+ units=fontdata.fontheader.units,
+ cffinfo=fontdata.cffinfo,
+ fontheader=fontdata.fontheader,
+ horizontalheader=fontdata.horizontalheader,
+ verticalheader=fontdata.verticalheader,
+ maximumprofile=fontdata.maximumprofile,
+ names=fontdata.names,
+ postscript=fontdata.postscript,
+ } or {
+ filename=filename,
+ format="unknown",
+ glyphs={},
+ units=0,
+ }
+end
+function readers.loadfont(filename,n,instance)
+ local fontdata=loadfont {
+ filename=filename,
+ glyphs=true,
+ shapes=false,
+ lookups=true,
+ variable=true,
+ subfont=n,
+ instance=instance,
+ }
+ if fontdata then
+ return {
+ tableversion=tableversion,
+ creator="context mkiv",
+ size=fontdata.filesize,
+ time=fontdata.filetime,
+ glyphs=fontdata.glyphs,
+ descriptions=fontdata.descriptions,
+ format=fontdata.format,
+ goodies={},
+ metadata=getinfo(fontdata,n,false,false,true,true),
+ properties={
+ hasitalics=fontdata.hasitalics or false,
+ maxcolorclass=fontdata.maxcolorclass,
+ hascolor=fontdata.hascolor or false,
+ instance=fontdata.instance,
+ factors=fontdata.factors,
+ },
+ resources={
+ filename=filename,
+ private=privateoffset,
+ duplicates=fontdata.duplicates or {},
+ features=fontdata.features or {},
+ sublookups=fontdata.sublookups or {},
+ marks=fontdata.marks or {},
+ markclasses=fontdata.markclasses or {},
+ marksets=fontdata.marksets or {},
+ sequences=fontdata.sequences or {},
+ variants=fontdata.variants,
+ version=getname(fontdata,"version"),
+ cidinfo=fontdata.cidinfo,
+ mathconstants=fontdata.mathconstants,
+ colorpalettes=fontdata.colorpalettes,
+ svgshapes=fontdata.svgshapes,
+ pngshapes=fontdata.pngshapes,
+ variabledata=fontdata.variabledata,
+ foundtables=fontdata.foundtables,
+ },
+ }
+ end
+end
+function readers.getinfo(filename,specification)
+ local subfont=nil
+ local platformnames=false
+ local rawfamilynames=false
+ local instancenames=true
+ local tableoffsets=false
+ if type(specification)=="table" then
+ subfont=tonumber(specification.subfont)
+ platformnames=specification.platformnames
+ rawfamilynames=specification.rawfamilynames
+ tableoffsets=specification.tableoffsets
+ else
+ subfont=tonumber(specification)
+ end
+ local fontdata=loadfont {
+ filename=filename,
+ details=true,
+ platformnames=platformnames,
+ instancenames=true,
+ tableoffsets=tableoffsets,
+ }
+ if fontdata then
+ local subfonts=fontdata.subfonts
+ if not subfonts then
+ return getinfo(fontdata,nil,platformnames,rawfamilynames,false,instancenames)
+ elseif not subfont then
+ local info={}
+ for i=1,#subfonts do
+ info[i]=getinfo(fontdata,i,platformnames,rawfamilynames,false,instancenames)
+ end
+ return info
+ elseif subfont>=1 and subfont<=#subfonts then
+ return getinfo(fontdata,subfont,platformnames,rawfamilynames,false,instancenames)
+ else
+ return {
+ filename=filename,
+ comment="there is no subfont "..subfont.." in this file"
+ }
+ end
+ else
+ return {
+ filename=filename,
+ comment="the file cannot be opened for reading",
+ }
+ end
+end
+function readers.rehash(fontdata,hashmethod)
+ report("the %a helper is not yet implemented","rehash")
+end
+function readers.checkhash(fontdata)
+ report("the %a helper is not yet implemented","checkhash")
+end
+function readers.pack(fontdata,hashmethod)
+ report("the %a helper is not yet implemented","pack")
+end
+function readers.unpack(fontdata)
+ report("the %a helper is not yet implemented","unpack")
+end
+function readers.expand(fontdata)
+ report("the %a helper is not yet implemented","unpack")
+end
+function readers.compact(fontdata)
+ report("the %a helper is not yet implemented","compact")
+end
+local extenders={}
+function readers.registerextender(extender)
+ extenders[#extenders+1]=extender
+end
+function readers.extend(fontdata)
+ for i=1,#extenders do
+ local extender=extenders[i]
+ local name=extender.name or "unknown"
+ local action=extender.action
+ if action then
+ action(fontdata)
+ end
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otr”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-oti” dbae7722baae24d917a17176553825cf] ---
+
+if not modules then modules={} end modules ['font-oti']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local lower=string.lower
+local fonts=fonts
+local constructors=fonts.constructors
+local otf=constructors.handlers.otf
+local otffeatures=constructors.features.otf
+local registerotffeature=otffeatures.register
+local otftables=otf.tables or {}
+otf.tables=otftables
+local allocate=utilities.storage.allocate
+registerotffeature {
+ name="features",
+ description="initialization of feature handler",
+ default=true,
+}
+local function setmode(tfmdata,value)
+ if value then
+ tfmdata.properties.mode=lower(value)
+ end
+end
+otf.modeinitializer=setmode
+local function setlanguage(tfmdata,value)
+ if value then
+ local cleanvalue=lower(value)
+ local languages=otftables and otftables.languages
+ local properties=tfmdata.properties
+ if not languages then
+ properties.language=cleanvalue
+ elseif languages[value] then
+ properties.language=cleanvalue
+ else
+ properties.language="dflt"
+ end
+ end
+end
+local function setscript(tfmdata,value)
+ if value then
+ local cleanvalue=lower(value)
+ local scripts=otftables and otftables.scripts
+ local properties=tfmdata.properties
+ if not scripts then
+ properties.script=cleanvalue
+ elseif scripts[value] then
+ properties.script=cleanvalue
+ else
+ properties.script="dflt"
+ end
+ end
+end
+registerotffeature {
+ name="mode",
+ description="mode",
+ initializers={
+ base=setmode,
+ node=setmode,
+ plug=setmode,
+ }
+}
+registerotffeature {
+ name="language",
+ description="language",
+ initializers={
+ base=setlanguage,
+ node=setlanguage,
+ plug=setlanguage,
+ }
+}
+registerotffeature {
+ name="script",
+ description="script",
+ initializers={
+ base=setscript,
+ node=setscript,
+ plug=setscript,
+ }
+}
+otftables.featuretypes=allocate {
+ gpos_single="position",
+ gpos_pair="position",
+ gpos_cursive="position",
+ gpos_mark2base="position",
+ gpos_mark2ligature="position",
+ gpos_mark2mark="position",
+ gpos_context="position",
+ gpos_contextchain="position",
+ gsub_single="substitution",
+ gsub_multiple="substitution",
+ gsub_alternate="substitution",
+ gsub_ligature="substitution",
+ gsub_context="substitution",
+ gsub_contextchain="substitution",
+ gsub_reversecontextchain="substitution",
+ gsub_reversesub="substitution",
+}
+function otffeatures.checkeddefaultscript(featuretype,autoscript,scripts)
+ if featuretype=="position" then
+ local default=scripts.dflt
+ if default then
+ if autoscript=="position" or autoscript==true then
+ return default
+ else
+ report_otf("script feature %s not applied, enable default positioning")
+ end
+ else
+ end
+ elseif featuretype=="substitution" then
+ local default=scripts.dflt
+ if default then
+ if autoscript=="substitution" or autoscript==true then
+ return default
+ end
+ end
+ end
+end
+function otffeatures.checkeddefaultlanguage(featuretype,autolanguage,languages)
+ if featuretype=="position" then
+ local default=languages.dflt
+ if default then
+ if autolanguage=="position" or autolanguage==true then
+ return default
+ else
+ report_otf("language feature %s not applied, enable default positioning")
+ end
+ else
+ end
+ elseif featuretype=="substitution" then
+ local default=languages.dflt
+ if default then
+ if autolanguage=="substitution" or autolanguage==true then
+ return default
+ end
+ end
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-oti”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ott” aba6d8335a5f38a5a62d3631492f3392] ---
+
+if not modules then modules={} end modules ["font-ott"]={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+local type,next,tonumber,tostring,rawget,rawset=type,next,tonumber,tostring,rawget,rawset
+local gsub,lower,format,match,gmatch,find=string.gsub,string.lower,string.format,string.match,string.gmatch,string.find
+local sequenced=table.sequenced
+local is_boolean=string.is_boolean
+local setmetatableindex=table.setmetatableindex
+local setmetatablenewindex=table.setmetatablenewindex
+local allocate=utilities.storage.allocate
+local fonts=fonts
+local otf=fonts.handlers.otf
+local otffeatures=otf.features
+local tables=otf.tables or {}
+otf.tables=tables
+local statistics=otf.statistics or {}
+otf.statistics=statistics
+local scripts=allocate {
+ ["adlm"]="adlam",
+ ["aghb"]="caucasian albanian",
+ ["ahom"]="ahom",
+ ["arab"]="arabic",
+ ["armi"]="imperial aramaic",
+ ["armn"]="armenian",
+ ["avst"]="avestan",
+ ["bali"]="balinese",
+ ["bamu"]="bamum",
+ ["bass"]="bassa vah",
+ ["batk"]="batak",
+ ["beng"]="bengali",
+ ["bhks"]="bhaiksuki",
+ ["bng2"]="bengali variant 2",
+ ["bopo"]="bopomofo",
+ ["brah"]="brahmi",
+ ["brai"]="braille",
+ ["bugi"]="buginese",
+ ["buhd"]="buhid",
+ ["byzm"]="byzantine music",
+ ["cakm"]="chakma",
+ ["cans"]="canadian syllabics",
+ ["cari"]="carian",
+ ["cham"]="cham",
+ ["cher"]="cherokee",
+ ["copt"]="coptic",
+ ["cprt"]="cypriot syllabary",
+ ["cyrl"]="cyrillic",
+ ["dev2"]="devanagari variant 2",
+ ["deva"]="devanagari",
+ ["dogr"]="dogra",
+ ["dsrt"]="deseret",
+ ["dupl"]="duployan",
+ ["egyp"]="egyptian heiroglyphs",
+ ["elba"]="elbasan",
+ ["ethi"]="ethiopic",
+ ["geor"]="georgian",
+ ["gjr2"]="gujarati variant 2",
+ ["glag"]="glagolitic",
+ ["gong"]="gunjala gondi",
+ ["gonm"]="masaram gondi",
+ ["goth"]="gothic",
+ ["gran"]="grantha",
+ ["grek"]="greek",
+ ["gujr"]="gujarati",
+ ["gur2"]="gurmukhi variant 2",
+ ["guru"]="gurmukhi",
+ ["hang"]="hangul",
+ ["hani"]="cjk ideographic",
+ ["hano"]="hanunoo",
+ ["hatr"]="hatran",
+ ["hebr"]="hebrew",
+ ["hluw"]="anatolian hieroglyphs",
+ ["hmng"]="pahawh hmong",
+ ["hung"]="old hungarian",
+ ["ital"]="old italic",
+ ["jamo"]="hangul jamo",
+ ["java"]="javanese",
+ ["kali"]="kayah li",
+ ["kana"]="hiragana and katakana",
+ ["khar"]="kharosthi",
+ ["khmr"]="khmer",
+ ["khoj"]="khojki",
+ ["knd2"]="kannada variant 2",
+ ["knda"]="kannada",
+ ["kthi"]="kaithi",
+ ["lana"]="tai tham",
+ ["lao" ]="lao",
+ ["latn"]="latin",
+ ["lepc"]="lepcha",
+ ["limb"]="limbu",
+ ["lina"]="linear a",
+ ["linb"]="linear b",
+ ["lisu"]="lisu",
+ ["lyci"]="lycian",
+ ["lydi"]="lydian",
+ ["mahj"]="mahajani",
+ ["maka"]="makasar",
+ ["mand"]="mandaic and mandaean",
+ ["mani"]="manichaean",
+ ["marc"]="marchen",
+ ["math"]="mathematical alphanumeric symbols",
+ ["medf"]="medefaidrin",
+ ["mend"]="mende kikakui",
+ ["merc"]="meroitic cursive",
+ ["mero"]="meroitic hieroglyphs",
+ ["mlm2"]="malayalam variant 2",
+ ["mlym"]="malayalam",
+ ["modi"]="modi",
+ ["mong"]="mongolian",
+ ["mroo"]="mro",
+ ["mtei"]="meitei Mayek",
+ ["mult"]="multani",
+ ["musc"]="musical symbols",
+ ["mym2"]="myanmar variant 2",
+ ["mymr"]="myanmar",
+ ["narb"]="old north arabian",
+ ["nbat"]="nabataean",
+ ["newa"]="newa",
+ ["nko" ]='n"ko',
+ ["nshu"]="nüshu",
+ ["ogam"]="ogham",
+ ["olck"]="ol chiki",
+ ["orkh"]="old turkic and orkhon runic",
+ ["ory2"]="odia variant 2",
+ ["orya"]="oriya",
+ ["osge"]="osage",
+ ["osma"]="osmanya",
+ ["palm"]="palmyrene",
+ ["pauc"]="pau cin hau",
+ ["perm"]="old permic",
+ ["phag"]="phags-pa",
+ ["phli"]="inscriptional pahlavi",
+ ["phlp"]="psalter pahlavi",
+ ["phnx"]="phoenician",
+ ["plrd"]="miao",
+ ["prti"]="inscriptional parthian",
+ ["rjng"]="rejang",
+ ["rohg"]="hanifi rohingya",
+ ["runr"]="runic",
+ ["samr"]="samaritan",
+ ["sarb"]="old south arabian",
+ ["saur"]="saurashtra",
+ ["sgnw"]="sign writing",
+ ["shaw"]="shavian",
+ ["shrd"]="sharada",
+ ["sidd"]="siddham",
+ ["sind"]="khudawadi",
+ ["sinh"]="sinhala",
+ ["sogd"]="sogdian",
+ ["sogo"]="old sogdian",
+ ["sora"]="sora sompeng",
+ ["soyo"]="soyombo",
+ ["sund"]="sundanese",
+ ["sylo"]="syloti nagri",
+ ["syrc"]="syriac",
+ ["tagb"]="tagbanwa",
+ ["takr"]="takri",
+ ["tale"]="tai le",
+ ["talu"]="tai lu",
+ ["taml"]="tamil",
+ ["tang"]="tangut",
+ ["tavt"]="tai viet",
+ ["tel2"]="telugu variant 2",
+ ["telu"]="telugu",
+ ["tfng"]="tifinagh",
+ ["tglg"]="tagalog",
+ ["thaa"]="thaana",
+ ["thai"]="thai",
+ ["tibt"]="tibetan",
+ ["tirh"]="tirhuta",
+ ["tml2"]="tamil variant 2",
+ ["ugar"]="ugaritic cuneiform",
+ ["vai" ]="vai",
+ ["wara"]="warang citi",
+ ["xpeo"]="old persian cuneiform",
+ ["xsux"]="sumero-akkadian cuneiform",
+ ["yi" ]="yi",
+ ["zanb"]="zanabazar square",
+}
+local languages=allocate {
+ ["aba" ]="abaza",
+ ["abk" ]="abkhazian",
+ ["ach" ]="acholi",
+ ["acr" ]="achi",
+ ["ady" ]="adyghe",
+ ["afk" ]="afrikaans",
+ ["afr" ]="afar",
+ ["agw" ]="agaw",
+ ["aio" ]="aiton",
+ ["aka" ]="akan",
+ ["als" ]="alsatian",
+ ["alt" ]="altai",
+ ["amh" ]="amharic",
+ ["ang" ]="anglo-saxon",
+ ["apph"]="phonetic transcription—americanist conventions",
+ ["ara" ]="arabic",
+ ["arg" ]="aragonese",
+ ["ari" ]="aari",
+ ["ark" ]="rakhine",
+ ["asm" ]="assamese",
+ ["ast" ]="asturian",
+ ["ath" ]="athapaskan",
+ ["avr" ]="avar",
+ ["awa" ]="awadhi",
+ ["aym" ]="aymara",
+ ["azb" ]="torki",
+ ["aze" ]="azerbaijani",
+ ["bad" ]="badaga",
+ ["bad0"]="banda",
+ ["bag" ]="baghelkhandi",
+ ["bal" ]="balkar",
+ ["ban" ]="balinese",
+ ["bar" ]="bavarian",
+ ["bau" ]="baulé",
+ ["bbc" ]="batak toba",
+ ["bbr" ]="berber",
+ ["bch" ]="bench",
+ ["bcr" ]="bible cree",
+ ["bdy" ]="bandjalang",
+ ["bel" ]="belarussian",
+ ["bem" ]="bemba",
+ ["ben" ]="bengali",
+ ["bgc" ]="haryanvi",
+ ["bgq" ]="bagri",
+ ["bgr" ]="bulgarian",
+ ["bhi" ]="bhili",
+ ["bho" ]="bhojpuri",
+ ["bik" ]="bikol",
+ ["bil" ]="bilen",
+ ["bis" ]="bislama",
+ ["bjj" ]="kanauji",
+ ["bkf" ]="blackfoot",
+ ["bli" ]="baluchi",
+ ["blk" ]="pa'o karen",
+ ["bln" ]="balante",
+ ["blt" ]="balti",
+ ["bmb" ]="bambara (bamanankan)",
+ ["bml" ]="bamileke",
+ ["bos" ]="bosnian",
+ ["bpy" ]="bishnupriya manipuri",
+ ["bre" ]="breton",
+ ["brh" ]="brahui",
+ ["bri" ]="braj bhasha",
+ ["brm" ]="burmese",
+ ["brx" ]="bodo",
+ ["bsh" ]="bashkir",
+ ["bsk" ]="burushaski",
+ ["bti" ]="beti",
+ ["bts" ]="batak simalungun",
+ ["bug" ]="bugis",
+ ["byv" ]="medumba",
+ ["cak" ]="kaqchikel",
+ ["cat" ]="catalan",
+ ["cbk" ]="zamboanga chavacano",
+ ["cchn"]="chinantec",
+ ["ceb" ]="cebuano",
+ ["cgg" ]="chiga",
+ ["cha" ]="chamorro",
+ ["che" ]="chechen",
+ ["chg" ]="chaha gurage",
+ ["chh" ]="chattisgarhi",
+ ["chi" ]="chichewa (chewa, nyanja)",
+ ["chk" ]="chukchi",
+ ["chk0"]="chuukese",
+ ["cho" ]="choctaw",
+ ["chp" ]="chipewyan",
+ ["chr" ]="cherokee",
+ ["chu" ]="chuvash",
+ ["chy" ]="cheyenne",
+ ["cja" ]="western cham",
+ ["cjm" ]="eastern cham",
+ ["cmr" ]="comorian",
+ ["cop" ]="coptic",
+ ["cor" ]="cornish",
+ ["cos" ]="corsican",
+ ["cpp" ]="creoles",
+ ["cre" ]="cree",
+ ["crr" ]="carrier",
+ ["crt" ]="crimean tatar",
+ ["csb" ]="kashubian",
+ ["csl" ]="church slavonic",
+ ["csy" ]="czech",
+ ["ctg" ]="chittagonian",
+ ["cuk" ]="san blas kuna",
+ ["dan" ]="danish",
+ ["dar" ]="dargwa",
+ ["dax" ]="dayi",
+ ["dcr" ]="woods cree",
+ ["deu" ]="german",
+ ["dgo" ]="dogri",
+ ["dgr" ]="dogri",
+ ["dhg" ]="dhangu",
+ ["dhv" ]="divehi (dhivehi, maldivian)",
+ ["diq" ]="dimli",
+ ["div" ]="divehi (dhivehi, maldivian)",
+ ["djr" ]="zarma",
+ ["djr0"]="djambarrpuyngu",
+ ["dng" ]="dangme",
+ ["dnj" ]="dan",
+ ["dnk" ]="dinka",
+ ["dri" ]="dari",
+ ["duj" ]="dhuwal",
+ ["dun" ]="dungan",
+ ["dzn" ]="dzongkha",
+ ["ebi" ]="ebira",
+ ["ecr" ]="eastern cree",
+ ["edo" ]="edo",
+ ["efi" ]="efik",
+ ["ell" ]="greek",
+ ["emk" ]="eastern maninkakan",
+ ["eng" ]="english",
+ ["erz" ]="erzya",
+ ["esp" ]="spanish",
+ ["esu" ]="central yupik",
+ ["eti" ]="estonian",
+ ["euq" ]="basque",
+ ["evk" ]="evenki",
+ ["evn" ]="even",
+ ["ewe" ]="ewe",
+ ["fan" ]="french antillean",
+ ["fan0"]=" fang",
+ ["far" ]="persian",
+ ["fat" ]="fanti",
+ ["fin" ]="finnish",
+ ["fji" ]="fijian",
+ ["fle" ]="dutch (flemish)",
+ ["fmp" ]="fe’fe’",
+ ["fne" ]="forest nenets",
+ ["fon" ]="fon",
+ ["fos" ]="faroese",
+ ["fra" ]="french",
+ ["frc" ]="cajun french",
+ ["fri" ]="frisian",
+ ["frl" ]="friulian",
+ ["frp" ]="arpitan",
+ ["fta" ]="futa",
+ ["ful" ]="fulah",
+ ["fuv" ]="nigerian fulfulde",
+ ["gad" ]="ga",
+ ["gae" ]="scottish gaelic (gaelic)",
+ ["gag" ]="gagauz",
+ ["gal" ]="galician",
+ ["gar" ]="garshuni",
+ ["gaw" ]="garhwali",
+ ["gez" ]="ge'ez",
+ ["gih" ]="githabul",
+ ["gil" ]="gilyak",
+ ["gil0"]="kiribati (gilbertese)",
+ ["gkp" ]="kpelle (guinea)",
+ ["glk" ]="gilaki",
+ ["gmz" ]="gumuz",
+ ["gnn" ]="gumatj",
+ ["gog" ]="gogo",
+ ["gon" ]="gondi",
+ ["grn" ]="greenlandic",
+ ["gro" ]="garo",
+ ["gua" ]="guarani",
+ ["guc" ]="wayuu",
+ ["guf" ]="gupapuyngu",
+ ["guj" ]="gujarati",
+ ["guz" ]="gusii",
+ ["hai" ]="haitian (haitian creole)",
+ ["hal" ]="halam",
+ ["har" ]="harauti",
+ ["hau" ]="hausa",
+ ["haw" ]="hawaiian",
+ ["hay" ]="haya",
+ ["haz" ]="hazaragi",
+ ["hbn" ]="hammer-banna",
+ ["her" ]="herero",
+ ["hil" ]="hiligaynon",
+ ["hin" ]="hindi",
+ ["hma" ]="high mari",
+ ["hmn" ]="hmong",
+ ["hmo" ]="hiri motu",
+ ["hnd" ]="hindko",
+ ["ho" ]="ho",
+ ["hri" ]="harari",
+ ["hrv" ]="croatian",
+ ["hun" ]="hungarian",
+ ["hye" ]="armenian",
+ ["hye0"]="armenian east",
+ ["iba" ]="iban",
+ ["ibb" ]="ibibio",
+ ["ibo" ]="igbo",
+ ["ido" ]="ido",
+ ["ijo" ]="ijo languages",
+ ["ile" ]="interlingue",
+ ["ilo" ]="ilokano",
+ ["ina" ]="interlingua",
+ ["ind" ]="indonesian",
+ ["ing" ]="ingush",
+ ["inu" ]="inuktitut",
+ ["ipk" ]="inupiat",
+ ["ipph"]="phonetic transcription—ipa conventions",
+ ["iri" ]="irish",
+ ["irt" ]="irish traditional",
+ ["isl" ]="icelandic",
+ ["ism" ]="inari sami",
+ ["ita" ]="italian",
+ ["iwr" ]="hebrew",
+ ["jam" ]="jamaican creole",
+ ["jan" ]="japanese",
+ ["jav" ]="javanese",
+ ["jbo" ]="lojban",
+ ["jct" ]="krymchak",
+ ["jii" ]="yiddish",
+ ["jud" ]="ladino",
+ ["jul" ]="jula",
+ ["kab" ]="kabardian",
+ ["kab0"]="kabyle",
+ ["kac" ]="kachchi",
+ ["kal" ]="kalenjin",
+ ["kan" ]="kannada",
+ ["kar" ]="karachay",
+ ["kat" ]="georgian",
+ ["kaz" ]="kazakh",
+ ["kde" ]="makonde",
+ ["kea" ]="kabuverdianu (crioulo)",
+ ["keb" ]="kebena",
+ ["kek" ]="kekchi",
+ ["kge" ]="khutsuri georgian",
+ ["kha" ]="khakass",
+ ["khk" ]="khanty-kazim",
+ ["khm" ]="khmer",
+ ["khs" ]="khanty-shurishkar",
+ ["kht" ]="khamti shan",
+ ["khv" ]="khanty-vakhi",
+ ["khw" ]="khowar",
+ ["kik" ]="kikuyu (gikuyu)",
+ ["kir" ]="kirghiz (kyrgyz)",
+ ["kis" ]="kisii",
+ ["kiu" ]="kirmanjki",
+ ["kjd" ]="southern kiwai",
+ ["kjp" ]="eastern pwo karen",
+ ["kjz" ]="bumthangkha",
+ ["kkn" ]="kokni",
+ ["klm" ]="kalmyk",
+ ["kmb" ]="kamba",
+ ["kmn" ]="kumaoni",
+ ["kmo" ]="komo",
+ ["kms" ]="komso",
+ ["kmz" ]="khorasani turkic",
+ ["knr" ]="kanuri",
+ ["kod" ]="kodagu",
+ ["koh" ]="korean old hangul",
+ ["kok" ]="konkani",
+ ["kom" ]="komi",
+ ["kon" ]="kikongo",
+ ["kon0"]="kongo",
+ ["kop" ]="komi-permyak",
+ ["kor" ]="korean",
+ ["kos" ]="kosraean",
+ ["koz" ]="komi-zyrian",
+ ["kpl" ]="kpelle",
+ ["kri" ]="krio",
+ ["krk" ]="karakalpak",
+ ["krl" ]="karelian",
+ ["krm" ]="karaim",
+ ["krn" ]="karen",
+ ["krt" ]="koorete",
+ ["ksh" ]="kashmiri",
+ ["ksh0"]="ripuarian",
+ ["ksi" ]="khasi",
+ ["ksm" ]="kildin sami",
+ ["ksw" ]="s’gaw karen",
+ ["kua" ]="kuanyama",
+ ["kui" ]="kui",
+ ["kul" ]="kulvi",
+ ["kum" ]="kumyk",
+ ["kur" ]="kurdish",
+ ["kuu" ]="kurukh",
+ ["kuy" ]="kuy",
+ ["kyk" ]="koryak",
+ ["kyu" ]="western kayah",
+ ["lad" ]="ladin",
+ ["lah" ]="lahuli",
+ ["lak" ]="lak",
+ ["lam" ]="lambani",
+ ["lao" ]="lao",
+ ["lat" ]="latin",
+ ["laz" ]="laz",
+ ["lcr" ]="l-cree",
+ ["ldk" ]="ladakhi",
+ ["lez" ]="lezgi",
+ ["lij" ]="ligurian",
+ ["lim" ]="limburgish",
+ ["lin" ]="lingala",
+ ["lis" ]="lisu",
+ ["ljp" ]="lampung",
+ ["lki" ]="laki",
+ ["lma" ]="low mari",
+ ["lmb" ]="limbu",
+ ["lmo" ]="lombard",
+ ["lmw" ]="lomwe",
+ ["lom" ]="loma",
+ ["lrc" ]="luri",
+ ["lsb" ]="lower sorbian",
+ ["lsm" ]="lule sami",
+ ["lth" ]="lithuanian",
+ ["ltz" ]="luxembourgish",
+ ["lua" ]="luba-lulua",
+ ["lub" ]="luba-katanga",
+ ["lug" ]="ganda",
+ ["luh" ]="luyia",
+ ["luo" ]="luo",
+ ["lvi" ]="latvian",
+ ["mad" ]="madura",
+ ["mag" ]="magahi",
+ ["mah" ]="marshallese",
+ ["maj" ]="majang",
+ ["mak" ]="makhuwa",
+ ["mal" ]="malayalam reformed",
+ ["mam" ]="mam",
+ ["man" ]="mansi",
+ ["map" ]="mapudungun",
+ ["mar" ]="marathi",
+ ["maw" ]="marwari",
+ ["mbn" ]="mbundu",
+ ["mbo" ]="mbo",
+ ["mch" ]="manchu",
+ ["mcr" ]="moose cree",
+ ["mde" ]="mende",
+ ["mdr" ]="mandar",
+ ["men" ]="me'en",
+ ["mer" ]="meru",
+ ["mfa" ]="pattani malay",
+ ["mfe" ]="morisyen",
+ ["min" ]="minangkabau",
+ ["miz" ]="mizo",
+ ["mkd" ]="macedonian",
+ ["mkr" ]="makasar",
+ ["mkw" ]="kituba",
+ ["mle" ]="male",
+ ["mlg" ]="malagasy",
+ ["mln" ]="malinke",
+ ["mlr" ]="malayalam reformed",
+ ["mly" ]="malay",
+ ["mnd" ]="mandinka",
+ ["mng" ]="mongolian",
+ ["mni" ]="manipuri",
+ ["mnk" ]="maninka",
+ ["mnx" ]="manx",
+ ["moh" ]="mohawk",
+ ["mok" ]="moksha",
+ ["mol" ]="moldavian",
+ ["mon" ]="mon",
+ ["mor" ]="moroccan",
+ ["mos" ]="mossi",
+ ["mri" ]="maori",
+ ["mth" ]="maithili",
+ ["mts" ]="maltese",
+ ["mun" ]="mundari",
+ ["mus" ]="muscogee",
+ ["mwl" ]="mirandese",
+ ["mww" ]="hmong daw",
+ ["myn" ]="mayan",
+ ["mzn" ]="mazanderani",
+ ["nag" ]="naga-assamese",
+ ["nah" ]="nahuatl",
+ ["nan" ]="nanai",
+ ["nap" ]="neapolitan",
+ ["nas" ]="naskapi",
+ ["nau" ]="nauruan",
+ ["nav" ]="navajo",
+ ["ncr" ]="n-cree",
+ ["ndb" ]="ndebele",
+ ["ndc" ]="ndau",
+ ["ndg" ]="ndonga",
+ ["nds" ]="low saxon",
+ ["nep" ]="nepali",
+ ["new" ]="newari",
+ ["nga" ]="ngbaka",
+ ["ngr" ]="nagari",
+ ["nhc" ]="norway house cree",
+ ["nis" ]="nisi",
+ ["niu" ]="niuean",
+ ["nkl" ]="nyankole",
+ ["nko" ]="n'ko",
+ ["nld" ]="dutch",
+ ["noe" ]="nimadi",
+ ["nog" ]="nogai",
+ ["nor" ]="norwegian",
+ ["nov" ]="novial",
+ ["nsm" ]="northern sami",
+ ["nso" ]="sotho, northern",
+ ["nta" ]="northern tai",
+ ["nto" ]="esperanto",
+ ["nym" ]="nyamwezi",
+ ["nyn" ]="norwegian nynorsk",
+ ["nza" ]="mbembe tigon",
+ ["oci" ]="occitan",
+ ["ocr" ]="oji-cree",
+ ["ojb" ]="ojibway",
+ ["ori" ]="odia",
+ ["oro" ]="oromo",
+ ["oss" ]="ossetian",
+ ["paa" ]="palestinian aramaic",
+ ["pag" ]="pangasinan",
+ ["pal" ]="pali",
+ ["pam" ]="pampangan",
+ ["pan" ]="punjabi",
+ ["pap" ]="palpa",
+ ["pap0"]="papiamentu",
+ ["pas" ]="pashto",
+ ["pau" ]="palauan",
+ ["pcc" ]="bouyei",
+ ["pcd" ]="picard",
+ ["pdc" ]="pennsylvania german",
+ ["pgr" ]="polytonic greek",
+ ["phk" ]="phake",
+ ["pih" ]="norfolk",
+ ["pil" ]="filipino",
+ ["plg" ]="palaung",
+ ["plk" ]="polish",
+ ["pms" ]="piemontese",
+ ["pnb" ]="western panjabi",
+ ["poh" ]="pocomchi",
+ ["pon" ]="pohnpeian",
+ ["pro" ]="provencal",
+ ["ptg" ]="portuguese",
+ ["pwo" ]="western pwo karen",
+ ["qin" ]="chin",
+ ["quc" ]="k’iche’",
+ ["quh" ]="quechua (bolivia)",
+ ["quz" ]="quechua",
+ ["qvi" ]="quechua (ecuador)",
+ ["qwh" ]="quechua (peru)",
+ ["raj" ]="rajasthani",
+ ["rar" ]="rarotongan",
+ ["rbu" ]="russian buriat",
+ ["rcr" ]="r-cree",
+ ["rej" ]="rejang",
+ ["ria" ]="riang",
+ ["rif" ]="tarifit",
+ ["rit" ]="ritarungo",
+ ["rkw" ]="arakwal",
+ ["rms" ]="romansh",
+ ["rmy" ]="vlax romani",
+ ["rom" ]="romanian",
+ ["roy" ]="romany",
+ ["rsy" ]="rusyn",
+ ["rtm" ]="rotuman",
+ ["rua" ]="kinyarwanda",
+ ["run" ]="rundi",
+ ["rup" ]="aromanian",
+ ["rus" ]="russian",
+ ["sad" ]="sadri",
+ ["san" ]="sanskrit",
+ ["sas" ]="sasak",
+ ["sat" ]="santali",
+ ["say" ]="sayisi",
+ ["scn" ]="sicilian",
+ ["sco" ]="scots",
+ ["scs" ]="north slavey",
+ ["sek" ]="sekota",
+ ["sel" ]="selkup",
+ ["sga" ]="old irish",
+ ["sgo" ]="sango",
+ ["sgs" ]="samogitian",
+ ["shi" ]="tachelhit",
+ ["shn" ]="shan",
+ ["sib" ]="sibe",
+ ["sid" ]="sidamo",
+ ["sig" ]="silte gurage",
+ ["sks" ]="skolt sami",
+ ["sky" ]="slovak",
+ ["sla" ]="slavey",
+ ["slv" ]="slovenian",
+ ["sml" ]="somali",
+ ["smo" ]="samoan",
+ ["sna" ]="sena",
+ ["sna0"]="shona",
+ ["snd" ]="sindhi",
+ ["snh" ]="sinhala (sinhalese)",
+ ["snk" ]="soninke",
+ ["sog" ]="sodo gurage",
+ ["sop" ]="songe",
+ ["sot" ]="sotho, southern",
+ ["sqi" ]="albanian",
+ ["srb" ]="serbian",
+ ["srd" ]="sardinian",
+ ["srk" ]="saraiki",
+ ["srr" ]="serer",
+ ["ssl" ]="south slavey",
+ ["ssm" ]="southern sami",
+ ["stq" ]="saterland frisian",
+ ["suk" ]="sukuma",
+ ["sun" ]="sundanese",
+ ["sur" ]="suri",
+ ["sva" ]="svan",
+ ["sve" ]="swedish",
+ ["swa" ]="swadaya aramaic",
+ ["swk" ]="swahili",
+ ["swz" ]="swati",
+ ["sxt" ]="sutu",
+ ["sxu" ]="upper saxon",
+ ["syl" ]="sylheti",
+ ["syr" ]="syriac",
+ ["syre"]="estrangela syriac",
+ ["syrj"]="western syriac",
+ ["syrn"]="eastern syriac",
+ ["szl" ]="silesian",
+ ["tab" ]="tabasaran",
+ ["taj" ]="tajiki",
+ ["tam" ]="tamil",
+ ["tat" ]="tatar",
+ ["tcr" ]="th-cree",
+ ["tdd" ]="dehong dai",
+ ["tel" ]="telugu",
+ ["tet" ]="tetum",
+ ["tgl" ]="tagalog",
+ ["tgn" ]="tongan",
+ ["tgr" ]="tigre",
+ ["tgy" ]="tigrinya",
+ ["tha" ]="thai",
+ ["tht" ]="tahitian",
+ ["tib" ]="tibetan",
+ ["tiv" ]="tiv",
+ ["tkm" ]="turkmen",
+ ["tmh" ]="tamashek",
+ ["tmn" ]="temne",
+ ["tna" ]="tswana",
+ ["tne" ]="tundra nenets",
+ ["tng" ]="tonga",
+ ["tod" ]="todo",
+ ["tod0"]="toma",
+ ["tpi" ]="tok pisin",
+ ["trk" ]="turkish",
+ ["tsg" ]="tsonga",
+ ["tsj" ]="tshangla",
+ ["tua" ]="turoyo aramaic",
+ ["tul" ]="tulu",
+ ["tum" ]="tulu",
+ ["tuv" ]="tuvin",
+ ["tvl" ]="tuvalu",
+ ["twi" ]="twi",
+ ["tyz" ]="tày",
+ ["tzm" ]="tamazight",
+ ["tzo" ]="tzotzil",
+ ["udm" ]="udmurt",
+ ["ukr" ]="ukrainian",
+ ["umb" ]="umbundu",
+ ["urd" ]="urdu",
+ ["usb" ]="upper sorbian",
+ ["uyg" ]="uyghur",
+ ["uzb" ]="uzbek",
+ ["vec" ]="venetian",
+ ["ven" ]="venda",
+ ["vit" ]="vietnamese",
+ ["vol" ]="volapük",
+ ["vro" ]="võro",
+ ["wa" ]="wa",
+ ["wag" ]="wagdi",
+ ["war" ]="waray-waray",
+ ["wcr" ]="west-cree",
+ ["wel" ]="welsh",
+ ["wlf" ]="wolof",
+ ["wln" ]="walloon",
+ ["wtm" ]="mewati",
+ ["xbd" ]="lü",
+ ["xhs" ]="xhosa",
+ ["xjb" ]="minjangbal",
+ ["xkf" ]="khengkha",
+ ["xog" ]="soga",
+ ["xpe" ]="kpelle (liberia)",
+ ["yak" ]="sakha",
+ ["yao" ]="yao",
+ ["yap" ]="yapese",
+ ["yba" ]="yoruba",
+ ["ycr" ]="y-cree",
+ ["yic" ]="yi classic",
+ ["yim" ]="yi modern",
+ ["zea" ]="zealandic",
+ ["zgh" ]="standard morrocan tamazigh",
+ ["zha" ]="zhuang",
+ ["zhh" ]="chinese, hong kong sar",
+ ["zhp" ]="chinese phonetic",
+ ["zhs" ]="chinese simplified",
+ ["zht" ]="chinese traditional",
+ ["znd" ]="zande",
+ ["zul" ]="zulu",
+ ["zza" ]="zazaki",
+}
+local features=allocate {
+ ["aalt"]="access all alternates",
+ ["abvf"]="above-base forms",
+ ["abvm"]="above-base mark positioning",
+ ["abvs"]="above-base substitutions",
+ ["afrc"]="alternative fractions",
+ ["akhn"]="akhands",
+ ["blwf"]="below-base forms",
+ ["blwm"]="below-base mark positioning",
+ ["blws"]="below-base substitutions",
+ ["c2pc"]="petite capitals from capitals",
+ ["c2sc"]="small capitals from capitals",
+ ["calt"]="contextual alternates",
+ ["case"]="case-sensitive forms",
+ ["ccmp"]="glyph composition/decomposition",
+ ["cfar"]="conjunct form after ro",
+ ["cjct"]="conjunct forms",
+ ["clig"]="contextual ligatures",
+ ["cpct"]="centered cjk punctuation",
+ ["cpsp"]="capital spacing",
+ ["cswh"]="contextual swash",
+ ["curs"]="cursive positioning",
+ ["dflt"]="default processing",
+ ["dist"]="distances",
+ ["dlig"]="discretionary ligatures",
+ ["dnom"]="denominators",
+ ["dtls"]="dotless forms",
+ ["expt"]="expert forms",
+ ["falt"]="final glyph alternates",
+ ["fin2"]="terminal forms #2",
+ ["fin3"]="terminal forms #3",
+ ["fina"]="terminal forms",
+ ["flac"]="flattened accents over capitals",
+ ["frac"]="fractions",
+ ["fwid"]="full width",
+ ["half"]="half forms",
+ ["haln"]="halant forms",
+ ["halt"]="alternate half width",
+ ["hist"]="historical forms",
+ ["hkna"]="horizontal kana alternates",
+ ["hlig"]="historical ligatures",
+ ["hngl"]="hangul",
+ ["hojo"]="hojo kanji forms",
+ ["hwid"]="half width",
+ ["init"]="initial forms",
+ ["isol"]="isolated forms",
+ ["ital"]="italics",
+ ["jalt"]="justification alternatives",
+ ["jp04"]="jis2004 forms",
+ ["jp78"]="jis78 forms",
+ ["jp83"]="jis83 forms",
+ ["jp90"]="jis90 forms",
+ ["kern"]="kerning",
+ ["lfbd"]="left bounds",
+ ["liga"]="standard ligatures",
+ ["ljmo"]="leading jamo forms",
+ ["lnum"]="lining figures",
+ ["locl"]="localized forms",
+ ["ltra"]="left-to-right alternates",
+ ["ltrm"]="left-to-right mirrored forms",
+ ["mark"]="mark positioning",
+ ["med2"]="medial forms #2",
+ ["medi"]="medial forms",
+ ["mgrk"]="mathematical greek",
+ ["mkmk"]="mark to mark positioning",
+ ["mset"]="mark positioning via substitution",
+ ["nalt"]="alternate annotation forms",
+ ["nlck"]="nlc kanji forms",
+ ["nukt"]="nukta forms",
+ ["numr"]="numerators",
+ ["onum"]="old style figures",
+ ["opbd"]="optical bounds",
+ ["ordn"]="ordinals",
+ ["ornm"]="ornaments",
+ ["palt"]="proportional alternate width",
+ ["pcap"]="petite capitals",
+ ["pkna"]="proportional kana",
+ ["pnum"]="proportional figures",
+ ["pref"]="pre-base forms",
+ ["pres"]="pre-base substitutions",
+ ["pstf"]="post-base forms",
+ ["psts"]="post-base substitutions",
+ ["pwid"]="proportional widths",
+ ["qwid"]="quarter widths",
+ ["rand"]="randomize",
+ ["rclt"]="required contextual alternates",
+ ["rkrf"]="rakar forms",
+ ["rlig"]="required ligatures",
+ ["rphf"]="reph form",
+ ["rtbd"]="right bounds",
+ ["rtla"]="right-to-left alternates",
+ ["rtlm"]="right to left mirrored forms",
+ ["rvrn"]="required variation alternates",
+ ["ruby"]="ruby notation forms",
+ ["salt"]="stylistic alternates",
+ ["sinf"]="scientific inferiors",
+ ["size"]="optical size",
+ ["smcp"]="small capitals",
+ ["smpl"]="simplified forms",
+ ["ssty"]="script style",
+ ["stch"]="stretching glyph decomposition",
+ ["subs"]="subscript",
+ ["sups"]="superscript",
+ ["swsh"]="swash",
+ ["titl"]="titling",
+ ["tjmo"]="trailing jamo forms",
+ ["tnam"]="traditional name forms",
+ ["tnum"]="tabular figures",
+ ["trad"]="traditional forms",
+ ["twid"]="third widths",
+ ["unic"]="unicase",
+ ["valt"]="alternate vertical metrics",
+ ["vatu"]="vattu variants",
+ ["vert"]="vertical writing",
+ ["vhal"]="alternate vertical half metrics",
+ ["vjmo"]="vowel jamo forms",
+ ["vkna"]="vertical kana alternates",
+ ["vkrn"]="vertical kerning",
+ ["vpal"]="proportional alternate vertical metrics",
+ ["vrtr"]="vertical alternates for rotation",
+ ["vrt2"]="vertical rotation",
+ ["zero"]="slashed zero",
+ ["trep"]="traditional tex replacements",
+ ["tlig"]="traditional tex ligatures",
+ ["ss.."]="stylistic set ..",
+ ["cv.."]="character variant ..",
+ ["js.."]="justification ..",
+ ["dv.."]="devanagari ..",
+ ["ml.."]="malayalam ..",
+}
+local baselines=allocate {
+ ["hang"]="hanging baseline",
+ ["icfb"]="ideographic character face bottom edge baseline",
+ ["icft"]="ideographic character face tope edige baseline",
+ ["ideo"]="ideographic em-box bottom edge baseline",
+ ["idtp"]="ideographic em-box top edge baseline",
+ ["math"]="mathematical centered baseline",
+ ["romn"]="roman baseline"
+}
+tables.scripts=scripts
+tables.languages=languages
+tables.features=features
+tables.baselines=baselines
+local acceptscripts=true directives.register("otf.acceptscripts",function(v) acceptscripts=v end)
+local acceptlanguages=true directives.register("otf.acceptlanguages",function(v) acceptlanguages=v end)
+local report_checks=logs.reporter("fonts","checks")
+if otffeatures.features then
+ for k,v in next,otffeatures.features do
+ features[k]=v
+ end
+ otffeatures.features=features
+end
+local function swapped(h)
+ local r={}
+ for k,v in next,h do
+ r[gsub(v,"[^a-z0-9]","")]=k
+ end
+ return r
+end
+local verbosescripts=allocate(swapped(scripts ))
+local verboselanguages=allocate(swapped(languages))
+local verbosefeatures=allocate(swapped(features ))
+local verbosebaselines=allocate(swapped(baselines))
+local function resolve(t,k)
+ if k then
+ k=gsub(lower(k),"[^a-z0-9]","")
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ end
+end
+setmetatableindex(verbosescripts,resolve)
+setmetatableindex(verboselanguages,resolve)
+setmetatableindex(verbosefeatures,resolve)
+setmetatableindex(verbosebaselines,resolve)
+setmetatableindex(scripts,function(t,k)
+ if k then
+ k=lower(k)
+ if k=="dflt" then
+ return k
+ end
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ k=gsub(k," ","")
+ v=rawget(t,v)
+ if v then
+ return v
+ elseif acceptscripts then
+ report_checks("registering extra script %a",k)
+ rawset(t,k,k)
+ return k
+ end
+ end
+ return "dflt"
+end)
+setmetatableindex(languages,function(t,k)
+ if k then
+ k=lower(k)
+ if k=="dflt" then
+ return k
+ end
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ k=gsub(k," ","")
+ v=rawget(t,v)
+ if v then
+ return v
+ elseif acceptlanguages then
+ report_checks("registering extra language %a",k)
+ rawset(t,k,k)
+ return k
+ end
+ end
+ return "dflt"
+end)
+if setmetatablenewindex then
+ setmetatablenewindex(languages,"ignore")
+ setmetatablenewindex(scripts,"ignore")
+ setmetatablenewindex(baselines,"ignore")
+end
+local function resolve(t,k)
+ if k then
+ k=lower(k)
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ k=gsub(k," ","")
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ local tag,dd=match(k,"(..)(%d+)")
+ if tag and dd then
+ local v=rawget(t,tag)
+ if v then
+ return v
+ else
+ local v=rawget(t,tag.."..")
+ if v then
+ return (gsub(v,"%.%.",tonumber(dd)))
+ end
+ end
+ end
+ end
+ return k
+end
+setmetatableindex(features,resolve)
+local function assign(t,k,v)
+ if k and v then
+ v=lower(v)
+ rawset(t,k,v)
+ end
+end
+if setmetatablenewindex then
+ setmetatablenewindex(features,assign)
+end
+local checkers={
+ rand=function(v)
+ return v==true and "random" or v
+ end
+}
+if not storage then
+ return
+end
+local usedfeatures=statistics.usedfeatures or {}
+statistics.usedfeatures=usedfeatures
+table.setmetatableindex(usedfeatures,function(t,k) if k then local v={} t[k]=v return v end end)
+storage.register("fonts/otf/usedfeatures",usedfeatures,"fonts.handlers.otf.statistics.usedfeatures" )
+local normalizedaxis=otf.readers.helpers.normalizedaxis or function(s) return s end
+function otffeatures.normalize(features,wrap)
+ if features then
+ local h={}
+ for key,value in next,features do
+ local k=lower(key)
+ if k=="language" then
+ local v=gsub(lower(value),"[^a-z0-9]","")
+ h.language=rawget(verboselanguages,v) or (languages[v] and v) or "dflt"
+ elseif k=="script" then
+ local v=gsub(lower(value),"[^a-z0-9]","")
+ h.script=rawget(verbosescripts,v) or (scripts[v] and v) or "dflt"
+ elseif k=="axis" then
+ h[k]=normalizedaxis(value)
+ if not callbacks.supported.glyph_stream_provider then
+ h.variableshapes=true
+ end
+ else
+ local uk=usedfeatures[key]
+ local uv=uk[value]
+ if uv then
+ else
+ uv=tonumber(value)
+ if uv then
+ elseif type(value)=="string" then
+ local b=is_boolean(value)
+ if type(b)=="nil" then
+ if wrap and find(value,",") then
+ uv="{"..lower(value).."}"
+ else
+ uv=lower(value)
+ end
+ else
+ uv=b
+ end
+ elseif type(value)=="table" then
+ uv=sequenced(t,",")
+ else
+ uv=value
+ end
+ if not rawget(features,k) then
+ k=rawget(verbosefeatures,k) or k
+ end
+ local c=checkers[k]
+ if c then
+ uv=c(uv) or vc
+ end
+ uk[value]=uv
+ end
+ h[k]=uv
+ end
+ end
+ return h
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ott”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-cff” 98d5a660ea803b65cb883c009ecf3c0b] ---
+
+if not modules then modules={} end modules ['font-cff']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber,rawget=next,type,tonumber,rawget
+local byte,char,gmatch=string.byte,string.char,string.gmatch
+local concat,remove,unpack=table.concat,table.remove,table.unpack
+local floor,abs,round,ceil,min,max=math.floor,math.abs,math.round,math.ceil,math.min,math.max
+local P,C,R,S,C,Cs,Ct=lpeg.P,lpeg.C,lpeg.R,lpeg.S,lpeg.C,lpeg.Cs,lpeg.Ct
+local lpegmatch=lpeg.match
+local formatters=string.formatters
+local bytetable=string.bytetable
+local idiv=number.idiv
+local rshift,band,extract=bit32.rshift,bit32.band,bit32.extract
+local readers=fonts.handlers.otf.readers
+local streamreader=readers.streamreader
+local readstring=streamreader.readstring
+local readbyte=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readuint=streamreader.readcardinal3
+local readulong=streamreader.readcardinal4
+local setposition=streamreader.setposition
+local getposition=streamreader.getposition
+local readbytetable=streamreader.readbytetable
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ readstring=streamreader.readstring
+ readbyte=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readuint=streamreader.readcardinal3
+ readulong=streamreader.readcardinal4
+ setposition=streamreader.setposition
+ getposition=streamreader.getposition
+ readbytetable=streamreader.readbytetable
+end)
+local setmetatableindex=table.setmetatableindex
+local trace_charstrings=false trackers.register("fonts.cff.charstrings",function(v) trace_charstrings=v end)
+local report=logs.reporter("otf reader","cff")
+local parsedictionaries
+local parsecharstring
+local parsecharstrings
+local resetcharstrings
+local parseprivates
+local startparsing
+local stopparsing
+local defaultstrings={ [0]=
+ ".notdef","space","exclam","quotedbl","numbersign","dollar","percent",
+ "ampersand","quoteright","parenleft","parenright","asterisk","plus",
+ "comma","hyphen","period","slash","zero","one","two","three","four",
+ "five","six","seven","eight","nine","colon","semicolon","less",
+ "equal","greater","question","at","A","B","C","D","E","F","G","H",
+ "I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W",
+ "X","Y","Z","bracketleft","backslash","bracketright","asciicircum",
+ "underscore","quoteleft","a","b","c","d","e","f","g","h","i","j",
+ "k","l","m","n","o","p","q","r","s","t","u","v","w","x","y",
+ "z","braceleft","bar","braceright","asciitilde","exclamdown","cent",
+ "sterling","fraction","yen","florin","section","currency",
+ "quotesingle","quotedblleft","guillemotleft","guilsinglleft",
+ "guilsinglright","fi","fl","endash","dagger","daggerdbl",
+ "periodcentered","paragraph","bullet","quotesinglbase","quotedblbase",
+ "quotedblright","guillemotright","ellipsis","perthousand","questiondown",
+ "grave","acute","circumflex","tilde","macron","breve","dotaccent",
+ "dieresis","ring","cedilla","hungarumlaut","ogonek","caron","emdash",
+ "AE","ordfeminine","Lslash","Oslash","OE","ordmasculine","ae",
+ "dotlessi","lslash","oslash","oe","germandbls","onesuperior",
+ "logicalnot","mu","trademark","Eth","onehalf","plusminus","Thorn",
+ "onequarter","divide","brokenbar","degree","thorn","threequarters",
+ "twosuperior","registered","minus","eth","multiply","threesuperior",
+ "copyright","Aacute","Acircumflex","Adieresis","Agrave","Aring",
+ "Atilde","Ccedilla","Eacute","Ecircumflex","Edieresis","Egrave",
+ "Iacute","Icircumflex","Idieresis","Igrave","Ntilde","Oacute",
+ "Ocircumflex","Odieresis","Ograve","Otilde","Scaron","Uacute",
+ "Ucircumflex","Udieresis","Ugrave","Yacute","Ydieresis","Zcaron",
+ "aacute","acircumflex","adieresis","agrave","aring","atilde",
+ "ccedilla","eacute","ecircumflex","edieresis","egrave","iacute",
+ "icircumflex","idieresis","igrave","ntilde","oacute","ocircumflex",
+ "odieresis","ograve","otilde","scaron","uacute","ucircumflex",
+ "udieresis","ugrave","yacute","ydieresis","zcaron","exclamsmall",
+ "Hungarumlautsmall","dollaroldstyle","dollarsuperior","ampersandsmall",
+ "Acutesmall","parenleftsuperior","parenrightsuperior","twodotenleader",
+ "onedotenleader","zerooldstyle","oneoldstyle","twooldstyle",
+ "threeoldstyle","fouroldstyle","fiveoldstyle","sixoldstyle",
+ "sevenoldstyle","eightoldstyle","nineoldstyle","commasuperior",
+ "threequartersemdash","periodsuperior","questionsmall","asuperior",
+ "bsuperior","centsuperior","dsuperior","esuperior","isuperior",
+ "lsuperior","msuperior","nsuperior","osuperior","rsuperior","ssuperior",
+ "tsuperior","ff","ffi","ffl","parenleftinferior","parenrightinferior",
+ "Circumflexsmall","hyphensuperior","Gravesmall","Asmall","Bsmall",
+ "Csmall","Dsmall","Esmall","Fsmall","Gsmall","Hsmall","Ismall",
+ "Jsmall","Ksmall","Lsmall","Msmall","Nsmall","Osmall","Psmall",
+ "Qsmall","Rsmall","Ssmall","Tsmall","Usmall","Vsmall","Wsmall",
+ "Xsmall","Ysmall","Zsmall","colonmonetary","onefitted","rupiah",
+ "Tildesmall","exclamdownsmall","centoldstyle","Lslashsmall",
+ "Scaronsmall","Zcaronsmall","Dieresissmall","Brevesmall","Caronsmall",
+ "Dotaccentsmall","Macronsmall","figuredash","hypheninferior",
+ "Ogoneksmall","Ringsmall","Cedillasmall","questiondownsmall","oneeighth",
+ "threeeighths","fiveeighths","seveneighths","onethird","twothirds",
+ "zerosuperior","foursuperior","fivesuperior","sixsuperior",
+ "sevensuperior","eightsuperior","ninesuperior","zeroinferior",
+ "oneinferior","twoinferior","threeinferior","fourinferior",
+ "fiveinferior","sixinferior","seveninferior","eightinferior",
+ "nineinferior","centinferior","dollarinferior","periodinferior",
+ "commainferior","Agravesmall","Aacutesmall","Acircumflexsmall",
+ "Atildesmall","Adieresissmall","Aringsmall","AEsmall","Ccedillasmall",
+ "Egravesmall","Eacutesmall","Ecircumflexsmall","Edieresissmall",
+ "Igravesmall","Iacutesmall","Icircumflexsmall","Idieresissmall",
+ "Ethsmall","Ntildesmall","Ogravesmall","Oacutesmall","Ocircumflexsmall",
+ "Otildesmall","Odieresissmall","OEsmall","Oslashsmall","Ugravesmall",
+ "Uacutesmall","Ucircumflexsmall","Udieresissmall","Yacutesmall",
+ "Thornsmall","Ydieresissmall","001.000","001.001","001.002","001.003",
+ "Black","Bold","Book","Light","Medium","Regular","Roman","Semibold",
+}
+local cffreaders={
+ readbyte,
+ readushort,
+ readuint,
+ readulong,
+}
+local function readheader(f)
+ local offset=getposition(f)
+ local major=readbyte(f)
+ local header={
+ offset=offset,
+ major=major,
+ minor=readbyte(f),
+ size=readbyte(f),
+ }
+ if major==1 then
+ header.dsize=readbyte(f)
+ elseif major==2 then
+ header.dsize=readushort(f)
+ else
+ end
+ setposition(f,offset+header.size)
+ return header
+end
+local function readlengths(f,longcount)
+ local count=longcount and readulong(f) or readushort(f)
+ if count==0 then
+ return {}
+ end
+ local osize=readbyte(f)
+ local read=cffreaders[osize]
+ if not read then
+ report("bad offset size: %i",osize)
+ return {}
+ end
+ local lengths={}
+ local previous=read(f)
+ for i=1,count do
+ local offset=read(f)
+ local length=offset-previous
+ if length<0 then
+ report("bad offset: %i",length)
+ length=0
+ end
+ lengths[i]=length
+ previous=offset
+ end
+ return lengths
+end
+local function readfontnames(f)
+ local names=readlengths(f)
+ for i=1,#names do
+ names[i]=readstring(f,names[i])
+ end
+ return names
+end
+local function readtopdictionaries(f)
+ local dictionaries=readlengths(f)
+ for i=1,#dictionaries do
+ dictionaries[i]=readstring(f,dictionaries[i])
+ end
+ return dictionaries
+end
+local function readstrings(f)
+ local lengths=readlengths(f)
+ local strings=setmetatableindex({},defaultstrings)
+ local index=#defaultstrings
+ for i=1,#lengths do
+ index=index+1
+ strings[index]=readstring(f,lengths[i])
+ end
+ return strings
+end
+do
+ local stack={}
+ local top=0
+ local result={}
+ local strings={}
+ local p_single=P("\00")/function()
+ result.version=strings[stack[top]] or "unset"
+ top=0
+ end+P("\01")/function()
+ result.notice=strings[stack[top]] or "unset"
+ top=0
+ end+P("\02")/function()
+ result.fullname=strings[stack[top]] or "unset"
+ top=0
+ end+P("\03")/function()
+ result.familyname=strings[stack[top]] or "unset"
+ top=0
+ end+P("\04")/function()
+ result.weight=strings[stack[top]] or "unset"
+ top=0
+ end+P("\05")/function()
+ result.fontbbox={ unpack(stack,1,4) }
+ top=0
+ end+P("\06")/function()
+ result.bluevalues={ unpack(stack,1,top) }
+ top=0
+ end+P("\07")/function()
+ result.otherblues={ unpack(stack,1,top) }
+ top=0
+ end+P("\08")/function()
+ result.familyblues={ unpack(stack,1,top) }
+ top=0
+ end+P("\09")/function()
+ result.familyotherblues={ unpack(stack,1,top) }
+ top=0
+ end+P("\10")/function()
+ result.strhw=stack[top]
+ top=0
+ end+P("\11")/function()
+ result.strvw=stack[top]
+ top=0
+ end+P("\13")/function()
+ result.uniqueid=stack[top]
+ top=0
+ end+P("\14")/function()
+ result.xuid=concat(stack,"",1,top)
+ top=0
+ end+P("\15")/function()
+ result.charset=stack[top]
+ top=0
+ end+P("\16")/function()
+ result.encoding=stack[top]
+ top=0
+ end+P("\17")/function()
+ result.charstrings=stack[top]
+ top=0
+ end+P("\18")/function()
+ result.private={
+ size=stack[top-1],
+ offset=stack[top],
+ }
+ top=0
+ end+P("\19")/function()
+ result.subroutines=stack[top]
+ top=0
+ end+P("\20")/function()
+ result.defaultwidthx=stack[top]
+ top=0
+ end+P("\21")/function()
+ result.nominalwidthx=stack[top]
+ top=0
+ end
++P("\24")/function()
+ result.vstore=stack[top]
+ top=0
+ end+P("\25")/function()
+ result.maxstack=stack[top]
+ top=0
+ end
+ local p_double=P("\12")*(
+ P("\00")/function()
+ result.copyright=stack[top]
+ top=0
+ end+P("\01")/function()
+ result.monospaced=stack[top]==1 and true or false
+ top=0
+ end+P("\02")/function()
+ result.italicangle=stack[top]
+ top=0
+ end+P("\03")/function()
+ result.underlineposition=stack[top]
+ top=0
+ end+P("\04")/function()
+ result.underlinethickness=stack[top]
+ top=0
+ end+P("\05")/function()
+ result.painttype=stack[top]
+ top=0
+ end+P("\06")/function()
+ result.charstringtype=stack[top]
+ top=0
+ end+P("\07")/function()
+ result.fontmatrix={ unpack(stack,1,6) }
+ top=0
+ end+P("\08")/function()
+ result.strokewidth=stack[top]
+ top=0
+ end+P("\09")/function()
+ result.bluescale=stack[top]
+ top=0
+ end+P("\10")/function()
+ result.bluesnap=stack[top]
+ top=0
+ end+P("\11")/function()
+ result.bluefuzz=stack[top]
+ top=0
+ end+P("\12")/function()
+ result.stemsnaph={ unpack(stack,1,top) }
+ top=0
+ end+P("\13")/function()
+ result.stemsnapv={ unpack(stack,1,top) }
+ top=0
+ end+P("\20")/function()
+ result.syntheticbase=stack[top]
+ top=0
+ end+P("\21")/function()
+ result.postscript=strings[stack[top]] or "unset"
+ top=0
+ end+P("\22")/function()
+ result.basefontname=strings[stack[top]] or "unset"
+ top=0
+ end+P("\21")/function()
+ result.basefontblend=stack[top]
+ top=0
+ end+P("\30")/function()
+ result.cid.registry=strings[stack[top-2]] or "unset"
+ result.cid.ordering=strings[stack[top-1]] or "unset"
+ result.cid.supplement=stack[top]
+ top=0
+ end+P("\31")/function()
+ result.cid.fontversion=stack[top]
+ top=0
+ end+P("\32")/function()
+ result.cid.fontrevision=stack[top]
+ top=0
+ end+P("\33")/function()
+ result.cid.fonttype=stack[top]
+ top=0
+ end+P("\34")/function()
+ result.cid.count=stack[top]
+ top=0
+ end+P("\35")/function()
+ result.cid.uidbase=stack[top]
+ top=0
+ end+P("\36")/function()
+ result.cid.fdarray=stack[top]
+ top=0
+ end+P("\37")/function()
+ result.cid.fdselect=stack[top]
+ top=0
+ end+P("\38")/function()
+ result.cid.fontname=strings[stack[top]] or "unset"
+ top=0
+ end
+ )
+ local remap={
+ ["\x00"]="00",["\x01"]="01",["\x02"]="02",["\x03"]="03",["\x04"]="04",["\x05"]="05",["\x06"]="06",["\x07"]="07",["\x08"]="08",["\x09"]="09",["\x0A"]="0.",["\x0B"]="0E",["\x0C"]="0E-",["\x0D"]="0",["\x0E"]="0-",["\x0F"]="0",
+ ["\x10"]="10",["\x11"]="11",["\x12"]="12",["\x13"]="13",["\x14"]="14",["\x15"]="15",["\x16"]="16",["\x17"]="17",["\x18"]="18",["\x19"]="19",["\x1A"]="1.",["\x1B"]="1E",["\x1C"]="1E-",["\x1D"]="1",["\x1E"]="1-",["\x1F"]="1",
+ ["\x20"]="20",["\x21"]="21",["\x22"]="22",["\x23"]="23",["\x24"]="24",["\x25"]="25",["\x26"]="26",["\x27"]="27",["\x28"]="28",["\x29"]="29",["\x2A"]="2.",["\x2B"]="2E",["\x2C"]="2E-",["\x2D"]="2",["\x2E"]="2-",["\x2F"]="2",
+ ["\x30"]="30",["\x31"]="31",["\x32"]="32",["\x33"]="33",["\x34"]="34",["\x35"]="35",["\x36"]="36",["\x37"]="37",["\x38"]="38",["\x39"]="39",["\x3A"]="3.",["\x3B"]="3E",["\x3C"]="3E-",["\x3D"]="3",["\x3E"]="3-",["\x3F"]="3",
+ ["\x40"]="40",["\x41"]="41",["\x42"]="42",["\x43"]="43",["\x44"]="44",["\x45"]="45",["\x46"]="46",["\x47"]="47",["\x48"]="48",["\x49"]="49",["\x4A"]="4.",["\x4B"]="4E",["\x4C"]="4E-",["\x4D"]="4",["\x4E"]="4-",["\x4F"]="4",
+ ["\x50"]="50",["\x51"]="51",["\x52"]="52",["\x53"]="53",["\x54"]="54",["\x55"]="55",["\x56"]="56",["\x57"]="57",["\x58"]="58",["\x59"]="59",["\x5A"]="5.",["\x5B"]="5E",["\x5C"]="5E-",["\x5D"]="5",["\x5E"]="5-",["\x5F"]="5",
+ ["\x60"]="60",["\x61"]="61",["\x62"]="62",["\x63"]="63",["\x64"]="64",["\x65"]="65",["\x66"]="66",["\x67"]="67",["\x68"]="68",["\x69"]="69",["\x6A"]="6.",["\x6B"]="6E",["\x6C"]="6E-",["\x6D"]="6",["\x6E"]="6-",["\x6F"]="6",
+ ["\x70"]="70",["\x71"]="71",["\x72"]="72",["\x73"]="73",["\x74"]="74",["\x75"]="75",["\x76"]="76",["\x77"]="77",["\x78"]="78",["\x79"]="79",["\x7A"]="7.",["\x7B"]="7E",["\x7C"]="7E-",["\x7D"]="7",["\x7E"]="7-",["\x7F"]="7",
+ ["\x80"]="80",["\x81"]="81",["\x82"]="82",["\x83"]="83",["\x84"]="84",["\x85"]="85",["\x86"]="86",["\x87"]="87",["\x88"]="88",["\x89"]="89",["\x8A"]="8.",["\x8B"]="8E",["\x8C"]="8E-",["\x8D"]="8",["\x8E"]="8-",["\x8F"]="8",
+ ["\x90"]="90",["\x91"]="91",["\x92"]="92",["\x93"]="93",["\x94"]="94",["\x95"]="95",["\x96"]="96",["\x97"]="97",["\x98"]="98",["\x99"]="99",["\x9A"]="9.",["\x9B"]="9E",["\x9C"]="9E-",["\x9D"]="9",["\x9E"]="9-",["\x9F"]="9",
+ ["\xA0"]=".0",["\xA1"]=".1",["\xA2"]=".2",["\xA3"]=".3",["\xA4"]=".4",["\xA5"]=".5",["\xA6"]=".6",["\xA7"]=".7",["\xA8"]=".8",["\xA9"]=".9",["\xAA"]="..",["\xAB"]=".E",["\xAC"]=".E-",["\xAD"]=".",["\xAE"]=".-",["\xAF"]=".",
+ ["\xB0"]="E0",["\xB1"]="E1",["\xB2"]="E2",["\xB3"]="E3",["\xB4"]="E4",["\xB5"]="E5",["\xB6"]="E6",["\xB7"]="E7",["\xB8"]="E8",["\xB9"]="E9",["\xBA"]="E.",["\xBB"]="EE",["\xBC"]="EE-",["\xBD"]="E",["\xBE"]="E-",["\xBF"]="E",
+ ["\xC0"]="E-0",["\xC1"]="E-1",["\xC2"]="E-2",["\xC3"]="E-3",["\xC4"]="E-4",["\xC5"]="E-5",["\xC6"]="E-6",["\xC7"]="E-7",["\xC8"]="E-8",["\xC9"]="E-9",["\xCA"]="E-.",["\xCB"]="E-E",["\xCC"]="E-E-",["\xCD"]="E-",["\xCE"]="E--",["\xCF"]="E-",
+ ["\xD0"]="-0",["\xD1"]="-1",["\xD2"]="-2",["\xD3"]="-3",["\xD4"]="-4",["\xD5"]="-5",["\xD6"]="-6",["\xD7"]="-7",["\xD8"]="-8",["\xD9"]="-9",["\xDA"]="-.",["\xDB"]="-E",["\xDC"]="-E-",["\xDD"]="-",["\xDE"]="--",["\xDF"]="-",
+ }
+ local p_last=S("\x0F\x1F\x2F\x3F\x4F\x5F\x6F\x7F\x8F\x9F\xAF\xBF")+R("\xF0\xFF")
+ local p_nibbles=P("\30")*Cs(((1-p_last)/remap)^0*(P(1)/remap))/function(n)
+ top=top+1
+ stack[top]=tonumber(n) or 0
+ end
+ local p_byte=C(R("\32\246"))/function(b0)
+ top=top+1
+ stack[top]=byte(b0)-139
+ end
+ local p_positive=C(R("\247\250"))*C(1)/function(b0,b1)
+ top=top+1
+ stack[top]=(byte(b0)-247)*256+byte(b1)+108
+ end
+ local p_negative=C(R("\251\254"))*C(1)/function(b0,b1)
+ top=top+1
+ stack[top]=-(byte(b0)-251)*256-byte(b1)-108
+ end
+ local p_short=P("\28")*C(1)*C(1)/function(b1,b2)
+ top=top+1
+ local n=0x100*byte(b1)+byte(b2)
+ if n>=0x8000 then
+ stack[top]=n-0xFFFF-1
+ else
+ stack[top]=n
+ end
+ end
+ local p_long=P("\29")*C(1)*C(1)*C(1)*C(1)/function(b1,b2,b3,b4)
+ top=top+1
+ local n=0x1000000*byte(b1)+0x10000*byte(b2)+0x100*byte(b3)+byte(b4)
+ if n>=0x8000000 then
+ stack[top]=n-0xFFFFFFFF-1
+ else
+ stack[top]=n
+ end
+ end
+ local p_unsupported=P(1)/function(detail)
+ top=0
+ end
+ local p_dictionary=(
+ p_byte+p_positive+p_negative+p_short+p_long+p_nibbles+p_single+p_double+p_unsupported
+ )^1
+ parsedictionaries=function(data,dictionaries,what)
+ stack={}
+ strings=data.strings
+ for i=1,#dictionaries do
+ top=0
+ result=what=="cff" and {
+ monospaced=false,
+ italicangle=0,
+ underlineposition=-100,
+ underlinethickness=50,
+ painttype=0,
+ charstringtype=2,
+ fontmatrix={ 0.001,0,0,0.001,0,0 },
+ fontbbox={ 0,0,0,0 },
+ strokewidth=0,
+ charset=0,
+ encoding=0,
+ cid={
+ fontversion=0,
+ fontrevision=0,
+ fonttype=0,
+ count=8720,
+ }
+ } or {
+ charstringtype=2,
+ charset=0,
+ vstore=0,
+ cid={
+ },
+ }
+ lpegmatch(p_dictionary,dictionaries[i])
+ dictionaries[i]=result
+ end
+ result={}
+ top=0
+ stack={}
+ end
+ parseprivates=function(data,dictionaries)
+ stack={}
+ strings=data.strings
+ for i=1,#dictionaries do
+ local private=dictionaries[i].private
+ if private and private.data then
+ top=0
+ result={
+ forcebold=false,
+ languagegroup=0,
+ expansionfactor=0.06,
+ initialrandomseed=0,
+ subroutines=0,
+ defaultwidthx=0,
+ nominalwidthx=0,
+ cid={
+ },
+ }
+ lpegmatch(p_dictionary,private.data)
+ private.data=result
+ end
+ end
+ result={}
+ top=0
+ stack={}
+ end
+ local x=0
+ local y=0
+ local width=false
+ local r=0
+ local stems=0
+ local globalbias=0
+ local localbias=0
+ local nominalwidth=0
+ local defaultwidth=0
+ local charset=false
+ local globals=false
+ local locals=false
+ local depth=1
+ local xmin=0
+ local xmax=0
+ local ymin=0
+ local ymax=0
+ local checked=false
+ local keepcurve=false
+ local version=2
+ local regions=false
+ local nofregions=0
+ local region=false
+ local factors=false
+ local axis=false
+ local vsindex=0
+ local function showstate(where)
+ report("%w%-10s : [%s] n=%i",depth*2,where,concat(stack," ",1,top),top)
+ end
+ local function showvalue(where,value,showstack)
+ if showstack then
+ report("%w%-10s : %s : [%s] n=%i",depth*2,where,tostring(value),concat(stack," ",1,top),top)
+ else
+ report("%w%-10s : %s",depth*2,where,tostring(value))
+ end
+ end
+ local function xymoveto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"m" }
+ end
+ if checked then
+ if x>xmax then xmax=x elseif x<xmin then xmin=x end
+ if y>ymax then ymax=y elseif y<ymin then ymin=y end
+ else
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ end
+ end
+ local function xmoveto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"m" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif x>xmax then
+ xmax=x
+ elseif x<xmin then
+ xmin=x
+ end
+ end
+ local function ymoveto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"m" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif y>ymax then
+ ymax=y
+ elseif y<ymin then
+ ymin=y
+ end
+ end
+ local function moveto()
+ if trace_charstrings then
+ showstate("moveto")
+ end
+ top=0
+ xymoveto()
+ end
+ local function xylineto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"l" }
+ end
+ if checked then
+ if x>xmax then xmax=x elseif x<xmin then xmin=x end
+ if y>ymax then ymax=y elseif y<ymin then ymin=y end
+ else
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ end
+ end
+ local function xlineto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"l" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif x>xmax then
+ xmax=x
+ elseif x<xmin then
+ xmin=x
+ end
+ end
+ local function ylineto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"l" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif y>ymax then
+ ymax=y
+ elseif y<ymin then
+ ymin=y
+ end
+ end
+ local function xycurveto(x1,y1,x2,y2,x3,y3)
+ if trace_charstrings then
+ showstate("curveto")
+ end
+ if keepcurve then
+ r=r+1
+ result[r]={ x1,y1,x2,y2,x3,y3,"c" }
+ end
+ if checked then
+ if x1>xmax then xmax=x1 elseif x1<xmin then xmin=x1 end
+ if y1>ymax then ymax=y1 elseif y1<ymin then ymin=y1 end
+ else
+ xmin=x1
+ ymin=y1
+ xmax=x1
+ ymax=y1
+ checked=true
+ end
+ if x2>xmax then xmax=x2 elseif x2<xmin then xmin=x2 end
+ if y2>ymax then ymax=y2 elseif y2<ymin then ymin=y2 end
+ if x3>xmax then xmax=x3 elseif x3<xmin then xmin=x3 end
+ if y3>ymax then ymax=y3 elseif y3<ymin then ymin=y3 end
+ end
+ local function rmoveto()
+ if not width then
+ if top>2 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width=true
+ end
+ end
+ if trace_charstrings then
+ showstate("rmoveto")
+ end
+ x=x+stack[top-1]
+ y=y+stack[top]
+ top=0
+ xymoveto()
+ end
+ local function hmoveto()
+ if not width then
+ if top>1 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width=true
+ end
+ end
+ if trace_charstrings then
+ showstate("hmoveto")
+ end
+ x=x+stack[top]
+ top=0
+ xmoveto()
+ end
+ local function vmoveto()
+ if not width then
+ if top>1 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width=true
+ end
+ end
+ if trace_charstrings then
+ showstate("vmoveto")
+ end
+ y=y+stack[top]
+ top=0
+ ymoveto()
+ end
+ local function rlineto()
+ if trace_charstrings then
+ showstate("rlineto")
+ end
+ for i=1,top,2 do
+ x=x+stack[i]
+ y=y+stack[i+1]
+ xylineto()
+ end
+ top=0
+ end
+ local function hlineto()
+ if trace_charstrings then
+ showstate("hlineto")
+ end
+ if top==1 then
+ x=x+stack[1]
+ xlineto()
+ else
+ local swap=true
+ for i=1,top do
+ if swap then
+ x=x+stack[i]
+ xlineto()
+ swap=false
+ else
+ y=y+stack[i]
+ ylineto()
+ swap=true
+ end
+ end
+ end
+ top=0
+ end
+ local function vlineto()
+ if trace_charstrings then
+ showstate("vlineto")
+ end
+ if top==1 then
+ y=y+stack[1]
+ ylineto()
+ else
+ local swap=false
+ for i=1,top do
+ if swap then
+ x=x+stack[i]
+ xlineto()
+ swap=false
+ else
+ y=y+stack[i]
+ ylineto()
+ swap=true
+ end
+ end
+ end
+ top=0
+ end
+ local function rrcurveto()
+ if trace_charstrings then
+ showstate("rrcurveto")
+ end
+ for i=1,top,6 do
+ local ax=x+stack[i]
+ local ay=y+stack[i+1]
+ local bx=ax+stack[i+2]
+ local by=ay+stack[i+3]
+ x=bx+stack[i+4]
+ y=by+stack[i+5]
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top=0
+ end
+ local function hhcurveto()
+ if trace_charstrings then
+ showstate("hhcurveto")
+ end
+ local s=1
+ if top%2~=0 then
+ y=y+stack[1]
+ s=2
+ end
+ for i=s,top,4 do
+ local ax=x+stack[i]
+ local ay=y
+ local bx=ax+stack[i+1]
+ local by=ay+stack[i+2]
+ x=bx+stack[i+3]
+ y=by
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top=0
+ end
+ local function vvcurveto()
+ if trace_charstrings then
+ showstate("vvcurveto")
+ end
+ local s=1
+ local d=0
+ if top%2~=0 then
+ d=stack[1]
+ s=2
+ end
+ for i=s,top,4 do
+ local ax=x+d
+ local ay=y+stack[i]
+ local bx=ax+stack[i+1]
+ local by=ay+stack[i+2]
+ x=bx
+ y=by+stack[i+3]
+ xycurveto(ax,ay,bx,by,x,y)
+ d=0
+ end
+ top=0
+ end
+ local function xxcurveto(swap)
+ local last=top%4~=0 and stack[top]
+ if last then
+ top=top-1
+ end
+ for i=1,top,4 do
+ local ax,ay,bx,by
+ if swap then
+ ax=x+stack[i]
+ ay=y
+ bx=ax+stack[i+1]
+ by=ay+stack[i+2]
+ y=by+stack[i+3]
+ if last and i+3==top then
+ x=bx+last
+ else
+ x=bx
+ end
+ swap=false
+ else
+ ax=x
+ ay=y+stack[i]
+ bx=ax+stack[i+1]
+ by=ay+stack[i+2]
+ x=bx+stack[i+3]
+ if last and i+3==top then
+ y=by+last
+ else
+ y=by
+ end
+ swap=true
+ end
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top=0
+ end
+ local function hvcurveto()
+ if trace_charstrings then
+ showstate("hvcurveto")
+ end
+ xxcurveto(true)
+ end
+ local function vhcurveto()
+ if trace_charstrings then
+ showstate("vhcurveto")
+ end
+ xxcurveto(false)
+ end
+ local function rcurveline()
+ if trace_charstrings then
+ showstate("rcurveline")
+ end
+ for i=1,top-2,6 do
+ local ax=x+stack[i]
+ local ay=y+stack[i+1]
+ local bx=ax+stack[i+2]
+ local by=ay+stack[i+3]
+ x=bx+stack[i+4]
+ y=by+stack[i+5]
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ x=x+stack[top-1]
+ y=y+stack[top]
+ xylineto()
+ top=0
+ end
+ local function rlinecurve()
+ if trace_charstrings then
+ showstate("rlinecurve")
+ end
+ if top>6 then
+ for i=1,top-6,2 do
+ x=x+stack[i]
+ y=y+stack[i+1]
+ xylineto()
+ end
+ end
+ local ax=x+stack[top-5]
+ local ay=y+stack[top-4]
+ local bx=ax+stack[top-3]
+ local by=ay+stack[top-2]
+ x=bx+stack[top-1]
+ y=by+stack[top]
+ xycurveto(ax,ay,bx,by,x,y)
+ top=0
+ end
+ local function flex()
+ if trace_charstrings then
+ showstate("flex")
+ end
+ local ax=x+stack[1]
+ local ay=y+stack[2]
+ local bx=ax+stack[3]
+ local by=ay+stack[4]
+ local cx=bx+stack[5]
+ local cy=by+stack[6]
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[7]
+ local dy=cy+stack[8]
+ local ex=dx+stack[9]
+ local ey=dy+stack[10]
+ x=ex+stack[11]
+ y=ey+stack[12]
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function hflex()
+ if trace_charstrings then
+ showstate("hflex")
+ end
+ local ax=x+stack[1]
+ local ay=y
+ local bx=ax+stack[2]
+ local by=ay+stack[3]
+ local cx=bx+stack[4]
+ local cy=by
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[5]
+ local dy=by
+ local ex=dx+stack[6]
+ local ey=y
+ x=ex+stack[7]
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function hflex1()
+ if trace_charstrings then
+ showstate("hflex1")
+ end
+ local ax=x+stack[1]
+ local ay=y+stack[2]
+ local bx=ax+stack[3]
+ local by=ay+stack[4]
+ local cx=bx+stack[5]
+ local cy=by
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[6]
+ local dy=by
+ local ex=dx+stack[7]
+ local ey=dy+stack[8]
+ x=ex+stack[9]
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function flex1()
+ if trace_charstrings then
+ showstate("flex1")
+ end
+ local ax=x+stack[1]
+ local ay=y+stack[2]
+ local bx=ax+stack[3]
+ local by=ay+stack[4]
+ local cx=bx+stack[5]
+ local cy=by+stack[6]
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[7]
+ local dy=cy+stack[8]
+ local ex=dx+stack[9]
+ local ey=dy+stack[10]
+ if abs(ex-x)>abs(ey-y) then
+ x=ex+stack[11]
+ else
+ y=ey+stack[11]
+ end
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function getstem()
+ if top==0 then
+ elseif top%2~=0 then
+ if width then
+ remove(stack,1)
+ else
+ width=remove(stack,1)
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ end
+ top=top-1
+ end
+ if trace_charstrings then
+ showstate("stem")
+ end
+ stems=stems+idiv(top,2)
+ top=0
+ end
+ local function getmask()
+ if top==0 then
+ elseif top%2~=0 then
+ if width then
+ remove(stack,1)
+ else
+ width=remove(stack,1)
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ end
+ top=top-1
+ end
+ if trace_charstrings then
+ showstate(operator==19 and "hintmark" or "cntrmask")
+ end
+ stems=stems+idiv(top,2)
+ top=0
+ if stems==0 then
+ elseif stems<=8 then
+ return 1
+ else
+ return idiv(stems+7,8)
+ end
+ end
+ local function unsupported(t)
+ if trace_charstrings then
+ showstate("unsupported "..t)
+ end
+ top=0
+ end
+ local function unsupportedsub(t)
+ if trace_charstrings then
+ showstate("unsupported sub "..t)
+ end
+ top=0
+ end
+ local function getstem3()
+ if trace_charstrings then
+ showstate("stem3")
+ end
+ top=0
+ end
+ local function divide()
+ if version==1 then
+ local d=stack[top]
+ top=top-1
+ stack[top]=stack[top]/d
+ end
+ end
+ local function closepath()
+ if version==1 then
+ if trace_charstrings then
+ showstate("closepath")
+ end
+ end
+ top=0
+ end
+ local function hsbw()
+ if version==1 then
+ if trace_charstrings then
+ showstate("hsbw")
+ end
+ width=stack[top]
+ end
+ top=0
+ end
+ local function seac()
+ if version==1 then
+ if trace_charstrings then
+ showstate("seac")
+ end
+ end
+ top=0
+ end
+ local function sbw()
+ if version==1 then
+ if trace_charstrings then
+ showstate("sbw")
+ end
+ width=stack[top-1]
+ end
+ top=0
+ end
+ local function callothersubr()
+ if version==1 then
+ if trace_charstrings then
+ showstate("callothersubr (unsupported)")
+ end
+ end
+ top=0
+ end
+ local function pop()
+ if version==1 then
+ if trace_charstrings then
+ showstate("pop (unsupported)")
+ end
+ top=top+1
+ stack[top]=0
+ else
+ top=0
+ end
+ end
+ local function setcurrentpoint()
+ if version==1 then
+ if trace_charstrings then
+ showstate("pop (unsupported)")
+ end
+ x=x+stack[top-1]
+ y=y+stack[top]
+ end
+ top=0
+ end
+ local reginit=false
+ local function updateregions(n)
+ if regions then
+ local current=regions[n] or regions[1]
+ nofregions=#current
+ if axis and n~=reginit then
+ factors={}
+ for i=1,nofregions do
+ local region=current[i]
+ local s=1
+ for j=1,#axis do
+ local f=axis[j]
+ local r=region[j]
+ local start=r.start
+ local peak=r.peak
+ local stop=r.stop
+ if start>peak or peak>stop then
+ elseif start<0 and stop>0 and peak~=0 then
+ elseif peak==0 then
+ elseif f<start or f>stop then
+ s=0
+ break
+ elseif f<peak then
+ s=s*(f-start)/(peak-start)
+ elseif f>peak then
+ s=s*(stop-f)/(stop-peak)
+ else
+ end
+ end
+ factors[i]=s
+ end
+ end
+ end
+ reginit=n
+ end
+ local function setvsindex()
+ local vsindex=stack[top]
+ if trace_charstrings then
+ showstate(formatters["vsindex %i"](vsindex))
+ end
+ updateregions(vsindex)
+ top=top-1
+ end
+ local function blend()
+ local n=stack[top]
+ top=top-1
+ if axis then
+ if trace_charstrings then
+ local t=top-nofregions*n
+ local m=t-n
+ for i=1,n do
+ local k=m+i
+ local d=m+n+(i-1)*nofregions
+ local old=stack[k]
+ local new=old
+ for r=1,nofregions do
+ new=new+stack[d+r]*factors[r]
+ end
+ stack[k]=new
+ showstate(formatters["blend %i of %i: %s -> %s"](i,n,old,new))
+ end
+ top=t
+ elseif n==1 then
+ top=top-nofregions
+ local v=stack[top]
+ for r=1,nofregions do
+ v=v+stack[top+r]*factors[r]
+ end
+ stack[top]=v
+ else
+ top=top-nofregions*n
+ local d=top
+ local k=top-n
+ for i=1,n do
+ k=k+1
+ local v=stack[k]
+ for r=1,nofregions do
+ v=v+stack[d+r]*factors[r]
+ end
+ stack[k]=v
+ d=d+nofregions
+ end
+ end
+ else
+ end
+ end
+ local actions={ [0]=unsupported,
+ getstem,
+ unsupported,
+ getstem,
+ vmoveto,
+ rlineto,
+ hlineto,
+ vlineto,
+ rrcurveto,
+ unsupported,
+ unsupported,
+ unsupported,
+ unsupported,
+ hsbw,
+ unsupported,
+ setvsindex,
+ blend,
+ unsupported,
+ getstem,
+ getmask,
+ getmask,
+ rmoveto,
+ hmoveto,
+ getstem,
+ rcurveline,
+ rlinecurve,
+ vvcurveto,
+ hhcurveto,
+ unsupported,
+ unsupported,
+ vhcurveto,
+ hvcurveto,
+ }
+ local subactions={
+ [000]=dotsection,
+ [001]=getstem3,
+ [002]=getstem3,
+ [006]=seac,
+ [007]=sbw,
+ [012]=divide,
+ [016]=callothersubr,
+ [017]=pop,
+ [033]=setcurrentpoint,
+ [034]=hflex,
+ [035]=flex,
+ [036]=hflex1,
+ [037]=flex1,
+ }
+ local chars=setmetatableindex(function (t,k)
+ local v=char(k)
+ t[k]=v
+ return v
+ end)
+ local c_endchar=chars[14]
+ local encode={}
+ setmetatableindex(encode,function(t,i)
+ for i=-2048,-1130 do
+ t[i]=char(28,band(rshift(i,8),0xFF),band(i,0xFF))
+ end
+ for i=-1131,-108 do
+ local v=0xFB00-i-108
+ t[i]=char(band(rshift(v,8),0xFF),band(v,0xFF))
+ end
+ for i=-107,107 do
+ t[i]=chars[i+139]
+ end
+ for i=108,1131 do
+ local v=0xF700+i-108
+ t[i]=char(extract(v,8,8),extract(v,0,8))
+ end
+ for i=1132,2048 do
+ t[i]=char(28,band(rshift(i,8),0xFF),band(i,0xFF))
+ end
+ setmetatableindex(encode,function(t,k)
+ local r=round(k)
+ local v=rawget(t,r)
+ if v then
+ return v
+ end
+ local v1=floor(k)
+ local v2=floor((k-v1)*0x10000)
+ return char(255,extract(v1,8,8),extract(v1,0,8),extract(v2,8,8),extract(v2,0,8))
+ end)
+ return t[i]
+ end)
+ readers.cffencoder=encode
+ local function p_setvsindex()
+ local vsindex=stack[top]
+ updateregions(vsindex)
+ top=top-1
+ end
+ local function p_blend()
+ local n=stack[top]
+ top=top-1
+ if not axis then
+ elseif n==1 then
+ top=top-nofregions
+ local v=stack[top]
+ for r=1,nofregions do
+ v=v+stack[top+r]*factors[r]
+ end
+ stack[top]=round(v)
+ else
+ top=top-nofregions*n
+ local d=top
+ local k=top-n
+ for i=1,n do
+ k=k+1
+ local v=stack[k]
+ for r=1,nofregions do
+ v=v+stack[d+r]*factors[r]
+ end
+ stack[k]=round(v)
+ d=d+nofregions
+ end
+ end
+ end
+ local function p_getstem()
+ local n=0
+ if top%2~=0 then
+ n=1
+ end
+ if top>n then
+ stems=stems+idiv(top-n,2)
+ end
+ end
+ local function p_getmask()
+ local n=0
+ if top%2~=0 then
+ n=1
+ end
+ if top>n then
+ stems=stems+idiv(top-n,2)
+ end
+ if stems==0 then
+ return 0
+ elseif stems<=8 then
+ return 1
+ else
+ return idiv(stems+7,8)
+ end
+ end
+ local process
+ local function call(scope,list,bias)
+ depth=depth+1
+ if top==0 then
+ showstate(formatters["unknown %s call %s"](scope,"?"))
+ top=0
+ else
+ local index=stack[top]+bias
+ top=top-1
+ if trace_charstrings then
+ showvalue(scope,index,true)
+ end
+ local tab=list[index]
+ if tab then
+ process(tab)
+ else
+ showstate(formatters["unknown %s call %s"](scope,index))
+ top=0
+ end
+ end
+ depth=depth-1
+ end
+ local justpass=false
+ process=function(tab)
+ local i=1
+ local n=#tab
+ while i<=n do
+ local t=tab[i]
+ if t>=32 then
+ top=top+1
+ if t<=246 then
+ stack[top]=t-139
+ i=i+1
+ elseif t<=250 then
+ stack[top]=t*256-63124+tab[i+1]
+ i=i+2
+ elseif t<=254 then
+ stack[top]=-t*256+64148-tab[i+1]
+ i=i+2
+ else
+ local n=0x100*tab[i+1]+tab[i+2]
+ if n>=0x8000 then
+ stack[top]=n-0x10000+(0x100*tab[i+3]+tab[i+4])/0xFFFF
+ else
+ stack[top]=n+(0x100*tab[i+3]+tab[i+4])/0xFFFF
+ end
+ i=i+5
+ end
+ elseif t==28 then
+ top=top+1
+ local n=0x100*tab[i+1]+tab[i+2]
+ if n>=0x8000 then
+ stack[top]=n-0x10000
+ else
+ stack[top]=n
+ end
+ i=i+3
+ elseif t==11 then
+ if trace_charstrings then
+ showstate("return")
+ end
+ return
+ elseif t==10 then
+ call("local",locals,localbias)
+ i=i+1
+ elseif t==14 then
+ if width then
+ elseif top>0 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ else
+ width=true
+ end
+ if trace_charstrings then
+ showstate("endchar")
+ end
+ return
+ elseif t==29 then
+ call("global",globals,globalbias)
+ i=i+1
+ elseif t==12 then
+ i=i+1
+ local t=tab[i]
+ if justpass then
+ if t>=34 and t<=37 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ r=r+1;result[r]=chars[12]
+ r=r+1;result[r]=chars[t]
+ top=0
+ else
+ local a=subactions[t]
+ if a then
+ a(t)
+ else
+ top=0
+ end
+ end
+ else
+ local a=subactions[t]
+ if a then
+ a(t)
+ else
+ if trace_charstrings then
+ showvalue("<subaction>",t)
+ end
+ top=0
+ end
+ end
+ i=i+1
+ elseif justpass then
+ if t==15 then
+ p_setvsindex()
+ i=i+1
+ elseif t==16 then
+ local s=p_blend() or 0
+ i=i+s+1
+ elseif t==1 or t==3 or t==18 or operation==23 then
+ p_getstem()
+if true then
+ if top>0 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ top=0
+ end
+ r=r+1;result[r]=chars[t]
+else
+ top=0
+end
+ i=i+1
+ elseif t==19 or t==20 then
+ local s=p_getmask() or 0
+if true then
+ if top>0 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ top=0
+ end
+ r=r+1;result[r]=chars[t]
+ for j=1,s do
+ i=i+1
+ r=r+1;result[r]=chars[tab[i]]
+ end
+else
+ i=i+s
+ top=0
+end
+ i=i+1
+ elseif t==9 then
+ top=0
+ i=i+1
+ elseif t==13 then
+ local s=hsbw() or 0
+ i=i+s+1
+ else
+ if top>0 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ top=0
+ end
+ r=r+1;result[r]=chars[t]
+ i=i+1
+ end
+ else
+ local a=actions[t]
+ if a then
+ local s=a(t)
+ if s then
+ i=i+s+1
+ else
+ i=i+1
+ end
+ else
+ if trace_charstrings then
+ showvalue("<action>",t)
+ end
+ top=0
+ i=i+1
+ end
+ end
+ end
+ end
+ local function setbias(globals,locals,nobias)
+ if nobias then
+ return 0,0
+ else
+ local g=#globals
+ local l=#locals
+ return
+ ((g<1240 and 107) or (g<33900 and 1131) or 32768)+1,
+ ((l<1240 and 107) or (l<33900 and 1131) or 32768)+1
+ end
+ end
+ local function processshape(tab,index)
+ if not tab then
+ glyphs[index]={
+ boundingbox={ 0,0,0,0 },
+ width=0,
+ name=charset and charset[index] or nil,
+ }
+ return
+ end
+ tab=bytetable(tab)
+ x=0
+ y=0
+ width=false
+ r=0
+ top=0
+ stems=0
+ result={}
+ xmin=0
+ xmax=0
+ ymin=0
+ ymax=0
+ checked=false
+ if trace_charstrings then
+ report("glyph: %i",index)
+ report("data : % t",tab)
+ end
+ if regions then
+ updateregions(vsindex)
+ end
+ process(tab)
+ local boundingbox={
+ round(xmin),
+ round(ymin),
+ round(xmax),
+ round(ymax),
+ }
+ if width==true or width==false then
+ width=defaultwidth
+ else
+ width=nominalwidth+width
+ end
+ local glyph=glyphs[index]
+ if justpass then
+ r=r+1
+ result[r]=c_endchar
+ local stream=concat(result)
+ if glyph then
+ glyph.stream=stream
+ else
+ glyphs[index]={ stream=stream }
+ end
+ elseif glyph then
+ glyph.segments=keepcurve~=false and result or nil
+ glyph.boundingbox=boundingbox
+ if not glyph.width then
+ glyph.width=width
+ end
+ if charset and not glyph.name then
+ glyph.name=charset[index]
+ end
+ elseif keepcurve then
+ glyphs[index]={
+ segments=result,
+ boundingbox=boundingbox,
+ width=width,
+ name=charset and charset[index] or nil,
+ }
+ else
+ glyphs[index]={
+ boundingbox=boundingbox,
+ width=width,
+ name=charset and charset[index] or nil,
+ }
+ end
+ if trace_charstrings then
+ report("width : %s",tostring(width))
+ report("boundingbox: % t",boundingbox)
+ end
+ end
+ startparsing=function(fontdata,data,streams)
+ reginit=false
+ axis=false
+ regions=data.regions
+ justpass=streams==true
+ if regions then
+ regions={ regions }
+ axis=data.factors or false
+ end
+ end
+ stopparsing=function(fontdata,data)
+ stack={}
+ glyphs=false
+ result={}
+ top=0
+ locals=false
+ globals=false
+ strings=false
+ end
+ local function setwidths(private)
+ if not private then
+ return 0,0
+ end
+ local privatedata=private.data
+ if not privatedata then
+ return 0,0
+ end
+ return privatedata.nominalwidthx or 0,privatedata.defaultwidthx or 0
+ end
+ parsecharstrings=function(fontdata,data,glphs,doshapes,tversion,streams,nobias)
+ local dictionary=data.dictionaries[1]
+ local charstrings=dictionary.charstrings
+ keepcurve=doshapes
+ version=tversion
+ strings=data.strings
+ globals=data.routines or {}
+ locals=dictionary.subroutines or {}
+ charset=dictionary.charset
+ vsindex=dictionary.vsindex or 0
+ glyphs=glphs or {}
+ globalbias,localbias=setbias(globals,locals,nobias)
+ nominalwidth,defaultwidth=setwidths(dictionary.private)
+ if charstrings then
+ startparsing(fontdata,data,streams)
+ for index=1,#charstrings do
+ processshape(charstrings[index],index-1)
+ end
+ stopparsing(fontdata,data)
+ else
+ report("no charstrings")
+ end
+ return glyphs
+ end
+ parsecharstring=function(fontdata,data,dictionary,tab,glphs,index,doshapes,tversion,streams)
+ keepcurve=doshapes
+ version=tversion
+ strings=data.strings
+ globals=data.routines or {}
+ locals=dictionary.subroutines or {}
+ charset=false
+ vsindex=dictionary.vsindex or 0
+ glyphs=glphs or {}
+ justpass=streams==true
+ globalbias,localbias=setbias(globals,locals,nobias)
+ nominalwidth,defaultwidth=setwidths(dictionary.private)
+ processshape(tab,index-1)
+ end
+end
+local function readglobals(f,data)
+ local routines=readlengths(f)
+ for i=1,#routines do
+ routines[i]=readbytetable(f,routines[i])
+ end
+ data.routines=routines
+end
+local function readencodings(f,data)
+ data.encodings={}
+end
+local function readcharsets(f,data,dictionary)
+ local header=data.header
+ local strings=data.strings
+ local nofglyphs=data.nofglyphs
+ local charsetoffset=dictionary.charset
+ if charsetoffset and charsetoffset~=0 then
+ setposition(f,header.offset+charsetoffset)
+ local format=readbyte(f)
+ local charset={ [0]=".notdef" }
+ dictionary.charset=charset
+ if format==0 then
+ for i=1,nofglyphs do
+ charset[i]=strings[readushort(f)]
+ end
+ elseif format==1 or format==2 then
+ local readcount=format==1 and readbyte or readushort
+ local i=1
+ while i<=nofglyphs do
+ local sid=readushort(f)
+ local n=readcount(f)
+ for s=sid,sid+n do
+ charset[i]=strings[s]
+ i=i+1
+ if i>nofglyphs then
+ break
+ end
+ end
+ end
+ else
+ report("cff parser: unsupported charset format %a",format)
+ end
+ else
+ dictionary.nocharset=true
+ dictionary.charset=nil
+ end
+end
+local function readprivates(f,data)
+ local header=data.header
+ local dictionaries=data.dictionaries
+ local private=dictionaries[1].private
+ if private then
+ setposition(f,header.offset+private.offset)
+ private.data=readstring(f,private.size)
+ end
+end
+local function readlocals(f,data,dictionary)
+ local header=data.header
+ local private=dictionary.private
+ if private then
+ local subroutineoffset=private.data.subroutines
+ if subroutineoffset~=0 then
+ setposition(f,header.offset+private.offset+subroutineoffset)
+ local subroutines=readlengths(f)
+ for i=1,#subroutines do
+ subroutines[i]=readbytetable(f,subroutines[i])
+ end
+ dictionary.subroutines=subroutines
+ private.data.subroutines=nil
+ else
+ dictionary.subroutines={}
+ end
+ else
+ dictionary.subroutines={}
+ end
+end
+local function readcharstrings(f,data,what)
+ local header=data.header
+ local dictionaries=data.dictionaries
+ local dictionary=dictionaries[1]
+ local stringtype=dictionary.charstringtype
+ local offset=dictionary.charstrings
+ if type(offset)~="number" then
+ elseif stringtype==2 then
+ setposition(f,header.offset+offset)
+ local charstrings=readlengths(f,what=="cff2")
+ local nofglyphs=#charstrings
+ for i=1,nofglyphs do
+ charstrings[i]=readstring(f,charstrings[i])
+ end
+ data.nofglyphs=nofglyphs
+ dictionary.charstrings=charstrings
+ else
+ report("unsupported charstr type %i",stringtype)
+ data.nofglyphs=0
+ dictionary.charstrings={}
+ end
+end
+local function readcidprivates(f,data)
+ local header=data.header
+ local dictionaries=data.dictionaries[1].cid.dictionaries
+ for i=1,#dictionaries do
+ local dictionary=dictionaries[i]
+ local private=dictionary.private
+ if private then
+ setposition(f,header.offset+private.offset)
+ private.data=readstring(f,private.size)
+ end
+ end
+ parseprivates(data,dictionaries)
+end
+readers.parsecharstrings=parsecharstrings
+local function readnoselect(f,fontdata,data,glyphs,doshapes,version,streams)
+ local dictionaries=data.dictionaries
+ local dictionary=dictionaries[1]
+ readglobals(f,data)
+ readcharstrings(f,data,version)
+ if version=="cff2" then
+ dictionary.charset=nil
+ else
+ readencodings(f,data)
+ readcharsets(f,data,dictionary)
+ end
+ readprivates(f,data)
+ parseprivates(data,data.dictionaries)
+ readlocals(f,data,dictionary)
+ startparsing(fontdata,data,streams)
+ parsecharstrings(fontdata,data,glyphs,doshapes,version,streams)
+ stopparsing(fontdata,data)
+end
+local function readfdselect(f,fontdata,data,glyphs,doshapes,version,streams)
+ local header=data.header
+ local dictionaries=data.dictionaries
+ local dictionary=dictionaries[1]
+ local cid=dictionary.cid
+ local cidselect=cid and cid.fdselect
+ readglobals(f,data)
+ readcharstrings(f,data,version)
+ if version~="cff2" then
+ readencodings(f,data)
+ end
+ local charstrings=dictionary.charstrings
+ local fdindex={}
+ local nofglyphs=data.nofglyphs
+ local maxindex=-1
+ setposition(f,header.offset+cidselect)
+ local format=readbyte(f)
+ if format==1 then
+ for i=0,nofglyphs do
+ local index=readbyte(f)
+ fdindex[i]=index
+ if index>maxindex then
+ maxindex=index
+ end
+ end
+ elseif format==3 then
+ local nofranges=readushort(f)
+ local first=readushort(f)
+ local index=readbyte(f)
+ while true do
+ local last=readushort(f)
+ if index>maxindex then
+ maxindex=index
+ end
+ for i=first,last do
+ fdindex[i]=index
+ end
+ if last>=nofglyphs then
+ break
+ else
+ first=last+1
+ index=readbyte(f)
+ end
+ end
+ else
+ end
+ if maxindex>=0 then
+ local cidarray=cid.fdarray
+ if cidarray then
+ setposition(f,header.offset+cidarray)
+ local dictionaries=readlengths(f)
+ for i=1,#dictionaries do
+ dictionaries[i]=readstring(f,dictionaries[i])
+ end
+ parsedictionaries(data,dictionaries)
+ cid.dictionaries=dictionaries
+ readcidprivates(f,data)
+ for i=1,#dictionaries do
+ readlocals(f,data,dictionaries[i])
+ end
+ startparsing(fontdata,data,streams)
+ for i=1,#charstrings do
+ parsecharstring(fontdata,data,dictionaries[fdindex[i]+1],charstrings[i],glyphs,i,doshapes,version,streams)
+ end
+ stopparsing(fontdata,data)
+ else
+ report("no cid array")
+ end
+ end
+end
+local gotodatatable=readers.helpers.gotodatatable
+local function cleanup(data,dictionaries)
+end
+function readers.cff(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cff",specification.details or specification.glyphs)
+ if tableoffset then
+ local header=readheader(f)
+ if header.major~=1 then
+ report("only version %s is supported for table %a",1,"cff")
+ return
+ end
+ local glyphs=fontdata.glyphs
+ local names=readfontnames(f)
+ local dictionaries=readtopdictionaries(f)
+ local strings=readstrings(f)
+ local data={
+ header=header,
+ names=names,
+ dictionaries=dictionaries,
+ strings=strings,
+ nofglyphs=fontdata.nofglyphs,
+ }
+ parsedictionaries(data,dictionaries,"cff")
+ local dic=dictionaries[1]
+ local cid=dic.cid
+ local cffinfo={
+ familyname=dic.familyname,
+ fullname=dic.fullname,
+ boundingbox=dic.boundingbox,
+ weight=dic.weight,
+ italicangle=dic.italicangle,
+ underlineposition=dic.underlineposition,
+ underlinethickness=dic.underlinethickness,
+ defaultwidth=dic.defaultwidthx,
+ nominalwidth=dic.nominalwidthx,
+ monospaced=dic.monospaced,
+ }
+ fontdata.cidinfo=cid and {
+ registry=cid.registry,
+ ordering=cid.ordering,
+ supplement=cid.supplement,
+ }
+ fontdata.cffinfo=cffinfo
+ local all=specification.shapes or specification.streams or false
+ if specification.glyphs or all then
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,all,"cff",specification.streams)
+ else
+ readnoselect(f,fontdata,data,glyphs,all,"cff",specification.streams)
+ end
+ end
+ local private=dic.private
+ if private then
+ local data=private.data
+ if type(data)=="table" then
+ cffinfo.defaultwidth=data.defaultwidthx or cffinfo.defaultwidth
+ cffinfo.nominalwidth=data.nominalwidthx or cffinfo.nominalwidth
+ cffinfo.bluevalues=data.bluevalues
+ cffinfo.otherblues=data.otherblues
+ cffinfo.familyblues=data.familyblues
+ cffinfo.familyotherblues=data.familyotherblues
+ cffinfo.bluescale=data.bluescale
+ cffinfo.blueshift=data.blueshift
+ cffinfo.bluefuzz=data.bluefuzz
+ cffinfo.stdhw=data.stdhw
+ cffinfo.stdvw=data.stdvw
+ end
+ end
+ cleanup(data,dictionaries)
+ end
+end
+function readers.cff2(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cff2",specification.glyphs)
+ if tableoffset then
+ local header=readheader(f)
+ if header.major~=2 then
+ report("only version %s is supported for table %a",2,"cff2")
+ return
+ end
+ local glyphs=fontdata.glyphs
+ local dictionaries={ readstring(f,header.dsize) }
+ local data={
+ header=header,
+ dictionaries=dictionaries,
+ nofglyphs=fontdata.nofglyphs,
+ }
+ parsedictionaries(data,dictionaries,"cff2")
+ local offset=dictionaries[1].vstore
+ if offset>0 then
+ local storeoffset=dictionaries[1].vstore+data.header.offset+2
+ local regions,deltas=readers.helpers.readvariationdata(f,storeoffset,factors)
+ data.regions=regions
+ data.deltas=deltas
+ else
+ data.regions={}
+ data.deltas={}
+ end
+ data.factors=specification.factors
+ local cid=data.dictionaries[1].cid
+ local all=specification.shapes or specification.streams or false
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,all,"cff2",specification.streams)
+ else
+ readnoselect(f,fontdata,data,glyphs,all,"cff2",specification.streams)
+ end
+ cleanup(data,dictionaries)
+ end
+end
+function readers.cffcheck(filename)
+ local f=io.open(filename,"rb")
+ if f then
+ local fontdata={
+ glyphs={},
+ }
+ local header=readheader(f)
+ if header.major~=1 then
+ report("only version %s is supported for table %a",1,"cff")
+ return
+ end
+ local names=readfontnames(f)
+ local dictionaries=readtopdictionaries(f)
+ local strings=readstrings(f)
+ local glyphs={}
+ local data={
+ header=header,
+ names=names,
+ dictionaries=dictionaries,
+ strings=strings,
+ glyphs=glyphs,
+ nofglyphs=0,
+ }
+ parsedictionaries(data,dictionaries,"cff")
+ local cid=data.dictionaries[1].cid
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,false)
+ else
+ readnoselect(f,fontdata,data,glyphs,false)
+ end
+ return data
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-cff”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ttf” 44e61cef50dab9b1aaf48130f9367c34] ---
+
+if not modules then modules={} end modules ['font-ttf']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,unpack=next,type,unpack
+local band,rshift=bit32.band,bit32.rshift
+local sqrt,round=math.sqrt,math.round
+local char,rep=string.char,string.rep
+local concat=table.concat
+local idiv=number.idiv
+local setmetatableindex=table.setmetatableindex
+local report=logs.reporter("otf reader","ttf")
+local trace_deltas=false
+local readers=fonts.handlers.otf.readers
+local streamreader=readers.streamreader
+local setposition=streamreader.setposition
+local getposition=streamreader.getposition
+local skipbytes=streamreader.skip
+local readbyte=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readulong=streamreader.readcardinal4
+local readchar=streamreader.readinteger1
+local readshort=streamreader.readinteger2
+local read2dot14=streamreader.read2dot14
+local readinteger=streamreader.readinteger1
+local readcardinaltable=streamreader.readcardinaltable
+local readintegertable=streamreader.readintegertable
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ setposition=streamreader.setposition
+ getposition=streamreader.getposition
+ skipbytes=streamreader.skip
+ readbyte=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readulong=streamreader.readcardinal4
+ readchar=streamreader.readinteger1
+ readshort=streamreader.readinteger2
+ read2dot14=streamreader.read2dot14
+ readinteger=streamreader.readinteger1
+ readcardinaltable=streamreader.readcardinaltable
+ readintegertable=streamreader.readintegertable
+end)
+local short=2
+local ushort=2
+local ulong=4
+local helpers=readers.helpers
+local gotodatatable=helpers.gotodatatable
+local function mergecomposites(glyphs,shapes)
+ local function merge(index,shape,components)
+ local contours={}
+ local points={}
+ local nofcontours=0
+ local nofpoints=0
+ local offset=0
+ local deltas=shape.deltas
+ for i=1,#components do
+ local component=components[i]
+ local subindex=component.index
+ local subshape=shapes[subindex]
+ local subcontours=subshape.contours
+ local subpoints=subshape.points
+ if not subcontours then
+ local subcomponents=subshape.components
+ if subcomponents then
+ subcontours,subpoints=merge(subindex,subshape,subcomponents)
+ end
+ end
+ if subpoints then
+ local matrix=component.matrix
+ local xscale=matrix[1]
+ local xrotate=matrix[2]
+ local yrotate=matrix[3]
+ local yscale=matrix[4]
+ local xoffset=matrix[5]
+ local yoffset=matrix[6]
+ local count=#subpoints
+ if xscale==1 and yscale==1 and xrotate==0 and yrotate==0 then
+ for i=1,count do
+ local p=subpoints[i]
+ nofpoints=nofpoints+1
+ points[nofpoints]={
+ p[1]+xoffset,
+ p[2]+yoffset,
+ p[3]
+ }
+ end
+ else
+ for i=1,count do
+ local p=subpoints[i]
+ local x=p[1]
+ local y=p[2]
+ nofpoints=nofpoints+1
+ points[nofpoints]={
+ xscale*x+xrotate*y+xoffset,
+ yscale*y+yrotate*x+yoffset,
+ p[3]
+ }
+ end
+ end
+ local subcount=#subcontours
+ if subcount==1 then
+ nofcontours=nofcontours+1
+ contours[nofcontours]=offset+subcontours[1]
+ else
+ for i=1,#subcontours do
+ nofcontours=nofcontours+1
+ contours[nofcontours]=offset+subcontours[i]
+ end
+ end
+ offset=offset+count
+ else
+ report("missing contours composite %s, component %s of %s, glyph %s",index,i,#components,subindex)
+ end
+ end
+ shape.points=points
+ shape.contours=contours
+ shape.components=nil
+ return contours,points
+ end
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local components=shape.components
+ if components then
+ merge(index,shape,components)
+ end
+ end
+ end
+end
+local function readnothing(f)
+ return {
+ type="nothing",
+ }
+end
+local function curveto(m_x,m_y,l_x,l_y,r_x,r_y)
+ return
+ l_x+2/3*(m_x-l_x),l_y+2/3*(m_y-l_y),
+ r_x+2/3*(m_x-r_x),r_y+2/3*(m_y-r_y),
+ r_x,r_y,"c"
+end
+local function applyaxis(glyph,shape,deltas,dowidth)
+ local points=shape.points
+ if points then
+ local nofpoints=#points
+ local h=nofpoints+2
+ local l=nofpoints+1
+ local dw=0
+ local dl=0
+ for i=1,#deltas do
+ local deltaset=deltas[i]
+ local xvalues=deltaset.xvalues
+ local yvalues=deltaset.yvalues
+ local dpoints=deltaset.points
+ local factor=deltaset.factor
+ if dpoints then
+ local nofdpoints=#dpoints
+ for i=1,nofdpoints do
+ local d=dpoints[i]
+ local p=points[d]
+ if p then
+ if xvalues then
+ local x=xvalues[i]
+ if x and x~=0 then
+ p[1]=p[1]+factor*x
+ end
+ end
+ if yvalues then
+ local y=yvalues[i]
+ if y and y~=0 then
+ p[2]=p[2]+factor*y
+ end
+ end
+ elseif dowidth then
+ if d==h then
+ local x=xvalues[i]
+ if x then
+ dw=dw+factor*x
+ end
+ elseif d==l then
+ local x=xvalues[i]
+ if x then
+ dl=dl+factor*x
+ end
+ end
+ end
+ end
+ else
+ for i=1,nofpoints do
+ local p=points[i]
+ if xvalues then
+ local x=xvalues[i]
+ if x and x~=0 then
+ p[1]=p[1]+factor*x
+ end
+ end
+ if yvalues then
+ local y=yvalues[i]
+ if y and y~=0 then
+ p[2]=p[2]+factor*y
+ end
+ end
+ end
+ if dowidth then
+ local x=xvalues[h]
+ if x then
+ dw=dw+factor*x
+ end
+ local x=xvalues[l]
+ if x then
+ dl=dl+factor*x
+ end
+ end
+ end
+ end
+ if dowidth then
+ local width=glyph.width or 0
+ glyph.width=width+dw-dl
+ end
+ else
+ report("no points for glyph %a",glyph.name)
+ end
+end
+local quadratic=false
+local function contours2outlines_normal(glyphs,shapes)
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local glyph=glyphs[index]
+ local contours=shape.contours
+ local points=shape.points
+ if contours then
+ local nofcontours=#contours
+ local segments={}
+ local nofsegments=0
+ glyph.segments=segments
+ if nofcontours>0 then
+ local px=0
+ local py=0
+ local first=1
+ for i=1,nofcontours do
+ local last=contours[i]
+ if last>=first then
+ local first_pt=points[first]
+ local first_on=first_pt[3]
+ if first==last then
+ first_pt[3]="m"
+ nofsegments=nofsegments+1
+ segments[nofsegments]=first_pt
+ else
+ local first_on=first_pt[3]
+ local last_pt=points[last]
+ local last_on=last_pt[3]
+ local start=1
+ local control_pt=false
+ if first_on then
+ start=2
+ else
+ if last_on then
+ first_pt=last_pt
+ else
+ first_pt={ (first_pt[1]+last_pt[1])/2,(first_pt[2]+last_pt[2])/2,false }
+ end
+ control_pt=first_pt
+ end
+ local x=first_pt[1]
+ local y=first_pt[2]
+ if not done then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ done=true
+ end
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"m" }
+ if not quadratic then
+ px=x
+ py=y
+ end
+ local previous_pt=first_pt
+ for i=first,last do
+ local current_pt=points[i]
+ local current_on=current_pt[3]
+ local previous_on=previous_pt[3]
+ if previous_on then
+ if current_on then
+ local x,y=current_pt[1],current_pt[2]
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"l" }
+ if not quadratic then
+ px,py=x,y
+ end
+ else
+ control_pt=current_pt
+ end
+ elseif current_on then
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ local x2=current_pt[1]
+ local y2=current_pt[2]
+ nofsegments=nofsegments+1
+ if quadratic then
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ control_pt=false
+ else
+ local x2=(previous_pt[1]+current_pt[1])/2
+ local y2=(previous_pt[2]+current_pt[2])/2
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ nofsegments=nofsegments+1
+ if quadratic then
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ control_pt=current_pt
+ end
+ previous_pt=current_pt
+ end
+ if first_pt==last_pt then
+ else
+ nofsegments=nofsegments+1
+ local x2=first_pt[1]
+ local y2=first_pt[2]
+ if not control_pt then
+ segments[nofsegments]={ x2,y2,"l" }
+ elseif quadratic then
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ else
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ end
+ end
+ first=last+1
+ end
+ end
+ end
+ end
+ end
+end
+local function contours2outlines_shaped(glyphs,shapes,keepcurve)
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local glyph=glyphs[index]
+ local contours=shape.contours
+ local points=shape.points
+ if contours then
+ local nofcontours=#contours
+ local segments=keepcurve and {} or nil
+ local nofsegments=0
+ if keepcurve then
+ glyph.segments=segments
+ end
+ if nofcontours>0 then
+ local xmin,ymin,xmax,ymax,done=0,0,0,0,false
+ local px,py=0,0
+ local first=1
+ for i=1,nofcontours do
+ local last=contours[i]
+ if last>=first then
+ local first_pt=points[first]
+ local first_on=first_pt[3]
+ if first==last then
+ if keepcurve then
+ first_pt[3]="m"
+ nofsegments=nofsegments+1
+ segments[nofsegments]=first_pt
+ end
+ else
+ local first_on=first_pt[3]
+ local last_pt=points[last]
+ local last_on=last_pt[3]
+ local start=1
+ local control_pt=false
+ if first_on then
+ start=2
+ else
+ if last_on then
+ first_pt=last_pt
+ else
+ first_pt={ (first_pt[1]+last_pt[1])/2,(first_pt[2]+last_pt[2])/2,false }
+ end
+ control_pt=first_pt
+ end
+ local x=first_pt[1]
+ local y=first_pt[2]
+ if not done then
+ xmin,ymin,xmax,ymax=x,y,x,y
+ done=true
+ else
+ if x<xmin then xmin=x elseif x>xmax then xmax=x end
+ if y<ymin then ymin=y elseif y>ymax then ymax=y end
+ end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"m" }
+ end
+ if not quadratic then
+ px=x
+ py=y
+ end
+ local previous_pt=first_pt
+ for i=first,last do
+ local current_pt=points[i]
+ local current_on=current_pt[3]
+ local previous_on=previous_pt[3]
+ if previous_on then
+ if current_on then
+ local x=current_pt[1]
+ local y=current_pt[2]
+ if x<xmin then xmin=x elseif x>xmax then xmax=x end
+ if y<ymin then ymin=y elseif y>ymax then ymax=y end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"l" }
+ end
+ if not quadratic then
+ px=x
+ py=y
+ end
+ else
+ control_pt=current_pt
+ end
+ elseif current_on then
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ local x2=current_pt[1]
+ local y2=current_pt[2]
+ if quadratic then
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ end
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if x2<xmin then xmin=x2 elseif x2>xmax then xmax=x2 end
+ if y2<ymin then ymin=y2 elseif y2>ymax then ymax=y2 end
+ if px<xmin then xmin=px elseif px>xmax then xmax=px end
+ if py<ymin then ymin=py elseif py>ymax then ymax=py end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ control_pt=false
+ else
+ local x2=(previous_pt[1]+current_pt[1])/2
+ local y2=(previous_pt[2]+current_pt[2])/2
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ if quadratic then
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ end
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if x2<xmin then xmin=x2 elseif x2>xmax then xmax=x2 end
+ if y2<ymin then ymin=y2 elseif y2>ymax then ymax=y2 end
+ if px<xmin then xmin=px elseif px>xmax then xmax=px end
+ if py<ymin then ymin=py elseif py>ymax then ymax=py end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ control_pt=current_pt
+ end
+ previous_pt=current_pt
+ end
+ if first_pt==last_pt then
+ elseif not control_pt then
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ first_pt[1],first_pt[2],"l" }
+ end
+ else
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ local x2=first_pt[1]
+ local y2=first_pt[2]
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if quadratic then
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ end
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ if x2<xmin then xmin=x2 elseif x2>xmax then xmax=x2 end
+ if y2<ymin then ymin=y2 elseif y2>ymax then ymax=y2 end
+ if px<xmin then xmin=px elseif px>xmax then xmax=px end
+ if py<ymin then ymin=py elseif py>ymax then ymax=py end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ end
+ end
+ end
+ first=last+1
+ end
+ glyph.boundingbox={ round(xmin),round(ymin),round(xmax),round(ymax) }
+ end
+ end
+ end
+ end
+end
+local c_zero=char(0)
+local s_zero=char(0,0)
+local function toushort(n)
+ return char(band(rshift(n,8),0xFF),band(n,0xFF))
+end
+local function toshort(n)
+ if n<0 then
+ n=n+0x10000
+ end
+ return char(band(rshift(n,8),0xFF),band(n,0xFF))
+end
+local chars=setmetatableindex(function(t,k)
+ for i=0,255 do local v=char(i) t[i]=v end return t[k]
+end)
+local function repackpoints(glyphs,shapes)
+ local noboundingbox={ 0,0,0,0 }
+ local result={}
+ local xpoints={}
+ local ypoints={}
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local r=0
+ local glyph=glyphs[index]
+ local contours=shape.contours
+ local nofcontours=contours and #contours or 0
+ local boundingbox=glyph.boundingbox or noboundingbox
+ r=r+1 result[r]=toshort(nofcontours)
+ r=r+1 result[r]=toshort(boundingbox[1])
+ r=r+1 result[r]=toshort(boundingbox[2])
+ r=r+1 result[r]=toshort(boundingbox[3])
+ r=r+1 result[r]=toshort(boundingbox[4])
+ if nofcontours>0 then
+ for i=1,nofcontours do
+ r=r+1 result[r]=toshort(contours[i]-1)
+ end
+ r=r+1 result[r]=s_zero
+ local points=shape.points
+ local currentx=0
+ local currenty=0
+ local x=0
+ local y=0
+ local lastflag=nil
+ local nofflags=0
+ for i=1,#points do
+ local pt=points[i]
+ local px=pt[1]
+ local py=pt[2]
+ local fl=pt[3] and 0x01 or 0x00
+ if px==currentx then
+ fl=fl+0x10
+ else
+ local dx=round(px-currentx)
+ x=x+1
+ if dx<-255 or dx>255 then
+ xpoints[x]=toshort(dx)
+ elseif dx<0 then
+ fl=fl+0x02
+ xpoints[x]=chars[-dx]
+ elseif dx>0 then
+ fl=fl+0x12
+ xpoints[x]=chars[dx]
+ else
+ fl=fl+0x02
+ xpoints[x]=c_zero
+ end
+ end
+ if py==currenty then
+ fl=fl+0x20
+ else
+ local dy=round(py-currenty)
+ y=y+1
+ if dy<-255 or dy>255 then
+ ypoints[y]=toshort(dy)
+ elseif dy<0 then
+ fl=fl+0x04
+ ypoints[y]=chars[-dy]
+ elseif dy>0 then
+ fl=fl+0x24
+ ypoints[y]=chars[dy]
+ else
+ fl=fl+0x04
+ ypoints[y]=c_zero
+ end
+ end
+ currentx=px
+ currenty=py
+ if lastflag==fl then
+ if nofflags==255 then
+ lastflag=lastflag+0x08
+ r=r+1 result[r]=char(lastflag,nofflags-1)
+ nofflags=1
+ lastflag=fl
+ else
+ nofflags=nofflags+1
+ end
+ else
+ if nofflags==1 then
+ r=r+1 result[r]=chars[lastflag]
+ elseif nofflags==2 then
+ r=r+1 result[r]=char(lastflag,lastflag)
+ elseif nofflags>2 then
+ lastflag=lastflag+0x08
+ r=r+1 result[r]=char(lastflag,nofflags-1)
+ end
+ nofflags=1
+ lastflag=fl
+ end
+ end
+ if nofflags==1 then
+ r=r+1 result[r]=chars[lastflag]
+ elseif nofflags==2 then
+ r=r+1 result[r]=char(lastflag,lastflag)
+ elseif nofflags>2 then
+ lastflag=lastflag+0x08
+ r=r+1 result[r]=char(lastflag,nofflags-1)
+ end
+ r=r+1 result[r]=concat(xpoints,"",1,x)
+ r=r+1 result[r]=concat(ypoints,"",1,y)
+ end
+ local stream=concat(result,"",1,r)
+ local length=#stream
+ local padding=idiv(length+3,4)*4-length
+ if padding>0 then
+ if padding==1 then
+ padding="\0"
+ elseif padding==2 then
+ padding="\0\0"
+ else
+ padding="\0\0\0"
+ end
+ padding=stream..padding
+ end
+ glyph.stream=stream
+ end
+ end
+end
+local flags={}
+local function readglyph(f,nofcontours)
+ local points={}
+ local contours={}
+ for i=1,nofcontours do
+ contours[i]=readshort(f)+1
+ end
+ local nofpoints=contours[nofcontours]
+ local nofinstructions=readushort(f)
+ skipbytes(f,nofinstructions)
+ local i=1
+ while i<=nofpoints do
+ local flag=readbyte(f)
+ flags[i]=flag
+ if band(flag,0x08)~=0 then
+ local n=readbyte(f)
+ if n==1 then
+ i=i+1
+ flags[i]=flag
+ else
+ for j=1,n do
+ i=i+1
+ flags[i]=flag
+ end
+ end
+ end
+ i=i+1
+ end
+ local x=0
+ for i=1,nofpoints do
+ local flag=flags[i]
+ if band(flag,0x02)~=0 then
+ if band(flag,0x10)~=0 then
+ x=x+readbyte(f)
+ else
+ x=x-readbyte(f)
+ end
+ elseif band(flag,0x10)~=0 then
+ else
+ x=x+readshort(f)
+ end
+ points[i]={ x,0,band(flag,0x01)~=0 }
+ end
+ local y=0
+ for i=1,nofpoints do
+ local flag=flags[i]
+ if band(flag,0x04)~=0 then
+ if band(flag,0x20)~=0 then
+ y=y+readbyte(f)
+ else
+ y=y-readbyte(f)
+ end
+ elseif band(flag,0x20)~=0 then
+ else
+ y=y+readshort(f)
+ end
+ points[i][2]=y
+ end
+ return {
+ type="glyph",
+ points=points,
+ contours=contours,
+ nofpoints=nofpoints,
+ }
+end
+local function readcomposite(f)
+ local components={}
+ local nofcomponents=0
+ local instructions=false
+ while true do
+ local flags=readushort(f)
+ local index=readushort(f)
+ local f_xyarg=band(flags,0x0002)~=0
+ local f_offset=band(flags,0x0800)~=0
+ local xscale=1
+ local xrotate=0
+ local yrotate=0
+ local yscale=1
+ local xoffset=0
+ local yoffset=0
+ local base=false
+ local reference=false
+ if f_xyarg then
+ if band(flags,0x0001)~=0 then
+ xoffset=readshort(f)
+ yoffset=readshort(f)
+ else
+ xoffset=readchar(f)
+ yoffset=readchar(f)
+ end
+ else
+ if band(flags,0x0001)~=0 then
+ base=readshort(f)
+ reference=readshort(f)
+ else
+ base=readchar(f)
+ reference=readchar(f)
+ end
+ end
+ if band(flags,0x0008)~=0 then
+ xscale=read2dot14(f)
+ yscale=xscale
+ if f_xyarg and f_offset then
+ xoffset=xoffset*xscale
+ yoffset=yoffset*yscale
+ end
+ elseif band(flags,0x0040)~=0 then
+ xscale=read2dot14(f)
+ yscale=read2dot14(f)
+ if f_xyarg and f_offset then
+ xoffset=xoffset*xscale
+ yoffset=yoffset*yscale
+ end
+ elseif band(flags,0x0080)~=0 then
+ xscale=read2dot14(f)
+ xrotate=read2dot14(f)
+ yrotate=read2dot14(f)
+ yscale=read2dot14(f)
+ if f_xyarg and f_offset then
+ xoffset=xoffset*sqrt(xscale^2+xrotate^2)
+ yoffset=yoffset*sqrt(yrotate^2+yscale^2)
+ end
+ end
+ nofcomponents=nofcomponents+1
+ components[nofcomponents]={
+ index=index,
+ usemine=band(flags,0x0200)~=0,
+ round=band(flags,0x0006)~=0,
+ base=base,
+ reference=reference,
+ matrix={ xscale,xrotate,yrotate,yscale,xoffset,yoffset },
+ }
+ if band(flags,0x0100)~=0 then
+ instructions=true
+ end
+ if band(flags,0x0020)==0 then
+ break
+ end
+ end
+ return {
+ type="composite",
+ components=components,
+ }
+end
+function readers.loca(f,fontdata,specification)
+ if specification.glyphs then
+ local datatable=fontdata.tables.loca
+ if datatable then
+ local offset=fontdata.tables.glyf.offset
+ local format=fontdata.fontheader.indextolocformat
+ local profile=fontdata.maximumprofile
+ local nofglyphs=profile and profile.nofglyphs
+ local locations={}
+ setposition(f,datatable.offset)
+ if format==1 then
+ if not nofglyphs then
+ nofglyphs=idiv(datatable.length,4)-1
+ end
+ for i=0,nofglyphs do
+ locations[i]=offset+readulong(f)
+ end
+ fontdata.nofglyphs=nofglyphs
+ else
+ if not nofglyphs then
+ nofglyphs=idiv(datatable.length,2)-1
+ end
+ for i=0,nofglyphs do
+ locations[i]=offset+readushort(f)*2
+ end
+ end
+ fontdata.nofglyphs=nofglyphs
+ fontdata.locations=locations
+ end
+ end
+end
+function readers.glyf(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"glyf",specification.glyphs)
+ if tableoffset then
+ local locations=fontdata.locations
+ if locations then
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs
+ local filesize=fontdata.filesize
+ local nothing={ 0,0,0,0 }
+ local shapes={}
+ local loadshapes=specification.shapes or specification.instance or specification.streams
+ for index=0,nofglyphs-1 do
+ local location=locations[index]
+ local length=locations[index+1]-location
+ if location>=filesize then
+ report("discarding %s glyphs due to glyph location bug",nofglyphs-index+1)
+ fontdata.nofglyphs=index-1
+ fontdata.badfont=true
+ break
+ elseif length>0 then
+ setposition(f,location)
+ local nofcontours=readshort(f)
+ glyphs[index].boundingbox={
+ readshort(f),
+ readshort(f),
+ readshort(f),
+ readshort(f),
+ }
+ if not loadshapes then
+ elseif nofcontours==0 then
+ shapes[index]=readnothing(f)
+ elseif nofcontours>0 then
+ shapes[index]=readglyph(f,nofcontours)
+ else
+ shapes[index]=readcomposite(f,nofcontours)
+ end
+ else
+ if loadshapes then
+ shapes[index]=readnothing(f)
+ end
+ glyphs[index].boundingbox=nothing
+ end
+ end
+ if loadshapes then
+ if readers.gvar then
+ readers.gvar(f,fontdata,specification,glyphs,shapes)
+ end
+ mergecomposites(glyphs,shapes)
+ if specification.instance then
+ if specification.streams then
+ repackpoints(glyphs,shapes)
+ else
+ contours2outlines_shaped(glyphs,shapes,specification.shapes)
+ end
+ elseif specification.shapes then
+ if specification.streams then
+ repackpoints(glyphs,shapes)
+ else
+ contours2outlines_normal(glyphs,shapes)
+ end
+ elseif specification.streams then
+ repackpoints(glyphs,shapes)
+ end
+ end
+ end
+ end
+end
+local function readtuplerecord(f,nofaxis)
+ local record={}
+ for i=1,nofaxis do
+ record[i]=read2dot14(f)
+ end
+ return record
+end
+local function readpoints(f)
+ local count=readbyte(f)
+ if count==0 then
+ return nil,0
+ else
+ if count<128 then
+ elseif band(count,0x80)~=0 then
+ count=band(count,0x7F)*256+readbyte(f)
+ else
+ end
+ local points={}
+ local p=0
+ local n=1
+ while p<count do
+ local control=readbyte(f)
+ local runreader=band(control,0x80)~=0 and readushort or readbyte
+ local runlength=band(control,0x7F)
+ for i=1,runlength+1 do
+ n=n+runreader(f)
+ p=p+1
+ points[p]=n
+ end
+ end
+ return points,p
+ end
+end
+local function readdeltas(f,nofpoints)
+ local deltas={}
+ local p=0
+ local z=0
+ while nofpoints>0 do
+ local control=readbyte(f)
+if not control then
+ break
+end
+ local allzero=band(control,0x80)~=0
+ local runlength=band(control,0x3F)+1
+ if allzero then
+ z=z+runlength
+ else
+ local runreader=band(control,0x40)~=0 and readshort or readinteger
+ if z>0 then
+ for i=1,z do
+ p=p+1
+ deltas[p]=0
+ end
+ z=0
+ end
+ for i=1,runlength do
+ p=p+1
+ deltas[p]=runreader(f)
+ end
+ end
+ nofpoints=nofpoints-runlength
+ end
+ if p>0 then
+ return deltas
+ else
+ end
+end
+local function readdeltas(f,nofpoints)
+ local deltas={}
+ local p=0
+ while nofpoints>0 do
+ local control=readbyte(f)
+ if control then
+ local allzero=band(control,0x80)~=0
+ local runlength=band(control,0x3F)+1
+ if allzero then
+ for i=1,runlength do
+ p=p+1
+ deltas[p]=0
+ end
+ else
+ local runreader=band(control,0x40)~=0 and readshort or readinteger
+ for i=1,runlength do
+ p=p+1
+ deltas[p]=runreader(f)
+ end
+ end
+ nofpoints=nofpoints-runlength
+ else
+ break
+ end
+ end
+ if p>0 then
+ return deltas
+ else
+ end
+end
+function readers.gvar(f,fontdata,specification,glyphdata,shapedata)
+ local instance=specification.instance
+ if not instance then
+ return
+ end
+ local factors=specification.factors
+ if not factors then
+ return
+ end
+ local tableoffset=gotodatatable(f,fontdata,"gvar",specification.variable or specification.shapes)
+ if tableoffset then
+ local version=readulong(f)
+ local nofaxis=readushort(f)
+ local noftuples=readushort(f)
+ local tupleoffset=tableoffset+readulong(f)
+ local nofglyphs=readushort(f)
+ local flags=readushort(f)
+ local dataoffset=tableoffset+readulong(f)
+ local data={}
+ local tuples={}
+ local glyphdata=fontdata.glyphs
+ local dowidth=not fontdata.variabledata.hvarwidths
+ if band(flags,0x0001)~=0 then
+ for i=1,nofglyphs+1 do
+ data[i]=dataoffset+readulong(f)
+ end
+ else
+ for i=1,nofglyphs+1 do
+ data[i]=dataoffset+2*readushort(f)
+ end
+ end
+ if noftuples>0 then
+ setposition(f,tupleoffset)
+ for i=1,noftuples do
+ tuples[i]=readtuplerecord(f,nofaxis)
+ end
+ end
+ local nextoffset=false
+ local startoffset=data[1]
+ for i=1,nofglyphs do
+ nextoffset=data[i+1]
+ local glyph=glyphdata[i-1]
+ local name=trace_deltas and glyph.name
+ if startoffset==nextoffset then
+ if name then
+ report("no deltas for glyph %a",name)
+ end
+ else
+ local shape=shapedata[i-1]
+ if not shape then
+ if name then
+ report("no shape for glyph %a",name)
+ end
+ else
+ lastoffset=startoffset
+ setposition(f,startoffset)
+ local flags=readushort(f)
+ local count=band(flags,0x0FFF)
+ local offset=startoffset+readushort(f)
+ local deltas={}
+ local allpoints=(shape.nofpoints or 0)
+ local shared=false
+ local nofshared=0
+ if band(flags,0x8000)~=0 then
+ local current=getposition(f)
+ setposition(f,offset)
+ shared,nofshared=readpoints(f)
+ offset=getposition(f)
+ setposition(f,current)
+ end
+ for j=1,count do
+ local size=readushort(f)
+ local flags=readushort(f)
+ local index=band(flags,0x0FFF)
+ local haspeak=band(flags,0x8000)~=0
+ local intermediate=band(flags,0x4000)~=0
+ local private=band(flags,0x2000)~=0
+ local peak=nil
+ local start=nil
+ local stop=nil
+ local xvalues=nil
+ local yvalues=nil
+ local points=shared
+ local nofpoints=nofshared
+ if haspeak then
+ peak=readtuplerecord(f,nofaxis)
+ else
+ if index+1>#tuples then
+ report("error, bad tuple index",index)
+ end
+ peak=tuples[index+1]
+ end
+ if intermediate then
+ start=readtuplerecord(f,nofaxis)
+ stop=readtuplerecord(f,nofaxis)
+ end
+ if size>0 then
+ local current=getposition(f)
+ setposition(f,offset)
+ if private then
+ points,nofpoints=readpoints(f)
+ end
+ if nofpoints==0 then
+ nofpoints=allpoints+4
+ end
+ if nofpoints>0 then
+ xvalues=readdeltas(f,nofpoints)
+ yvalues=readdeltas(f,nofpoints)
+ end
+ offset=offset+size
+ setposition(f,current)
+ end
+ if not xvalues and not yvalues then
+ points=nil
+ end
+ local s=1
+ for i=1,nofaxis do
+ local f=factors[i]
+ local peak=peak and peak [i] or 0
+ local start=start and start[i] or (peak<0 and peak or 0)
+ local stop=stop and stop [i] or (peak>0 and peak or 0)
+ if start>peak or peak>stop then
+ elseif start<0 and stop>0 and peak~=0 then
+ elseif peak==0 then
+ elseif f<start or f>stop then
+ s=0
+ break
+ elseif f<peak then
+ s=s*(f-start)/(peak-start)
+ elseif f>peak then
+ s=s*(stop-f)/(stop-peak)
+ else
+ end
+ end
+ if s==0 then
+ if name then
+ report("no deltas applied for glyph %a",name)
+ end
+ else
+ deltas[#deltas+1]={
+ factor=s,
+ points=points,
+ xvalues=xvalues,
+ yvalues=yvalues,
+ }
+ end
+ end
+ if shape.type=="glyph" then
+ applyaxis(glyph,shape,deltas,dowidth)
+ else
+ shape.deltas=deltas
+ end
+ end
+ end
+ startoffset=nextoffset
+ end
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ttf”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-dsp” b5bf2f1c198e027a0d4ededcdf3947b4] ---
+
+if not modules then modules={} end modules ['font-dsp']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+local band=bit32.band
+local extract=bit32.extract
+local bor=bit32.bor
+local lshift=bit32.lshift
+local rshift=bit32.rshift
+local gsub=string.gsub
+local lower=string.lower
+local sub=string.sub
+local strip=string.strip
+local tohash=table.tohash
+local concat=table.concat
+local copy=table.copy
+local reversed=table.reversed
+local sort=table.sort
+local insert=table.insert
+local round=math.round
+local settings_to_hash=utilities.parsers.settings_to_hash_colon_too
+local setmetatableindex=table.setmetatableindex
+local formatters=string.formatters
+local sortedkeys=table.sortedkeys
+local sortedhash=table.sortedhash
+local sequenced=table.sequenced
+local report=logs.reporter("otf reader")
+local readers=fonts.handlers.otf.readers
+local streamreader=readers.streamreader
+local setposition=streamreader.setposition
+local getposition=streamreader.getposition
+local readuinteger=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readulong=streamreader.readcardinal4
+local readinteger=streamreader.readinteger1
+local readshort=streamreader.readinteger2
+local readstring=streamreader.readstring
+local readtag=streamreader.readtag
+local readbytes=streamreader.readbytes
+local readfixed=streamreader.readfixed4
+local read2dot14=streamreader.read2dot14
+local skipshort=streamreader.skipshort
+local skipbytes=streamreader.skip
+local readbytetable=streamreader.readbytetable
+local readbyte=streamreader.readbyte
+local readcardinaltable=streamreader.readcardinaltable
+local readintegertable=streamreader.readintegertable
+local readfword=readshort
+local short=2
+local ushort=2
+local ulong=4
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ setposition=streamreader.setposition
+ getposition=streamreader.getposition
+ readuinteger=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readulong=streamreader.readcardinal4
+ readinteger=streamreader.readinteger1
+ readshort=streamreader.readinteger2
+ readstring=streamreader.readstring
+ readtag=streamreader.readtag
+ readbytes=streamreader.readbytes
+ readfixed=streamreader.readfixed4
+ read2dot14=streamreader.read2dot14
+ skipshort=streamreader.skipshort
+ skipbytes=streamreader.skip
+ readbytetable=streamreader.readbytetable
+ readbyte=streamreader.readbyte
+ readcardinaltable=streamreader.readcardinaltable
+ readintegertable=streamreader.readintegertable
+ readfword=readshort
+end)
+local gsubhandlers={}
+local gposhandlers={}
+readers.gsubhandlers=gsubhandlers
+readers.gposhandlers=gposhandlers
+local helpers=readers.helpers
+local gotodatatable=helpers.gotodatatable
+local setvariabledata=helpers.setvariabledata
+local lookupidoffset=-1
+local classes={
+ "base",
+ "ligature",
+ "mark",
+ "component",
+}
+local gsubtypes={
+ "single",
+ "multiple",
+ "alternate",
+ "ligature",
+ "context",
+ "chainedcontext",
+ "extension",
+ "reversechainedcontextsingle",
+}
+local gpostypes={
+ "single",
+ "pair",
+ "cursive",
+ "marktobase",
+ "marktoligature",
+ "marktomark",
+ "context",
+ "chainedcontext",
+ "extension",
+}
+local chaindirections={
+ context=0,
+ chainedcontext=1,
+ reversechainedcontextsingle=-1,
+}
+local function setmetrics(data,where,tag,d)
+ local w=data[where]
+ if w then
+ local v=w[tag]
+ if v then
+ w[tag]=v+d
+ end
+ end
+end
+local variabletags={
+ hasc=function(data,d) setmetrics(data,"windowsmetrics","typoascender",d) end,
+ hdsc=function(data,d) setmetrics(data,"windowsmetrics","typodescender",d) end,
+ hlgp=function(data,d) setmetrics(data,"windowsmetrics","typolinegap",d) end,
+ hcla=function(data,d) setmetrics(data,"windowsmetrics","winascent",d) end,
+ hcld=function(data,d) setmetrics(data,"windowsmetrics","windescent",d) end,
+ vasc=function(data,d) setmetrics(data,"vhea not done","ascent",d) end,
+ vdsc=function(data,d) setmetrics(data,"vhea not done","descent",d) end,
+ vlgp=function(data,d) setmetrics(data,"vhea not done","linegap",d) end,
+ xhgt=function(data,d) setmetrics(data,"windowsmetrics","xheight",d) end,
+ cpht=function(data,d) setmetrics(data,"windowsmetrics","capheight",d) end,
+ sbxs=function(data,d) setmetrics(data,"windowsmetrics","subscriptxsize",d) end,
+ sbys=function(data,d) setmetrics(data,"windowsmetrics","subscriptysize",d) end,
+ sbxo=function(data,d) setmetrics(data,"windowsmetrics","subscriptxoffset",d) end,
+ sbyo=function(data,d) setmetrics(data,"windowsmetrics","subscriptyoffset",d) end,
+ spxs=function(data,d) setmetrics(data,"windowsmetrics","superscriptxsize",d) end,
+ spys=function(data,d) setmetrics(data,"windowsmetrics","superscriptysize",d) end,
+ spxo=function(data,d) setmetrics(data,"windowsmetrics","superscriptxoffset",d) end,
+ spyo=function(data,d) setmetrics(data,"windowsmetrics","superscriptyoffset",d) end,
+ strs=function(data,d) setmetrics(data,"windowsmetrics","strikeoutsize",d) end,
+ stro=function(data,d) setmetrics(data,"windowsmetrics","strikeoutpos",d) end,
+ unds=function(data,d) setmetrics(data,"postscript","underlineposition",d) end,
+ undo=function(data,d) setmetrics(data,"postscript","underlinethickness",d) end,
+}
+local read_cardinal={
+ streamreader.readcardinal1,
+ streamreader.readcardinal2,
+ streamreader.readcardinal3,
+ streamreader.readcardinal4,
+}
+local read_integer={
+ streamreader.readinteger1,
+ streamreader.readinteger2,
+ streamreader.readinteger3,
+ streamreader.readinteger4,
+}
+local lookupnames={
+ gsub={
+ single="gsub_single",
+ multiple="gsub_multiple",
+ alternate="gsub_alternate",
+ ligature="gsub_ligature",
+ context="gsub_context",
+ chainedcontext="gsub_contextchain",
+ reversechainedcontextsingle="gsub_reversecontextchain",
+ },
+ gpos={
+ single="gpos_single",
+ pair="gpos_pair",
+ cursive="gpos_cursive",
+ marktobase="gpos_mark2base",
+ marktoligature="gpos_mark2ligature",
+ marktomark="gpos_mark2mark",
+ context="gpos_context",
+ chainedcontext="gpos_contextchain",
+ }
+}
+local lookupflags=setmetatableindex(function(t,k)
+ local v={
+ band(k,0x0008)~=0 and true or false,
+ band(k,0x0004)~=0 and true or false,
+ band(k,0x0002)~=0 and true or false,
+ band(k,0x0001)~=0 and true or false,
+ }
+ t[k]=v
+ return v
+end)
+local function axistofactors(str)
+ local t=settings_to_hash(str)
+ for k,v in next,t do
+ t[k]=tonumber(v) or v
+ end
+ return t
+end
+local hash=table.setmetatableindex(function(t,k)
+ local v=sequenced(axistofactors(k),",")
+ t[k]=v
+ return v
+end)
+helpers.normalizedaxishash=hash
+local cleanname=fonts.names and fonts.names.cleanname or function(name)
+ return name and (gsub(lower(name),"[^%a%d]","")) or nil
+end
+helpers.cleanname=cleanname
+function helpers.normalizedaxis(str)
+ return hash[str] or str
+end
+local function getaxisscale(segments,minimum,default,maximum,user)
+ if not minimum or not default or not maximum then
+ return false
+ end
+ if user<minimum then
+ user=minimum
+ elseif user>maximum then
+ user=maximum
+ end
+ if user<default then
+ default=- (default-user)/(default-minimum)
+ elseif user>default then
+ default=(user-default)/(maximum-default)
+ else
+ default=0
+ end
+ if not segments then
+ return default
+ end
+ local e
+ for i=1,#segments do
+ local s=segments[i]
+ if type(s)~="number" then
+ report("using default axis scale")
+ return default
+ elseif s[1]>=default then
+ if s[2]==default then
+ return default
+ else
+ e=i
+ break
+ end
+ end
+ end
+ if e then
+ local b=segments[e-1]
+ local e=segments[e]
+ return b[2]+(e[2]-b[2])*(default-b[1])/(e[1]-b[1])
+ else
+ return false
+ end
+end
+local function getfactors(data,instancespec)
+ if instancespec==true then
+ elseif type(instancespec)~="string" or instancespec=="" then
+ return
+ end
+ local variabledata=data.variabledata
+ if not variabledata then
+ return
+ end
+ local instances=variabledata.instances
+ local axis=variabledata.axis
+ local segments=variabledata.segments
+ if instances and axis then
+ local values
+ if instancespec==true then
+ values={}
+ for i=1,#axis do
+ values[i]={
+ value=axis[i].default,
+ }
+ end
+ else
+ for i=1,#instances do
+ local instance=instances[i]
+ if cleanname(instance.subfamily)==instancespec then
+ values=instance.values
+ break
+ end
+ end
+ end
+ if values then
+ local factors={}
+ for i=1,#axis do
+ local a=axis[i]
+ factors[i]=getaxisscale(segments,a.minimum,a.default,a.maximum,values[i].value)
+ end
+ return factors
+ end
+ local values=axistofactors(hash[instancespec] or instancespec)
+ if values then
+ local factors={}
+ for i=1,#axis do
+ local a=axis[i]
+ local d=a.default
+ factors[i]=getaxisscale(segments,a.minimum,d,a.maximum,values[a.name or a.tag] or d)
+ end
+ return factors
+ end
+ end
+end
+local function getscales(regions,factors)
+ local scales={}
+ for i=1,#regions do
+ local region=regions[i]
+ local s=1
+ for j=1,#region do
+ local axis=region[j]
+ local f=factors[j]
+ local start=axis.start
+ local peak=axis.peak
+ local stop=axis.stop
+ if start>peak or peak>stop then
+ elseif start<0 and stop>0 and peak~=0 then
+ elseif peak==0 then
+ elseif f<start or f>stop then
+ s=0
+ break
+ elseif f<peak then
+ s=s*(f-start)/(peak-start)
+ elseif f>peak then
+ s=s*(stop-f)/(stop-peak)
+ else
+ end
+ end
+ scales[i]=s
+ end
+ return scales
+end
+helpers.getaxisscale=getaxisscale
+helpers.getfactors=getfactors
+helpers.getscales=getscales
+helpers.axistofactors=axistofactors
+local function readvariationdata(f,storeoffset,factors)
+ local position=getposition(f)
+ setposition(f,storeoffset)
+ local format=readushort(f)
+ local regionoffset=storeoffset+readulong(f)
+ local nofdeltadata=readushort(f)
+ local deltadata=readcardinaltable(f,nofdeltadata,ulong)
+ setposition(f,regionoffset)
+ local nofaxis=readushort(f)
+ local nofregions=readushort(f)
+ local regions={}
+ for i=1,nofregions do
+ local t={}
+ for i=1,nofaxis do
+ t[i]={
+ start=read2dot14(f),
+ peak=read2dot14(f),
+ stop=read2dot14(f),
+ }
+ end
+ regions[i]=t
+ end
+ if factors then
+ for i=1,nofdeltadata do
+ setposition(f,storeoffset+deltadata[i])
+ local nofdeltasets=readushort(f)
+ local nofshorts=readushort(f)
+ local nofregions=readushort(f)
+ local usedregions={}
+ local deltas={}
+ for i=1,nofregions do
+ usedregions[i]=regions[readushort(f)+1]
+ end
+ for i=1,nofdeltasets do
+ local t=readintegertable(f,nofshorts,short)
+ for i=nofshorts+1,nofregions do
+ t[i]=readinteger(f)
+ end
+ deltas[i]=t
+ end
+ deltadata[i]={
+ regions=usedregions,
+ deltas=deltas,
+ scales=factors and getscales(usedregions,factors) or nil,
+ }
+ end
+ end
+ setposition(f,position)
+ return regions,deltadata
+end
+helpers.readvariationdata=readvariationdata
+local function readcoverage(f,offset,simple)
+ setposition(f,offset)
+ local coverageformat=readushort(f)
+ if coverageformat==1 then
+ local nofcoverage=readushort(f)
+ if simple then
+ if nofcoverage==1 then
+ return { readushort(f) }
+ elseif nofcoverage==2 then
+ return { readushort(f),readushort(f) }
+ else
+ return readcardinaltable(f,nofcoverage,ushort)
+ end
+ elseif nofcoverage==1 then
+ return { [readushort(f)]=0 }
+ elseif nofcoverage==2 then
+ return { [readushort(f)]=0,[readushort(f)]=1 }
+ else
+ local coverage={}
+ for i=0,nofcoverage-1 do
+ coverage[readushort(f)]=i
+ end
+ return coverage
+ end
+ elseif coverageformat==2 then
+ local nofranges=readushort(f)
+ local coverage={}
+ local n=simple and 1 or 0
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local coverindex=readushort(f)
+ if simple then
+ for i=firstindex,lastindex do
+ coverage[n]=i
+ n=n+1
+ end
+ else
+ for i=firstindex,lastindex do
+ coverage[i]=n
+ n=n+1
+ end
+ end
+ end
+ return coverage
+ else
+ report("unknown coverage format %a ",coverageformat)
+ return {}
+ end
+end
+local function readclassdef(f,offset,preset)
+ setposition(f,offset)
+ local classdefformat=readushort(f)
+ local classdef={}
+ if type(preset)=="number" then
+ for k=0,preset-1 do
+ classdef[k]=1
+ end
+ end
+ if classdefformat==1 then
+ local index=readushort(f)
+ local nofclassdef=readushort(f)
+ for i=1,nofclassdef do
+ classdef[index]=readushort(f)+1
+ index=index+1
+ end
+ elseif classdefformat==2 then
+ local nofranges=readushort(f)
+ local n=0
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local class=readushort(f)+1
+ for i=firstindex,lastindex do
+ classdef[i]=class
+ end
+ end
+ else
+ report("unknown classdef format %a ",classdefformat)
+ end
+ if type(preset)=="table" then
+ for k in next,preset do
+ if not classdef[k] then
+ classdef[k]=1
+ end
+ end
+ end
+ return classdef
+end
+local function classtocoverage(defs)
+ if defs then
+ local list={}
+ for index,class in next,defs do
+ local c=list[class]
+ if c then
+ c[#c+1]=index
+ else
+ list[class]={ index }
+ end
+ end
+ return list
+ end
+end
+local skips={ [0]=0,
+ 1,
+ 1,
+ 2,
+ 1,
+ 2,
+ 2,
+ 3,
+ 2,
+ 2,
+ 3,
+ 2,
+ 3,
+ 3,
+ 4,
+}
+local function readvariation(f,offset)
+ local p=getposition(f)
+ setposition(f,offset)
+ local outer=readushort(f)
+ local inner=readushort(f)
+ local format=readushort(f)
+ setposition(f,p)
+ if format==0x8000 then
+ return outer,inner
+ end
+end
+local function readposition(f,format,mainoffset,getdelta)
+ if format==0 then
+ return false
+ end
+ if format==0x04 then
+ local h=readshort(f)
+ if h==0 then
+ return true
+ else
+ return { 0,0,h,0 }
+ end
+ end
+ if format==0x05 then
+ local x=readshort(f)
+ local h=readshort(f)
+ if x==0 and h==0 then
+ return true
+ else
+ return { x,0,h,0 }
+ end
+ end
+ if format==0x44 then
+ local h=readshort(f)
+ if getdelta then
+ local d=readshort(f)
+ if d>0 then
+ local outer,inner=readvariation(f,mainoffset+d)
+ if outer then
+ h=h+getdelta(outer,inner)
+ end
+ end
+ else
+ skipshort(f,1)
+ end
+ if h==0 then
+ return true
+ else
+ return { 0,0,h,0 }
+ end
+ end
+ local x=band(format,0x1)~=0 and readshort(f) or 0
+ local y=band(format,0x2)~=0 and readshort(f) or 0
+ local h=band(format,0x4)~=0 and readshort(f) or 0
+ local v=band(format,0x8)~=0 and readshort(f) or 0
+ if format>=0x10 then
+ local X=band(format,0x10)~=0 and skipshort(f) or 0
+ local Y=band(format,0x20)~=0 and skipshort(f) or 0
+ local H=band(format,0x40)~=0 and skipshort(f) or 0
+ local V=band(format,0x80)~=0 and skipshort(f) or 0
+ local s=skips[extract(format,4,4)]
+ if s>0 then
+ skipshort(f,s)
+ end
+ if getdelta then
+ if X>0 then
+ local outer,inner=readvariation(f,mainoffset+X)
+ if outer then
+ x=x+getdelta(outer,inner)
+ end
+ end
+ if Y>0 then
+ local outer,inner=readvariation(f,mainoffset+Y)
+ if outer then
+ y=y+getdelta(outer,inner)
+ end
+ end
+ if H>0 then
+ local outer,inner=readvariation(f,mainoffset+H)
+ if outer then
+ h=h+getdelta(outer,inner)
+ end
+ end
+ if V>0 then
+ local outer,inner=readvariation(f,mainoffset+V)
+ if outer then
+ v=v+getdelta(outer,inner)
+ end
+ end
+ end
+ return { x,y,h,v }
+ elseif x==0 and y==0 and h==0 and v==0 then
+ return true
+ else
+ return { x,y,h,v }
+ end
+end
+local function readanchor(f,offset,getdelta)
+ if not offset or offset==0 then
+ return nil
+ end
+ setposition(f,offset)
+ local format=readshort(f)
+ local x=readshort(f)
+ local y=readshort(f)
+ if format==3 then
+ if getdelta then
+ local X=readshort(f)
+ local Y=readshort(f)
+ if X>0 then
+ local outer,inner=readvariation(f,offset+X)
+ if outer then
+ x=x+getdelta(outer,inner)
+ end
+ end
+ if Y>0 then
+ local outer,inner=readvariation(f,offset+Y)
+ if outer then
+ y=y+getdelta(outer,inner)
+ end
+ end
+ else
+ skipshort(f,2)
+ end
+ return { x,y }
+ else
+ return { x,y }
+ end
+end
+local function readfirst(f,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ return { readushort(f) }
+end
+function readarray(f,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ local n=readushort(f)
+ if n==1 then
+ return { readushort(f) },1
+ elseif n>0 then
+ return readcardinaltable(f,n,ushort),n
+ end
+end
+local function readcoveragearray(f,offset,t,simple)
+ if not t then
+ return nil
+ end
+ local n=#t
+ if n==0 then
+ return nil
+ end
+ for i=1,n do
+ t[i]=readcoverage(f,offset+t[i],simple)
+ end
+ return t
+end
+local function covered(subset,all)
+ local used,u
+ for i=1,#subset do
+ local s=subset[i]
+ if all[s] then
+ if used then
+ u=u+1
+ used[u]=s
+ else
+ u=1
+ used={ s }
+ end
+ end
+ end
+ return used
+end
+local function readlookuparray(f,noflookups,nofcurrent)
+ local lookups={}
+ if noflookups>0 then
+ local length=0
+ for i=1,noflookups do
+ local index=readushort(f)+1
+ if index>length then
+ length=index
+ end
+ local lookup=readushort(f)+1
+ local list=lookups[index]
+ if list then
+ list[#list+1]=lookup
+ else
+ lookups[index]={ lookup }
+ end
+ end
+ for index=1,length do
+ if not lookups[index] then
+ lookups[index]=false
+ end
+ end
+ end
+ return lookups
+end
+local function unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ coverage=readcoverage(f,tableoffset+coverage,true)
+ for i=1,#subclasssets do
+ local offset=subclasssets[i]
+ if offset>0 then
+ local firstcoverage=coverage[i]
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofcurrent=readushort(f)
+ local noflookups=readushort(f)
+ local current={ { firstcoverage } }
+ for i=2,nofcurrent do
+ current[i]={ readushort(f) }
+ end
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ current=current,
+ lookups=lookups
+ }
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","unchainedcontext",subtype)
+ end
+ return {
+ format="glyphs",
+ rules=rules,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local currentclassdef=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ coverage=readcoverage(f,tableoffset+coverage)
+ currentclassdef=readclassdef(f,tableoffset+currentclassdef,coverage)
+ local currentclasses=classtocoverage(currentclassdef,fontdata.glyphs)
+ for class=1,#subclasssets do
+ local offset=subclasssets[class]
+ if offset>0 then
+ local firstcoverage=currentclasses[class]
+ if firstcoverage then
+ firstcoverage=covered(firstcoverage,coverage)
+ if firstcoverage then
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofcurrent=readushort(f)
+ local noflookups=readushort(f)
+ local current={ firstcoverage }
+ for i=2,nofcurrent do
+ current[i]=currentclasses[readushort(f)+1]
+ end
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ current=current,
+ lookups=lookups
+ }
+ end
+ else
+ report("no coverage")
+ end
+ else
+ report("no coverage class")
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","unchainedcontext",subtype)
+ end
+ return {
+ format="class",
+ rules=rules,
+ }
+ elseif subtype==3 then
+ local nofglyphs=readushort(f)
+ local noflookups=readushort(f)
+ local current=readcardinaltable(f,nofglyphs,ushort)
+ local lookups=readlookuparray(f,noflookups,#current)
+ current=readcoveragearray(f,tableoffset,current,true)
+ return {
+ format="coverage",
+ rules={
+ {
+ current=current,
+ lookups=lookups,
+ }
+ }
+ }
+ else
+ report("unsupported subtype %a in %a %s",subtype,"unchainedcontext",what)
+ end
+end
+local function chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ coverage=readcoverage(f,tableoffset+coverage,true)
+ for i=1,#subclasssets do
+ local offset=subclasssets[i]
+ if offset>0 then
+ local firstcoverage=coverage[i]
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofbefore=readushort(f)
+ local before
+ if nofbefore>0 then
+ before={}
+ for i=1,nofbefore do
+ before[i]={ readushort(f) }
+ end
+ end
+ local nofcurrent=readushort(f)
+ local current={ { firstcoverage } }
+ for i=2,nofcurrent do
+ current[i]={ readushort(f) }
+ end
+ local nofafter=readushort(f)
+ local after
+ if nofafter>0 then
+ after={}
+ for i=1,nofafter do
+ after[i]={ readushort(f) }
+ end
+ end
+ local noflookups=readushort(f)
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ before=before,
+ current=current,
+ after=after,
+ lookups=lookups,
+ }
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","chainedcontext",subtype)
+ end
+ return {
+ format="glyphs",
+ rules=rules,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local beforeclassdef=readushort(f)
+ local currentclassdef=readushort(f)
+ local afterclassdef=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ local coverage=readcoverage(f,tableoffset+coverage)
+ local beforeclassdef=readclassdef(f,tableoffset+beforeclassdef,nofglyphs)
+ local currentclassdef=readclassdef(f,tableoffset+currentclassdef,coverage)
+ local afterclassdef=readclassdef(f,tableoffset+afterclassdef,nofglyphs)
+ local beforeclasses=classtocoverage(beforeclassdef,fontdata.glyphs)
+ local currentclasses=classtocoverage(currentclassdef,fontdata.glyphs)
+ local afterclasses=classtocoverage(afterclassdef,fontdata.glyphs)
+ for class=1,#subclasssets do
+ local offset=subclasssets[class]
+ if offset>0 then
+ local firstcoverage=currentclasses[class]
+ if firstcoverage then
+ firstcoverage=covered(firstcoverage,coverage)
+ if firstcoverage then
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofbefore=readushort(f)
+ local before
+ if nofbefore>0 then
+ before={}
+ for i=1,nofbefore do
+ before[i]=beforeclasses[readushort(f)+1]
+ end
+ end
+ local nofcurrent=readushort(f)
+ local current={ firstcoverage }
+ for i=2,nofcurrent do
+ current[i]=currentclasses[readushort(f)+1]
+ end
+ local nofafter=readushort(f)
+ local after
+ if nofafter>0 then
+ after={}
+ for i=1,nofafter do
+ after[i]=afterclasses[readushort(f)+1]
+ end
+ end
+ local noflookups=readushort(f)
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ before=before,
+ current=current,
+ after=after,
+ lookups=lookups,
+ }
+ end
+ else
+ report("no coverage")
+ end
+ else
+ report("class is not covered")
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","chainedcontext",subtype)
+ end
+ return {
+ format="class",
+ rules=rules,
+ }
+ elseif subtype==3 then
+ local before=readarray(f)
+ local current=readarray(f)
+ local after=readarray(f)
+ local noflookups=readushort(f)
+ local lookups=readlookuparray(f,noflookups,#current)
+ before=readcoveragearray(f,tableoffset,before,true)
+ current=readcoveragearray(f,tableoffset,current,true)
+ after=readcoveragearray(f,tableoffset,after,true)
+ return {
+ format="coverage",
+ rules={
+ {
+ before=before,
+ current=current,
+ after=after,
+ lookups=lookups,
+ }
+ }
+ }
+ else
+ report("unsupported subtype %a in %a %s",subtype,"chainedcontext",what)
+ end
+end
+local function extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,types,handlers,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local lookuptype=types[readushort(f)]
+ local faroffset=readulong(f)
+ local handler=handlers[lookuptype]
+ if handler then
+ return handler(f,fontdata,lookupid,tableoffset+faroffset,0,glyphs,nofglyphs),lookuptype
+ else
+ report("no handler for lookuptype %a subtype %a in %s %s",lookuptype,subtype,what,"extension")
+ end
+ else
+ report("unsupported subtype %a in %s %s",subtype,what,"extension")
+ end
+end
+function gsubhandlers.single(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local delta=readshort(f)
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index in next,coverage do
+ local newindex=(index+delta)%65536
+ if index>nofglyphs or newindex>nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)","single",subtype,index,newindex,nofglyphs)
+ coverage[index]=nil
+ else
+ coverage[index]=newindex
+ end
+ end
+ return {
+ coverage=coverage
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local nofreplacements=readushort(f)
+ local replacements=readcardinaltable(f,nofreplacements,ushort)
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ newindex=newindex+1
+ if index>nofglyphs or newindex>nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)","single",subtype,index,newindex,nofglyphs)
+ coverage[index]=nil
+ else
+ coverage[index]=replacements[newindex]
+ end
+ end
+ return {
+ coverage=coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"single")
+ end
+end
+local function sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local nofsequence=readushort(f)
+ local sequences=readcardinaltable(f,nofsequence,ushort)
+ for i=1,nofsequence do
+ setposition(f,tableoffset+sequences[i])
+ sequences[i]=readcardinaltable(f,readushort(f),ushort)
+ end
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ newindex=newindex+1
+ if index>nofglyphs or newindex>nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)",what,subtype,index,newindex,nofglyphs)
+ coverage[index]=nil
+ else
+ coverage[index]=sequences[newindex]
+ end
+ end
+ return {
+ coverage=coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,what)
+ end
+end
+function gsubhandlers.multiple(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"multiple")
+end
+function gsubhandlers.alternate(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"alternate")
+end
+function gsubhandlers.ligature(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local nofsets=readushort(f)
+ local ligatures=readcardinaltable(f,nofsets,ushort)
+ for i=1,nofsets do
+ local offset=lookupoffset+offset+ligatures[i]
+ setposition(f,offset)
+ local n=readushort(f)
+ if n==1 then
+ ligatures[i]={ offset+readushort(f) }
+ else
+ local l={}
+ for i=1,n do
+ l[i]=offset+readushort(f)
+ end
+ ligatures[i]=l
+ end
+ end
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ local hash={}
+ local ligatures=ligatures[newindex+1]
+ for i=1,#ligatures do
+ local offset=ligatures[i]
+ setposition(f,offset)
+ local lig=readushort(f)
+ local cnt=readushort(f)
+ local hsh=hash
+ for i=2,cnt do
+ local c=readushort(f)
+ local h=hsh[c]
+ if not h then
+ h={}
+ hsh[c]=h
+ end
+ hsh=h
+ end
+ hsh.ligature=lig
+ end
+ coverage[index]=hash
+ end
+ return {
+ coverage=coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"ligature")
+ end
+end
+function gsubhandlers.context(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"substitution"),"context"
+end
+function gsubhandlers.chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"substitution"),"chainedcontext"
+end
+function gsubhandlers.extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,gsubtypes,gsubhandlers,"substitution")
+end
+function gsubhandlers.reversechainedcontextsingle(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local current=readfirst(f)
+ local before=readarray(f)
+ local after=readarray(f)
+ local replacements=readarray(f)
+ current=readcoveragearray(f,tableoffset,current,true)
+ before=readcoveragearray(f,tableoffset,before,true)
+ after=readcoveragearray(f,tableoffset,after,true)
+ return {
+ format="reversecoverage",
+ rules={
+ {
+ before=before,
+ current=current,
+ after=after,
+ replacements=replacements,
+ }
+ }
+ },"reversechainedcontextsingle"
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"reversechainedcontextsingle")
+ end
+end
+local function readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+ local done={}
+ for i=1,#sets do
+ local offset=sets[i]
+ local reused=done[offset]
+ if not reused then
+ offset=tableoffset+offset
+ setposition(f,offset)
+ local n=readushort(f)
+ reused={}
+ for i=1,n do
+ reused[i]={
+ readushort(f),
+ readposition(f,format1,offset,getdelta),
+ readposition(f,format2,offset,getdelta),
+ }
+ end
+ done[offset]=reused
+ end
+ sets[i]=reused
+ end
+ return sets
+end
+local function readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,mainoffset,getdelta)
+ local classlist1={}
+ for i=1,nofclasses1 do
+ local classlist2={}
+ classlist1[i]=classlist2
+ for j=1,nofclasses2 do
+ local one=readposition(f,format1,mainoffset,getdelta)
+ local two=readposition(f,format2,mainoffset,getdelta)
+ if one or two then
+ classlist2[j]={ one,two }
+ else
+ classlist2[j]=false
+ end
+ end
+ end
+ return classlist1
+end
+function gposhandlers.single(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local coverage=readushort(f)
+ local format=readushort(f)
+ local value=readposition(f,format,tableoffset,getdelta)
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ coverage[index]=value
+ end
+ return {
+ format="single",
+ coverage=coverage,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local format=readushort(f)
+ local nofvalues=readushort(f)
+ local values={}
+ for i=1,nofvalues do
+ values[i]=readposition(f,format,tableoffset,getdelta)
+ end
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ coverage[index]=values[newindex+1]
+ end
+ return {
+ format="single",
+ coverage=coverage,
+ }
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"single")
+ end
+end
+function gposhandlers.pair(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local coverage=readushort(f)
+ local format1=readushort(f)
+ local format2=readushort(f)
+ local sets=readarray(f)
+ sets=readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+ coverage=readcoverage(f,tableoffset+coverage)
+ local shared={}
+ for index,newindex in next,coverage do
+ local set=sets[newindex+1]
+ local hash={}
+ for i=1,#set do
+ local value=set[i]
+ if value then
+ local other=value[1]
+ local share=shared[value]
+ if share==nil then
+ local first=value[2]
+ local second=value[3]
+ if first or second then
+ share={ first,second or nil }
+ else
+ share=false
+ end
+ shared[value]=share
+ end
+ hash[other]=share or nil
+ end
+ end
+ coverage[index]=hash
+ end
+ return {
+ shared=shared and true or nil,
+ format="pair",
+ coverage=coverage,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local format1=readushort(f)
+ local format2=readushort(f)
+ local classdef1=readushort(f)
+ local classdef2=readushort(f)
+ local nofclasses1=readushort(f)
+ local nofclasses2=readushort(f)
+ local classlist=readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,tableoffset,getdelta)
+ coverage=readcoverage(f,tableoffset+coverage)
+ classdef1=readclassdef(f,tableoffset+classdef1,coverage)
+ classdef2=readclassdef(f,tableoffset+classdef2,nofglyphs)
+ local usedcoverage={}
+ local shared={}
+ for g1,c1 in next,classdef1 do
+ if coverage[g1] then
+ local l1=classlist[c1]
+ if l1 then
+ local hash={}
+ for paired,class in next,classdef2 do
+ local offsets=l1[class]
+ if offsets then
+ local first=offsets[1]
+ local second=offsets[2]
+ if first or second then
+ local s1=shared[first]
+ if s1==nil then
+ s1={}
+ shared[first]=s1
+ end
+ local s2=s1[second]
+ if s2==nil then
+ s2={ first,second or nil }
+ s1[second]=s2
+ end
+ hash[paired]=s2
+ end
+ end
+ end
+ usedcoverage[g1]=hash
+ end
+ end
+ end
+ return {
+ shared=shared and true or nil,
+ format="pair",
+ coverage=usedcoverage,
+ }
+ elseif subtype==3 then
+ report("yet unsupported subtype %a in %a positioning",subtype,"pair")
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"pair")
+ end
+end
+function gposhandlers.cursive(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local coverage=tableoffset+readushort(f)
+ local nofrecords=readushort(f)
+ local records={}
+ for i=1,nofrecords do
+ local entry=readushort(f)
+ local exit=readushort(f)
+ records[i]={
+ entry~=0 and (tableoffset+entry) or false,
+ exit~=0 and (tableoffset+exit ) or nil,
+ }
+ end
+ local cc=(fontdata.temporary.cursivecount or 0)+1
+ fontdata.temporary.cursivecount=cc
+ cc="cc-"..cc
+ coverage=readcoverage(f,coverage)
+ for i=1,nofrecords do
+ local r=records[i]
+ records[i]={
+ cc,
+ readanchor(f,r[1],getdelta) or false,
+ readanchor(f,r[2],getdelta) or nil,
+ }
+ end
+ for index,newindex in next,coverage do
+ coverage[index]=records[newindex+1]
+ end
+ return {
+ coverage=coverage,
+ }
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"cursive")
+ end
+end
+local function handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,ligature)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local markcoverage=tableoffset+readushort(f)
+ local basecoverage=tableoffset+readushort(f)
+ local nofclasses=readushort(f)
+ local markoffset=tableoffset+readushort(f)
+ local baseoffset=tableoffset+readushort(f)
+ local markcoverage=readcoverage(f,markcoverage)
+ local basecoverage=readcoverage(f,basecoverage,true)
+ setposition(f,markoffset)
+ local markclasses={}
+ local nofmarkclasses=readushort(f)
+ local lastanchor=fontdata.lastanchor or 0
+ local usedanchors={}
+ for i=1,nofmarkclasses do
+ local class=readushort(f)+1
+ local offset=readushort(f)
+ if offset==0 then
+ markclasses[i]=false
+ else
+ markclasses[i]={ class,markoffset+offset }
+ end
+ usedanchors[class]=true
+ end
+ for i=1,nofmarkclasses do
+ local mc=markclasses[i]
+ if mc then
+ mc[2]=readanchor(f,mc[2],getdelta)
+ end
+ end
+ setposition(f,baseoffset)
+ local nofbaserecords=readushort(f)
+ local baserecords={}
+ if ligature then
+ for i=1,nofbaserecords do
+ local offset=readushort(f)
+ if offset==0 then
+ baserecords[i]=false
+ else
+ baserecords[i]=baseoffset+offset
+ end
+ end
+ for i=1,nofbaserecords do
+ local recordoffset=baserecords[i]
+ if recordoffset then
+ setposition(f,recordoffset)
+ local nofcomponents=readushort(f)
+ local components={}
+ for i=1,nofcomponents do
+ local classes={}
+ for i=1,nofclasses do
+ local offset=readushort(f)
+ if offset~=0 then
+ classes[i]=recordoffset+offset
+ else
+ classes[i]=false
+ end
+ end
+ components[i]=classes
+ end
+ baserecords[i]=components
+ end
+ end
+ local baseclasses={}
+ for i=1,nofclasses do
+ baseclasses[i]={}
+ end
+ for i=1,nofbaserecords do
+ local components=baserecords[i]
+ if components then
+ local b=basecoverage[i]
+ for c=1,#components do
+ local classes=components[c]
+ if classes then
+ for i=1,nofclasses do
+ local anchor=readanchor(f,classes[i],getdelta)
+ local bclass=baseclasses[i]
+ local bentry=bclass[b]
+ if bentry then
+ bentry[c]=anchor
+ else
+ bclass[b]={ [c]=anchor }
+ end
+ end
+ end
+ end
+ end
+ end
+ for index,newindex in next,markcoverage do
+ markcoverage[index]=markclasses[newindex+1] or nil
+ end
+ return {
+ format="ligature",
+ baseclasses=baseclasses,
+ coverage=markcoverage,
+ }
+ else
+ for i=1,nofbaserecords do
+ local r={}
+ for j=1,nofclasses do
+ local offset=readushort(f)
+ if offset==0 then
+ r[j]=false
+ else
+ r[j]=baseoffset+offset
+ end
+ end
+ baserecords[i]=r
+ end
+ local baseclasses={}
+ for i=1,nofclasses do
+ baseclasses[i]={}
+ end
+ for i=1,nofbaserecords do
+ local r=baserecords[i]
+ local b=basecoverage[i]
+ for j=1,nofclasses do
+ baseclasses[j][b]=readanchor(f,r[j],getdelta)
+ end
+ end
+ for index,newindex in next,markcoverage do
+ markcoverage[index]=markclasses[newindex+1] or nil
+ end
+ return {
+ format="base",
+ baseclasses=baseclasses,
+ coverage=markcoverage,
+ }
+ end
+ else
+ report("unsupported subtype %a in",subtype)
+ end
+end
+function gposhandlers.marktobase(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+end
+function gposhandlers.marktoligature(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,true)
+end
+function gposhandlers.marktomark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+end
+function gposhandlers.context(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"positioning"),"context"
+end
+function gposhandlers.chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"positioning"),"chainedcontext"
+end
+function gposhandlers.extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,gpostypes,gposhandlers,"positioning")
+end
+do
+ local plugins={}
+ function plugins.size(f,fontdata,tableoffset,feature)
+ if fontdata.designsize then
+ else
+ local function check(offset)
+ setposition(f,offset)
+ local designsize=readushort(f)
+ if designsize>0 then
+ local fontstyleid=readushort(f)
+ local guimenuid=readushort(f)
+ local minsize=readushort(f)
+ local maxsize=readushort(f)
+ if minsize==0 and maxsize==0 and fontstyleid==0 and guimenuid==0 then
+ minsize=designsize
+ maxsize=designsize
+ end
+ if designsize>=minsize and designsize<=maxsize then
+ return minsize,maxsize,designsize
+ end
+ end
+ end
+ local minsize,maxsize,designsize=check(tableoffset+feature.offset+feature.parameters)
+ if not designsize then
+ minsize,maxsize,designsize=check(tableoffset+feature.parameters)
+ if designsize then
+ report("bad size feature in %a, falling back to wrong offset",fontdata.filename or "?")
+ else
+ report("bad size feature in %a,",fontdata.filename or "?")
+ end
+ end
+ if designsize then
+ fontdata.minsize=minsize
+ fontdata.maxsize=maxsize
+ fontdata.designsize=designsize
+ end
+ end
+ end
+ local function reorderfeatures(fontdata,scripts,features)
+ local scriptlangs={}
+ local featurehash={}
+ local featureorder={}
+ for script,languages in next,scripts do
+ for language,record in next,languages do
+ local hash={}
+ local list=record.featureindices
+ for k=1,#list do
+ local index=list[k]
+ local feature=features[index]
+ local lookups=feature.lookups
+ local tag=feature.tag
+ if tag then
+ hash[tag]=true
+ end
+ if lookups then
+ for i=1,#lookups do
+ local lookup=lookups[i]
+ local o=featureorder[lookup]
+ if o then
+ local okay=true
+ for i=1,#o do
+ if o[i]==tag then
+ okay=false
+ break
+ end
+ end
+ if okay then
+ o[#o+1]=tag
+ end
+ else
+ featureorder[lookup]={ tag }
+ end
+ local f=featurehash[lookup]
+ if f then
+ local h=f[tag]
+ if h then
+ local s=h[script]
+ if s then
+ s[language]=true
+ else
+ h[script]={ [language]=true }
+ end
+ else
+ f[tag]={ [script]={ [language]=true } }
+ end
+ else
+ featurehash[lookup]={ [tag]={ [script]={ [language]=true } } }
+ end
+ local h=scriptlangs[tag]
+ if h then
+ local s=h[script]
+ if s then
+ s[language]=true
+ else
+ h[script]={ [language]=true }
+ end
+ else
+ scriptlangs[tag]={ [script]={ [language]=true } }
+ end
+ end
+ end
+ end
+ end
+ end
+ return scriptlangs,featurehash,featureorder
+ end
+ local function readscriplan(f,fontdata,scriptoffset)
+ setposition(f,scriptoffset)
+ local nofscripts=readushort(f)
+ local scripts={}
+ for i=1,nofscripts do
+ scripts[readtag(f)]=scriptoffset+readushort(f)
+ end
+ local languagesystems=setmetatableindex("table")
+ for script,offset in next,scripts do
+ setposition(f,offset)
+ local defaultoffset=readushort(f)
+ local noflanguages=readushort(f)
+ local languages={}
+ if defaultoffset>0 then
+ languages.dflt=languagesystems[offset+defaultoffset]
+ end
+ for i=1,noflanguages do
+ local language=readtag(f)
+ local offset=offset+readushort(f)
+ languages[language]=languagesystems[offset]
+ end
+ scripts[script]=languages
+ end
+ for offset,usedfeatures in next,languagesystems do
+ if offset>0 then
+ setposition(f,offset)
+ local featureindices={}
+ usedfeatures.featureindices=featureindices
+ usedfeatures.lookuporder=readushort(f)
+ usedfeatures.requiredindex=readushort(f)
+ local noffeatures=readushort(f)
+ for i=1,noffeatures do
+ featureindices[i]=readushort(f)+1
+ end
+ end
+ end
+ return scripts
+ end
+ local function readfeatures(f,fontdata,featureoffset)
+ setposition(f,featureoffset)
+ local features={}
+ local noffeatures=readushort(f)
+ for i=1,noffeatures do
+ features[i]={
+ tag=readtag(f),
+ offset=readushort(f)
+ }
+ end
+ for i=1,noffeatures do
+ local feature=features[i]
+ local offset=featureoffset+feature.offset
+ setposition(f,offset)
+ local parameters=readushort(f)
+ local noflookups=readushort(f)
+ if noflookups>0 then
+ local lookups=readcardinaltable(f,noflookups,ushort)
+ feature.lookups=lookups
+ for j=1,noflookups do
+ lookups[j]=lookups[j]+1
+ end
+ end
+ if parameters>0 then
+ feature.parameters=parameters
+ local plugin=plugins[feature.tag]
+ if plugin then
+ plugin(f,fontdata,featureoffset,feature)
+ end
+ end
+ end
+ return features
+ end
+ local function readlookups(f,lookupoffset,lookuptypes,featurehash,featureorder)
+ setposition(f,lookupoffset)
+ local noflookups=readushort(f)
+ local lookups=readcardinaltable(f,noflookups,ushort)
+ for lookupid=1,noflookups do
+ local offset=lookups[lookupid]
+ setposition(f,lookupoffset+offset)
+ local subtables={}
+ local typebits=readushort(f)
+ local flagbits=readushort(f)
+ local lookuptype=lookuptypes[typebits]
+ local lookupflags=lookupflags[flagbits]
+ local nofsubtables=readushort(f)
+ for j=1,nofsubtables do
+ subtables[j]=offset+readushort(f)
+ end
+ local markclass=band(flagbits,0x0010)~=0
+ if markclass then
+ markclass=readushort(f)
+ end
+ local markset=rshift(flagbits,8)
+ if markset>0 then
+ markclass=markset
+ end
+ lookups[lookupid]={
+ type=lookuptype,
+ flags=lookupflags,
+ name=lookupid,
+ subtables=subtables,
+ markclass=markclass,
+ features=featurehash[lookupid],
+ order=featureorder[lookupid],
+ }
+ end
+ return lookups
+ end
+ local f_lookupname=formatters["%s_%s_%s"]
+ local function resolvelookups(f,lookupoffset,fontdata,lookups,lookuptypes,lookuphandlers,what,tableoffset)
+ local sequences=fontdata.sequences or {}
+ local sublookuplist=fontdata.sublookups or {}
+ fontdata.sequences=sequences
+ fontdata.sublookups=sublookuplist
+ local nofsublookups=#sublookuplist
+ local nofsequences=#sequences
+ local lastsublookup=nofsublookups
+ local lastsequence=nofsequences
+ local lookupnames=lookupnames[what]
+ local sublookuphash={}
+ local sublookupcheck={}
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs or #glyphs
+ local noflookups=#lookups
+ local lookupprefix=sub(what,2,2)
+ local usedlookups=false
+ for lookupid=1,noflookups do
+ local lookup=lookups[lookupid]
+ local lookuptype=lookup.type
+ local subtables=lookup.subtables
+ local features=lookup.features
+ local handler=lookuphandlers[lookuptype]
+ if handler then
+ local nofsubtables=#subtables
+ local order=lookup.order
+ local flags=lookup.flags
+ if flags[1] then flags[1]="mark" end
+ if flags[2] then flags[2]="ligature" end
+ if flags[3] then flags[3]="base" end
+ local markclass=lookup.markclass
+ if nofsubtables>0 then
+ local steps={}
+ local nofsteps=0
+ local oldtype=nil
+ for s=1,nofsubtables do
+ local step,lt=handler(f,fontdata,lookupid,lookupoffset,subtables[s],glyphs,nofglyphs)
+ if lt then
+ lookuptype=lt
+ if oldtype and lt~=oldtype then
+ report("messy %s lookup type %a and %a",what,lookuptype,oldtype)
+ end
+ oldtype=lookuptype
+ end
+ if not step then
+ report("unsupported %s lookup type %a",what,lookuptype)
+ else
+ nofsteps=nofsteps+1
+ steps[nofsteps]=step
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local before=rule.before
+ local current=rule.current
+ local after=rule.after
+ local replacements=rule.replacements
+ if before then
+ for i=1,#before do
+ before[i]=tohash(before[i])
+ end
+ rule.before=reversed(before)
+ end
+ if current then
+ if replacements then
+ local first=current[1]
+ local hash={}
+ local repl={}
+ for i=1,#first do
+ local c=first[i]
+ hash[c]=true
+ repl[c]=replacements[i]
+ end
+ rule.current={ hash }
+ rule.replacements=repl
+ else
+ for i=1,#current do
+ current[i]=tohash(current[i])
+ end
+ end
+ else
+ end
+ if after then
+ for i=1,#after do
+ after[i]=tohash(after[i])
+ end
+ end
+ if usedlookups then
+ local lookups=rule.lookups
+ if lookups then
+ for k,v in next,lookups do
+ if v then
+ for k,v in next,v do
+ usedlookups[v]=usedlookups[v]+1
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if nofsteps~=nofsubtables then
+ report("bogus subtables removed in %s lookup type %a",what,lookuptype)
+ end
+ lookuptype=lookupnames[lookuptype] or lookuptype
+ if features then
+ nofsequences=nofsequences+1
+ local l={
+ index=nofsequences,
+ name=f_lookupname(lookupprefix,"s",lookupid+lookupidoffset),
+ steps=steps,
+ nofsteps=nofsteps,
+ type=lookuptype,
+ markclass=markclass or nil,
+ flags=flags,
+ order=order,
+ features=features,
+ }
+ sequences[nofsequences]=l
+ lookup.done=l
+ else
+ nofsublookups=nofsublookups+1
+ local l={
+ index=nofsublookups,
+ name=f_lookupname(lookupprefix,"l",lookupid+lookupidoffset),
+ steps=steps,
+ nofsteps=nofsteps,
+ type=lookuptype,
+ markclass=markclass or nil,
+ flags=flags,
+ }
+ sublookuplist[nofsublookups]=l
+ sublookuphash[lookupid]=nofsublookups
+ sublookupcheck[lookupid]=0
+ lookup.done=l
+ end
+ else
+ report("no subtables for lookup %a",lookupid)
+ end
+ else
+ report("no handler for lookup %a with type %a",lookupid,lookuptype)
+ end
+ end
+ if usedlookups then
+ report("used %s lookups: % t",what,sortedkeys(usedlookups))
+ end
+ local reported={}
+ local function report_issue(i,what,sequence,kind)
+ local name=sequence.name
+ if not reported[name] then
+ report("rule %i in %s lookup %a has %s lookups",i,what,name,kind)
+ reported[name]=true
+ end
+ end
+ for i=lastsequence+1,nofsequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ for i=1,#steps do
+ local step=steps[i]
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local rlookups=rule.lookups
+ if not rlookups then
+ report_issue(i,what,sequence,"no")
+ elseif not next(rlookups) then
+ rule.lookups=nil
+ else
+ local length=#rlookups
+ for index=1,length do
+ local lookuplist=rlookups[index]
+ if lookuplist then
+ local length=#lookuplist
+ local found={}
+ local noffound=0
+ for index=1,length do
+ local lookupid=lookuplist[index]
+ if lookupid then
+ local h=sublookuphash[lookupid]
+ if not h then
+ local lookup=lookups[lookupid]
+ if lookup then
+ local d=lookup.done
+ if d then
+ nofsublookups=nofsublookups+1
+ local l={
+ index=nofsublookups,
+ name=f_lookupname(lookupprefix,"d",lookupid+lookupidoffset),
+ derived=true,
+ steps=d.steps,
+ nofsteps=d.nofsteps,
+ type=d.lookuptype or "gsub_single",
+ markclass=d.markclass or nil,
+ flags=d.flags,
+ }
+ sublookuplist[nofsublookups]=copy(l)
+ sublookuphash[lookupid]=nofsublookups
+ sublookupcheck[lookupid]=1
+ h=nofsublookups
+ else
+ report_issue(i,what,sequence,"missing")
+ rule.lookups=nil
+ break
+ end
+ else
+ report_issue(i,what,sequence,"bad")
+ rule.lookups=nil
+ break
+ end
+ else
+ sublookupcheck[lookupid]=sublookupcheck[lookupid]+1
+ end
+ if h then
+ noffound=noffound+1
+ found[noffound]=h
+ end
+ end
+ end
+ rlookups[index]=noffound>0 and found or false
+ else
+ rlookups[index]=false
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ for i,n in sortedhash(sublookupcheck) do
+ local l=lookups[i]
+ local t=l.type
+ if n==0 and t~="extension" then
+ local d=l.done
+ report("%s lookup %s of type %a is not used",what,d and d.name or l.name,t)
+ end
+ end
+ end
+ local function loadvariations(f,fontdata,variationsoffset,lookuptypes,featurehash,featureorder)
+ setposition(f,variationsoffset)
+ local version=readulong(f)
+ local nofrecords=readulong(f)
+ local records={}
+ for i=1,nofrecords do
+ records[i]={
+ conditions=readulong(f),
+ substitutions=readulong(f),
+ }
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ local offset=record.conditions
+ if offset==0 then
+ record.condition=nil
+ record.matchtype="always"
+ else
+ local offset=variationsoffset+offset
+ setposition(f,offset)
+ local nofconditions=readushort(f)
+ local conditions={}
+ for i=1,nofconditions do
+ conditions[i]=offset+readulong(f)
+ end
+ record.conditions=conditions
+ record.matchtype="condition"
+ end
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ if record.matchtype=="condition" then
+ local conditions=record.conditions
+ for i=1,#conditions do
+ setposition(f,conditions[i])
+ conditions[i]={
+ format=readushort(f),
+ axis=readushort(f),
+ minvalue=read2dot14(f),
+ maxvalue=read2dot14(f),
+ }
+ end
+ end
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ local offset=record.substitutions
+ if offset==0 then
+ record.substitutions={}
+ else
+ setposition(f,variationsoffset+offset)
+ local version=readulong(f)
+ local nofsubstitutions=readushort(f)
+ local substitutions={}
+ for i=1,nofsubstitutions do
+ substitutions[readushort(f)]=readulong(f)
+ end
+ for index,alternates in sortedhash(substitutions) do
+ if index==0 then
+ record.substitutions=false
+ else
+ local tableoffset=variationsoffset+offset+alternates
+ setposition(f,tableoffset)
+ local parameters=readulong(f)
+ local noflookups=readushort(f)
+ local lookups=readcardinaltable(f,noflookups,ushort)
+ record.substitutions=lookups
+ end
+ end
+ end
+ end
+ setvariabledata(fontdata,"features",records)
+ end
+ local function readscripts(f,fontdata,what,lookuptypes,lookuphandlers,lookupstoo)
+ local tableoffset=gotodatatable(f,fontdata,what,true)
+ if tableoffset then
+ local version=readulong(f)
+ local scriptoffset=tableoffset+readushort(f)
+ local featureoffset=tableoffset+readushort(f)
+ local lookupoffset=tableoffset+readushort(f)
+ local variationsoffset=version>0x00010000 and (tableoffset+readulong(f)) or 0
+ if not scriptoffset then
+ return
+ end
+ local scripts=readscriplan(f,fontdata,scriptoffset)
+ local features=readfeatures(f,fontdata,featureoffset)
+ local scriptlangs,featurehash,featureorder=reorderfeatures(fontdata,scripts,features)
+ if fontdata.features then
+ fontdata.features[what]=scriptlangs
+ else
+ fontdata.features={ [what]=scriptlangs }
+ end
+ if not lookupstoo then
+ return
+ end
+ local lookups=readlookups(f,lookupoffset,lookuptypes,featurehash,featureorder)
+ if lookups then
+ resolvelookups(f,lookupoffset,fontdata,lookups,lookuptypes,lookuphandlers,what,tableoffset)
+ end
+ if variationsoffset>0 then
+ loadvariations(f,fontdata,variationsoffset,lookuptypes,featurehash,featureorder)
+ end
+ end
+ end
+ local function checkkerns(f,fontdata,specification)
+ local datatable=fontdata.tables.kern
+ if not datatable then
+ return
+ end
+ local features=fontdata.features
+ local gposfeatures=features and features.gpos
+ local name
+ if not gposfeatures or not gposfeatures.kern then
+ name="kern"
+ elseif specification.globalkerns then
+ name="globalkern"
+ else
+ report("ignoring global kern table, using gpos kern feature")
+ return
+ end
+ setposition(f,datatable.offset)
+ local version=readushort(f)
+ local noftables=readushort(f)
+ if noftables>1 then
+ report("adding global kern table as gpos feature %a",name)
+ local kerns=setmetatableindex("table")
+ for i=1,noftables do
+ local version=readushort(f)
+ local length=readushort(f)
+ local coverage=readushort(f)
+ local format=rshift(coverage,8)
+ if format==0 then
+ local nofpairs=readushort(f)
+ local searchrange=readushort(f)
+ local entryselector=readushort(f)
+ local rangeshift=readushort(f)
+ for i=1,nofpairs do
+ kerns[readushort(f)][readushort(f)]=readfword(f)
+ end
+ elseif format==2 then
+ else
+ end
+ end
+ local feature={ dflt={ dflt=true } }
+ if not features then
+ fontdata.features={ gpos={ [name]=feature } }
+ elseif not gposfeatures then
+ fontdata.features.gpos={ [name]=feature }
+ else
+ gposfeatures[name]=feature
+ end
+ local sequences=fontdata.sequences
+ if not sequences then
+ sequences={}
+ fontdata.sequences=sequences
+ end
+ local nofsequences=#sequences+1
+ sequences[nofsequences]={
+ index=nofsequences,
+ name=name,
+ steps={
+ {
+ coverage=kerns,
+ format="kern",
+ },
+ },
+ nofsteps=1,
+ type="gpos_pair",
+ flags={ false,false,false,false },
+ order={ name },
+ features={ [name]=feature },
+ }
+ else
+ report("ignoring empty kern table of feature %a",name)
+ end
+ end
+ function readers.gsub(f,fontdata,specification)
+ if specification.details then
+ readscripts(f,fontdata,"gsub",gsubtypes,gsubhandlers,specification.lookups)
+ end
+ end
+ function readers.gpos(f,fontdata,specification)
+ if specification.details then
+ readscripts(f,fontdata,"gpos",gpostypes,gposhandlers,specification.lookups)
+ if specification.lookups then
+ checkkerns(f,fontdata,specification)
+ end
+ end
+ end
+end
+function readers.gdef(f,fontdata,specification)
+ if not specification.glyphs then
+ return
+ end
+ local datatable=fontdata.tables.gdef
+ if datatable then
+ local tableoffset=datatable.offset
+ setposition(f,tableoffset)
+ local version=readulong(f)
+ local classoffset=readushort(f)
+ local attachmentoffset=readushort(f)
+ local ligaturecarets=readushort(f)
+ local markclassoffset=readushort(f)
+ local marksetsoffset=version>=0x00010002 and readushort(f) or 0
+ local varsetsoffset=version>=0x00010003 and readulong(f) or 0
+ local glyphs=fontdata.glyphs
+ local marks={}
+ local markclasses=setmetatableindex("table")
+ local marksets=setmetatableindex("table")
+ fontdata.marks=marks
+ fontdata.markclasses=markclasses
+ fontdata.marksets=marksets
+ if classoffset~=0 then
+ setposition(f,tableoffset+classoffset)
+ local classformat=readushort(f)
+ if classformat==1 then
+ local firstindex=readushort(f)
+ local lastindex=firstindex+readushort(f)-1
+ for index=firstindex,lastindex do
+ local class=classes[readushort(f)]
+ if class=="mark" then
+ marks[index]=true
+ end
+ glyphs[index].class=class
+ end
+ elseif classformat==2 then
+ local nofranges=readushort(f)
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local class=classes[readushort(f)]
+ if class then
+ for index=firstindex,lastindex do
+ glyphs[index].class=class
+ if class=="mark" then
+ marks[index]=true
+ end
+ end
+ end
+ end
+ end
+ end
+ if markclassoffset~=0 then
+ setposition(f,tableoffset+markclassoffset)
+ local classformat=readushort(f)
+ if classformat==1 then
+ local firstindex=readushort(f)
+ local lastindex=firstindex+readushort(f)-1
+ for index=firstindex,lastindex do
+ markclasses[readushort(f)][index]=true
+ end
+ elseif classformat==2 then
+ local nofranges=readushort(f)
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local class=markclasses[readushort(f)]
+ for index=firstindex,lastindex do
+ class[index]=true
+ end
+ end
+ end
+ end
+ if marksetsoffset~=0 then
+ marksetsoffset=tableoffset+marksetsoffset
+ setposition(f,marksetsoffset)
+ local format=readushort(f)
+ if format==1 then
+ local nofsets=readushort(f)
+ local sets=readcardinaltable(f,nofsets,ulong)
+ for i=1,nofsets do
+ local offset=sets[i]
+ if offset~=0 then
+ marksets[i]=readcoverage(f,marksetsoffset+offset)
+ end
+ end
+ end
+ end
+ local factors=specification.factors
+ if (specification.variable or factors) and varsetsoffset~=0 then
+ local regions,deltas=readvariationdata(f,tableoffset+varsetsoffset,factors)
+ if factors then
+ fontdata.temporary.getdelta=function(outer,inner)
+ local delta=deltas[outer+1]
+ if delta then
+ local d=delta.deltas[inner+1]
+ if d then
+ local scales=delta.scales
+ local dd=0
+ for i=1,#scales do
+ local di=d[i]
+ if di then
+ dd=dd+scales[i]*di
+ else
+ break
+ end
+ end
+ return round(dd)
+ end
+ end
+ return 0
+ end
+ end
+ end
+ end
+end
+local function readmathvalue(f)
+ local v=readshort(f)
+ skipshort(f,1)
+ return v
+end
+local function readmathconstants(f,fontdata,offset)
+ setposition(f,offset)
+ fontdata.mathconstants={
+ ScriptPercentScaleDown=readshort(f),
+ ScriptScriptPercentScaleDown=readshort(f),
+ DelimitedSubFormulaMinHeight=readushort(f),
+ DisplayOperatorMinHeight=readushort(f),
+ MathLeading=readmathvalue(f),
+ AxisHeight=readmathvalue(f),
+ AccentBaseHeight=readmathvalue(f),
+ FlattenedAccentBaseHeight=readmathvalue(f),
+ SubscriptShiftDown=readmathvalue(f),
+ SubscriptTopMax=readmathvalue(f),
+ SubscriptBaselineDropMin=readmathvalue(f),
+ SuperscriptShiftUp=readmathvalue(f),
+ SuperscriptShiftUpCramped=readmathvalue(f),
+ SuperscriptBottomMin=readmathvalue(f),
+ SuperscriptBaselineDropMax=readmathvalue(f),
+ SubSuperscriptGapMin=readmathvalue(f),
+ SuperscriptBottomMaxWithSubscript=readmathvalue(f),
+ SpaceAfterScript=readmathvalue(f),
+ UpperLimitGapMin=readmathvalue(f),
+ UpperLimitBaselineRiseMin=readmathvalue(f),
+ LowerLimitGapMin=readmathvalue(f),
+ LowerLimitBaselineDropMin=readmathvalue(f),
+ StackTopShiftUp=readmathvalue(f),
+ StackTopDisplayStyleShiftUp=readmathvalue(f),
+ StackBottomShiftDown=readmathvalue(f),
+ StackBottomDisplayStyleShiftDown=readmathvalue(f),
+ StackGapMin=readmathvalue(f),
+ StackDisplayStyleGapMin=readmathvalue(f),
+ StretchStackTopShiftUp=readmathvalue(f),
+ StretchStackBottomShiftDown=readmathvalue(f),
+ StretchStackGapAboveMin=readmathvalue(f),
+ StretchStackGapBelowMin=readmathvalue(f),
+ FractionNumeratorShiftUp=readmathvalue(f),
+ FractionNumeratorDisplayStyleShiftUp=readmathvalue(f),
+ FractionDenominatorShiftDown=readmathvalue(f),
+ FractionDenominatorDisplayStyleShiftDown=readmathvalue(f),
+ FractionNumeratorGapMin=readmathvalue(f),
+ FractionNumeratorDisplayStyleGapMin=readmathvalue(f),
+ FractionRuleThickness=readmathvalue(f),
+ FractionDenominatorGapMin=readmathvalue(f),
+ FractionDenominatorDisplayStyleGapMin=readmathvalue(f),
+ SkewedFractionHorizontalGap=readmathvalue(f),
+ SkewedFractionVerticalGap=readmathvalue(f),
+ OverbarVerticalGap=readmathvalue(f),
+ OverbarRuleThickness=readmathvalue(f),
+ OverbarExtraAscender=readmathvalue(f),
+ UnderbarVerticalGap=readmathvalue(f),
+ UnderbarRuleThickness=readmathvalue(f),
+ UnderbarExtraDescender=readmathvalue(f),
+ RadicalVerticalGap=readmathvalue(f),
+ RadicalDisplayStyleVerticalGap=readmathvalue(f),
+ RadicalRuleThickness=readmathvalue(f),
+ RadicalExtraAscender=readmathvalue(f),
+ RadicalKernBeforeDegree=readmathvalue(f),
+ RadicalKernAfterDegree=readmathvalue(f),
+ RadicalDegreeBottomRaisePercent=readshort(f),
+ }
+end
+local function readmathglyphinfo(f,fontdata,offset)
+ setposition(f,offset)
+ local italics=readushort(f)
+ local accents=readushort(f)
+ local extensions=readushort(f)
+ local kerns=readushort(f)
+ local glyphs=fontdata.glyphs
+ if italics~=0 then
+ setposition(f,offset+italics)
+ local coverage=readushort(f)
+ local nofglyphs=readushort(f)
+ coverage=readcoverage(f,offset+italics+coverage,true)
+ setposition(f,offset+italics+4)
+ for i=1,nofglyphs do
+ local italic=readmathvalue(f)
+ if italic~=0 then
+ local glyph=glyphs[coverage[i]]
+ local math=glyph.math
+ if not math then
+ glyph.math={ italic=italic }
+ else
+ math.italic=italic
+ end
+ end
+ end
+ fontdata.hasitalics=true
+ end
+ if accents~=0 then
+ setposition(f,offset+accents)
+ local coverage=readushort(f)
+ local nofglyphs=readushort(f)
+ coverage=readcoverage(f,offset+accents+coverage,true)
+ setposition(f,offset+accents+4)
+ for i=1,nofglyphs do
+ local accent=readmathvalue(f)
+ if accent~=0 then
+ local glyph=glyphs[coverage[i]]
+ local math=glyph.math
+ if not math then
+ glyph.math={ accent=accent }
+ else
+ math.accent=accent
+ end
+ end
+ end
+ end
+ if extensions~=0 then
+ setposition(f,offset+extensions)
+ end
+ if kerns~=0 then
+ local kernoffset=offset+kerns
+ setposition(f,kernoffset)
+ local coverage=readushort(f)
+ local nofglyphs=readushort(f)
+ if nofglyphs>0 then
+ local function get(offset)
+ setposition(f,kernoffset+offset)
+ local n=readushort(f)
+ if n==0 then
+ local k=readmathvalue(f)
+ if k==0 then
+ else
+ return { { kern=k } }
+ end
+ else
+ local l={}
+ for i=1,n do
+ l[i]={ height=readmathvalue(f) }
+ end
+ for i=1,n do
+ l[i].kern=readmathvalue(f)
+ end
+ l[n+1]={ kern=readmathvalue(f) }
+ return l
+ end
+ end
+ local kernsets={}
+ for i=1,nofglyphs do
+ local topright=readushort(f)
+ local topleft=readushort(f)
+ local bottomright=readushort(f)
+ local bottomleft=readushort(f)
+ kernsets[i]={
+ topright=topright~=0 and topright or nil,
+ topleft=topleft~=0 and topleft or nil,
+ bottomright=bottomright~=0 and bottomright or nil,
+ bottomleft=bottomleft~=0 and bottomleft or nil,
+ }
+ end
+ coverage=readcoverage(f,kernoffset+coverage,true)
+ for i=1,nofglyphs do
+ local kernset=kernsets[i]
+ if next(kernset) then
+ local k=kernset.topright if k then kernset.topright=get(k) end
+ local k=kernset.topleft if k then kernset.topleft=get(k) end
+ local k=kernset.bottomright if k then kernset.bottomright=get(k) end
+ local k=kernset.bottomleft if k then kernset.bottomleft=get(k) end
+ if next(kernset) then
+ local glyph=glyphs[coverage[i]]
+ local math=glyph.math
+ if math then
+ math.kerns=kernset
+ else
+ glyph.math={ kerns=kernset }
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local function readmathvariants(f,fontdata,offset)
+ setposition(f,offset)
+ local glyphs=fontdata.glyphs
+ local minoverlap=readushort(f)
+ local vcoverage=readushort(f)
+ local hcoverage=readushort(f)
+ local vnofglyphs=readushort(f)
+ local hnofglyphs=readushort(f)
+ local vconstruction=readcardinaltable(f,vnofglyphs,ushort)
+ local hconstruction=readcardinaltable(f,hnofglyphs,ushort)
+ fontdata.mathconstants.MinConnectorOverlap=minoverlap
+ local function get(offset,coverage,nofglyphs,construction,kvariants,kparts,kitalic)
+ if coverage~=0 and nofglyphs>0 then
+ local coverage=readcoverage(f,offset+coverage,true)
+ for i=1,nofglyphs do
+ local c=construction[i]
+ if c~=0 then
+ local index=coverage[i]
+ local glyph=glyphs[index]
+ local math=glyph.math
+ setposition(f,offset+c)
+ local assembly=readushort(f)
+ local nofvariants=readushort(f)
+ if nofvariants>0 then
+ local variants,v=nil,0
+ for i=1,nofvariants do
+ local variant=readushort(f)
+ if variant==index then
+ elseif variants then
+ v=v+1
+ variants[v]=variant
+ else
+ v=1
+ variants={ variant }
+ end
+ skipshort(f)
+ end
+ if not variants then
+ elseif not math then
+ math={ [kvariants]=variants }
+ glyph.math=math
+ else
+ math[kvariants]=variants
+ end
+ end
+ if assembly~=0 then
+ setposition(f,offset+c+assembly)
+ local italic=readmathvalue(f)
+ local nofparts=readushort(f)
+ local parts={}
+ for i=1,nofparts do
+ local p={
+ glyph=readushort(f),
+ start=readushort(f),
+ ["end"]=readushort(f),
+ advance=readushort(f),
+ }
+ local flags=readushort(f)
+ if band(flags,0x0001)~=0 then
+ p.extender=1
+ end
+ parts[i]=p
+ end
+ if not math then
+ math={
+ [kparts]=parts
+ }
+ glyph.math=math
+ else
+ math[kparts]=parts
+ end
+ if italic and italic~=0 then
+ math[kitalic]=italic
+ end
+ end
+ end
+ end
+ end
+ end
+ get(offset,vcoverage,vnofglyphs,vconstruction,"vvariants","vparts","vitalic")
+ get(offset,hcoverage,hnofglyphs,hconstruction,"hvariants","hparts","hitalic")
+end
+function readers.math(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"math",specification.glyphs)
+ if tableoffset then
+ local version=readulong(f)
+ local constants=readushort(f)
+ local glyphinfo=readushort(f)
+ local variants=readushort(f)
+ if constants==0 then
+ report("the math table of %a has no constants",fontdata.filename)
+ else
+ readmathconstants(f,fontdata,tableoffset+constants)
+ end
+ if glyphinfo~=0 then
+ readmathglyphinfo(f,fontdata,tableoffset+glyphinfo)
+ end
+ if variants~=0 then
+ readmathvariants(f,fontdata,tableoffset+variants)
+ end
+ end
+end
+function readers.colr(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"colr",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ if version~=0 then
+ report("table version %a of %a is not supported (yet), maybe font %s is bad",version,"colr",fontdata.filename)
+ return
+ end
+ if not fontdata.tables.cpal then
+ report("color table %a in font %a has no mandate %a table","colr",fontdata.filename,"cpal")
+ fontdata.colorpalettes={}
+ end
+ local glyphs=fontdata.glyphs
+ local nofglyphs=readushort(f)
+ local baseoffset=readulong(f)
+ local layeroffset=readulong(f)
+ local noflayers=readushort(f)
+ local layerrecords={}
+ local maxclass=0
+ setposition(f,tableoffset+layeroffset)
+ for i=1,noflayers do
+ local slot=readushort(f)
+ local class=readushort(f)
+ if class<0xFFFF then
+ class=class+1
+ if class>maxclass then
+ maxclass=class
+ end
+ end
+ layerrecords[i]={
+ slot=slot,
+ class=class,
+ }
+ end
+ fontdata.maxcolorclass=maxclass
+ setposition(f,tableoffset+baseoffset)
+ for i=0,nofglyphs-1 do
+ local glyphindex=readushort(f)
+ local firstlayer=readushort(f)
+ local noflayers=readushort(f)
+ local t={}
+ for i=1,noflayers do
+ t[i]=layerrecords[firstlayer+i]
+ end
+ glyphs[glyphindex].colors=t
+ end
+ end
+ fontdata.hascolor=true
+end
+function readers.cpal(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cpal",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local nofpaletteentries=readushort(f)
+ local nofpalettes=readushort(f)
+ local nofcolorrecords=readushort(f)
+ local firstcoloroffset=readulong(f)
+ local colorrecords={}
+ local palettes=readcardinaltable(f,nofpalettes,ushort)
+ if version==1 then
+ local palettettypesoffset=readulong(f)
+ local palettelabelsoffset=readulong(f)
+ local paletteentryoffset=readulong(f)
+ end
+ setposition(f,tableoffset+firstcoloroffset)
+ for i=1,nofcolorrecords do
+ local b,g,r,a=readbytes(f,4)
+ colorrecords[i]={
+ r,g,b,a~=255 and a or nil,
+ }
+ end
+ for i=1,nofpalettes do
+ local p={}
+ local o=palettes[i]
+ for j=1,nofpaletteentries do
+ p[j]=colorrecords[o+j]
+ end
+ palettes[i]=p
+ end
+ fontdata.colorpalettes=palettes
+ end
+end
+function readers.svg(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"svg",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local glyphs=fontdata.glyphs
+ local indexoffset=tableoffset+readulong(f)
+ local reserved=readulong(f)
+ setposition(f,indexoffset)
+ local nofentries=readushort(f)
+ local entries={}
+ for i=1,nofentries do
+ entries[i]={
+ first=readushort(f),
+ last=readushort(f),
+ offset=indexoffset+readulong(f),
+ length=readulong(f),
+ }
+ end
+ for i=1,nofentries do
+ local entry=entries[i]
+ setposition(f,entry.offset)
+ entries[i]={
+ first=entry.first,
+ last=entry.last,
+ data=readstring(f,entry.length)
+ }
+ end
+ fontdata.svgshapes=entries
+ end
+ fontdata.hascolor=true
+end
+function readers.sbix(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"sbix",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local flags=readushort(f)
+ local nofstrikes=readulong(f)
+ local strikes={}
+ local nofglyphs=fontdata.nofglyphs
+ for i=1,nofstrikes do
+ strikes[i]=readulong(f)
+ end
+ local shapes={}
+ local done=0
+ for i=1,nofstrikes do
+ local strikeoffset=strikes[i]+tableoffset
+ setposition(f,strikeoffset)
+ strikes[i]={
+ ppem=readushort(f),
+ ppi=readushort(f),
+ offset=strikeoffset
+ }
+ end
+ sort(strikes,function(a,b)
+ if b.ppem==a.ppem then
+ return b.ppi<a.ppi
+ else
+ return b.ppem<a.ppem
+ end
+ end)
+ local glyphs={}
+ for i=1,nofstrikes do
+ local strike=strikes[i]
+ local strikeppem=strike.ppem
+ local strikeppi=strike.ppi
+ local strikeoffset=strike.offset
+ setposition(f,strikeoffset)
+ for i=0,nofglyphs do
+ glyphs[i]=readulong(f)
+ end
+ local glyphoffset=glyphs[0]
+ for i=0,nofglyphs-1 do
+ local nextoffset=glyphs[i+1]
+ if not shapes[i] then
+ local datasize=nextoffset-glyphoffset
+ if datasize>0 then
+ setposition(f,strikeoffset+glyphoffset)
+ shapes[i]={
+ x=readshort(f),
+ y=readshort(f),
+ tag=readtag(f),
+ data=readstring(f,datasize-8),
+ ppem=strikeppem,
+ ppi=strikeppi,
+ }
+ done=done+1
+ if done==nofglyphs then
+ break
+ end
+ end
+ end
+ glyphoffset=nextoffset
+ end
+ end
+ fontdata.pngshapes=shapes
+ end
+end
+do
+ local function getmetrics(f)
+ return {
+ ascender=readinteger(f),
+ descender=readinteger(f),
+ widthmax=readuinteger(f),
+ caretslopedumerator=readinteger(f),
+ caretslopedenominator=readinteger(f),
+ caretoffset=readinteger(f),
+ minorigin=readinteger(f),
+ minadvance=readinteger(f),
+ maxbefore=readinteger(f),
+ minafter=readinteger(f),
+ pad1=readinteger(f),
+ pad2=readinteger(f),
+ }
+ end
+ local function getbigmetrics(f)
+ return {
+ height=readuinteger(f),
+ width=readuinteger(f),
+ horiBearingX=readinteger(f),
+ horiBearingY=readinteger(f),
+ horiAdvance=readuinteger(f),
+ vertBearingX=readinteger(f),
+ vertBearingY=readinteger(f),
+ vertAdvance=readuinteger(f),
+ }
+ end
+ local function getsmallmetrics(f)
+ return {
+ height=readuinteger(f),
+ width=readuinteger(f),
+ bearingX=readinteger(f),
+ bearingY=readinteger(f),
+ advance=readuinteger(f),
+ }
+ end
+ function readers.cblc(f,fontdata,specification)
+ local ctdttableoffset=gotodatatable(f,fontdata,"cbdt",specification.glyphs)
+ if not ctdttableoffset then
+ return
+ end
+ local cblctableoffset=gotodatatable(f,fontdata,"cblc",specification.glyphs)
+ if cblctableoffset then
+ local majorversion=readushort(f)
+ local minorversion=readushort(f)
+ local nofsizetables=readulong(f)
+ local sizetables={}
+ local shapes={}
+ local subtables={}
+ for i=1,nofsizetables do
+ sizetables[i]={
+ subtables=readulong(f),
+ indexsize=readulong(f),
+ nofsubtables=readulong(f),
+ colorref=readulong(f),
+ hormetrics=getmetrics(f),
+ vermetrics=getmetrics(f),
+ firstindex=readushort(f),
+ lastindex=readushort(f),
+ ppemx=readbyte(f),
+ ppemy=readbyte(f),
+ bitdepth=readbyte(f),
+ flags=readbyte(f),
+ }
+ end
+ sort(sizetables,function(a,b)
+ if b.ppemx==a.ppemx then
+ return b.bitdepth<a.bitdepth
+ else
+ return b.ppemx<a.ppemx
+ end
+ end)
+ for i=1,nofsizetables do
+ local s=sizetables[i]
+ local d=false
+ for j=s.firstindex,s.lastindex do
+ if not shapes[j] then
+ shapes[j]=i
+ d=true
+ end
+ end
+ if d then
+ s.used=true
+ end
+ end
+ for i=1,nofsizetables do
+ local s=sizetables[i]
+ if s.used then
+ local offset=s.subtables
+ setposition(f,cblctableoffset+offset)
+ for j=1,s.nofsubtables do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local tableoffset=readulong(f)+offset
+ for k=firstindex,lastindex do
+ if shapes[k]==i then
+ local s=subtables[tableoffset]
+ if not s then
+ s={
+ firstindex=firstindex,
+ lastindex=lastindex,
+ }
+ subtables[tableoffset]=s
+ end
+ shapes[k]=s
+ end
+ end
+ end
+ end
+ end
+ for offset,subtable in sortedhash(subtables) do
+ local tabletype=readushort(f)
+ subtable.format=readushort(f)
+ local baseoffset=readulong(f)+ctdttableoffset
+ local offsets={}
+ local metrics=nil
+ if tabletype==1 then
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i]=readulong(f)+baseoffset
+ end
+ skipbytes(f,4)
+ elseif tabletype==2 then
+ local size=readulong(f)
+ local done=baseoffset
+ metrics=getbigmetrics(f)
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i]=done
+ done=done+size
+ end
+ elseif tabletype==3 then
+ local n=subtable.lastindex-subtable.firstindex+2
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i]=readushort(f)+baseoffset
+ end
+ if math.odd(n) then
+ skipbytes(f,4)
+ else
+ skipbytes(f,2)
+ end
+ elseif tabletype==4 then
+ for i=1,readulong(f) do
+ offsets[readushort(f)]=readushort(f)+baseoffset
+ end
+ elseif tabletype==5 then
+ local size=readulong(f)
+ local done=baseoffset
+ metrics=getbigmetrics(f)
+ local n=readulong(f)
+ for i=1,n do
+ offsets[readushort(f)]=done
+ done=done+size
+ end
+ if math.odd(n) then
+ skipbytes(f,2)
+ end
+ else
+ return
+ end
+ subtable.offsets=offsets
+ subtable.metrics=metrics
+ end
+ local default={ width=0,height=0 }
+ local glyphs=fontdata.glyphs
+ for index,subtable in sortedhash(shapes) do
+ if type(subtable)=="table" then
+ local data=nil
+ local metrics=default
+ local format=subtable.format
+ local offset=subtable.offsets[index]
+ setposition(f,offset)
+ if format==17 then
+ metrics=getsmallmetrics(f)
+ data=readstring(f,readulong(f))
+ elseif format==18 then
+ metrics=getbigmetrics(f)
+ data=readstring(f,readulong(f))
+ elseif format==19 then
+ metrics=subtable.metrics
+ data=readstring(f,readulong(f))
+ else
+ end
+ local x=metrics.width
+ local y=metrics.height
+ shapes[index]={
+ x=x,
+ y=y,
+ data=data,
+ }
+ local glyph=glyphs[index]
+ if not glyph.boundingbox then
+ local width=glyph.width
+ local height=width*y/x
+ glyph.boundingbox={ 0,0,width,height }
+ end
+ else
+ shapes[index]={
+ x=0,
+ y=0,
+ data="",
+ }
+ end
+ end
+ fontdata.pngshapes=shapes
+ end
+ end
+ function readers.cbdt(f,fontdata,specification)
+ end
+end
+function readers.stat(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"stat",true)
+ if tableoffset then
+ local extras=fontdata.extras
+ local version=readulong(f)
+ local axissize=readushort(f)
+ local nofaxis=readushort(f)
+ local axisoffset=readulong(f)
+ local nofvalues=readushort(f)
+ local valuesoffset=readulong(f)
+ local fallbackname=extras[readushort(f)]
+ local axis={}
+ local values={}
+ setposition(f,tableoffset+axisoffset)
+ for i=1,nofaxis do
+ local tag=readtag(f)
+ axis[i]={
+ tag=tag,
+ name=lower(extras[readushort(f)] or tag),
+ ordering=readushort(f),
+ variants={}
+ }
+ end
+ setposition(f,tableoffset+valuesoffset)
+ for i=1,nofvalues do
+ values[i]=readushort(f)
+ end
+ for i=1,nofvalues do
+ setposition(f,tableoffset+valuesoffset+values[i])
+ local format=readushort(f)
+ local index=readushort(f)+1
+ local flags=readushort(f)
+ local name=lower(extras[readushort(f)] or "no name")
+ local value=readfixed(f)
+ local variant
+ if format==1 then
+ variant={
+ flags=flags,
+ name=name,
+ value=value,
+ }
+ elseif format==2 then
+ variant={
+ flags=flags,
+ name=name,
+ value=value,
+ minimum=readfixed(f),
+ maximum=readfixed(f),
+ }
+ elseif format==3 then
+ variant={
+ flags=flags,
+ name=name,
+ value=value,
+ link=readfixed(f),
+ }
+ end
+ insert(axis[index].variants,variant)
+ end
+ sort(axis,function(a,b)
+ return a.ordering<b.ordering
+ end)
+ for i=1,#axis do
+ local a=axis[i]
+ sort(a.variants,function(a,b)
+ return a.name<b.name
+ end)
+ a.ordering=nil
+ end
+ setvariabledata(fontdata,"designaxis",axis)
+ setvariabledata(fontdata,"fallbackname",fallbackname)
+ end
+end
+function readers.avar(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"avar",true)
+ if tableoffset then
+ local function collect()
+ local nofvalues=readushort(f)
+ local values={}
+ local lastfrom=false
+ local lastto=false
+ for i=1,nofvalues do
+ local from=read2dot14(f)
+ local to=read2dot14(f)
+ if lastfrom and from<=lastfrom then
+ elseif lastto and to>=lastto then
+ else
+ values[#values+1]={ from,to }
+ lastfrom,lastto=from,to
+ end
+ end
+ nofvalues=#values
+ if nofvalues>2 then
+ local some=values[1]
+ if some[1]==-1 and some[2]==-1 then
+ some=values[nofvalues]
+ if some[1]==1 and some[2]==1 then
+ for i=2,nofvalues-1 do
+ some=values[i]
+ if some[1]==0 and some[2]==0 then
+ return values
+ end
+ end
+ end
+ end
+ end
+ return false
+ end
+ local version=readulong(f)
+ local reserved=readushort(f)
+ local nofaxis=readushort(f)
+ local segments={}
+ for i=1,nofaxis do
+ segments[i]=collect()
+ end
+ setvariabledata(fontdata,"segments",segments)
+ end
+end
+function readers.fvar(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"fvar",true)
+ if tableoffset then
+ local version=readulong(f)
+ local offsettoaxis=tableoffset+readushort(f)
+ local reserved=skipshort(f)
+ local nofaxis=readushort(f)
+ local sizeofaxis=readushort(f)
+ local nofinstances=readushort(f)
+ local sizeofinstances=readushort(f)
+ local extras=fontdata.extras
+ local axis={}
+ local instances={}
+ setposition(f,offsettoaxis)
+ for i=1,nofaxis do
+ axis[i]={
+ tag=readtag(f),
+ minimum=readfixed(f),
+ default=readfixed(f),
+ maximum=readfixed(f),
+ flags=readushort(f),
+ name=lower(extras[readushort(f)] or "bad name"),
+ }
+ local n=sizeofaxis-20
+ if n>0 then
+ skipbytes(f,n)
+ elseif n<0 then
+ end
+ end
+ local nofbytes=2+2+2+nofaxis*4
+ local readpsname=nofbytes<=sizeofinstances
+ local skippable=sizeofinstances-nofbytes
+ for i=1,nofinstances do
+ local subfamid=readushort(f)
+ local flags=readushort(f)
+ local values={}
+ for i=1,nofaxis do
+ values[i]={
+ axis=axis[i].tag,
+ value=readfixed(f),
+ }
+ end
+ local psnameid=readpsname and readushort(f) or 0xFFFF
+ if subfamid==2 or subfamid==17 then
+ elseif subfamid==0xFFFF then
+ subfamid=nil
+ elseif subfamid<=256 or subfamid>=32768 then
+ subfamid=nil
+ end
+ if psnameid==6 then
+ elseif psnameid==0xFFFF then
+ psnameid=nil
+ elseif psnameid<=256 or psnameid>=32768 then
+ psnameid=nil
+ end
+ instances[i]={
+ subfamily=extras[subfamid],
+ psname=psnameid and extras[psnameid] or nil,
+ values=values,
+ }
+ if skippable>0 then
+ skipbytes(f,skippable)
+ end
+ end
+ setvariabledata(fontdata,"axis",axis)
+ setvariabledata(fontdata,"instances",instances)
+ end
+end
+function readers.hvar(f,fontdata,specification)
+ local factors=specification.factors
+ if not factors then
+ return
+ end
+ local tableoffset=gotodatatable(f,fontdata,"hvar",specification.variable)
+ if not tableoffset then
+ return
+ end
+ local version=readulong(f)
+ local variationoffset=tableoffset+readulong(f)
+ local advanceoffset=tableoffset+readulong(f)
+ local lsboffset=tableoffset+readulong(f)
+ local rsboffset=tableoffset+readulong(f)
+ local regions={}
+ local variations={}
+ local innerindex={}
+ local outerindex={}
+ if variationoffset>0 then
+ regions,deltas=readvariationdata(f,variationoffset,factors)
+ end
+ if not regions then
+ return
+ end
+ if advanceoffset>0 then
+ setposition(f,advanceoffset)
+ local format=readushort(f)
+ local mapcount=readushort(f)
+ local entrysize=rshift(band(format,0x0030),4)+1
+ local nofinnerbits=band(format,0x000F)+1
+ local innermask=lshift(1,nofinnerbits)-1
+ local readcardinal=read_cardinal[entrysize]
+ for i=0,mapcount-1 do
+ local mapdata=readcardinal(f)
+ outerindex[i]=rshift(mapdata,nofinnerbits)
+ innerindex[i]=band(mapdata,innermask)
+ end
+ setvariabledata(fontdata,"hvarwidths",true)
+ local glyphs=fontdata.glyphs
+ for i=0,fontdata.nofglyphs-1 do
+ local glyph=glyphs[i]
+ local width=glyph.width
+ if width then
+ local outer=outerindex[i] or 0
+ local inner=innerindex[i] or i
+ if outer and inner then
+ local delta=deltas[outer+1]
+ if delta then
+ local d=delta.deltas[inner+1]
+ if d then
+ local scales=delta.scales
+ local deltaw=0
+ for i=1,#scales do
+ local di=d[i]
+ if di then
+ deltaw=deltaw+scales[i]*di
+ else
+ break
+ end
+ end
+ glyph.width=width+round(deltaw)
+ end
+ end
+ end
+ end
+ end
+ end
+end
+function readers.vvar(f,fontdata,specification)
+ if not specification.variable then
+ return
+ end
+end
+function readers.mvar(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"mvar",specification.variable)
+ if tableoffset then
+ local version=readulong(f)
+ local reserved=skipshort(f,1)
+ local recordsize=readushort(f)
+ local nofrecords=readushort(f)
+ local offsettostore=tableoffset+readushort(f)
+ local dimensions={}
+ local factors=specification.factors
+ if factors then
+ local regions,deltas=readvariationdata(f,offsettostore,factors)
+ for i=1,nofrecords do
+ local tag=readtag(f)
+ local var=variabletags[tag]
+ if var then
+ local outer=readushort(f)
+ local inner=readushort(f)
+ local delta=deltas[outer+1]
+ if delta then
+ local d=delta.deltas[inner+1]
+ if d then
+ local scales=delta.scales
+ local dd=0
+ for i=1,#scales do
+ dd=dd+scales[i]*d[i]
+ end
+ var(fontdata,round(dd))
+ end
+ end
+ else
+ skipshort(f,2)
+ end
+ if recordsize>8 then
+ skipbytes(recordsize-8)
+ end
+ end
+ end
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-dsp”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-oup” 669e479e716999edc626a1f045bd76fa] ---
+
+if not modules then modules={} end modules ['font-oup']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type=next,type
+local P,R,S=lpeg.P,lpeg.R,lpeg.S
+local lpegmatch=lpeg.match
+local insert,remove,copy,unpack=table.insert,table.remove,table.copy,table.unpack
+local formatters=string.formatters
+local sortedkeys=table.sortedkeys
+local sortedhash=table.sortedhash
+local tohash=table.tohash
+local setmetatableindex=table.setmetatableindex
+local report_error=logs.reporter("otf reader","error")
+local report_markwidth=logs.reporter("otf reader","markwidth")
+local report_cleanup=logs.reporter("otf reader","cleanup")
+local report_optimizations=logs.reporter("otf reader","merges")
+local report_unicodes=logs.reporter("otf reader","unicodes")
+local trace_markwidth=false trackers.register("otf.markwidth",function(v) trace_markwidth=v end)
+local trace_cleanup=false trackers.register("otf.cleanups",function(v) trace_cleanups=v end)
+local trace_optimizations=false trackers.register("otf.optimizations",function(v) trace_optimizations=v end)
+local trace_unicodes=false trackers.register("otf.unicodes",function(v) trace_unicodes=v end)
+local readers=fonts.handlers.otf.readers
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local f_private=formatters["P%05X"]
+local f_unicode=formatters["U%05X"]
+local f_index=formatters["I%05X"]
+local f_character_y=formatters["%C"]
+local f_character_n=formatters["[ %C ]"]
+local check_duplicates=true
+local check_soft_hyphen=true
+directives.register("otf.checksofthyphen",function(v)
+ check_soft_hyphen=v
+end)
+local function replaced(list,index,replacement)
+ if type(list)=="number" then
+ return replacement
+ elseif type(replacement)=="table" then
+ local t={}
+ local n=index-1
+ for i=1,n do
+ t[i]=list[i]
+ end
+ for i=1,#replacement do
+ n=n+1
+ t[n]=replacement[i]
+ end
+ for i=index+1,#list do
+ n=n+1
+ t[n]=list[i]
+ end
+ else
+ list[index]=replacement
+ return list
+ end
+end
+local function unifyresources(fontdata,indices)
+ local descriptions=fontdata.descriptions
+ local resources=fontdata.resources
+ if not descriptions or not resources then
+ return
+ end
+ local nofindices=#indices
+ local variants=fontdata.resources.variants
+ if variants then
+ for selector,unicodes in next,variants do
+ for unicode,index in next,unicodes do
+ unicodes[unicode]=indices[index]
+ end
+ end
+ end
+ local function remark(marks)
+ if marks then
+ local newmarks={}
+ for k,v in next,marks do
+ local u=indices[k]
+ if u then
+ newmarks[u]=v
+ elseif trace_optimizations then
+ report_optimizations("discarding mark %i",k)
+ end
+ end
+ return newmarks
+ end
+ end
+ local marks=resources.marks
+ if marks then
+ resources.marks=remark(marks)
+ end
+ local markclasses=resources.markclasses
+ if markclasses then
+ for class,marks in next,markclasses do
+ markclasses[class]=remark(marks)
+ end
+ end
+ local marksets=resources.marksets
+ if marksets then
+ for class,marks in next,marksets do
+ marksets[class]=remark(marks)
+ end
+ end
+ local done={}
+ local duplicates=check_duplicates and resources.duplicates
+ if duplicates and not next(duplicates) then
+ duplicates=false
+ end
+ local function recover(cover)
+ for i=1,#cover do
+ local c=cover[i]
+ if not done[c] then
+ local t={}
+ for k,v in next,c do
+ local ug=indices[k]
+ if ug then
+ t[ug]=v
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,"coverage",k,nofindices)
+ end
+ end
+ cover[i]=t
+ done[c]=d
+ end
+ end
+ end
+ local function recursed(c,kind)
+ local t={}
+ for g,d in next,c do
+ if type(d)=="table" then
+ local ug=indices[g]
+ if ug then
+ t[ug]=recursed(d,kind)
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g,nofindices)
+ end
+ else
+ t[g]=indices[d]
+ end
+ end
+ return t
+ end
+ local function unifythem(sequences)
+ if not sequences then
+ return
+ end
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local features=sequence.features
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gsub_single" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ local ud1=indices[d1]
+ if ud1 then
+ t1[ug1]=ud1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=ud1
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",3,kind,d1,nofindices)
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=indices[d1]
+ else
+ report_error("fuzzy case %i in unifying %s: %i",2,kind,g1)
+ end
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ local t2=done[d1]
+ if not t2 then
+ t2={}
+ for g2,d2 in next,d1 do
+ local ug2=indices[g2]
+ if ug2 then
+ t2[ug2]=d2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g2,nofindices,nofindices)
+ end
+ end
+ done[d1]=t2
+ end
+ t1[ug1]=t2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gsub_ligature" then
+ local c=step.coverage
+ if c then
+ step.coverage=recursed(c,kind)
+ end
+ elseif kind=="gsub_alternate" or kind=="gsub_multiple" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ for i=1,#d1 do
+ local d1i=d1[i]
+ local d1u=indices[d1i]
+ if d1u then
+ d1[i]=d1u
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,i,d1i,nofindices)
+ end
+ end
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=copy(d1)
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ for i=1,#d1 do
+ local d1i=d1[i]
+ local d1u=indices[d1i]
+ if d1u then
+ d1[i]=d1u
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,d1i,nofindices)
+ end
+ end
+ t1[indices[g1]]=d1
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gpos_single" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=d1
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gpos_mark2base" or kind=="gpos_mark2mark" or kind=="gpos_mark2ligature" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ local c=step.baseclasses
+ if c then
+ local t1=done[c]
+ if not t1 then
+ for g1,d1 in next,c do
+ local t2=done[d1]
+ if not t2 then
+ t2={}
+ for g2,d2 in next,d1 do
+ local ug2=indices[g2]
+ if ug2 then
+ t2[ug2]=d2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g2,nofindices)
+ end
+ end
+ done[d1]=t2
+ end
+ c[g1]=t2
+ end
+ done[c]=c
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=copy(d1)
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local before=rule.before if before then recover(before) end
+ local after=rule.after if after then recover(after) end
+ local current=rule.current if current then recover(current) end
+ local replacements=rule.replacements
+ if replacements then
+ if not done[replacements] then
+ local r={}
+ for k,v in next,replacements do
+ r[indices[k]]=indices[v]
+ end
+ rule.replacements=r
+ done[replacements]=r
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ unifythem(resources.sequences)
+ unifythem(resources.sublookups)
+end
+local function copyduplicates(fontdata)
+ if check_duplicates then
+ local descriptions=fontdata.descriptions
+ local resources=fontdata.resources
+ local duplicates=resources.duplicates
+ if check_soft_hyphen then
+ local ds=descriptions[0xAD]
+ if not ds or ds.width==0 then
+ if ds then
+ descriptions[0xAD]=nil
+ if trace_unicodes then
+ report_unicodes("patching soft hyphen")
+ end
+ else
+ if trace_unicodes then
+ report_unicodes("adding soft hyphen")
+ end
+ end
+ if not duplicates then
+ duplicates={}
+ resources.duplicates=duplicates
+ end
+ local dh=duplicates[0x2D]
+ if dh then
+ dh[#dh+1]={ [0xAD]=true }
+ else
+ duplicates[0x2D]={ [0xAD]=true }
+ end
+ end
+ end
+ if duplicates then
+ for u,d in next,duplicates do
+ local du=descriptions[u]
+ if du then
+ local t={ f_character_y(u),"@",f_index(du.index),"->" }
+ local n=0
+ local m=25
+ for u in next,d do
+ if descriptions[u] then
+ if n<m then
+ t[n+4]=f_character_n(u)
+ end
+ else
+ local c=copy(du)
+ c.unicode=u
+ descriptions[u]=c
+ if n<m then
+ t[n+4]=f_character_y(u)
+ end
+ end
+ n=n+1
+ end
+ if trace_unicodes then
+ if n<=m then
+ report_unicodes("%i : % t",n,t)
+ else
+ report_unicodes("%i : % t ...",n,t)
+ end
+ end
+ else
+ end
+ end
+ end
+ end
+end
+local ignore={
+ ["notdef"]=true,
+ [".notdef"]=true,
+ ["null"]=true,
+ [".null"]=true,
+ ["nonmarkingreturn"]=true,
+}
+local function checklookups(fontdata,missing,nofmissing)
+ local descriptions=fontdata.descriptions
+ local resources=fontdata.resources
+ if missing and nofmissing and nofmissing<=0 then
+ return
+ end
+ local singles={}
+ local alternates={}
+ local ligatures={}
+ if not missing then
+ missing={}
+ nofmissing=0
+ for u,d in next,descriptions do
+ if not d.unicode then
+ nofmissing=nofmissing+1
+ missing[u]=true
+ end
+ end
+ end
+ local function collectthem(sequences)
+ if not sequences then
+ return
+ end
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gsub_single" then
+ local c=step.coverage
+ if c then
+ singles[#singles+1]=c
+ end
+ elseif kind=="gsub_alternate" then
+ local c=step.coverage
+ if c then
+ alternates[#alternates+1]=c
+ end
+ elseif kind=="gsub_ligature" then
+ local c=step.coverage
+ if c then
+ ligatures[#ligatures+1]=c
+ end
+ end
+ end
+ end
+ end
+ end
+ collectthem(resources.sequences)
+ collectthem(resources.sublookups)
+ local loops=0
+ while true do
+ loops=loops+1
+ local old=nofmissing
+ for i=1,#singles do
+ local c=singles[i]
+ for g1,g2 in next,c do
+ if missing[g1] then
+ local u2=descriptions[g2].unicode
+ if u2 then
+ missing[g1]=false
+ descriptions[g1].unicode=u2
+ nofmissing=nofmissing-1
+ end
+ end
+ if missing[g2] then
+ local u1=descriptions[g1].unicode
+ if u1 then
+ missing[g2]=false
+ descriptions[g2].unicode=u1
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ end
+ for i=1,#alternates do
+ local c=alternates[i]
+ for g1,d1 in next,c do
+ if missing[g1] then
+ for i=1,#d1 do
+ local g2=d1[i]
+ local u2=descriptions[g2].unicode
+ if u2 then
+ missing[g1]=false
+ descriptions[g1].unicode=u2
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ if not missing[g1] then
+ for i=1,#d1 do
+ local g2=d1[i]
+ if missing[g2] then
+ local u1=descriptions[g1].unicode
+ if u1 then
+ missing[g2]=false
+ descriptions[g2].unicode=u1
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ end
+ end
+ end
+ if nofmissing<=0 then
+ if trace_unicodes then
+ report_unicodes("all missings done in %s loops",loops)
+ end
+ return
+ elseif old==nofmissing then
+ break
+ end
+ end
+ local t,n
+ local function recursed(c)
+ for g,d in next,c do
+ if g~="ligature" then
+ local u=descriptions[g].unicode
+ if u then
+ n=n+1
+ t[n]=u
+ recursed(d)
+ n=n-1
+ end
+ elseif missing[d] then
+ local l={}
+ local m=0
+ for i=1,n do
+ local u=t[i]
+ if type(u)=="table" then
+ for i=1,#u do
+ m=m+1
+ l[m]=u[i]
+ end
+ else
+ m=m+1
+ l[m]=u
+ end
+ end
+ missing[d]=false
+ descriptions[d].unicode=l
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ if nofmissing>0 then
+ t={}
+ n=0
+ local loops=0
+ while true do
+ loops=loops+1
+ local old=nofmissing
+ for i=1,#ligatures do
+ recursed(ligatures[i])
+ end
+ if nofmissing<=0 then
+ if trace_unicodes then
+ report_unicodes("all missings done in %s loops",loops)
+ end
+ return
+ elseif old==nofmissing then
+ break
+ end
+ end
+ t=nil
+ n=0
+ end
+ if trace_unicodes and nofmissing>0 then
+ local done={}
+ for i,r in next,missing do
+ if r then
+ local data=descriptions[i]
+ local name=data and data.name or f_index(i)
+ if not ignore[name] then
+ done[name]=true
+ end
+ end
+ end
+ if next(done) then
+ report_unicodes("not unicoded: % t",sortedkeys(done))
+ end
+ end
+end
+local function unifymissing(fontdata)
+ if not fonts.mappings then
+ require("font-map")
+ require("font-agl")
+ end
+ local unicodes={}
+ local resources=fontdata.resources
+ resources.unicodes=unicodes
+ for unicode,d in next,fontdata.descriptions do
+ if unicode<privateoffset then
+ local name=d.name
+ if name then
+ unicodes[name]=unicode
+ end
+ end
+ end
+ fonts.mappings.addtounicode(fontdata,fontdata.filename,checklookups)
+ resources.unicodes=nil
+end
+local firstprivate=fonts.privateoffsets and fonts.privateoffsets.textbase or 0xF0000
+local puafirst=0xE000
+local pualast=0xF8FF
+local function unifyglyphs(fontdata,usenames)
+ local private=fontdata.private or privateoffset
+ local glyphs=fontdata.glyphs
+ local indices={}
+ local descriptions={}
+ local names=usenames and {}
+ local resources=fontdata.resources
+ local zero=glyphs[0]
+ local zerocode=zero.unicode
+ if not zerocode then
+ zerocode=private
+ zero.unicode=zerocode
+ private=private+1
+ end
+ descriptions[zerocode]=zero
+ if names then
+ local name=glyphs[0].name or f_private(zerocode)
+ indices[0]=name
+ names[name]=zerocode
+ else
+ indices[0]=zerocode
+ end
+ if names then
+ for index=1,#glyphs do
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=private
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ private=private+1
+ elseif unicode>=firstprivate then
+ unicode=private
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ private=private+1
+ elseif unicode>=puafirst and unicode<=pualast then
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ elseif descriptions[unicode] then
+ unicode=private
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ private=private+1
+ else
+ local name=glyph.name or f_unicode(unicode)
+ indices[index]=name
+ names[name]=unicode
+ end
+ descriptions[unicode]=glyph
+ end
+ elseif trace_unicodes then
+ for index=1,#glyphs do
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=firstprivate then
+ local name=glyph.name
+ if name then
+ report_unicodes("moving glyph %a indexed %05X from private %U to %U ",name,index,unicode,private)
+ else
+ report_unicodes("moving glyph indexed %05X from private %U to %U ",index,unicode,private)
+ end
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=puafirst and unicode<=pualast then
+ local name=glyph.name
+ if name then
+ report_unicodes("keeping private unicode %U for glyph %a indexed %05X",unicode,name,index)
+ else
+ report_unicodes("keeping private unicode %U for glyph indexed %05X",unicode,index)
+ end
+ indices[index]=unicode
+ elseif descriptions[unicode] then
+ local name=glyph.name
+ if name then
+ report_unicodes("assigning duplicate unicode %U to %U for glyph %a indexed %05X ",unicode,private,name,index)
+ else
+ report_unicodes("assigning duplicate unicode %U to %U for glyph indexed %05X ",unicode,private,index)
+ end
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ else
+ indices[index]=unicode
+ end
+ descriptions[unicode]=glyph
+ end
+ else
+ for index=1,#glyphs do
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=firstprivate then
+ local name=glyph.name
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=puafirst and unicode<=pualast then
+ local name=glyph.name
+ indices[index]=unicode
+ elseif descriptions[unicode] then
+ local name=glyph.name
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ else
+ indices[index]=unicode
+ end
+ descriptions[unicode]=glyph
+ end
+ end
+ for index=1,#glyphs do
+ local math=glyphs[index].math
+ if math then
+ local list=math.vparts
+ if list then
+ for i=1,#list do local l=list[i] l.glyph=indices[l.glyph] end
+ end
+ local list=math.hparts
+ if list then
+ for i=1,#list do local l=list[i] l.glyph=indices[l.glyph] end
+ end
+ local list=math.vvariants
+ if list then
+ for i=1,#list do list[i]=indices[list[i]] end
+ end
+ local list=math.hvariants
+ if list then
+ for i=1,#list do list[i]=indices[list[i]] end
+ end
+ end
+ end
+ local colorpalettes=resources.colorpalettes
+ if colorpalettes then
+ for index=1,#glyphs do
+ local colors=glyphs[index].colors
+ if colors then
+ for i=1,#colors do
+ local c=colors[i]
+ c.slot=indices[c.slot]
+ end
+ end
+ end
+ end
+ fontdata.private=private
+ fontdata.glyphs=nil
+ fontdata.names=names
+ fontdata.descriptions=descriptions
+ fontdata.hashmethod=hashmethod
+ return indices,names
+end
+local p_crappyname do
+ local p_hex=R("af","AF","09")
+ local p_digit=R("09")
+ local p_done=S("._-")^0+P(-1)
+ local p_alpha=R("az","AZ")
+ local p_ALPHA=R("AZ")
+ p_crappyname=(
+ lpeg.utfchartabletopattern({ "uni","u" },true)*S("Xx_")^0*p_hex^1
++lpeg.utfchartabletopattern({ "identity","glyph","jamo" },true)*p_hex^1
++lpeg.utfchartabletopattern({ "index","afii" },true)*p_digit^1
++p_digit*p_hex^3+p_alpha*p_digit^1
++P("aj")*p_digit^1+P("eh_")*(p_digit^1+p_ALPHA*p_digit^1)+(1-P("_"))^1*P("_uni")*p_hex^1+P("_")*P(1)^1
+ )*p_done
+end
+local forcekeep=false
+directives.register("otf.keepnames",function(v)
+ report_cleanup("keeping weird glyph names, expect larger files and more memory usage")
+ forcekeep=v
+end)
+local function stripredundant(fontdata)
+ local descriptions=fontdata.descriptions
+ if descriptions then
+ local n=0
+ local c=0
+ if (not context and fonts.privateoffsets.keepnames) or forcekeep then
+ for unicode,d in next,descriptions do
+ if d.class=="base" then
+ d.class=nil
+ c=c+1
+ end
+ end
+ else
+ for unicode,d in next,descriptions do
+ local name=d.name
+ if name and lpegmatch(p_crappyname,name) then
+ d.name=nil
+ n=n+1
+ end
+ if d.class=="base" then
+ d.class=nil
+ c=c+1
+ end
+ end
+ end
+ if trace_cleanup then
+ if n>0 then
+ report_cleanup("%s bogus names removed (verbose unicode)",n)
+ end
+ if c>0 then
+ report_cleanup("%s base class tags removed (default is base)",c)
+ end
+ end
+ end
+end
+readers.stripredundant=stripredundant
+function readers.getcomponents(fontdata)
+ local resources=fontdata.resources
+ if resources then
+ local sequences=resources.sequences
+ if sequences then
+ local collected={}
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ if sequence.type=="gsub_ligature" then
+ local steps=sequence.steps
+ if steps then
+ local l={}
+ local function traverse(p,k,v)
+ if k=="ligature" then
+ collected[v]={ unpack(l) }
+ else
+ insert(l,k)
+ for k,vv in next,v do
+ traverse(p,k,vv)
+ end
+ remove(l)
+ end
+ end
+ for i=1,#steps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ traverse(k,k,v)
+ end
+ end
+ end
+ end
+ end
+ end
+ if next(collected) then
+ while true do
+ local done=false
+ for k,v in next,collected do
+ for i=1,#v do
+ local vi=v[i]
+ if vi==k then
+ collected[k]=nil
+ break
+ else
+ local c=collected[vi]
+ if c then
+ done=true
+ local t={}
+ local n=i-1
+ for j=1,n do
+ t[j]=v[j]
+ end
+ for j=1,#c do
+ n=n+1
+ t[n]=c[j]
+ end
+ for j=i+1,#v do
+ n=n+1
+ t[n]=v[j]
+ end
+ collected[k]=t
+ break
+ end
+ end
+ end
+ end
+ if not done then
+ break
+ end
+ end
+ return collected
+ end
+ end
+ end
+end
+readers.unifymissing=unifymissing
+function readers.rehash(fontdata,hashmethod)
+ if not (fontdata and fontdata.glyphs) then
+ return
+ end
+ if hashmethod=="indices" then
+ fontdata.hashmethod="indices"
+ elseif hashmethod=="names" then
+ fontdata.hashmethod="names"
+ local indices=unifyglyphs(fontdata,true)
+ unifyresources(fontdata,indices)
+ copyduplicates(fontdata)
+ unifymissing(fontdata)
+ else
+ fontdata.hashmethod="unicodes"
+ local indices=unifyglyphs(fontdata)
+ unifyresources(fontdata,indices)
+ copyduplicates(fontdata)
+ unifymissing(fontdata)
+ stripredundant(fontdata)
+ end
+end
+function readers.checkhash(fontdata)
+ local hashmethod=fontdata.hashmethod
+ if hashmethod=="unicodes" then
+ fontdata.names=nil
+ elseif hashmethod=="names" and fontdata.names then
+ unifyresources(fontdata,fontdata.names)
+ copyduplicates(fontdata)
+ fontdata.hashmethod="unicodes"
+ fontdata.names=nil
+ else
+ readers.rehash(fontdata,"unicodes")
+ end
+end
+function readers.addunicodetable(fontdata)
+ local resources=fontdata.resources
+ local unicodes=resources.unicodes
+ if not unicodes then
+ local descriptions=fontdata.descriptions
+ if descriptions then
+ unicodes={}
+ resources.unicodes=unicodes
+ for u,d in next,descriptions do
+ local n=d.name
+ if n then
+ unicodes[n]=u
+ end
+ end
+ end
+ end
+end
+local concat,sort=table.concat,table.sort
+local next,type,tostring=next,type,tostring
+local criterium=1
+local threshold=0
+local trace_packing=false trackers.register("otf.packing",function(v) trace_packing=v end)
+local trace_loading=false trackers.register("otf.loading",function(v) trace_loading=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local function tabstr_normal(t)
+ local s={}
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ if type(v)=="table" then
+ s[n]=k..">"..tabstr_normal(v)
+ elseif v==true then
+ s[n]=k.."+"
+ elseif v then
+ s[n]=k.."="..v
+ else
+ s[n]=k.."-"
+ end
+ end
+ if n==0 then
+ return ""
+ elseif n==1 then
+ return s[1]
+ else
+ sort(s)
+ return concat(s,",")
+ end
+end
+local function tabstr_flat(t)
+ local s={}
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ s[n]=k.."="..v
+ end
+ if n==0 then
+ return ""
+ elseif n==1 then
+ return s[1]
+ else
+ sort(s)
+ return concat(s,",")
+ end
+end
+local function tabstr_mixed(t)
+ local s={}
+ local n=#t
+ if n==0 then
+ return ""
+ elseif n==1 then
+ local k=t[1]
+ if k==true then
+ return "++"
+ elseif k==false then
+ return "--"
+ else
+ return tostring(k)
+ end
+ else
+ for i=1,n do
+ local k=t[i]
+ if k==true then
+ s[i]="++"
+ elseif k==false then
+ s[i]="--"
+ else
+ s[i]=k
+ end
+ end
+ return concat(s,",")
+ end
+end
+local function tabstr_boolean(t)
+ local s={}
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ if v then
+ s[n]=k.."+"
+ else
+ s[n]=k.."-"
+ end
+ end
+ if n==0 then
+ return ""
+ elseif n==1 then
+ return s[1]
+ else
+ sort(s)
+ return concat(s,",")
+ end
+end
+function readers.pack(data)
+ if data then
+ local h,t,c={},{},{}
+ local hh,tt,cc={},{},{}
+ local nt,ntt=0,0
+ local function pack_normal(v)
+ local tag=tabstr_normal(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_normal_cc(v)
+ local tag=tabstr_normal(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ v[1]=0
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_flat(v)
+ local tag=tabstr_flat(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_indexed(v)
+ local tag=concat(v," ")
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_mixed(v)
+ local tag=tabstr_mixed(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_boolean(v)
+ local tag=tabstr_boolean(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_final(v)
+ if c[v]<=criterium then
+ return t[v]
+ else
+ local hv=hh[v]
+ if hv then
+ return hv
+ else
+ ntt=ntt+1
+ tt[ntt]=t[v]
+ hh[v]=ntt
+ cc[ntt]=c[v]
+ return ntt
+ end
+ end
+ end
+ local function pack_final_cc(v)
+ if c[v]<=criterium then
+ return t[v]
+ else
+ local hv=hh[v]
+ if hv then
+ return hv
+ else
+ ntt=ntt+1
+ tt[ntt]=t[v]
+ hh[v]=ntt
+ cc[ntt]=c[v]
+ return ntt
+ end
+ end
+ end
+ local function success(stage,pass)
+ if nt==0 then
+ if trace_loading or trace_packing then
+ report_otf("pack quality: nothing to pack")
+ end
+ return false
+ elseif nt>=threshold then
+ local one=0
+ local two=0
+ local rest=0
+ if pass==1 then
+ for k,v in next,c do
+ if v==1 then
+ one=one+1
+ elseif v==2 then
+ two=two+1
+ else
+ rest=rest+1
+ end
+ end
+ else
+ for k,v in next,cc do
+ if v>20 then
+ rest=rest+1
+ elseif v>10 then
+ two=two+1
+ else
+ one=one+1
+ end
+ end
+ data.tables=tt
+ end
+ if trace_loading or trace_packing then
+ report_otf("pack quality: stage %s, pass %s, %s packed, 1-10:%s, 11-20:%s, rest:%s (criterium: %s)",
+ stage,pass,one+two+rest,one,two,rest,criterium)
+ end
+ return true
+ else
+ if trace_loading or trace_packing then
+ report_otf("pack quality: stage %s, pass %s, %s packed, aborting pack (threshold: %s)",
+ stage,pass,nt,threshold)
+ end
+ return false
+ end
+ end
+ local function packers(pass)
+ if pass==1 then
+ return pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc
+ else
+ return pack_final,pack_final,pack_final,pack_final,pack_final,pack_final_cc
+ end
+ end
+ local resources=data.resources
+ local sequences=resources.sequences
+ local sublookups=resources.sublookups
+ local features=resources.features
+ local palettes=resources.colorpalettes
+ local variable=resources.variabledata
+ local chardata=characters and characters.data
+ local descriptions=data.descriptions or data.glyphs
+ if not descriptions then
+ return
+ end
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 1, pass %s",pass)
+ end
+ local pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc=packers(pass)
+ for unicode,description in next,descriptions do
+ local boundingbox=description.boundingbox
+ if boundingbox then
+ description.boundingbox=pack_indexed(boundingbox)
+ end
+ local math=description.math
+ if math then
+ local kerns=math.kerns
+ if kerns then
+ for tag,kern in next,kerns do
+ kerns[tag]=pack_normal(kern)
+ end
+ end
+ end
+ end
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local order=sequence.order
+ local features=sequence.features
+ local flags=sequence.flags
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format~="pair" then
+ for g1,d1 in next,c do
+ c[g1]=pack_normal(d1)
+ end
+ elseif step.shared then
+ local shared={}
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ if not shared[d2] then
+ local f=d2[1] if f and f~=true then d2[1]=pack_indexed(f) end
+ local s=d2[2] if s and s~=true then d2[2]=pack_indexed(s) end
+ shared[d2]=true
+ end
+ end
+ end
+ if pass==2 then
+ step.shared=nil
+ end
+ else
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ local f=d2[1] if f and f~=true then d2[1]=pack_indexed(f) end
+ local s=d2[2] if s and s~=true then d2[2]=pack_indexed(s) end
+ end
+ end
+ end
+ end
+ elseif kind=="gpos_single" then
+ local c=step.coverage
+ if c then
+ if step.format=="single" then
+ for g1,d1 in next,c do
+ if d1 and d1~=true then
+ c[g1]=pack_indexed(d1)
+ end
+ end
+ else
+ step.coverage=pack_normal(c)
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local f=d1[2] if f then d1[2]=pack_indexed(f) end
+ local s=d1[3] if s then d1[3]=pack_indexed(s) end
+ end
+ end
+ elseif kind=="gpos_mark2base" or kind=="gpos_mark2mark" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ d1[g2]=pack_indexed(d2)
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ d1[2]=pack_indexed(d1[2])
+ end
+ end
+ elseif kind=="gpos_mark2ligature" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ for g3,d3 in next,d2 do
+ d2[g3]=pack_indexed(d3)
+ end
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ d1[2]=pack_indexed(d1[2])
+ end
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local r=rule.before if r then for i=1,#r do r[i]=pack_boolean(r[i]) end end
+ local r=rule.after if r then for i=1,#r do r[i]=pack_boolean(r[i]) end end
+ local r=rule.current if r then for i=1,#r do r[i]=pack_boolean(r[i]) end end
+ local r=rule.replacements if r then rule.replacements=pack_flat (r) end
+ end
+ end
+ end
+ end
+ if order then
+ sequence.order=pack_indexed(order)
+ end
+ if features then
+ for script,feature in next,features do
+ features[script]=pack_normal(feature)
+ end
+ end
+ if flags then
+ sequence.flags=pack_normal(flags)
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ if features then
+ for k,list in next,features do
+ for feature,spec in next,list do
+ list[feature]=pack_normal(spec)
+ end
+ end
+ end
+ if palettes then
+ for i=1,#palettes do
+ local p=palettes[i]
+ for j=1,#p do
+ p[j]=pack_indexed(p[j])
+ end
+ end
+ end
+ if variable then
+ local instances=variable.instances
+ if instances then
+ for i=1,#instances do
+ local v=instances[i].values
+ for j=1,#v do
+ v[j]=pack_normal(v[j])
+ end
+ end
+ end
+ local function packdeltas(main)
+ if main then
+ local deltas=main.deltas
+ if deltas then
+ for i=1,#deltas do
+ local di=deltas[i]
+ local d=di.deltas
+ for j=1,#d do
+ d[j]=pack_indexed(d[j])
+ end
+ di.regions=pack_indexed(di.regions)
+ end
+ end
+ local regions=main.regions
+ if regions then
+ for i=1,#regions do
+ local r=regions[i]
+ for j=1,#r do
+ r[j]=pack_normal(r[j])
+ end
+ end
+ end
+ end
+ end
+ packdeltas(variable.global)
+ packdeltas(variable.horizontal)
+ packdeltas(variable.vertical)
+ packdeltas(variable.metrics)
+ end
+ if not success(1,pass) then
+ return
+ end
+ end
+ if nt>0 then
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 2, pass %s",pass)
+ end
+ local pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc=packers(pass)
+ for unicode,description in next,descriptions do
+ local math=description.math
+ if math then
+ local kerns=math.kerns
+ if kerns then
+ math.kerns=pack_normal(kerns)
+ end
+ end
+ end
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local features=sequence.features
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format=="pair" then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ d1[g2]=pack_normal(d2)
+ end
+ end
+ end
+ end
+ elseif kind=="gpos_mark2ligature" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ d1[g2]=pack_normal(d2)
+ end
+ end
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local r=rule.before if r then rule.before=pack_normal(r) end
+ local r=rule.after if r then rule.after=pack_normal(r) end
+ local r=rule.current if r then rule.current=pack_normal(r) end
+ end
+ end
+ end
+ end
+ if features then
+ sequence.features=pack_normal(features)
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ if variable then
+ local function unpackdeltas(main)
+ if main then
+ local regions=main.regions
+ if regions then
+ main.regions=pack_normal(regions)
+ end
+ end
+ end
+ unpackdeltas(variable.global)
+ unpackdeltas(variable.horizontal)
+ unpackdeltas(variable.vertical)
+ unpackdeltas(variable.metrics)
+ end
+ end
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 3, pass %s",pass)
+ end
+ local pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc=packers(pass)
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local features=sequence.features
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format=="pair" then
+ for g1,d1 in next,c do
+ c[g1]=pack_normal(d1)
+ end
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ c[g1]=pack_normal_cc(d1)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ end
+ end
+ end
+end
+local unpacked_mt={
+ __index=function(t,k)
+ t[k]=false
+ return k
+ end
+}
+function readers.unpack(data)
+ if data then
+ local tables=data.tables
+ if tables then
+ local resources=data.resources
+ local descriptions=data.descriptions or data.glyphs
+ local sequences=resources.sequences
+ local sublookups=resources.sublookups
+ local features=resources.features
+ local palettes=resources.colorpalettes
+ local variable=resources.variabledata
+ local unpacked={}
+ setmetatable(unpacked,unpacked_mt)
+ for unicode,description in next,descriptions do
+ local tv=tables[description.boundingbox]
+ if tv then
+ description.boundingbox=tv
+ end
+ local math=description.math
+ if math then
+ local kerns=math.kerns
+ if kerns then
+ local tm=tables[kerns]
+ if tm then
+ math.kerns=tm
+ kerns=unpacked[tm]
+ end
+ if kerns then
+ for k,kern in next,kerns do
+ local tv=tables[kern]
+ if tv then
+ kerns[k]=tv
+ end
+ end
+ end
+ end
+ end
+ end
+ local function unpackthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local order=sequence.order
+ local features=sequence.features
+ local flags=sequence.flags
+ local markclass=sequence.markclass
+ if features then
+ local tv=tables[features]
+ if tv then
+ sequence.features=tv
+ features=tv
+ end
+ for script,feature in next,features do
+ local tv=tables[feature]
+ if tv then
+ features[script]=tv
+ end
+ end
+ end
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format=="pair" then
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ c[g1]=tv
+ d1=tv
+ end
+ for g2,d2 in next,d1 do
+ local tv=tables[d2]
+ if tv then
+ d1[g2]=tv
+ d2=tv
+ end
+ local f=tables[d2[1]] if f then d2[1]=f end
+ local s=tables[d2[2]] if s then d2[2]=s end
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ c[g1]=tv
+ end
+ end
+ end
+ end
+ elseif kind=="gpos_single" then
+ local c=step.coverage
+ if c then
+ if step.format=="single" then
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ c[g1]=tv
+ end
+ end
+ else
+ local tv=tables[c]
+ if tv then
+ step.coverage=tv
+ end
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ d1=tv
+ c[g1]=d1
+ end
+ local f=tables[d1[2]] if f then d1[2]=f end
+ local s=tables[d1[3]] if s then d1[3]=s end
+ end
+ end
+ elseif kind=="gpos_mark2base" or kind=="gpos_mark2mark" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ local tv=tables[d2]
+ if tv then
+ d1[g2]=tv
+ end
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local tv=tables[d1[2]]
+ if tv then
+ d1[2]=tv
+ end
+ end
+ end
+ elseif kind=="gpos_mark2ligature" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ local tv=tables[d2]
+ if tv then
+ d2=tv
+ d1[g2]=d2
+ end
+ for g3,d3 in next,d2 do
+ local tv=tables[d2[g3]]
+ if tv then
+ d2[g3]=tv
+ end
+ end
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local tv=tables[d1[2]]
+ if tv then
+ d1[2]=tv
+ end
+ end
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local before=rule.before
+ if before then
+ local tv=tables[before]
+ if tv then
+ rule.before=tv
+ before=tv
+ end
+ for i=1,#before do
+ local tv=tables[before[i]]
+ if tv then
+ before[i]=tv
+ end
+ end
+ end
+ local after=rule.after
+ if after then
+ local tv=tables[after]
+ if tv then
+ rule.after=tv
+ after=tv
+ end
+ for i=1,#after do
+ local tv=tables[after[i]]
+ if tv then
+ after[i]=tv
+ end
+ end
+ end
+ local current=rule.current
+ if current then
+ local tv=tables[current]
+ if tv then
+ rule.current=tv
+ current=tv
+ end
+ for i=1,#current do
+ local tv=tables[current[i]]
+ if tv then
+ current[i]=tv
+ end
+ end
+ end
+ local replacements=rule.replacements
+ if replacements then
+ local tv=tables[replacements]
+ if tv then
+ rule.replacements=tv
+ end
+ end
+ end
+ end
+ end
+ end
+ if order then
+ local tv=tables[order]
+ if tv then
+ sequence.order=tv
+ end
+ end
+ if flags then
+ local tv=tables[flags]
+ if tv then
+ sequence.flags=tv
+ end
+ end
+ end
+ end
+ if sequences then
+ unpackthem(sequences)
+ end
+ if sublookups then
+ unpackthem(sublookups)
+ end
+ if features then
+ for k,list in next,features do
+ for feature,spec in next,list do
+ local tv=tables[spec]
+ if tv then
+ list[feature]=tv
+ end
+ end
+ end
+ end
+ if palettes then
+ for i=1,#palettes do
+ local p=palettes[i]
+ for j=1,#p do
+ local tv=tables[p[j]]
+ if tv then
+ p[j]=tv
+ end
+ end
+ end
+ end
+ if variable then
+ local instances=variable.instances
+ if instances then
+ for i=1,#instances do
+ local v=instances[i].values
+ for j=1,#v do
+ local tv=tables[v[j]]
+ if tv then
+ v[j]=tv
+ end
+ end
+ end
+ end
+ local function unpackdeltas(main)
+ if main then
+ local deltas=main.deltas
+ if deltas then
+ for i=1,#deltas do
+ local di=deltas[i]
+ local d=di.deltas
+ local r=di.regions
+ for j=1,#d do
+ local tv=tables[d[j]]
+ if tv then
+ d[j]=tv
+ end
+ end
+ local tv=di.regions
+ if tv then
+ di.regions=tv
+ end
+ end
+ end
+ local regions=main.regions
+ if regions then
+ local tv=tables[regions]
+ if tv then
+ main.regions=tv
+ regions=tv
+ end
+ for i=1,#regions do
+ local r=regions[i]
+ for j=1,#r do
+ local tv=tables[r[j]]
+ if tv then
+ r[j]=tv
+ end
+ end
+ end
+ end
+ end
+ end
+ unpackdeltas(variable.global)
+ unpackdeltas(variable.horizontal)
+ unpackdeltas(variable.vertical)
+ unpackdeltas(variable.metrics)
+ end
+ data.tables=nil
+ end
+ end
+end
+local mt={
+ __index=function(t,k)
+ if k=="height" then
+ local ht=t.boundingbox[4]
+ return ht<0 and 0 or ht
+ elseif k=="depth" then
+ local dp=-t.boundingbox[2]
+ return dp<0 and 0 or dp
+ elseif k=="width" then
+ return 0
+ elseif k=="name" then
+ return forcenotdef and ".notdef"
+ end
+ end
+}
+local function sameformat(sequence,steps,first,nofsteps,kind)
+ return true
+end
+local function mergesteps_1(lookup,strict)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if strict then
+ local f=first.format
+ for i=2,nofsteps do
+ if steps[i].format~=f then
+ if trace_optimizations then
+ report_optimizations("not merging %a steps of %a lookup %a, different formats",nofsteps,lookup.type,lookup.name)
+ end
+ return 0
+ end
+ end
+ end
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ if not target[k] then
+ target[k]=v
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function mergesteps_2(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if strict then
+ local f=first.format
+ for i=2,nofsteps do
+ if steps[i].format~=f then
+ if trace_optimizations then
+ report_optimizations("not merging %a steps of %a lookup %a, different formats",nofsteps,lookup.type,lookup.name)
+ end
+ return 0
+ end
+ end
+ end
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=target[k]
+ if tk then
+ for kk,vv in next,v do
+ if tk[kk]==nil then
+ tk[kk]=vv
+ end
+ end
+ else
+ target[k]=v
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function mergesteps_3(lookup,strict)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local coverage={}
+ for i=1,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=coverage[k]
+ if tk then
+ if trace_optimizations then
+ report_optimizations("quitting merge due to multiple checks")
+ end
+ return nofsteps
+ else
+ coverage[k]=v
+ end
+ end
+ end
+ end
+ local first=steps[1]
+ local baseclasses={}
+ for i=1,nofsteps do
+ local offset=i*10
+ local step=steps[i]
+ for k,v in sortedhash(step.baseclasses) do
+ baseclasses[offset+k]=v
+ end
+ for k,v in next,step.coverage do
+ v[1]=offset+v[1]
+ end
+ end
+ first.baseclasses=baseclasses
+ first.coverage=coverage
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function nested(old,new)
+ for k,v in next,old do
+ if k=="ligature" then
+ if not new.ligature then
+ new.ligature=v
+ end
+ else
+ local n=new[k]
+ if n then
+ nested(v,n)
+ else
+ new[k]=v
+ end
+ end
+ end
+end
+local function mergesteps_4(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=target[k]
+ if tk then
+ nested(v,tk)
+ else
+ target[k]=v
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function mergesteps_5(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ local hash=nil
+ for k,v in next,target do
+ hash=v[1]
+ break
+ end
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=target[k]
+ if tk then
+ if not tk[2] then
+ tk[2]=v[2]
+ end
+ if not tk[3] then
+ tk[3]=v[3]
+ end
+ else
+ target[k]=v
+ v[1]=hash
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function checkkerns(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local kerned=0
+ for i=1,nofsteps do
+ local step=steps[i]
+ if step.format=="pair" then
+ local coverage=step.coverage
+ local kerns=true
+ for g1,d1 in next,coverage do
+ if d1==true then
+ elseif not d1 then
+ elseif d1[1]~=0 or d1[2]~=0 or d1[4]~=0 then
+ kerns=false
+ break
+ end
+ end
+ if kerns then
+ if trace_optimizations then
+ report_optimizations("turning pairs of step %a of %a lookup %a into kerns",i,lookup.type,lookup.name)
+ end
+ local c={}
+ for g1,d1 in next,coverage do
+ if d1 and d1~=true then
+ c[g1]=d1[3]
+ end
+ end
+ step.coverage=c
+ step.format="move"
+ kerned=kerned+1
+ end
+ end
+ end
+ return kerned
+end
+local function checkpairs(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local kerned=0
+ local function onlykerns(step)
+ local coverage=step.coverage
+ for g1,d1 in next,coverage do
+ for g2,d2 in next,d1 do
+ if d2[2] then
+ return false
+ else
+ local v=d2[1]
+ if v==true then
+ elseif v and (v[1]~=0 or v[2]~=0 or v[4]~=0) then
+ return false
+ end
+ end
+ end
+ end
+ return coverage
+ end
+ for i=1,nofsteps do
+ local step=steps[i]
+ if step.format=="pair" then
+ local coverage=onlykerns(step)
+ if coverage then
+ if trace_optimizations then
+ report_optimizations("turning pairs of step %a of %a lookup %a into kerns",i,lookup.type,lookup.name)
+ end
+ for g1,d1 in next,coverage do
+ local d={}
+ for g2,d2 in next,d1 do
+ local v=d2[1]
+ if v==true then
+ elseif v then
+ d[g2]=v[3]
+ end
+ end
+ coverage[g1]=d
+ end
+ step.format="move"
+ kerned=kerned+1
+ end
+ end
+ end
+ return kerned
+end
+local compact_pairs=true
+local compact_singles=true
+local merge_pairs=true
+local merge_singles=true
+local merge_substitutions=true
+local merge_alternates=true
+local merge_multiples=true
+local merge_ligatures=true
+local merge_cursives=true
+local merge_marks=true
+directives.register("otf.compact.pairs",function(v) compact_pairs=v end)
+directives.register("otf.compact.singles",function(v) compact_singles=v end)
+directives.register("otf.merge.pairs",function(v) merge_pairs=v end)
+directives.register("otf.merge.singles",function(v) merge_singles=v end)
+directives.register("otf.merge.substitutions",function(v) merge_substitutions=v end)
+directives.register("otf.merge.alternates",function(v) merge_alternates=v end)
+directives.register("otf.merge.multiples",function(v) merge_multiples=v end)
+directives.register("otf.merge.ligatures",function(v) merge_ligatures=v end)
+directives.register("otf.merge.cursives",function(v) merge_cursives=v end)
+directives.register("otf.merge.marks",function(v) merge_marks=v end)
+function readers.compact(data)
+ if not data or data.compacted then
+ return
+ else
+ data.compacted=true
+ end
+ local resources=data.resources
+ local merged=0
+ local kerned=0
+ local allsteps=0
+ local function compact(what)
+ local lookups=resources[what]
+ if lookups then
+ for i=1,#lookups do
+ local lookup=lookups[i]
+ local nofsteps=lookup.nofsteps
+ local kind=lookup.type
+ allsteps=allsteps+nofsteps
+ if nofsteps>1 then
+ local merg=merged
+ if kind=="gsub_single" then
+ if merge_substitutions then
+ merged=merged+mergesteps_1(lookup)
+ end
+ elseif kind=="gsub_alternate" then
+ if merge_alternates then
+ merged=merged+mergesteps_1(lookup)
+ end
+ elseif kind=="gsub_multiple" then
+ if merge_multiples then
+ merged=merged+mergesteps_1(lookup)
+ end
+ elseif kind=="gsub_ligature" then
+ if merge_ligatures then
+ merged=merged+mergesteps_4(lookup)
+ end
+ elseif kind=="gpos_single" then
+ if merge_singles then
+ merged=merged+mergesteps_1(lookup,true)
+ end
+ if compact_singles then
+ kerned=kerned+checkkerns(lookup)
+ end
+ elseif kind=="gpos_pair" then
+ if merge_pairs then
+ merged=merged+mergesteps_2(lookup)
+ end
+ if compact_pairs then
+ kerned=kerned+checkpairs(lookup)
+ end
+ elseif kind=="gpos_cursive" then
+ if merge_cursives then
+ merged=merged+mergesteps_5(lookup)
+ end
+ elseif kind=="gpos_mark2mark" or kind=="gpos_mark2base" or kind=="gpos_mark2ligature" then
+ if merge_marks then
+ merged=merged+mergesteps_3(lookup)
+ end
+ end
+ if merg~=merged then
+ lookup.merged=true
+ end
+ elseif nofsteps==1 then
+ local kern=kerned
+ if kind=="gpos_single" then
+ if compact_singles then
+ kerned=kerned+checkkerns(lookup)
+ end
+ elseif kind=="gpos_pair" then
+ if compact_pairs then
+ kerned=kerned+checkpairs(lookup)
+ end
+ end
+ if kern~=kerned then
+ end
+ end
+ end
+ elseif trace_optimizations then
+ report_optimizations("no lookups in %a",what)
+ end
+ end
+ compact("sequences")
+ compact("sublookups")
+ if trace_optimizations then
+ if merged>0 then
+ report_optimizations("%i steps of %i removed due to merging",merged,allsteps)
+ end
+ if kerned>0 then
+ report_optimizations("%i steps of %i steps turned from pairs into kerns",kerned,allsteps)
+ end
+ end
+end
+local function mergesteps(t,k)
+ if k=="merged" then
+ local merged={}
+ for i=1,#t do
+ local step=t[i]
+ local coverage=step.coverage
+ for k in next,coverage do
+ local m=merged[k]
+ if m then
+ m[2]=i
+ else
+ merged[k]={ i,i }
+ end
+ end
+ end
+ t.merged=merged
+ return merged
+ end
+end
+local function checkmerge(sequence)
+ local steps=sequence.steps
+ if steps then
+ setmetatableindex(steps,mergesteps)
+ end
+end
+local function checkflags(sequence,resources)
+ if not sequence.skiphash then
+ local flags=sequence.flags
+ if flags then
+ local skipmark=flags[1]
+ local skipligature=flags[2]
+ local skipbase=flags[3]
+ local markclass=sequence.markclass
+ local skipsome=skipmark or skipligature or skipbase or markclass or false
+ if skipsome then
+ sequence.skiphash=setmetatableindex(function(t,k)
+ local c=resources.classes[k]
+ local v=c==skipmark
+ or (markclass and c=="mark" and not markclass[k])
+ or c==skipligature
+ or c==skipbase
+ or false
+ t[k]=v
+ return v
+ end)
+ else
+ sequence.skiphash=false
+ end
+ else
+ sequence.skiphash=false
+ end
+ end
+end
+local function checksteps(sequence)
+ local steps=sequence.steps
+ if steps then
+ for i=1,#steps do
+ steps[i].index=i
+ end
+ end
+end
+if fonts.helpers then
+ fonts.helpers.checkmerge=checkmerge
+ fonts.helpers.checkflags=checkflags
+ fonts.helpers.checksteps=checksteps
+end
+function readers.expand(data)
+ if not data or data.expanded then
+ return
+ else
+ data.expanded=true
+ end
+ local resources=data.resources
+ local sublookups=resources.sublookups
+ local sequences=resources.sequences
+ local markclasses=resources.markclasses
+ local descriptions=data.descriptions
+ if descriptions then
+ local defaultwidth=resources.defaultwidth or 0
+ local defaultheight=resources.defaultheight or 0
+ local defaultdepth=resources.defaultdepth or 0
+ local basename=trace_markwidth and file.basename(resources.filename)
+ for u,d in next,descriptions do
+ local bb=d.boundingbox
+ local wd=d.width
+ if not wd then
+ d.width=defaultwidth
+ elseif trace_markwidth and wd~=0 and d.class=="mark" then
+ report_markwidth("mark %a with width %b found in %a",d.name or "<noname>",wd,basename)
+ end
+ if bb then
+ local ht=bb[4]
+ local dp=-bb[2]
+ if ht==0 or ht<0 then
+ else
+ d.height=ht
+ end
+ if dp==0 or dp<0 then
+ else
+ d.depth=dp
+ end
+ end
+ end
+ end
+ local function expandlookups(sequences)
+ if sequences then
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ if steps then
+ local nofsteps=sequence.nofsteps
+ local kind=sequence.type
+ local markclass=sequence.markclass
+ if markclass then
+ if not markclasses then
+ report_warning("missing markclasses")
+ sequence.markclass=false
+ else
+ sequence.markclass=markclasses[markclass]
+ end
+ end
+ for i=1,nofsteps do
+ local step=steps[i]
+ local baseclasses=step.baseclasses
+ if baseclasses then
+ local coverage=step.coverage
+ for k,v in next,coverage do
+ v[1]=baseclasses[v[1]]
+ end
+ elseif kind=="gpos_cursive" then
+ local coverage=step.coverage
+ for k,v in next,coverage do
+ v[1]=coverage
+ end
+ end
+ local rules=step.rules
+ if rules then
+ local rulehash={ n=0 }
+ local rulesize=0
+ local coverage={}
+ local lookuptype=sequence.type
+ local nofrules=#rules
+ step.coverage=coverage
+ for currentrule=1,nofrules do
+ local rule=rules[currentrule]
+ local current=rule.current
+ local before=rule.before
+ local after=rule.after
+ local replacements=rule.replacements or false
+ local sequence={}
+ local nofsequences=0
+ if before then
+ for n=1,#before do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=before[n]
+ end
+ end
+ local start=nofsequences+1
+ for n=1,#current do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=current[n]
+ end
+ local stop=nofsequences
+ if after then
+ for n=1,#after do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=after[n]
+ end
+ end
+ local lookups=rule.lookups or false
+ local subtype=nil
+ if lookups then
+ for i=1,#lookups do
+ local lookups=lookups[i]
+ if lookups then
+ for k,v in next,lookups do
+ local lookup=sublookups[v]
+ if lookup then
+ lookups[k]=lookup
+ if not subtype then
+ subtype=lookup.type
+ end
+ else
+ end
+ end
+ end
+ end
+ end
+ if sequence[1] then
+ sequence.n=#sequence
+ local ruledata={
+ currentrule,
+ lookuptype,
+ sequence,
+ start,
+ stop,
+ lookups,
+ replacements,
+ subtype,
+ }
+ rulesize=rulesize+1
+ rulehash[rulesize]=ruledata
+ rulehash.n=rulesize
+ if true then
+ for unic in next,sequence[start] do
+ local cu=coverage[unic]
+ if cu then
+ local n=#cu+1
+ cu[n]=ruledata
+ cu.n=n
+ else
+ coverage[unic]={ ruledata,n=1 }
+ end
+ end
+ else
+ for unic in next,sequence[start] do
+ local cu=coverage[unic]
+ if cu then
+ else
+ coverage[unic]=rulehash
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ checkmerge(sequence)
+ checkflags(sequence,resources)
+ checksteps(sequence)
+ end
+ end
+ end
+ end
+ expandlookups(sequences)
+ expandlookups(sublookups)
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-oup”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otl” 940f9c5ad84f4968a8488f4da2d15e2d] ---
+
+if not modules then modules={} end modules ['font-otl']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+local lower=string.lower
+local type,next,tonumber,tostring,unpack=type,next,tonumber,tostring,unpack
+local abs=math.abs
+local derivetable=table.derive
+local formatters=string.formatters
+local setmetatableindex=table.setmetatableindex
+local allocate=utilities.storage.allocate
+local registertracker=trackers.register
+local registerdirective=directives.register
+local starttiming=statistics.starttiming
+local stoptiming=statistics.stoptiming
+local elapsedtime=statistics.elapsedtime
+local findbinfile=resolvers.findbinfile
+local trace_loading=false registertracker("otf.loading",function(v) trace_loading=v end)
+local trace_features=false registertracker("otf.features",function(v) trace_features=v end)
+local trace_defining=false registertracker("fonts.defining",function(v) trace_defining=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local fonts=fonts
+local otf=fonts.handlers.otf
+otf.version=3.109
+otf.cache=containers.define("fonts","otl",otf.version,true)
+otf.svgcache=containers.define("fonts","svg",otf.version,true)
+otf.pngcache=containers.define("fonts","png",otf.version,true)
+otf.pdfcache=containers.define("fonts","pdf",otf.version,true)
+otf.svgenabled=false
+otf.pngenabled=false
+local otfreaders=otf.readers
+local hashes=fonts.hashes
+local definers=fonts.definers
+local readers=fonts.readers
+local constructors=fonts.constructors
+local otffeatures=constructors.features.otf
+local registerotffeature=otffeatures.register
+local otfenhancers=constructors.enhancers.otf
+local registerotfenhancer=otfenhancers.register
+local forceload=false
+local cleanup=0
+local syncspace=true
+local forcenotdef=false
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local applyruntimefixes=fonts.treatments and fonts.treatments.applyfixes
+local wildcard="*"
+local default="dflt"
+local formats=fonts.formats
+formats.otf="opentype"
+formats.ttf="truetype"
+formats.ttc="truetype"
+registerdirective("fonts.otf.loader.cleanup",function(v) cleanup=tonumber(v) or (v and 1) or 0 end)
+registerdirective("fonts.otf.loader.force",function(v) forceload=v end)
+registerdirective("fonts.otf.loader.syncspace",function(v) syncspace=v end)
+registerdirective("fonts.otf.loader.forcenotdef",function(v) forcenotdef=v end)
+registerotfenhancer("check extra features",function() end)
+local checkmemory=utilities.lua and utilities.lua.checkmemory
+local threshold=100
+local tracememory=false
+registertracker("fonts.otf.loader.memory",function(v) tracememory=v end)
+if not checkmemory then
+ local collectgarbage=collectgarbage
+ checkmemory=function(previous,threshold)
+ local current=collectgarbage("count")
+ if previous then
+ local checked=(threshold or 64)*1024
+ if current-previous>checked then
+ collectgarbage("collect")
+ current=collectgarbage("count")
+ end
+ end
+ return current
+ end
+end
+function otf.load(filename,sub,instance)
+ local base=file.basename(file.removesuffix(filename))
+ local name=file.removesuffix(base)
+ local attr=lfs.attributes(filename)
+ local size=attr and attr.size or 0
+ local time=attr and attr.modification or 0
+ if sub=="" then
+ sub=false
+ end
+ local hash=name
+ if sub then
+ hash=hash.."-"..sub
+ end
+ if instance then
+ hash=hash.."-"..instance
+ end
+ hash=containers.cleanname(hash)
+ local data=containers.read(otf.cache,hash)
+ local reload=not data or data.size~=size or data.time~=time or data.tableversion~=otfreaders.tableversion
+ if forceload then
+ report_otf("forced reload of %a due to hard coded flag",filename)
+ reload=true
+ end
+ if reload then
+ report_otf("loading %a, hash %a",filename,hash)
+ starttiming(otfreaders,true)
+ data=otfreaders.loadfont(filename,sub or 1,instance)
+ if data then
+ local used=checkmemory()
+ local resources=data.resources
+ local svgshapes=resources.svgshapes
+ local pngshapes=resources.pngshapes
+ if cleanup==0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ if svgshapes then
+ resources.svgshapes=nil
+ if otf.svgenabled then
+ local timestamp=os.date()
+ containers.write(otf.svgcache,hash,{
+ svgshapes=svgshapes,
+ timestamp=timestamp,
+ })
+ data.properties.svg={
+ hash=hash,
+ timestamp=timestamp,
+ }
+ end
+ if cleanup>1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ end
+ if pngshapes then
+ resources.pngshapes=nil
+ if otf.pngenabled then
+ local timestamp=os.date()
+ containers.write(otf.pngcache,hash,{
+ pngshapes=pngshapes,
+ timestamp=timestamp,
+ })
+ data.properties.png={
+ hash=hash,
+ timestamp=timestamp,
+ }
+ end
+ if cleanup>1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ end
+ otfreaders.compact(data)
+ if cleanup==0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ otfreaders.rehash(data,"unicodes")
+ otfreaders.addunicodetable(data)
+ otfreaders.extend(data)
+ if cleanup==0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ otfreaders.pack(data)
+ report_otf("loading done")
+ report_otf("saving %a in cache",filename)
+ data=containers.write(otf.cache,hash,data)
+ if cleanup>1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ stoptiming(otfreaders)
+ if elapsedtime then
+ report_otf("loading, optimizing, packing and caching time %s",elapsedtime(otfreaders))
+ end
+ if cleanup>3 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ data=containers.read(otf.cache,hash)
+ if cleanup>2 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ else
+ stoptiming(otfreaders)
+ data=nil
+ report_otf("loading failed due to read error")
+ end
+ end
+ if data then
+ if trace_defining then
+ report_otf("loading from cache using hash %a",hash)
+ end
+ otfreaders.unpack(data)
+ otfreaders.expand(data)
+ otfreaders.addunicodetable(data)
+ otfenhancers.apply(data,filename,data)
+ if applyruntimefixes then
+ applyruntimefixes(filename,data)
+ end
+ data.metadata.math=data.resources.mathconstants
+ local classes=data.resources.classes
+ if not classes then
+ local descriptions=data.descriptions
+ classes=setmetatableindex(function(t,k)
+ local d=descriptions[k]
+ local v=(d and d.class or "base") or false
+ t[k]=v
+ return v
+ end)
+ data.resources.classes=classes
+ end
+ end
+ return data
+end
+function otf.setfeatures(tfmdata,features)
+ local okay=constructors.initializefeatures("otf",tfmdata,features,trace_features,report_otf)
+ if okay then
+ return constructors.collectprocessors("otf",tfmdata,features,trace_features,report_otf)
+ else
+ return {}
+ end
+end
+local function copytotfm(data,cache_id)
+ if data then
+ local metadata=data.metadata
+ local properties=derivetable(data.properties)
+ local descriptions=derivetable(data.descriptions)
+ local goodies=derivetable(data.goodies)
+ local characters={}
+ local parameters={}
+ local mathparameters={}
+ local resources=data.resources
+ local unicodes=resources.unicodes
+ local spaceunits=500
+ local spacer="space"
+ local designsize=metadata.designsize or 100
+ local minsize=metadata.minsize or designsize
+ local maxsize=metadata.maxsize or designsize
+ local mathspecs=metadata.math
+ if designsize==0 then
+ designsize=100
+ minsize=100
+ maxsize=100
+ end
+ if mathspecs then
+ for name,value in next,mathspecs do
+ mathparameters[name]=value
+ end
+ end
+ for unicode in next,data.descriptions do
+ characters[unicode]={}
+ end
+ if mathspecs then
+ for unicode,character in next,characters do
+ local d=descriptions[unicode]
+ local m=d.math
+ if m then
+ local italic=m.italic
+ local vitalic=m.vitalic
+ local variants=m.hvariants
+ local parts=m.hparts
+ if variants then
+ local c=character
+ for i=1,#variants do
+ local un=variants[i]
+ c.next=un
+ c=characters[un]
+ end
+ c.horiz_variants=parts
+ elseif parts then
+ character.horiz_variants=parts
+ italic=m.hitalic
+ end
+ local variants=m.vvariants
+ local parts=m.vparts
+ if variants then
+ local c=character
+ for i=1,#variants do
+ local un=variants[i]
+ c.next=un
+ c=characters[un]
+ end
+ c.vert_variants=parts
+ elseif parts then
+ character.vert_variants=parts
+ end
+ if italic and italic~=0 then
+ character.italic=italic
+ end
+ if vitalic and vitalic~=0 then
+ character.vert_italic=vitalic
+ end
+ local accent=m.accent
+ if accent then
+ character.accent=accent
+ end
+ local kerns=m.kerns
+ if kerns then
+ character.mathkerns=kerns
+ end
+ end
+ end
+ end
+ local filename=constructors.checkedfilename(resources)
+ local fontname=metadata.fontname
+ local fullname=metadata.fullname or fontname
+ local psname=fontname or fullname
+ local subfont=metadata.subfontindex
+ local units=metadata.units or 1000
+ if units==0 then
+ units=1000
+ metadata.units=1000
+ report_otf("changing %a units to %a",0,units)
+ end
+ local monospaced=metadata.monospaced
+ local charwidth=metadata.averagewidth
+ local charxheight=metadata.xheight
+ local italicangle=metadata.italicangle
+ local hasitalics=metadata.hasitalics
+ properties.monospaced=monospaced
+ properties.hasitalics=hasitalics
+ parameters.italicangle=italicangle
+ parameters.charwidth=charwidth
+ parameters.charxheight=charxheight
+ local space=0x0020
+ local emdash=0x2014
+ if monospaced then
+ if descriptions[space] then
+ spaceunits,spacer=descriptions[space].width,"space"
+ end
+ if not spaceunits and descriptions[emdash] then
+ spaceunits,spacer=descriptions[emdash].width,"emdash"
+ end
+ if not spaceunits and charwidth then
+ spaceunits,spacer=charwidth,"charwidth"
+ end
+ else
+ if descriptions[space] then
+ spaceunits,spacer=descriptions[space].width,"space"
+ end
+ if not spaceunits and descriptions[emdash] then
+ spaceunits,spacer=descriptions[emdash].width/2,"emdash/2"
+ end
+ if not spaceunits and charwidth then
+ spaceunits,spacer=charwidth,"charwidth"
+ end
+ end
+ spaceunits=tonumber(spaceunits) or units/2
+ parameters.slant=0
+ parameters.space=spaceunits
+ parameters.space_stretch=1*units/2
+ parameters.space_shrink=1*units/3
+ parameters.x_height=2*units/5
+ parameters.quad=units
+ if spaceunits<2*units/5 then
+ end
+ if italicangle and italicangle~=0 then
+ parameters.italicangle=italicangle
+ parameters.italicfactor=math.cos(math.rad(90+italicangle))
+ parameters.slant=- math.tan(italicangle*math.pi/180)
+ end
+ if monospaced then
+ parameters.space_stretch=0
+ parameters.space_shrink=0
+ elseif syncspace then
+ parameters.space_stretch=spaceunits/2
+ parameters.space_shrink=spaceunits/3
+ end
+ parameters.extra_space=parameters.space_shrink
+ if charxheight then
+ parameters.x_height=charxheight
+ else
+ local x=0x0078
+ if x then
+ local x=descriptions[x]
+ if x then
+ parameters.x_height=x.height
+ end
+ end
+ end
+ parameters.designsize=(designsize/10)*65536
+ parameters.minsize=(minsize/10)*65536
+ parameters.maxsize=(maxsize/10)*65536
+ parameters.ascender=abs(metadata.ascender or 0)
+ parameters.descender=abs(metadata.descender or 0)
+ parameters.units=units
+ parameters.vheight=metadata.defaultvheight
+ properties.space=spacer
+ properties.encodingbytes=2
+ properties.format=data.format or formats.otf
+ properties.filename=filename
+ properties.fontname=fontname
+ properties.fullname=fullname
+ properties.psname=psname
+ properties.name=filename or fullname
+ properties.subfont=subfont
+ properties.private=properties.private or data.private or privateoffset
+ return {
+ characters=characters,
+ descriptions=descriptions,
+ parameters=parameters,
+ mathparameters=mathparameters,
+ resources=resources,
+ properties=properties,
+ goodies=goodies,
+ }
+ end
+end
+local converters={
+ woff={
+ cachename="webfonts",
+ action=otf.readers.woff2otf,
+ }
+}
+local function checkconversion(specification)
+ local filename=specification.filename
+ local converter=converters[lower(file.suffix(filename))]
+ if converter then
+ local base=file.basename(filename)
+ local name=file.removesuffix(base)
+ local attr=lfs.attributes(filename)
+ local size=attr and attr.size or 0
+ local time=attr and attr.modification or 0
+ if size>0 then
+ local cleanname=containers.cleanname(name)
+ local cachename=caches.setfirstwritablefile(cleanname,converter.cachename)
+ if not io.exists(cachename) or (time~=lfs.attributes(cachename).modification) then
+ report_otf("caching font %a in %a",filename,cachename)
+ converter.action(filename,cachename)
+ lfs.touch(cachename,time,time)
+ end
+ specification.filename=cachename
+ end
+ end
+end
+local function otftotfm(specification)
+ local cache_id=specification.hash
+ local tfmdata=containers.read(constructors.cache,cache_id)
+ if not tfmdata then
+ checkconversion(specification)
+ local name=specification.name
+ local sub=specification.sub
+ local subindex=specification.subindex
+ local filename=specification.filename
+ local features=specification.features.normal
+ local instance=specification.instance or (features and features.axis)
+ local rawdata=otf.load(filename,sub,instance)
+ if rawdata and next(rawdata) then
+ local descriptions=rawdata.descriptions
+ rawdata.lookuphash={}
+ tfmdata=copytotfm(rawdata,cache_id)
+ if tfmdata and next(tfmdata) then
+ local features=constructors.checkedfeatures("otf",features)
+ local shared=tfmdata.shared
+ if not shared then
+ shared={}
+ tfmdata.shared=shared
+ end
+ shared.rawdata=rawdata
+ shared.dynamics={}
+ tfmdata.changed={}
+ shared.features=features
+ shared.processes=otf.setfeatures(tfmdata,features)
+ end
+ end
+ containers.write(constructors.cache,cache_id,tfmdata)
+ end
+ return tfmdata
+end
+local function read_from_otf(specification)
+ local tfmdata=otftotfm(specification)
+ if tfmdata then
+ tfmdata.properties.name=specification.name
+ tfmdata.properties.sub=specification.sub
+ tfmdata=constructors.scale(tfmdata,specification)
+ local allfeatures=tfmdata.shared.features or specification.features.normal
+ constructors.applymanipulators("otf",tfmdata,allfeatures,trace_features,report_otf)
+ constructors.setname(tfmdata,specification)
+ fonts.loggers.register(tfmdata,file.suffix(specification.filename),specification)
+ end
+ return tfmdata
+end
+local function checkmathsize(tfmdata,mathsize)
+ local mathdata=tfmdata.shared.rawdata.metadata.math
+ local mathsize=tonumber(mathsize)
+ if mathdata then
+ local parameters=tfmdata.parameters
+ parameters.scriptpercentage=mathdata.ScriptPercentScaleDown
+ parameters.scriptscriptpercentage=mathdata.ScriptScriptPercentScaleDown
+ parameters.mathsize=mathsize
+ end
+end
+registerotffeature {
+ name="mathsize",
+ description="apply mathsize specified in the font",
+ initializers={
+ base=checkmathsize,
+ node=checkmathsize,
+ }
+}
+function otf.collectlookups(rawdata,kind,script,language)
+ if not kind then
+ return
+ end
+ if not script then
+ script=default
+ end
+ if not language then
+ language=default
+ end
+ local lookupcache=rawdata.lookupcache
+ if not lookupcache then
+ lookupcache={}
+ rawdata.lookupcache=lookupcache
+ end
+ local kindlookup=lookupcache[kind]
+ if not kindlookup then
+ kindlookup={}
+ lookupcache[kind]=kindlookup
+ end
+ local scriptlookup=kindlookup[script]
+ if not scriptlookup then
+ scriptlookup={}
+ kindlookup[script]=scriptlookup
+ end
+ local languagelookup=scriptlookup[language]
+ if not languagelookup then
+ local sequences=rawdata.resources.sequences
+ local featuremap={}
+ local featurelist={}
+ if sequences then
+ for s=1,#sequences do
+ local sequence=sequences[s]
+ local features=sequence.features
+ if features then
+ features=features[kind]
+ if features then
+ features=features[script] or features[wildcard]
+ if features then
+ features=features[language] or features[wildcard]
+ if features then
+ if not featuremap[sequence] then
+ featuremap[sequence]=true
+ featurelist[#featurelist+1]=sequence
+ end
+ end
+ end
+ end
+ end
+ end
+ if #featurelist==0 then
+ featuremap,featurelist=false,false
+ end
+ else
+ featuremap,featurelist=false,false
+ end
+ languagelookup={ featuremap,featurelist }
+ scriptlookup[language]=languagelookup
+ end
+ return unpack(languagelookup)
+end
+local function getgsub(tfmdata,k,kind,value)
+ local shared=tfmdata.shared
+ local rawdata=shared and shared.rawdata
+ if rawdata then
+ local sequences=rawdata.resources.sequences
+ if sequences then
+ local properties=tfmdata.properties
+ local validlookups,lookuplist=otf.collectlookups(rawdata,kind,properties.script,properties.language)
+ if validlookups then
+ for i=1,#lookuplist do
+ local lookup=lookuplist[i]
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ for i=1,nofsteps do
+ local coverage=steps[i].coverage
+ if coverage then
+ local found=coverage[k]
+ if found then
+ return found,lookup.type
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+end
+otf.getgsub=getgsub
+function otf.getsubstitution(tfmdata,k,kind,value)
+ local found,kind=getgsub(tfmdata,k,kind,value)
+ if not found then
+ elseif kind=="gsub_single" then
+ return found
+ elseif kind=="gsub_alternate" then
+ local choice=tonumber(value) or 1
+ return found[choice] or found[1] or k
+ end
+ return k
+end
+otf.getalternate=otf.getsubstitution
+function otf.getmultiple(tfmdata,k,kind)
+ local found,kind=getgsub(tfmdata,k,kind)
+ if found and kind=="gsub_multiple" then
+ return found
+ end
+ return { k }
+end
+function otf.getkern(tfmdata,left,right,kind)
+ local kerns=getgsub(tfmdata,left,kind or "kern",true)
+ if kerns then
+ local found=kerns[right]
+ local kind=type(found)
+ if kind=="table" then
+ found=found[1][3]
+ elseif kind~="number" then
+ found=false
+ end
+ if found then
+ return found*tfmdata.parameters.factor
+ end
+ end
+ return 0
+end
+local function check_otf(forced,specification,suffix)
+ local name=specification.name
+ if forced then
+ name=specification.forcedname
+ end
+ local fullname=findbinfile(name,suffix) or ""
+ if fullname=="" then
+ fullname=fonts.names.getfilename(name,suffix) or ""
+ end
+ if fullname~="" and not fonts.names.ignoredfile(fullname) then
+ specification.filename=fullname
+ return read_from_otf(specification)
+ end
+end
+local function opentypereader(specification,suffix)
+ local forced=specification.forced or ""
+ if formats[forced] then
+ return check_otf(true,specification,forced)
+ else
+ return check_otf(false,specification,suffix)
+ end
+end
+readers.opentype=opentypereader
+function readers.otf(specification) return opentypereader(specification,"otf") end
+function readers.ttf(specification) return opentypereader(specification,"ttf") end
+function readers.ttc(specification) return opentypereader(specification,"ttf") end
+function readers.woff(specification)
+ checkconversion(specification)
+ opentypereader(specification,"")
+end
+function otf.scriptandlanguage(tfmdata,attr)
+ local properties=tfmdata.properties
+ return properties.script or "dflt",properties.language or "dflt"
+end
+local function justset(coverage,unicode,replacement)
+ coverage[unicode]=replacement
+end
+otf.coverup={
+ stepkey="steps",
+ actions={
+ chainsubstitution=justset,
+ chainposition=justset,
+ substitution=justset,
+ alternate=justset,
+ multiple=justset,
+ kern=justset,
+ pair=justset,
+ single=justset,
+ ligature=function(coverage,unicode,ligature)
+ local first=ligature[1]
+ local tree=coverage[first]
+ if not tree then
+ tree={}
+ coverage[first]=tree
+ end
+ for i=2,#ligature do
+ local l=ligature[i]
+ local t=tree[l]
+ if not t then
+ t={}
+ tree[l]=t
+ end
+ tree=t
+ end
+ tree.ligature=unicode
+ end,
+ },
+ register=function(coverage,featuretype,format)
+ return {
+ format=format,
+ coverage=coverage,
+ }
+ end
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otl”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-oto” 52804afd96f4be005f513a012b874668] ---
+
+if not modules then modules={} end modules ['font-oto']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local concat,unpack=table.concat,table.unpack
+local insert,remove=table.insert,table.remove
+local format,gmatch,gsub,find,match,lower,strip=string.format,string.gmatch,string.gsub,string.find,string.match,string.lower,string.strip
+local type,next,tonumber,tostring,rawget=type,next,tonumber,tostring,rawget
+local trace_baseinit=false trackers.register("otf.baseinit",function(v) trace_baseinit=v end)
+local trace_singles=false trackers.register("otf.singles",function(v) trace_singles=v end)
+local trace_multiples=false trackers.register("otf.multiples",function(v) trace_multiples=v end)
+local trace_alternatives=false trackers.register("otf.alternatives",function(v) trace_alternatives=v end)
+local trace_ligatures=false trackers.register("otf.ligatures",function(v) trace_ligatures=v end)
+local trace_kerns=false trackers.register("otf.kerns",function(v) trace_kerns=v end)
+local trace_preparing=false trackers.register("otf.preparing",function(v) trace_preparing=v end)
+local report_prepare=logs.reporter("fonts","otf prepare")
+local fonts=fonts
+local otf=fonts.handlers.otf
+local otffeatures=otf.features
+local registerotffeature=otffeatures.register
+otf.defaultbasealternate="none"
+local getprivate=fonts.constructors.getprivate
+local wildcard="*"
+local default="dflt"
+local formatters=string.formatters
+local f_unicode=formatters["%U"]
+local f_uniname=formatters["%U (%s)"]
+local f_unilist=formatters["% t (% t)"]
+local function gref(descriptions,n)
+ if type(n)=="number" then
+ local name=descriptions[n].name
+ if name then
+ return f_uniname(n,name)
+ else
+ return f_unicode(n)
+ end
+ elseif n then
+ local num={}
+ local nam={}
+ local j=0
+ for i=1,#n do
+ local ni=n[i]
+ if tonumber(ni) then
+ j=j+1
+ local di=descriptions[ni]
+ num[j]=f_unicode(ni)
+ nam[j]=di and di.name or "-"
+ end
+ end
+ return f_unilist(num,nam)
+ else
+ return "<error in base mode tracing>"
+ end
+end
+local function cref(feature,sequence)
+ return formatters["feature %a, type %a, chain lookup %a"](feature,sequence.type,sequence.name)
+end
+local function report_substitution(feature,sequence,descriptions,unicode,substitution)
+ if unicode==substitution then
+ report_prepare("%s: base substitution %s maps onto itself",
+ cref(feature,sequence),
+ gref(descriptions,unicode))
+ else
+ report_prepare("%s: base substitution %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ gref(descriptions,substitution))
+ end
+end
+local function report_alternate(feature,sequence,descriptions,unicode,replacement,value,comment)
+ if unicode==replacement then
+ report_prepare("%s: base alternate %s maps onto itself",
+ cref(feature,sequence),
+ gref(descriptions,unicode))
+ else
+ report_prepare("%s: base alternate %s => %s (%S => %S)",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ replacement and gref(descriptions,replacement),
+ value,
+ comment)
+ end
+end
+local function report_ligature(feature,sequence,descriptions,unicode,ligature)
+ report_prepare("%s: base ligature %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,ligature),
+ gref(descriptions,unicode))
+end
+local function report_kern(feature,sequence,descriptions,unicode,otherunicode,value)
+ report_prepare("%s: base kern %s + %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ gref(descriptions,otherunicode),
+ value)
+end
+local basehash,basehashes,applied={},1,{}
+local function registerbasehash(tfmdata)
+ local properties=tfmdata.properties
+ local hash=concat(applied," ")
+ local base=basehash[hash]
+ if not base then
+ basehashes=basehashes+1
+ base=basehashes
+ basehash[hash]=base
+ end
+ properties.basehash=base
+ properties.fullname=(properties.fullname or properties.name).."-"..base
+ applied={}
+end
+local function registerbasefeature(feature,value)
+ applied[#applied+1]=feature.."="..tostring(value)
+end
+local function makefake(tfmdata,name,present)
+ local private=getprivate(tfmdata)
+ local character={ intermediate=true,ligatures={} }
+ resources.unicodes[name]=private
+ tfmdata.characters[private]=character
+ tfmdata.descriptions[private]={ name=name }
+ present[name]=private
+ return character
+end
+local function make_1(present,tree,name)
+ for k,v in next,tree do
+ if k=="ligature" then
+ present[name]=v
+ else
+ make_1(present,v,name.."_"..k)
+ end
+ end
+end
+local function make_2(present,tfmdata,characters,tree,name,preceding,unicode,done)
+ for k,v in next,tree do
+ if k=="ligature" then
+ local character=characters[preceding]
+ if not character then
+ if trace_baseinit then
+ report_prepare("weird ligature in lookup %a, current %C, preceding %C",sequence.name,v,preceding)
+ end
+ character=makefake(tfmdata,name,present)
+ end
+ local ligatures=character.ligatures
+ if ligatures then
+ ligatures[unicode]={ char=v }
+ else
+ character.ligatures={ [unicode]={ char=v } }
+ end
+ if done then
+ local d=done[name]
+ if not d then
+ done[name]={ "dummy",v }
+ else
+ d[#d+1]=v
+ end
+ end
+ else
+ local code=present[name] or unicode
+ local name=name.."_"..k
+ make_2(present,tfmdata,characters,v,name,code,k,done)
+ end
+ end
+end
+local function preparesubstitutions(tfmdata,feature,value,validlookups,lookuplist)
+ local characters=tfmdata.characters
+ local descriptions=tfmdata.descriptions
+ local resources=tfmdata.resources
+ local changed=tfmdata.changed
+ local ligatures={}
+ local alternate=tonumber(value) or true and 1
+ local defaultalt=otf.defaultbasealternate
+ local trace_singles=trace_baseinit and trace_singles
+ local trace_alternatives=trace_baseinit and trace_alternatives
+ local trace_ligatures=trace_baseinit and trace_ligatures
+ if not changed then
+ changed={}
+ tfmdata.changed=changed
+ end
+ for i=1,#lookuplist do
+ local sequence=lookuplist[i]
+ local steps=sequence.steps
+ local kind=sequence.type
+ if kind=="gsub_single" then
+ for i=1,#steps do
+ for unicode,data in next,steps[i].coverage do
+ if unicode~=data then
+ changed[unicode]=data
+ end
+ if trace_singles then
+ report_substitution(feature,sequence,descriptions,unicode,data)
+ end
+ end
+ end
+ elseif kind=="gsub_alternate" then
+ for i=1,#steps do
+ for unicode,data in next,steps[i].coverage do
+ local replacement=data[alternate]
+ if replacement then
+ if unicode~=replacement then
+ changed[unicode]=replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,"normal")
+ end
+ elseif defaultalt=="first" then
+ replacement=data[1]
+ if unicode~=replacement then
+ changed[unicode]=replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,defaultalt)
+ end
+ elseif defaultalt=="last" then
+ replacement=data[#data]
+ if unicode~=replacement then
+ changed[unicode]=replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,defaultalt)
+ end
+ else
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,"unknown")
+ end
+ end
+ end
+ end
+ elseif kind=="gsub_ligature" then
+ for i=1,#steps do
+ for unicode,data in next,steps[i].coverage do
+ ligatures[#ligatures+1]={ unicode,data,"" }
+ if trace_ligatures then
+ report_ligature(feature,sequence,descriptions,unicode,data)
+ end
+ end
+ end
+ end
+ end
+ local nofligatures=#ligatures
+ if nofligatures>0 then
+ local characters=tfmdata.characters
+ local present={}
+ local done=trace_baseinit and trace_ligatures and {}
+ for i=1,nofligatures do
+ local ligature=ligatures[i]
+ local unicode=ligature[1]
+ local tree=ligature[2]
+ make_1(present,tree,"ctx_"..unicode)
+ end
+ for i=1,nofligatures do
+ local ligature=ligatures[i]
+ local unicode=ligature[1]
+ local tree=ligature[2]
+ local lookupname=ligature[3]
+ make_2(present,tfmdata,characters,tree,"ctx_"..unicode,unicode,unicode,done,sequence)
+ end
+ end
+end
+local function preparepositionings(tfmdata,feature,value,validlookups,lookuplist)
+ local characters=tfmdata.characters
+ local descriptions=tfmdata.descriptions
+ local resources=tfmdata.resources
+ local properties=tfmdata.properties
+ local traceindeed=trace_baseinit and trace_kerns
+ for i=1,#lookuplist do
+ local sequence=lookuplist[i]
+ local steps=sequence.steps
+ local kind=sequence.type
+ local format=sequence.format
+ if kind=="gpos_pair" then
+ for i=1,#steps do
+ local step=steps[i]
+ local format=step.format
+ if format=="kern" or format=="move" then
+ for unicode,data in next,steps[i].coverage do
+ local character=characters[unicode]
+ local kerns=character.kerns
+ if not kerns then
+ kerns={}
+ character.kerns=kerns
+ end
+ if traceindeed then
+ for otherunicode,kern in next,data do
+ if not kerns[otherunicode] and kern~=0 then
+ kerns[otherunicode]=kern
+ report_kern(feature,sequence,descriptions,unicode,otherunicode,kern)
+ end
+ end
+ else
+ for otherunicode,kern in next,data do
+ if not kerns[otherunicode] and kern~=0 then
+ kerns[otherunicode]=kern
+ end
+ end
+ end
+ end
+ else
+ for unicode,data in next,steps[i].coverage do
+ local character=characters[unicode]
+ local kerns=character.kerns
+ for otherunicode,kern in next,data do
+ local other=kern[2]
+ if other==true or (not other and not (kerns and kerns[otherunicode])) then
+ local kern=kern[1]
+ if kern==true then
+ elseif kern[1]~=0 or kern[2]~=0 or kern[4]~=0 then
+ else
+ kern=kern[3]
+ if kern~=0 then
+ if kerns then
+ kerns[otherunicode]=kern
+ else
+ kerns={ [otherunicode]=kern }
+ character.kerns=kerns
+ end
+ if traceindeed then
+ report_kern(feature,sequence,descriptions,unicode,otherunicode,kern)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local function initializehashes(tfmdata)
+end
+local function checkmathreplacements(tfmdata,fullname,fixitalics)
+ if tfmdata.mathparameters then
+ local characters=tfmdata.characters
+ local changed=tfmdata.changed
+ if next(changed) then
+ if trace_preparing or trace_baseinit then
+ report_prepare("checking math replacements for %a",fullname)
+ end
+ for unicode,replacement in next,changed do
+ local u=characters[unicode]
+ local r=characters[replacement]
+ if u and r then
+ local n=u.next
+ local v=u.vert_variants
+ local h=u.horiz_variants
+ if fixitalics then
+ local ui=u.italic
+ if ui and not r.italic then
+ if trace_preparing then
+ report_prepare("using %i units of italic correction from %C for %U",ui,unicode,replacement)
+ end
+ r.italic=ui
+ end
+ end
+ if n and not r.next then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","incremental step",unicode,replacement)
+ end
+ r.next=n
+ end
+ if v and not r.vert_variants then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","vertical variants",unicode,replacement)
+ end
+ r.vert_variants=v
+ end
+ if h and not r.horiz_variants then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","horizontal variants",unicode,replacement)
+ end
+ r.horiz_variants=h
+ end
+ else
+ if trace_preparing then
+ report_prepare("error replacing %C by %U",unicode,replacement)
+ end
+ end
+ end
+ end
+ end
+end
+local function featuresinitializer(tfmdata,value)
+ if true then
+ local starttime=trace_preparing and os.clock()
+ local features=tfmdata.shared.features
+ local fullname=tfmdata.properties.fullname or "?"
+ if features then
+ initializehashes(tfmdata)
+ local collectlookups=otf.collectlookups
+ local rawdata=tfmdata.shared.rawdata
+ local properties=tfmdata.properties
+ local script=properties.script
+ local language=properties.language
+ local rawresources=rawdata.resources
+ local rawfeatures=rawresources and rawresources.features
+ local basesubstitutions=rawfeatures and rawfeatures.gsub
+ local basepositionings=rawfeatures and rawfeatures.gpos
+ local substitutionsdone=false
+ local positioningsdone=false
+ if basesubstitutions or basepositionings then
+ local sequences=tfmdata.resources.sequences
+ for s=1,#sequences do
+ local sequence=sequences[s]
+ local sfeatures=sequence.features
+ if sfeatures then
+ local order=sequence.order
+ if order then
+ for i=1,#order do
+ local feature=order[i]
+ local value=features[feature]
+ if value then
+ local validlookups,lookuplist=collectlookups(rawdata,feature,script,language)
+ if not validlookups then
+ elseif basesubstitutions and basesubstitutions[feature] then
+ if trace_preparing then
+ report_prepare("filtering base %s feature %a for %a with value %a","sub",feature,fullname,value)
+ end
+ preparesubstitutions(tfmdata,feature,value,validlookups,lookuplist)
+ registerbasefeature(feature,value)
+ substitutionsdone=true
+ elseif basepositionings and basepositionings[feature] then
+ if trace_preparing then
+ report_prepare("filtering base %a feature %a for %a with value %a","pos",feature,fullname,value)
+ end
+ preparepositionings(tfmdata,feature,value,validlookups,lookuplist)
+ registerbasefeature(feature,value)
+ positioningsdone=true
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if substitutionsdone then
+ checkmathreplacements(tfmdata,fullname,features.fixitalics)
+ end
+ registerbasehash(tfmdata)
+ end
+ if trace_preparing then
+ report_prepare("preparation time is %0.3f seconds for %a",os.clock()-starttime,fullname)
+ end
+ end
+end
+registerotffeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ base=featuresinitializer,
+ }
+}
+otf.basemodeinitializer=featuresinitializer
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-oto”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otj” 66c7a910d95d4a52b81061de776898e1] ---
+
+if not modules then modules={} end modules ['font-otj']={
+ version=1.001,
+ comment="companion to font-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+if not nodes.properties then return end
+local next,rawget,tonumber=next,rawget,tonumber
+local fastcopy=table.fastcopy
+local registertracker=trackers.register
+local registerdirective=directives.register
+local trace_injections=false registertracker("fonts.injections",function(v) trace_injections=v end)
+local trace_marks=false registertracker("fonts.injections.marks",function(v) trace_marks=v end)
+local trace_cursive=false registertracker("fonts.injections.cursive",function(v) trace_cursive=v end)
+local trace_spaces=false registertracker("fonts.injections.spaces",function(v) trace_spaces=v end)
+local report_injections=logs.reporter("fonts","injections")
+local report_spaces=logs.reporter("fonts","spaces")
+local attributes,nodes,node=attributes,nodes,node
+fonts=fonts
+local hashes=fonts.hashes
+local fontdata=hashes.identifiers
+local fontmarks=hashes.marks
+nodes.injections=nodes.injections or {}
+local injections=nodes.injections
+local tracers=nodes.tracers
+local setcolor=tracers and tracers.colors.set
+local resetcolor=tracers and tracers.colors.reset
+local nodecodes=nodes.nodecodes
+local glyph_code=nodecodes.glyph
+local disc_code=nodecodes.disc
+local kern_code=nodecodes.kern
+local glue_code=nodecodes.glue
+local nuts=nodes.nuts
+local nodepool=nuts.pool
+local tonode=nuts.tonode
+local tonut=nuts.tonut
+local setfield=nuts.setfield
+local getnext=nuts.getnext
+local getprev=nuts.getprev
+local getid=nuts.getid
+local getfont=nuts.getfont
+local getchar=nuts.getchar
+local getoffsets=nuts.getoffsets
+local getboth=nuts.getboth
+local getdisc=nuts.getdisc
+local setdisc=nuts.setdisc
+local setoffsets=nuts.setoffsets
+local ischar=nuts.ischar
+local getkern=nuts.getkern
+local setkern=nuts.setkern
+local setlink=nuts.setlink
+local setwidth=nuts.setwidth
+local getwidth=nuts.getwidth
+local nextchar=nuts.traversers.char
+local nextglue=nuts.traversers.glue
+local insert_node_before=nuts.insert_before
+local insert_node_after=nuts.insert_after
+local properties=nodes.properties.data
+local fontkern=nuts.pool and nuts.pool.fontkern
+local italickern=nuts.pool and nuts.pool.italickern
+local useitalickerns=false
+directives.register("fonts.injections.useitalics",function(v)
+ if v then
+ report_injections("using italics for space kerns (tracing only)")
+ end
+ useitalickerns=v
+end)
+do if not fontkern then
+ local thekern=nuts.new("kern",0)
+ local setkern=nuts.setkern
+ local copy_node=nuts.copy_node
+ fontkern=function(k)
+ local n=copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+end end
+do if not italickern then
+ local thekern=nuts.new("kern",3)
+ local setkern=nuts.setkern
+ local copy_node=nuts.copy_node
+ italickern=function(k)
+ local n=copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+end end
+function injections.installnewkern() end
+local nofregisteredkerns=0
+local nofregisteredpositions=0
+local nofregisteredmarks=0
+local nofregisteredcursives=0
+local keepregisteredcounts=false
+function injections.keepcounts()
+ keepregisteredcounts=true
+end
+function injections.resetcounts()
+ nofregisteredkerns=0
+ nofregisteredpositions=0
+ nofregisteredmarks=0
+ nofregisteredcursives=0
+ keepregisteredcounts=false
+end
+function injections.reset(n)
+ local p=rawget(properties,n)
+ if p then
+ p.injections=false
+ else
+ properties[n]=false
+ end
+end
+function injections.copy(target,source)
+ local sp=rawget(properties,source)
+ if sp then
+ local tp=rawget(properties,target)
+ local si=sp.injections
+ if si then
+ si=fastcopy(si)
+ if tp then
+ tp.injections=si
+ else
+ properties[target]={
+ injections=si,
+ }
+ end
+ elseif tp then
+ tp.injections=false
+ else
+ properties[target]={ injections={} }
+ end
+ else
+ local tp=rawget(properties,target)
+ if tp then
+ tp.injections=false
+ else
+ properties[target]=false
+ end
+ end
+end
+function injections.setligaindex(n,index)
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections
+ if i then
+ i.ligaindex=index
+ else
+ p.injections={
+ ligaindex=index
+ }
+ end
+ else
+ properties[n]={
+ injections={
+ ligaindex=index
+ }
+ }
+ end
+end
+function injections.getligaindex(n,default)
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections
+ if i then
+ return i.ligaindex or default
+ end
+ end
+ return default
+end
+function injections.setcursive(start,nxt,factor,rlmode,exit,entry,tfmstart,tfmnext,r2lflag)
+ local dx=factor*(exit[1]-entry[1])
+ local dy=-factor*(exit[2]-entry[2])
+ local ws=tfmstart.width
+ local wn=tfmnext.width
+ nofregisteredcursives=nofregisteredcursives+1
+ if rlmode<0 then
+ dx=-(dx+wn)
+ else
+ dx=dx-ws
+ end
+ if dx==0 then
+ dx=0
+ end
+ local p=rawget(properties,start)
+ if p then
+ local i=p.injections
+ if i then
+ i.cursiveanchor=true
+ else
+ p.injections={
+ cursiveanchor=true,
+ }
+ end
+ else
+ properties[start]={
+ injections={
+ cursiveanchor=true,
+ },
+ }
+ end
+ local p=rawget(properties,nxt)
+ if p then
+ local i=p.injections
+ if i then
+ i.cursivex=dx
+ i.cursivey=dy
+ else
+ p.injections={
+ cursivex=dx,
+ cursivey=dy,
+ }
+ end
+ else
+ properties[nxt]={
+ injections={
+ cursivex=dx,
+ cursivey=dy,
+ },
+ }
+ end
+ return dx,dy,nofregisteredcursives
+end
+function injections.setposition(kind,current,factor,rlmode,spec,injection)
+ local x=factor*(spec[1] or 0)
+ local y=factor*(spec[2] or 0)
+ local w=factor*(spec[3] or 0)
+ local h=factor*(spec[4] or 0)
+ if x~=0 or w~=0 or y~=0 or h~=0 then
+ local yoffset=y-h
+ local leftkern=x
+ local rightkern=w-x
+ if leftkern~=0 or rightkern~=0 or yoffset~=0 then
+ nofregisteredpositions=nofregisteredpositions+1
+ if rlmode and rlmode<0 then
+ leftkern,rightkern=rightkern,leftkern
+ end
+ if not injection then
+ injection="injections"
+ end
+ local p=rawget(properties,current)
+ if p then
+ local i=p[injection]
+ if i then
+ if leftkern~=0 then
+ i.leftkern=(i.leftkern or 0)+leftkern
+ end
+ if rightkern~=0 then
+ i.rightkern=(i.rightkern or 0)+rightkern
+ end
+ if yoffset~=0 then
+ i.yoffset=(i.yoffset or 0)+yoffset
+ end
+ elseif leftkern~=0 or rightkern~=0 then
+ p[injection]={
+ leftkern=leftkern,
+ rightkern=rightkern,
+ yoffset=yoffset,
+ }
+ else
+ p[injection]={
+ yoffset=yoffset,
+ }
+ end
+ elseif leftkern~=0 or rightkern~=0 then
+ properties[current]={
+ [injection]={
+ leftkern=leftkern,
+ rightkern=rightkern,
+ yoffset=yoffset,
+ },
+ }
+ else
+ properties[current]={
+ [injection]={
+ yoffset=yoffset,
+ },
+ }
+ end
+ return x,y,w,h,nofregisteredpositions
+ end
+ end
+ return x,y,w,h
+end
+function injections.setkern(current,factor,rlmode,x,injection)
+ local dx=factor*x
+ if dx~=0 then
+ nofregisteredkerns=nofregisteredkerns+1
+ local p=rawget(properties,current)
+ if not injection then
+ injection="injections"
+ end
+ if p then
+ local i=p[injection]
+ if i then
+ i.leftkern=dx+(i.leftkern or 0)
+ else
+ p[injection]={
+ leftkern=dx,
+ }
+ end
+ else
+ properties[current]={
+ [injection]={
+ leftkern=dx,
+ },
+ }
+ end
+ return dx,nofregisteredkerns
+ else
+ return 0,0
+ end
+end
+function injections.setmove(current,factor,rlmode,x,injection)
+ local dx=factor*x
+ if dx~=0 then
+ nofregisteredkerns=nofregisteredkerns+1
+ local p=rawget(properties,current)
+ if not injection then
+ injection="injections"
+ end
+ if rlmode and rlmode<0 then
+ if p then
+ local i=p[injection]
+ if i then
+ i.rightkern=dx+(i.rightkern or 0)
+ else
+ p[injection]={
+ rightkern=dx,
+ }
+ end
+ else
+ properties[current]={
+ [injection]={
+ rightkern=dx,
+ },
+ }
+ end
+ else
+ if p then
+ local i=p[injection]
+ if i then
+ i.leftkern=dx+(i.leftkern or 0)
+ else
+ p[injection]={
+ leftkern=dx,
+ }
+ end
+ else
+ properties[current]={
+ [injection]={
+ leftkern=dx,
+ },
+ }
+ end
+ end
+ return dx,nofregisteredkerns
+ else
+ return 0,0
+ end
+end
+function injections.setmark(start,base,factor,rlmode,ba,ma,tfmbase,mkmk,checkmark)
+ local dx=factor*(ba[1]-ma[1])
+ local dy=factor*(ba[2]-ma[2])
+ nofregisteredmarks=nofregisteredmarks+1
+ if rlmode>=0 then
+ dx=tfmbase.width-dx
+ end
+ local p=rawget(properties,start)
+ if p then
+ local i=p.injections
+ if i then
+ if i.markmark then
+ else
+ i.markx=dx
+ i.marky=dy
+ i.markdir=rlmode or 0
+ i.markbase=nofregisteredmarks
+ i.markbasenode=base
+ i.markmark=mkmk
+ i.checkmark=checkmark
+ end
+ else
+ p.injections={
+ markx=dx,
+ marky=dy,
+ markdir=rlmode or 0,
+ markbase=nofregisteredmarks,
+ markbasenode=base,
+ markmark=mkmk,
+ checkmark=checkmark,
+ }
+ end
+ else
+ properties[start]={
+ injections={
+ markx=dx,
+ marky=dy,
+ markdir=rlmode or 0,
+ markbase=nofregisteredmarks,
+ markbasenode=base,
+ markmark=mkmk,
+ checkmark=checkmark,
+ },
+ }
+ end
+ return dx,dy,nofregisteredmarks
+end
+local function dir(n)
+ return (n and n<0 and "r-to-l") or (n and n>0 and "l-to-r") or "unset"
+end
+local function showchar(n,nested)
+ local char=getchar(n)
+ report_injections("%wfont %s, char %U, glyph %c",nested and 2 or 0,getfont(n),char,char)
+end
+local function show(n,what,nested,symbol)
+ if n then
+ local p=rawget(properties,n)
+ if p then
+ local i=p[what]
+ if i then
+ local leftkern=i.leftkern or 0
+ local rightkern=i.rightkern or 0
+ local yoffset=i.yoffset or 0
+ local markx=i.markx or 0
+ local marky=i.marky or 0
+ local markdir=i.markdir or 0
+ local markbase=i.markbase or 0
+ local cursivex=i.cursivex or 0
+ local cursivey=i.cursivey or 0
+ local ligaindex=i.ligaindex or 0
+ local cursbase=i.cursiveanchor
+ local margin=nested and 4 or 2
+ if rightkern~=0 or yoffset~=0 then
+ report_injections("%w%s pair: lx %p, rx %p, dy %p",margin,symbol,leftkern,rightkern,yoffset)
+ elseif leftkern~=0 then
+ report_injections("%w%s kern: dx %p",margin,symbol,leftkern)
+ end
+ if markx~=0 or marky~=0 or markbase~=0 then
+ report_injections("%w%s mark: dx %p, dy %p, dir %s, base %s",margin,symbol,markx,marky,markdir,markbase~=0 and "yes" or "no")
+ end
+ if cursivex~=0 or cursivey~=0 then
+ if cursbase then
+ report_injections("%w%s curs: base dx %p, dy %p",margin,symbol,cursivex,cursivey)
+ else
+ report_injections("%w%s curs: dx %p, dy %p",margin,symbol,cursivex,cursivey)
+ end
+ elseif cursbase then
+ report_injections("%w%s curs: base",margin,symbol)
+ end
+ if ligaindex~=0 then
+ report_injections("%w%s liga: index %i",margin,symbol,ligaindex)
+ end
+ end
+ end
+ end
+end
+local function showsub(n,what,where)
+ report_injections("begin subrun: %s",where)
+ for n in nextchar,n do
+ showchar(n,where)
+ show(n,what,where," ")
+ end
+ report_injections("end subrun")
+end
+local function trace(head,where)
+ report_injections()
+ report_injections("begin run %s: %s kerns, %s positions, %s marks and %s cursives registered",
+ where or "",nofregisteredkerns,nofregisteredpositions,nofregisteredmarks,nofregisteredcursives)
+ local n=head
+ while n do
+ local id=getid(n)
+ if id==glyph_code then
+ showchar(n)
+ show(n,"injections",false," ")
+ show(n,"preinjections",false,"<")
+ show(n,"postinjections",false,">")
+ show(n,"replaceinjections",false,"=")
+ show(n,"emptyinjections",false,"*")
+ elseif id==disc_code then
+ local pre,post,replace=getdisc(n)
+ if pre then
+ showsub(pre,"preinjections","pre")
+ end
+ if post then
+ showsub(post,"postinjections","post")
+ end
+ if replace then
+ showsub(replace,"replaceinjections","replace")
+ end
+ show(n,"emptyinjections",false,"*")
+ end
+ n=getnext(n)
+ end
+ report_injections("end run")
+end
+local function show_result(head)
+ local current=head
+ local skipping=false
+ while current do
+ local id=getid(current)
+ if id==glyph_code then
+ local w=getwidth(current)
+ local x,y=getoffsets(current)
+ report_injections("char: %C, width %p, xoffset %p, yoffset %p",getchar(current),w,x,y)
+ skipping=false
+ elseif id==kern_code then
+ report_injections("kern: %p",getkern(current))
+ skipping=false
+ elseif not skipping then
+ report_injections()
+ skipping=true
+ end
+ current=getnext(current)
+ end
+ report_injections()
+end
+local function inject_kerns_only(head,where)
+ if trace_injections then
+ trace(head,"kerns")
+ end
+ local current=head
+ local prev=nil
+ local next=nil
+ local prevdisc=nil
+ local pre=nil
+ local post=nil
+ local replace=nil
+ local pretail=nil
+ local posttail=nil
+ local replacetail=nil
+ while current do
+ local next=getnext(current)
+ local char,id=ischar(current)
+ if char then
+ local p=rawget(properties,current)
+ if p then
+ local i=p.injections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ head=insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if prevdisc then
+ local done=false
+ if post then
+ local i=p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(posttail,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ if replace then
+ local i=p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(replacetail,fontkern(leftkern))
+ done=true
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=fontkern(leftkern)
+ done=true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ prevdisc=nil
+ elseif char==false then
+ prevdisc=nil
+ elseif id==disc_code then
+ pre,post,replace,pretail,posttail,replacetail=getdisc(current,true)
+ local done=false
+ if pre then
+ for n in nextchar,pre do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.preinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ pre=insert_node_before(pre,n,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if post then
+ for n in nextchar,post do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ post=insert_node_before(post,n,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ for n in nextchar,replace do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=insert_node_before(replace,n,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevdisc=current
+ else
+ prevdisc=nil
+ end
+ prev=current
+ current=next
+ end
+ if keepregisteredcounts then
+ keepregisteredcounts=false
+ else
+ nofregisteredkerns=0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+local function inject_positions_only(head,where)
+ if trace_injections then
+ trace(head,"positions")
+ end
+ local current=head
+ local prev=nil
+ local next=nil
+ local prevdisc=nil
+ local prevglyph=nil
+ local pre=nil
+ local post=nil
+ local replace=nil
+ local pretail=nil
+ local posttail=nil
+ local replacetail=nil
+ while current do
+ local next=getnext(current)
+ local char,id=ischar(current)
+ if char then
+ local p=rawget(properties,current)
+ if p then
+ local i=p.injections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(current,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ local rightkern=i.rightkern
+ if leftkern and leftkern~=0 then
+ if rightkern and leftkern==-rightkern then
+ setoffsets(current,leftkern,false)
+ rightkern=0
+ else
+ head=insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if rightkern and rightkern~=0 then
+ insert_node_after(head,current,fontkern(rightkern))
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ if next and getid(next)==disc_code then
+ if replace then
+ else
+ replace=fontkern(rightkern)
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if prevdisc then
+ local done=false
+ if post then
+ local i=p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(posttail,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ if replace then
+ local i=p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(replacetail,fontkern(leftkern))
+ done=true
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=fontkern(leftkern)
+ done=true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ prevdisc=nil
+ prevglyph=current
+ elseif char==false then
+ prevdisc=nil
+ prevglyph=current
+ elseif id==disc_code then
+ pre,post,replace,pretail,posttail,replacetail=getdisc(current,true)
+ local done=false
+ if pre then
+ for n in nextchar,pre do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.preinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ pre=insert_node_before(pre,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(pre,n,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if post then
+ for n in nextchar,post do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.postinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ post=insert_node_before(post,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(post,n,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ for n in nextchar,replace do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.replaceinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=insert_node_before(replace,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(replace,n,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if prevglyph then
+ if pre then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.preinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ pre=insert_node_before(pre,pre,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ if replace then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.replaceinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ replace=insert_node_before(replace,replace,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevglyph=nil
+ prevdisc=current
+ else
+ prevglyph=nil
+ prevdisc=nil
+ end
+ prev=current
+ current=next
+ end
+ if keepregisteredcounts then
+ keepregisteredcounts=false
+ else
+ nofregisteredpositions=0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+local function showoffset(n,flag)
+ local x,y=getoffsets(n)
+ if x~=0 or y~=0 then
+ setcolor(n,"darkgray")
+ end
+end
+local function inject_everything(head,where)
+ if trace_injections then
+ trace(head,"everything")
+ end
+ local hascursives=nofregisteredcursives>0
+ local hasmarks=nofregisteredmarks>0
+ local current=head
+ local last=nil
+ local prev=nil
+ local next=nil
+ local prevdisc=nil
+ local prevglyph=nil
+ local pre=nil
+ local post=nil
+ local replace=nil
+ local pretail=nil
+ local posttail=nil
+ local replacetail=nil
+ local cursiveanchor=nil
+ local minc=0
+ local maxc=0
+ local glyphs={}
+ local marks={}
+ local nofmarks=0
+ local function processmark(p,n,pn)
+ local px,py=getoffsets(p)
+ local nx,ny=getoffsets(n)
+ local ox=0
+ local rightkern=nil
+ local pp=rawget(properties,p)
+ if pp then
+ pp=pp.injections
+ if pp then
+ rightkern=pp.rightkern
+ end
+ end
+ local markdir=pn.markdir
+ if rightkern then
+ ox=px-(pn.markx or 0)-rightkern
+ if markdir and markdir<0 then
+ if not pn.markmark then
+ ox=ox+(pn.leftkern or 0)
+ end
+ else
+ if false then
+ local leftkern=pp.leftkern
+ if leftkern then
+ ox=ox-leftkern
+ end
+ end
+ end
+ else
+ ox=px-(pn.markx or 0)
+ if markdir and markdir<0 then
+ if not pn.markmark then
+ local leftkern=pn.leftkern
+ if leftkern then
+ ox=ox+leftkern
+ end
+ end
+ end
+ if pn.checkmark then
+ local wn=getwidth(n)
+ if wn and wn~=0 then
+ wn=wn/2
+ if trace_injections then
+ report_injections("correcting non zero width mark %C",getchar(n))
+ end
+ insert_node_before(n,n,fontkern(-wn))
+ insert_node_after(n,n,fontkern(-wn))
+ end
+ end
+ end
+ local oy=ny+py+(pn.marky or 0)
+ if not pn.markmark then
+ local yoffset=pn.yoffset
+ if yoffset then
+ oy=oy+yoffset
+ end
+ end
+ setoffsets(n,ox,oy)
+ if trace_marks then
+ showoffset(n,true)
+ end
+ end
+ while current do
+ local next=getnext(current)
+ local char,id=ischar(current)
+ if char then
+ local p=rawget(properties,current)
+ if p then
+ local i=p.injections
+ if i then
+ local pm=i.markbasenode
+ if pm then
+ nofmarks=nofmarks+1
+ marks[nofmarks]=current
+ else
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(current,false,yoffset)
+ end
+ if hascursives then
+ local cursivex=i.cursivex
+ if cursivex then
+ if cursiveanchor then
+ if cursivex~=0 then
+ i.leftkern=(i.leftkern or 0)+cursivex
+ end
+ if maxc==0 then
+ minc=1
+ maxc=1
+ glyphs[1]=cursiveanchor
+ else
+ maxc=maxc+1
+ glyphs[maxc]=cursiveanchor
+ end
+ properties[cursiveanchor].cursivedy=i.cursivey
+ last=current
+ else
+ maxc=0
+ end
+ elseif maxc>0 then
+ local nx,ny=getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ setoffsets(ti,false,ny)
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ maxc=0
+ cursiveanchor=nil
+ end
+ if i.cursiveanchor then
+ cursiveanchor=current
+ else
+ if maxc>0 then
+ local nx,ny=getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ setoffsets(ti,false,ny)
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ maxc=0
+ end
+ cursiveanchor=nil
+ end
+ end
+ local leftkern=i.leftkern
+ local rightkern=i.rightkern
+ if leftkern and leftkern~=0 then
+ if rightkern and leftkern==-rightkern then
+ setoffsets(current,leftkern,false)
+ rightkern=0
+ else
+ head=insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if rightkern and rightkern~=0 then
+ insert_node_after(head,current,fontkern(rightkern))
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ if next and getid(next)==disc_code then
+ if replace then
+ else
+ replace=fontkern(rightkern)
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if prevdisc then
+ if p then
+ local done=false
+ if post then
+ local i=p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(posttail,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ if replace then
+ local i=p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(replacetail,fontkern(leftkern))
+ done=true
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=fontkern(leftkern)
+ done=true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ else
+ if hascursives and maxc>0 then
+ local nx,ny=getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ local xi,yi=getoffsets(ti)
+ setoffsets(ti,xi,yi+ny)
+ end
+ maxc=0
+ cursiveanchor=nil
+ end
+ end
+ prevdisc=nil
+ prevglyph=current
+ elseif char==false then
+ prevdisc=nil
+ prevglyph=current
+ elseif id==disc_code then
+ pre,post,replace,pretail,posttail,replacetail=getdisc(current,true)
+ local done=false
+ if pre then
+ for n in nextchar,pre do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.preinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ pre=insert_node_before(pre,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(pre,n,fontkern(rightkern))
+ done=true
+ end
+ if hasmarks then
+ local pm=i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if post then
+ for n in nextchar,post do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.postinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ post=insert_node_before(post,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(post,n,fontkern(rightkern))
+ done=true
+ end
+ if hasmarks then
+ local pm=i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ for n in nextchar,replace do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.replaceinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=insert_node_before(replace,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(replace,n,fontkern(rightkern))
+ done=true
+ end
+ if hasmarks then
+ local pm=i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if prevglyph then
+ if pre then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.preinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ pre=insert_node_before(pre,pre,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ if replace then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.replaceinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ replace=insert_node_before(replace,replace,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevglyph=nil
+ prevdisc=current
+ else
+ prevglyph=nil
+ prevdisc=nil
+ end
+ prev=current
+ current=next
+ end
+ if hascursives and maxc>0 then
+ local nx,ny=getoffsets(last)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ setoffsets(ti,false,ny)
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ end
+ if nofmarks>0 then
+ for i=1,nofmarks do
+ local m=marks[i]
+ local p=rawget(properties,m)
+ local i=p.injections
+ local b=i.markbasenode
+ processmark(b,m,i)
+ end
+ elseif hasmarks then
+ end
+ if keepregisteredcounts then
+ keepregisteredcounts=false
+ else
+ nofregisteredkerns=0
+ nofregisteredpositions=0
+ nofregisteredmarks=0
+ nofregisteredcursives=0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+local triggers=false
+function nodes.injections.setspacekerns(font,sequence)
+ if triggers then
+ triggers[font]=sequence
+ else
+ triggers={ [font]=sequence }
+ end
+end
+local getthreshold
+if context then
+ local threshold=1
+ local parameters=fonts.hashes.parameters
+ directives.register("otf.threshold",function(v) threshold=tonumber(v) or 1 end)
+ getthreshold=function(font)
+ local p=parameters[font]
+ local f=p.factor
+ local s=p.spacing
+ local t=threshold*(s and s.width or p.space or 0)-2
+ return t>0 and t or 0,f
+ end
+else
+ injections.threshold=0
+ getthreshold=function(font)
+ local p=fontdata[font].parameters
+ local f=p.factor
+ local s=p.spacing
+ local t=injections.threshold*(s and s.width or p.space or 0)-2
+ return t>0 and t or 0,f
+ end
+end
+injections.getthreshold=getthreshold
+function injections.isspace(n,threshold,id)
+ if (id or getid(n))==glue_code then
+ local w=getwidth(n)
+ if threshold and w>threshold then
+ return 32
+ end
+ end
+end
+local getspaceboth=getboth
+function injections.installgetspaceboth(gb)
+ getspaceboth=gb or getboth
+end
+local function injectspaces(head)
+ if not triggers then
+ return head
+ end
+ local lastfont=nil
+ local spacekerns=nil
+ local leftkerns=nil
+ local rightkerns=nil
+ local factor=0
+ local threshold=0
+ local leftkern=false
+ local rightkern=false
+ local function updatefont(font,trig)
+ leftkerns=trig.left
+ rightkerns=trig.right
+ lastfont=font
+ threshold,
+ factor=getthreshold(font)
+ end
+ for n in nextglue,head do
+ local prev,next=getspaceboth(n)
+ local prevchar=prev and ischar(prev)
+ local nextchar=next and ischar(next)
+ if nextchar then
+ local font=getfont(next)
+ local trig=triggers[font]
+ if trig then
+ if lastfont~=font then
+ updatefont(font,trig)
+ end
+ if rightkerns then
+ rightkern=rightkerns[nextchar]
+ end
+ end
+ end
+ if prevchar then
+ local font=getfont(prev)
+ local trig=triggers[font]
+ if trig then
+ if lastfont~=font then
+ updatefont(font,trig)
+ end
+ if leftkerns then
+ leftkern=leftkerns[prevchar]
+ end
+ end
+ end
+ if leftkern then
+ local old=getwidth(n)
+ if old>threshold then
+ if rightkern then
+ if useitalickerns then
+ local lnew=leftkern*factor
+ local rnew=rightkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p + %p] %C",prevchar,lnew,old,rnew,nextchar)
+ end
+ head=insert_node_before(head,n,italickern(lnew))
+ insert_node_after(head,n,italickern(rnew))
+ else
+ local new=old+(leftkern+rightkern)*factor
+ if trace_spaces then
+ report_spaces("%C [%p -> %p] %C",prevchar,old,new,nextchar)
+ end
+ setwidth(n,new)
+ end
+ rightkern=false
+ else
+ if useitalickerns then
+ local new=leftkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p]",prevchar,old,new)
+ end
+ insert_node_after(head,n,italickern(new))
+ else
+ local new=old+leftkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p -> %p]",prevchar,old,new)
+ end
+ setwidth(n,new)
+ end
+ end
+ end
+ leftkern=false
+ elseif rightkern then
+ local old=getwidth(n)
+ if old>threshold then
+ if useitalickerns then
+ local new=rightkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p]",nextchar,old,new)
+ end
+ insert_node_after(head,n,italickern(new))
+ else
+ local new=old+rightkern*factor
+ if trace_spaces then
+ report_spaces("[%p -> %p] %C",nextchar,old,new)
+ end
+ setwidth(n,new)
+ end
+ end
+ rightkern=false
+ end
+ end
+ triggers=false
+ return head
+end
+function injections.handler(head,where)
+ if triggers then
+ head=injectspaces(head)
+ end
+ if nofregisteredmarks>0 or nofregisteredcursives>0 then
+ if trace_injections then
+ report_injections("injection variant %a","everything")
+ end
+ return inject_everything(head,where)
+ elseif nofregisteredpositions>0 then
+ if trace_injections then
+ report_injections("injection variant %a","positions")
+ end
+ return inject_positions_only(head,where)
+ elseif nofregisteredkerns>0 then
+ if trace_injections then
+ report_injections("injection variant %a","kerns")
+ end
+ return inject_kerns_only(head,where)
+ else
+ return head
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otj”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ota” d6dfb94563d6a52675e274b2e673e4a6] ---
+
+if not modules then modules={} end modules ['font-ota']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local type=type
+if not trackers then trackers={ register=function() end } end
+local fonts,nodes,node=fonts,nodes,node
+local allocate=utilities.storage.allocate
+local otf=fonts.handlers.otf
+local analyzers=fonts.analyzers
+local initializers=allocate()
+local methods=allocate()
+analyzers.initializers=initializers
+analyzers.methods=methods
+local a_state=attributes.private('state')
+local nuts=nodes.nuts
+local tonut=nuts.tonut
+local getnext=nuts.getnext
+local getprev=nuts.getprev
+local getprev=nuts.getprev
+local getprop=nuts.getprop
+local setprop=nuts.setprop
+local getsubtype=nuts.getsubtype
+local getchar=nuts.getchar
+local ischar=nuts.ischar
+local end_of_math=nuts.end_of_math
+local nodecodes=nodes.nodecodes
+local disc_code=nodecodes.disc
+local math_code=nodecodes.math
+local fontdata=fonts.hashes.identifiers
+local categories=characters and characters.categories or {}
+local chardata=characters and characters.data
+local otffeatures=fonts.constructors.features.otf
+local registerotffeature=otffeatures.register
+local s_init=1 local s_rphf=7
+local s_medi=2 local s_half=8
+local s_fina=3 local s_pref=9
+local s_isol=4 local s_blwf=10
+local s_mark=5 local s_pstf=11
+local s_rest=6
+local states=allocate {
+ init=s_init,
+ medi=s_medi,
+ med2=s_medi,
+ fina=s_fina,
+ fin2=s_fina,
+ fin3=s_fina,
+ isol=s_isol,
+ mark=s_mark,
+ rest=s_rest,
+ rphf=s_rphf,
+ half=s_half,
+ pref=s_pref,
+ blwf=s_blwf,
+ pstf=s_pstf,
+}
+local features=allocate {
+ init=s_init,
+ medi=s_medi,
+ med2=s_medi,
+ fina=s_fina,
+ fin2=s_fina,
+ fin3=s_fina,
+ isol=s_isol,
+ rphf=s_rphf,
+ half=s_half,
+ pref=s_pref,
+ blwf=s_blwf,
+ pstf=s_pstf,
+}
+analyzers.states=states
+analyzers.features=features
+analyzers.useunicodemarks=false
+function analyzers.setstate(head,font)
+ local useunicodemarks=analyzers.useunicodemarks
+ local tfmdata=fontdata[font]
+ local descriptions=tfmdata.descriptions
+ local first,last,current,n,done=nil,nil,head,0,false
+ current=tonut(current)
+ while current do
+ local char,id=ischar(current,font)
+ if char and not getprop(current,a_state) then
+ done=true
+ local d=descriptions[char]
+ if d then
+ if d.class=="mark" then
+ done=true
+ setprop(current,a_state,s_mark)
+ elseif useunicodemarks and categories[char]=="mn" then
+ done=true
+ setprop(current,a_state,s_mark)
+ elseif n==0 then
+ first,last,n=current,current,1
+ setprop(current,a_state,s_init)
+ else
+ last,n=current,n+1
+ setprop(current,a_state,s_medi)
+ end
+ else
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first,last,n=nil,nil,0
+ end
+ elseif char==false then
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first,last,n=nil,nil,0
+ if id==math_code then
+ current=end_of_math(current)
+ end
+ elseif id==disc_code then
+ setprop(current,a_state,s_medi)
+ last=current
+ else
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first,last,n=nil,nil,0
+ if id==math_code then
+ current=end_of_math(current)
+ end
+ end
+ current=getnext(current)
+ end
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ return head,done
+end
+local function analyzeinitializer(tfmdata,value)
+ local script,language=otf.scriptandlanguage(tfmdata)
+ local action=initializers[script]
+ if not action then
+ elseif type(action)=="function" then
+ return action(tfmdata,value)
+ else
+ local action=action[language]
+ if action then
+ return action(tfmdata,value)
+ end
+ end
+end
+local function analyzeprocessor(head,font,attr)
+ local tfmdata=fontdata[font]
+ local script,language=otf.scriptandlanguage(tfmdata,attr)
+ local action=methods[script]
+ if not action then
+ elseif type(action)=="function" then
+ return action(head,font,attr)
+ else
+ action=action[language]
+ if action then
+ return action(head,font,attr)
+ end
+ end
+ return head,false
+end
+registerotffeature {
+ name="analyze",
+ description="analysis of character classes",
+ default=true,
+ initializers={
+ node=analyzeinitializer,
+ },
+ processors={
+ position=1,
+ node=analyzeprocessor,
+ }
+}
+methods.latn=analyzers.setstate
+local arab_warned={}
+local function warning(current,what)
+ local char=getchar(current)
+ if not arab_warned[char] then
+ log.report("analyze","arab: character %C has no %a class",char,what)
+ arab_warned[char]=true
+ end
+end
+local mappers=allocate {
+ l=s_init,
+ d=s_medi,
+ c=s_medi,
+ r=s_fina,
+ u=s_isol,
+}
+local classifiers=characters.classifiers
+if not classifiers then
+ local f_arabic,l_arabic=characters.blockrange("arabic")
+ local f_syriac,l_syriac=characters.blockrange("syriac")
+ local f_mandiac,l_mandiac=characters.blockrange("mandiac")
+ local f_nko,l_nko=characters.blockrange("nko")
+ local f_ext_a,l_ext_a=characters.blockrange("arabicextendeda")
+ classifiers=table.setmetatableindex(function(t,k)
+ if type(k)=="number" then
+ local c=chardata[k]
+ local v=false
+ if c then
+ local arabic=c.arabic
+ if arabic then
+ v=mappers[arabic]
+ if not v then
+ log.report("analyze","error in mapping arabic %C",k)
+ v=false
+ end
+ elseif (k>=f_arabic and k<=l_arabic) or
+ (k>=f_syriac and k<=l_syriac) or
+ (k>=f_mandiac and k<=l_mandiac) or
+ (k>=f_nko and k<=l_nko) or
+ (k>=f_ext_a and k<=l_ext_a) then
+ if categories[k]=="mn" then
+ v=s_mark
+ else
+ v=s_rest
+ end
+ end
+ end
+ t[k]=v
+ return v
+ end
+ end)
+ characters.classifiers=classifiers
+end
+function methods.arab(head,font,attr)
+ local first,last,c_first,c_last
+ local current=head
+ local done=false
+ current=tonut(current)
+ while current do
+ local char,id=ischar(current,font)
+ if char and not getprop(current,a_state) then
+ done=true
+ local classifier=classifiers[char]
+ if not classifier then
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ elseif classifier==s_mark then
+ setprop(current,a_state,s_mark)
+ elseif classifier==s_isol then
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ setprop(current,a_state,s_isol)
+ elseif classifier==s_medi then
+ if first then
+ last=current
+ c_last=classifier
+ setprop(current,a_state,s_medi)
+ else
+ setprop(current,a_state,s_init)
+ first=current
+ c_first=classifier
+ end
+ elseif classifier==s_fina then
+ if last then
+ if getprop(last,a_state)~=s_init then
+ setprop(last,a_state,s_medi)
+ end
+ setprop(current,a_state,s_fina)
+ first,last=nil,nil
+ elseif first then
+ setprop(current,a_state,s_fina)
+ first=nil
+ else
+ setprop(current,a_state,s_isol)
+ end
+ else
+ setprop(current,a_state,s_rest)
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ end
+ else
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ if id==math_code then
+ current=end_of_math(current)
+ end
+ end
+ current=getnext(current)
+ end
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ end
+ return head,done
+end
+methods.syrc=methods.arab
+methods.mand=methods.arab
+methods.nko=methods.arab
+directives.register("otf.analyze.useunicodemarks",function(v)
+ analyzers.useunicodemarks=v
+end)
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ota”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ots” d5504847a278385cd0d20ecf1b3d59cc] ---
+
+if not modules then modules={} end modules ['font-ots']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+local type,next,tonumber=type,next,tonumber
+local random=math.random
+local formatters=string.formatters
+local insert=table.insert
+local registertracker=trackers.register
+local logs=logs
+local trackers=trackers
+local nodes=nodes
+local attributes=attributes
+local fonts=fonts
+local otf=fonts.handlers.otf
+local tracers=nodes.tracers
+local trace_singles=false registertracker("otf.singles",function(v) trace_singles=v end)
+local trace_multiples=false registertracker("otf.multiples",function(v) trace_multiples=v end)
+local trace_alternatives=false registertracker("otf.alternatives",function(v) trace_alternatives=v end)
+local trace_ligatures=false registertracker("otf.ligatures",function(v) trace_ligatures=v end)
+local trace_contexts=false registertracker("otf.contexts",function(v) trace_contexts=v end)
+local trace_marks=false registertracker("otf.marks",function(v) trace_marks=v end)
+local trace_kerns=false registertracker("otf.kerns",function(v) trace_kerns=v end)
+local trace_cursive=false registertracker("otf.cursive",function(v) trace_cursive=v end)
+local trace_preparing=false registertracker("otf.preparing",function(v) trace_preparing=v end)
+local trace_bugs=false registertracker("otf.bugs",function(v) trace_bugs=v end)
+local trace_details=false registertracker("otf.details",function(v) trace_details=v end)
+local trace_steps=false registertracker("otf.steps",function(v) trace_steps=v end)
+local trace_skips=false registertracker("otf.skips",function(v) trace_skips=v end)
+local trace_plugins=false registertracker("otf.plugins",function(v) trace_plugins=v end)
+local trace_chains=false registertracker("otf.chains",function(v) trace_chains=v end)
+local trace_kernruns=false registertracker("otf.kernruns",function(v) trace_kernruns=v end)
+local trace_compruns=false registertracker("otf.compruns",function(v) trace_compruns=v end)
+local trace_testruns=false registertracker("otf.testruns",function(v) trace_testruns=v end)
+local forcediscretionaries=false
+local forcepairadvance=false
+directives.register("otf.forcediscretionaries",function(v)
+ forcediscretionaries=v
+end)
+directives.register("otf.forcepairadvance",function(v)
+ forcepairadvance=v
+end)
+local report_direct=logs.reporter("fonts","otf direct")
+local report_subchain=logs.reporter("fonts","otf subchain")
+local report_chain=logs.reporter("fonts","otf chain")
+local report_process=logs.reporter("fonts","otf process")
+local report_warning=logs.reporter("fonts","otf warning")
+local report_run=logs.reporter("fonts","otf run")
+registertracker("otf.substitutions","otf.singles","otf.multiples","otf.alternatives","otf.ligatures")
+registertracker("otf.positions","otf.marks","otf.kerns","otf.cursive")
+registertracker("otf.actions","otf.substitutions","otf.positions")
+registertracker("otf.sample","otf.steps","otf.substitutions","otf.positions","otf.analyzing")
+registertracker("otf.sample.silent","otf.steps=silent","otf.substitutions","otf.positions","otf.analyzing")
+local nuts=nodes.nuts
+local getfield=nuts.getfield
+local getnext=nuts.getnext
+local setnext=nuts.setnext
+local getprev=nuts.getprev
+local setprev=nuts.setprev
+local getboth=nuts.getboth
+local setboth=nuts.setboth
+local getid=nuts.getid
+local getprop=nuts.getprop
+local setprop=nuts.setprop
+local getsubtype=nuts.getsubtype
+local setsubtype=nuts.setsubtype
+local getchar=nuts.getchar
+local setchar=nuts.setchar
+local getdisc=nuts.getdisc
+local setdisc=nuts.setdisc
+local setlink=nuts.setlink
+local getcomponents=nuts.getcomponents
+local setcomponents=nuts.setcomponents
+local getwidth=nuts.getwidth
+local getattr=nuts.getattr
+local getglyphdata=nuts.getglyphdata
+local ischar=nuts.ischar
+local isglyph=nuts.isglyph
+local usesfont=nuts.uses_font
+local insert_node_after=nuts.insert_after
+local copy_node=nuts.copy
+local copy_node_list=nuts.copy_list
+local remove_node=nuts.remove
+local find_node_tail=nuts.tail
+local flush_node_list=nuts.flush_list
+local flush_node=nuts.flush_node
+local end_of_math=nuts.end_of_math
+local setmetatable=setmetatable
+local setmetatableindex=table.setmetatableindex
+local nextnode=nuts.traversers.node
+local nodecodes=nodes.nodecodes
+local glyphcodes=nodes.glyphcodes
+local disccodes=nodes.disccodes
+local glyph_code=nodecodes.glyph
+local glue_code=nodecodes.glue
+local disc_code=nodecodes.disc
+local math_code=nodecodes.math
+local dir_code=nodecodes.dir
+local localpar_code=nodecodes.localpar
+local discretionarydisc_code=disccodes.discretionary
+local ligatureglyph_code=glyphcodes.ligature
+local a_state=attributes.private('state')
+local a_noligature=attributes.private("noligature")
+local injections=nodes.injections
+local setmark=injections.setmark
+local setcursive=injections.setcursive
+local setkern=injections.setkern
+local setmove=injections.setmove
+local setposition=injections.setposition
+local resetinjection=injections.reset
+local copyinjection=injections.copy
+local setligaindex=injections.setligaindex
+local getligaindex=injections.getligaindex
+local fontdata=fonts.hashes.identifiers
+local fontfeatures=fonts.hashes.features
+local otffeatures=fonts.constructors.features.otf
+local registerotffeature=otffeatures.register
+local onetimemessage=fonts.loggers.onetimemessage or function() end
+local getrandom=utilities and utilities.randomizer and utilities.randomizer.get
+otf.defaultnodealternate="none"
+local tfmdata=false
+local characters=false
+local descriptions=false
+local marks=false
+local classes=false
+local currentfont=false
+local factor=0
+local threshold=0
+local checkmarks=false
+local discs=false
+local spaces=false
+local sweepnode=nil
+local sweephead={}
+local notmatchpre={}
+local notmatchpost={}
+local notmatchreplace={}
+local handlers={}
+local isspace=injections.isspace
+local getthreshold=injections.getthreshold
+local checkstep=(tracers and tracers.steppers.check) or function() end
+local registerstep=(tracers and tracers.steppers.register) or function() end
+local registermessage=(tracers and tracers.steppers.message) or function() end
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_direct(...)
+end
+local function logwarning(...)
+ report_direct(...)
+end
+local gref do
+ local f_unicode=formatters["U+%X"]
+ local f_uniname=formatters["U+%X (%s)"]
+ local f_unilist=formatters["% t"]
+ gref=function(n)
+ if type(n)=="number" then
+ local description=descriptions[n]
+ local name=description and description.name
+ if name then
+ return f_uniname(n,name)
+ else
+ return f_unicode(n)
+ end
+ elseif n then
+ local t={}
+ for i=1,#n do
+ local ni=n[i]
+ if tonumber(ni) then
+ local di=descriptions[ni]
+ local nn=di and di.name
+ if nn then
+ t[#t+1]=f_uniname(ni,nn)
+ else
+ t[#t+1]=f_unicode(ni)
+ end
+ end
+ end
+ return f_unilist(t)
+ else
+ return "<error in node mode tracing>"
+ end
+ end
+end
+local function cref(dataset,sequence,index)
+ if not dataset then
+ return "no valid dataset"
+ end
+ local merged=sequence.merged and "merged " or ""
+ if index then
+ return formatters["feature %a, type %a, %schain lookup %a, index %a"](
+ dataset[4],sequence.type,merged,sequence.name,index)
+ else
+ return formatters["feature %a, type %a, %schain lookup %a"](
+ dataset[4],sequence.type,merged,sequence.name)
+ end
+end
+local function pref(dataset,sequence)
+ return formatters["feature %a, type %a, %slookup %a"](
+ dataset[4],sequence.type,sequence.merged and "merged " or "",sequence.name)
+end
+local function mref(rlmode)
+ if not rlmode or rlmode>=0 then
+ return "l2r"
+ else
+ return "r2l"
+ end
+end
+local function flattendisk(head,disc)
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local prev,next=getboth(disc)
+ local ishead=head==disc
+ setdisc(disc)
+ flush_node(disc)
+ if pre then
+ flush_node_list(pre)
+ end
+ if post then
+ flush_node_list(post)
+ end
+ if ishead then
+ if replace then
+ if next then
+ setlink(replacetail,next)
+ end
+ return replace,replace
+ elseif next then
+ return next,next
+ else
+ end
+ else
+ if replace then
+ if next then
+ setlink(replacetail,next)
+ end
+ setlink(prev,replace)
+ return head,replace
+ else
+ setlink(prev,next)
+ return head,next
+ end
+ end
+end
+local function appenddisc(disc,list)
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local posthead=list
+ local replacehead=copy_node_list(list)
+ if post then
+ setlink(posttail,posthead)
+ else
+ post=posthead
+ end
+ if replace then
+ setlink(replacetail,replacehead)
+ else
+ replace=replacehead
+ end
+ setdisc(disc,pre,post,replace)
+end
+local copy_no_components=nuts.copy_no_components
+local copy_only_glyphs=nuts.copy_only_glyphs
+local set_components=setcomponents
+local take_components=getcomponents
+local function count_components(start,marks)
+ local char=isglyph(start)
+ if char then
+ if getsubtype(start)==ligatureglyph_code then
+ local i=0
+ local components=getcomponents(start)
+ while components do
+ i=i+count_components(components,marks)
+ components=getnext(components)
+ end
+ return i
+ elseif not marks[char] then
+ return 1
+ end
+ end
+ return 0
+end
+local function markstoligature(head,start,stop,char)
+ if start==stop and getchar(start)==char then
+ return head,start
+ else
+ local prev=getprev(start)
+ local next=getnext(stop)
+ setprev(start)
+ setnext(stop)
+ local base=copy_no_components(start,copyinjection)
+ if head==start then
+ head=base
+ end
+ resetinjection(base)
+ setchar(base,char)
+ setsubtype(base,ligatureglyph_code)
+ set_components(base,start)
+ setlink(prev,base,next)
+ return head,base
+ end
+end
+local function toligature(head,start,stop,char,dataset,sequence,skiphash,discfound,hasmarks)
+ if getattr(start,a_noligature)==1 then
+ return head,start
+ end
+ if start==stop and getchar(start)==char then
+ resetinjection(start)
+ setchar(start,char)
+ return head,start
+ end
+ local prev=getprev(start)
+ local next=getnext(stop)
+ local comp=start
+ setprev(start)
+ setnext(stop)
+ local base=copy_no_components(start,copyinjection)
+ if start==head then
+ head=base
+ end
+ resetinjection(base)
+ setchar(base,char)
+ setsubtype(base,ligatureglyph_code)
+ set_components(base,comp)
+ setlink(prev,base,next)
+ if not discfound then
+ local deletemarks=not skiphash or hasmarks
+ local components=start
+ local baseindex=0
+ local componentindex=0
+ local head=base
+ local current=base
+ while start do
+ local char=getchar(start)
+ if not marks[char] then
+ baseindex=baseindex+componentindex
+ componentindex=count_components(start,marks)
+ elseif not deletemarks then
+ setligaindex(start,baseindex+getligaindex(start,componentindex))
+ if trace_marks then
+ logwarning("%s: keep mark %s, gets index %s",pref(dataset,sequence),gref(char),getligaindex(start))
+ end
+ local n=copy_node(start)
+ copyinjection(n,start)
+ head,current=insert_node_after(head,current,n)
+ elseif trace_marks then
+ logwarning("%s: delete mark %s",pref(dataset,sequence),gref(char))
+ end
+ start=getnext(start)
+ end
+ local start=getnext(current)
+ while start do
+ local char=ischar(start)
+ if char then
+ if marks[char] then
+ setligaindex(start,baseindex+getligaindex(start,componentindex))
+ if trace_marks then
+ logwarning("%s: set mark %s, gets index %s",pref(dataset,sequence),gref(char),getligaindex(start))
+ end
+ start=getnext(start)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ else
+ local discprev,discnext=getboth(discfound)
+ if discprev and discnext then
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(discfound,true)
+ if not replace then
+ local prev=getprev(base)
+ local comp=take_components(base)
+ local copied=copy_only_glyphs(comp)
+ if pre then
+ setlink(discprev,pre)
+ else
+ setnext(discprev)
+ end
+ pre=comp
+ if post then
+ setlink(posttail,discnext)
+ setprev(post)
+ else
+ post=discnext
+ setprev(discnext)
+ end
+ setlink(prev,discfound,next)
+ setboth(base)
+ set_components(base,copied)
+ replace=base
+ if forcediscretionaries then
+ setdisc(discfound,pre,post,replace,discretionarydisc_code)
+ else
+ setdisc(discfound,pre,post,replace)
+ end
+ base=prev
+ end
+ end
+ end
+ return head,base
+end
+local function multiple_glyphs(head,start,multiple,skiphash,what,stop)
+ local nofmultiples=#multiple
+ if nofmultiples>0 then
+ resetinjection(start)
+ setchar(start,multiple[1])
+ if nofmultiples>1 then
+ local sn=getnext(start)
+ for k=2,nofmultiples do
+ local n=copy_node(start)
+ resetinjection(n)
+ setchar(n,multiple[k])
+ insert_node_after(head,start,n)
+ start=n
+ end
+ if what==true then
+ elseif what>1 then
+ local m=multiple[nofmultiples]
+ for i=2,what do
+ local n=copy_node(start)
+ resetinjection(n)
+ setchar(n,m)
+ insert_node_after(head,start,n)
+ start=n
+ end
+ end
+ end
+ return head,start,true
+ else
+ if trace_multiples then
+ logprocess("no multiple for %s",gref(getchar(start)))
+ end
+ return head,start,false
+ end
+end
+local function get_alternative_glyph(start,alternatives,value)
+ local n=#alternatives
+ if n==1 then
+ return alternatives[1],trace_alternatives and "1 (only one present)"
+ elseif value=="random" then
+ local r=getrandom and getrandom("glyph",1,n) or random(1,n)
+ return alternatives[r],trace_alternatives and formatters["value %a, taking %a"](value,r)
+ elseif value=="first" then
+ return alternatives[1],trace_alternatives and formatters["value %a, taking %a"](value,1)
+ elseif value=="last" then
+ return alternatives[n],trace_alternatives and formatters["value %a, taking %a"](value,n)
+ end
+ value=value==true and 1 or tonumber(value)
+ if type(value)~="number" then
+ return alternatives[1],trace_alternatives and formatters["invalid value %s, taking %a"](value,1)
+ end
+ if value>n then
+ local defaultalt=otf.defaultnodealternate
+ if defaultalt=="first" then
+ return alternatives[n],trace_alternatives and formatters["invalid value %s, taking %a"](value,1)
+ elseif defaultalt=="last" then
+ return alternatives[1],trace_alternatives and formatters["invalid value %s, taking %a"](value,n)
+ else
+ return false,trace_alternatives and formatters["invalid value %a, %s"](value,"out of range")
+ end
+ elseif value==0 then
+ return getchar(start),trace_alternatives and formatters["invalid value %a, %s"](value,"no change")
+ elseif value<1 then
+ return alternatives[1],trace_alternatives and formatters["invalid value %a, taking %a"](value,1)
+ else
+ return alternatives[value],trace_alternatives and formatters["value %a, taking %a"](value,value)
+ end
+end
+function handlers.gsub_single(head,start,dataset,sequence,replacement)
+ if trace_singles then
+ logprocess("%s: replacing %s by single %s",pref(dataset,sequence),gref(getchar(start)),gref(replacement))
+ end
+ resetinjection(start)
+ setchar(start,replacement)
+ return head,start,true
+end
+function handlers.gsub_alternate(head,start,dataset,sequence,alternative)
+ local kind=dataset[4]
+ local what=dataset[1]
+ local value=what==true and tfmdata.shared.features[kind] or what
+ local choice,comment=get_alternative_glyph(start,alternative,value)
+ if choice then
+ if trace_alternatives then
+ logprocess("%s: replacing %s by alternative %a to %s, %s",pref(dataset,sequence),gref(getchar(start)),gref(choice),comment)
+ end
+ resetinjection(start)
+ setchar(start,choice)
+ else
+ if trace_alternatives then
+ logwarning("%s: no variant %a for %s, %s",pref(dataset,sequence),value,gref(getchar(start)),comment)
+ end
+ end
+ return head,start,true
+end
+function handlers.gsub_multiple(head,start,dataset,sequence,multiple,rlmode,skiphash)
+ if trace_multiples then
+ logprocess("%s: replacing %s by multiple %s",pref(dataset,sequence),gref(getchar(start)),gref(multiple))
+ end
+ return multiple_glyphs(head,start,multiple,skiphash,dataset[1])
+end
+function handlers.gsub_ligature(head,start,dataset,sequence,ligature,rlmode,skiphash)
+ local current=getnext(start)
+ if not current then
+ return head,start,false,nil
+ end
+ local stop=nil
+ local startchar=getchar(start)
+ if skiphash and skiphash[startchar] then
+ while current do
+ local char=ischar(current,currentfont)
+ if char then
+ local lg=ligature[char]
+ if lg then
+ stop=current
+ ligature=lg
+ current=getnext(current)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if stop then
+ local lig=ligature.ligature
+ if lig then
+ if trace_ligatures then
+ local stopchar=getchar(stop)
+ head,start=markstoligature(head,start,stop,lig)
+ logprocess("%s: replacing %s upto %s by ligature %s case 1",pref(dataset,sequence),gref(startchar),gref(stopchar),gref(getchar(start)))
+ else
+ head,start=markstoligature(head,start,stop,lig)
+ end
+ return head,start,true,false
+ else
+ end
+ end
+ else
+ local discfound=false
+ local hasmarks=marks[startchar]
+ while current do
+ local char,id=ischar(current,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ current=getnext(current)
+ else
+ local lg=ligature[char]
+ if lg then
+ if marks[char] then
+ hasmarks=true
+ end
+ stop=current
+ ligature=lg
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ elseif char==false then
+ break
+ elseif id==disc_code then
+ discfound=current
+ break
+ else
+ break
+ end
+ end
+ if discfound then
+ local pre,post,replace=getdisc(discfound)
+ local match
+ if replace then
+ local char=ischar(replace,currentfont)
+ if char and ligature[char] then
+ match=true
+ end
+ end
+ if not match and pre then
+ local char=ischar(pre,currentfont)
+ if char and ligature[char] then
+ match=true
+ end
+ end
+ if not match and not pre or not replace then
+ local n=getnext(discfound)
+ local char=ischar(n,currentfont)
+ if char and ligature[char] then
+ match=true
+ end
+ end
+ if match then
+ local ishead=head==start
+ local prev=getprev(start)
+ if stop then
+ setnext(stop)
+ local copy=copy_node_list(start)
+ local tail=stop
+ local liat=find_node_tail(copy)
+ if pre then
+ setlink(liat,pre)
+ end
+ if replace then
+ setlink(tail,replace)
+ end
+ pre=copy
+ replace=start
+ else
+ setnext(start)
+ local copy=copy_node(start)
+ if pre then
+ setlink(copy,pre)
+ end
+ if replace then
+ setlink(start,replace)
+ end
+ pre=copy
+ replace=start
+ end
+ setdisc(discfound,pre,post,replace)
+ if prev then
+ setlink(prev,discfound)
+ else
+ setprev(discfound)
+ head=discfound
+ end
+ start=discfound
+ return head,start,true,true
+ end
+ end
+ local lig=ligature.ligature
+ if lig then
+ if stop then
+ if trace_ligatures then
+ local stopchar=getchar(stop)
+ head,start=toligature(head,start,stop,lig,dataset,sequence,skiphash,false,hasmarks)
+ logprocess("%s: replacing %s upto %s by ligature %s case 2",pref(dataset,sequence),gref(startchar),gref(stopchar),gref(lig))
+ else
+ head,start=toligature(head,start,stop,lig,dataset,sequence,skiphash,false,hasmarks)
+ end
+ else
+ resetinjection(start)
+ setchar(start,lig)
+ if trace_ligatures then
+ logprocess("%s: replacing %s by (no real) ligature %s case 3",pref(dataset,sequence),gref(startchar),gref(lig))
+ end
+ end
+ return head,start,true,false
+ else
+ end
+ end
+ return head,start,false,false
+end
+function handlers.gpos_single(head,start,dataset,sequence,kerns,rlmode,skiphash,step,injection)
+ local startchar=getchar(start)
+ local format=step.format
+ if format=="single" or type(kerns)=="table" then
+ local dx,dy,w,h=setposition(0,start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s xy (%p,%p) and wh (%p,%p)",pref(dataset,sequence),gref(startchar),format,dx,dy,w,h)
+ end
+ else
+ local k=(format=="move" and setmove or setkern)(start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s %p",pref(dataset,sequence),gref(startchar),format,k)
+ end
+ end
+ return head,start,true
+end
+function handlers.gpos_pair(head,start,dataset,sequence,kerns,rlmode,skiphash,step,injection)
+ local snext=getnext(start)
+ if not snext then
+ return head,start,false
+ else
+ local prev=start
+ while snext do
+ local nextchar=ischar(snext,currentfont)
+ if nextchar then
+ if skiphash and skiphash[nextchar] then
+ prev=snext
+ snext=getnext(snext)
+ else
+ local krn=kerns[nextchar]
+ if not krn then
+ break
+ end
+ local format=step.format
+ if format=="pair" then
+ local a=krn[1]
+ local b=krn[2]
+ if a==true then
+ elseif a then
+ local x,y,w,h=setposition(1,start,factor,rlmode,a,injection)
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting first of pair %s and %s by xy (%p,%p) and wh (%p,%p) as %s",pref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h,injection or "injections")
+ end
+ end
+ if b==true then
+ start=snext
+ elseif b then
+ local x,y,w,h=setposition(2,snext,factor,rlmode,b,injection)
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting second of pair %s and %s by xy (%p,%p) and wh (%p,%p) as %s",pref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h,injection or "injections")
+ end
+ start=snext
+ elseif forcepairadvance then
+ start=snext
+ end
+ return head,start,true
+ elseif krn~=0 then
+ local k=(format=="move" and setmove or setkern)(snext,factor,rlmode,krn,injection)
+ if trace_kerns then
+ logprocess("%s: inserting %s %p between %s and %s as %s",pref(dataset,sequence),format,k,gref(getchar(prev)),gref(nextchar),injection or "injections")
+ end
+ return head,start,true
+ else
+ break
+ end
+ end
+ else
+ break
+ end
+ end
+ return head,start,false
+ end
+end
+function handlers.gpos_mark2base(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basechar %s => (%p,%p)",
+ pref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ elseif trace_bugs then
+ logwarning("%s: mark %s is not anchored to %s",pref(dataset,sequence),gref(markchar),gref(basechar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: nothing preceding, case %i",pref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: nothing preceding, case %i",pref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head,start,false
+end
+function handlers.gpos_mark2ligature(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local index=getligaindex(start)
+ ba=ba[index]
+ if ba then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, index %s, bound %s, anchoring mark %s to baselig %s at index %s => (%p,%p)",
+ pref(dataset,sequence),index,bound,gref(markchar),gref(basechar),index,dx,dy)
+ end
+ return head,start,true
+ else
+ if trace_bugs then
+ logwarning("%s: no matching anchors for mark %s and baselig %s with index %a",pref(dataset,sequence),gref(markchar),gref(basechar),index)
+ end
+ end
+ end
+ elseif trace_bugs then
+ onetimemessage(currentfont,basechar,"no base anchors",report_fonts)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",pref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",pref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head,start,false
+end
+function handlers.gpos_mark2mark(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local base=getprev(start)
+ local slc=getligaindex(start)
+ if slc then
+ while base do
+ local blc=getligaindex(base)
+ if blc and blc~=slc then
+ base=getprev(base)
+ else
+ break
+ end
+ end
+ end
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],true,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basemark %s => (%p,%p)",
+ pref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head,start,false
+end
+function handlers.gpos_cursive(head,start,dataset,sequence,exitanchors,rlmode,skiphash,step)
+ local startchar=getchar(start)
+ if marks[startchar] then
+ if trace_cursive then
+ logprocess("%s: ignoring cursive for mark %s",pref(dataset,sequence),gref(startchar))
+ end
+ else
+ local nxt=getnext(start)
+ while nxt do
+ local nextchar=ischar(nxt,currentfont)
+ if not nextchar then
+ break
+ elseif marks[nextchar] then
+ nxt=getnext(nxt)
+ else
+ local exit=exitanchors[3]
+ if exit then
+ local entry=exitanchors[1][nextchar]
+ if entry then
+ entry=entry[2]
+ if entry then
+ local r2lflag=sequence.flags[4]
+ local dx,dy,bound=setcursive(start,nxt,factor,rlmode,exit,entry,characters[startchar],characters[nextchar],r2lflag)
+ if trace_cursive then
+ logprocess("%s: moving %s to %s cursive (%p,%p) using bound %s in %s mode",pref(dataset,sequence),gref(startchar),gref(nextchar),dx,dy,bound,mref(rlmode))
+ end
+ return head,start,true
+ end
+ end
+ end
+ break
+ end
+ end
+ end
+ return head,start,false
+end
+local chainprocs={}
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_subchain(...)
+end
+local logwarning=report_subchain
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_chain(...)
+end
+local logwarning=report_chain
+local function reversesub(head,start,stop,dataset,sequence,replacements,rlmode,skiphash)
+ local char=getchar(start)
+ local replacement=replacements[char]
+ if replacement then
+ if trace_singles then
+ logprocess("%s: single reverse replacement of %s by %s",cref(dataset,sequence),gref(char),gref(replacement))
+ end
+ resetinjection(start)
+ setchar(start,replacement)
+ return head,start,true
+ else
+ return head,start,false
+ end
+end
+chainprocs.reversesub=reversesub
+local function reportzerosteps(dataset,sequence)
+ logwarning("%s: no steps",cref(dataset,sequence))
+end
+local function reportmoresteps(dataset,sequence)
+ logwarning("%s: more than 1 step",cref(dataset,sequence))
+end
+local function getmapping(dataset,sequence,currentlookup)
+ local steps=currentlookup.steps
+ local nofsteps=currentlookup.nofsteps
+ if nofsteps==0 then
+ reportzerosteps(dataset,sequence)
+ currentlookup.mapping=false
+ return false
+ else
+ if nofsteps>1 then
+ reportmoresteps(dataset,sequence)
+ end
+ local mapping=steps[1].coverage
+ currentlookup.mapping=mapping
+ currentlookup.format=steps[1].format
+ return mapping
+ end
+end
+function chainprocs.gsub_remove(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ if trace_chains then
+ logprocess("%s: removing character %s",cref(dataset,sequence,chainindex),gref(getchar(start)))
+ end
+ head,start=remove_node(head,start,true)
+ return head,getprev(start),true
+end
+function chainprocs.gsub_single(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local current=start
+ while current do
+ local currentchar=ischar(current)
+ if currentchar then
+ local replacement=mapping[currentchar]
+ if not replacement or replacement=="" then
+ if trace_bugs then
+ logwarning("%s: no single for %s",cref(dataset,sequence,chainindex),gref(currentchar))
+ end
+ else
+ if trace_singles then
+ logprocess("%s: replacing single %s by %s",cref(dataset,sequence,chainindex),gref(currentchar),gref(replacement))
+ end
+ resetinjection(current)
+ setchar(current,replacement)
+ end
+ return head,start,true
+ elseif currentchar==false then
+ break
+ elseif current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gsub_alternate(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local kind=dataset[4]
+ local what=dataset[1]
+ local value=what==true and tfmdata.shared.features[kind] or what
+ local current=start
+ while current do
+ local currentchar=ischar(current)
+ if currentchar then
+ local alternatives=mapping[currentchar]
+ if alternatives then
+ local choice,comment=get_alternative_glyph(current,alternatives,value)
+ if choice then
+ if trace_alternatives then
+ logprocess("%s: replacing %s by alternative %a to %s, %s",cref(dataset,sequence),gref(currentchar),choice,gref(choice),comment)
+ end
+ resetinjection(start)
+ setchar(start,choice)
+ else
+ if trace_alternatives then
+ logwarning("%s: no variant %a for %s, %s",cref(dataset,sequence),value,gref(currentchar),comment)
+ end
+ end
+ end
+ return head,start,true
+ elseif currentchar==false then
+ break
+ elseif current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gsub_multiple(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local replacement=mapping[startchar]
+ if not replacement or replacement=="" then
+ if trace_bugs then
+ logwarning("%s: no multiple for %s",cref(dataset,sequence),gref(startchar))
+ end
+ else
+ if trace_multiples then
+ logprocess("%s: replacing %s by multiple characters %s",cref(dataset,sequence),gref(startchar),gref(replacement))
+ end
+ return multiple_glyphs(head,start,replacement,skiphash,dataset[1],stop)
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gsub_ligature(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local ligatures=mapping[startchar]
+ if not ligatures then
+ if trace_bugs then
+ logwarning("%s: no ligatures starting with %s",cref(dataset,sequence,chainindex),gref(startchar))
+ end
+ else
+ local hasmarks=marks[startchar]
+ local current=getnext(start)
+ local discfound=false
+ local last=stop
+ local nofreplacements=1
+ while current do
+ local id=getid(current)
+ if id==disc_code then
+ if not discfound then
+ discfound=current
+ end
+ if current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ else
+ local schar=getchar(current)
+ if skiphash and skiphash[schar] then
+ current=getnext(current)
+ else
+ local lg=ligatures[schar]
+ if lg then
+ ligatures=lg
+ last=current
+ nofreplacements=nofreplacements+1
+ if marks[char] then
+ hasmarks=true
+ end
+ if current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ else
+ break
+ end
+ end
+ end
+ end
+ local ligature=ligatures.ligature
+ if ligature then
+ if chainindex then
+ stop=last
+ end
+ if trace_ligatures then
+ if start==stop then
+ logprocess("%s: replacing character %s by ligature %s case 3",cref(dataset,sequence,chainindex),gref(startchar),gref(ligature))
+ else
+ logprocess("%s: replacing character %s upto %s by ligature %s case 4",cref(dataset,sequence,chainindex),gref(startchar),gref(getchar(stop)),gref(ligature))
+ end
+ end
+ head,start=toligature(head,start,stop,ligature,dataset,sequence,skiphash,discfound,hasmarks)
+ return head,start,true,nofreplacements,discfound
+ elseif trace_bugs then
+ if start==stop then
+ logwarning("%s: replacing character %s by ligature fails",cref(dataset,sequence,chainindex),gref(startchar))
+ else
+ logwarning("%s: replacing character %s upto %s by ligature fails",cref(dataset,sequence,chainindex),gref(startchar),gref(getchar(stop)))
+ end
+ end
+ end
+ end
+ return head,start,false,0,false
+end
+function chainprocs.gpos_single(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local kerns=mapping[startchar]
+ if kerns then
+ local format=currentlookup.format
+ if format=="single" then
+ local dx,dy,w,h=setposition(0,start,factor,rlmode,kerns)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),format,dx,dy,w,h)
+ end
+ else
+ local k=(format=="move" and setmove or setkern)(start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s %p",cref(dataset,sequence),gref(startchar),format,k)
+ end
+ end
+ return head,start,true
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_pair(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local snext=getnext(start)
+ if snext then
+ local startchar=getchar(start)
+ local kerns=mapping[startchar]
+ if kerns then
+ local prev=start
+ while snext do
+ local nextchar=ischar(snext,currentfont)
+ if not nextchar then
+ break
+ end
+ if skiphash and skiphash[nextchar] then
+ prev=snext
+ snext=getnext(snext)
+ else
+ local krn=kerns[nextchar]
+ if not krn then
+ break
+ end
+ local format=currentlookup.format
+ if format=="pair" then
+ local a=krn[1]
+ local b=krn[2]
+ if a==true then
+ elseif a then
+ local x,y,w,h=setposition(1,start,factor,rlmode,a,"injections")
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting first of pair %s and %s by (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h)
+ end
+ end
+ if b==true then
+ start=snext
+ elseif b then
+ local x,y,w,h=setposition(2,snext,factor,rlmode,b,"injections")
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting second of pair %s and %s by (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h)
+ end
+ start=snext
+ elseif forcepairadvance then
+ start=snext
+ end
+ return head,start,true
+ elseif krn~=0 then
+ local k=(format=="move" and setmove or setkern)(snext,factor,rlmode,krn)
+ if trace_kerns then
+ logprocess("%s: inserting %s %p between %s and %s",cref(dataset,sequence),format,k,gref(getchar(prev)),gref(nextchar))
+ end
+ return head,start,true
+ else
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_mark2base(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local markanchors=mapping[markchar]
+ if markanchors then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basechar %s => (%p,%p)",
+ cref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_mark2ligature(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local markanchors=mapping[markchar]
+ if markanchors then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",cref(dataset,sequence),markchar,1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",cref(dataset,sequence),markchar,2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local index=getligaindex(start)
+ ba=ba[index]
+ if ba then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to baselig %s at index %s => (%p,%p)",
+ cref(dataset,sequence),a or bound,gref(markchar),gref(basechar),index,dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s, prev node is no char, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s, prev node is no char, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s, mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s, mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_mark2mark(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local markanchors=mapping[markchar]
+ if markanchors then
+ local base=getprev(start)
+ local slc=getligaindex(start)
+ if slc then
+ while base do
+ local blc=getligaindex(base)
+ if blc and blc~=slc then
+ base=getprev(base)
+ else
+ break
+ end
+ end
+ end
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],true,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basemark %s => (%p,%p)",
+ cref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no mark, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no mark, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_cursive(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local exitanchors=mapping[startchar]
+ if exitanchors then
+ if marks[startchar] then
+ if trace_cursive then
+ logprocess("%s: ignoring cursive for mark %s",pref(dataset,sequence),gref(startchar))
+ end
+ else
+ local nxt=getnext(start)
+ while nxt do
+ local nextchar=ischar(nxt,currentfont)
+ if not nextchar then
+ break
+ elseif marks[nextchar] then
+ nxt=getnext(nxt)
+ else
+ local exit=exitanchors[3]
+ if exit then
+ local entry=exitanchors[1][nextchar]
+ if entry then
+ entry=entry[2]
+ if entry then
+ local r2lflag=sequence.flags[4]
+ local dx,dy,bound=setcursive(start,nxt,factor,rlmode,exit,entry,characters[startchar],characters[nextchar],r2lflag)
+ if trace_cursive then
+ logprocess("%s: moving %s to %s cursive (%p,%p) using bound %s in %s mode",pref(dataset,sequence),gref(startchar),gref(nextchar),dx,dy,bound,mref(rlmode))
+ end
+ return head,start,true
+ end
+ end
+ elseif trace_bugs then
+ onetimemessage(currentfont,startchar,"no entry anchors",report_fonts)
+ end
+ break
+ end
+ end
+ end
+ elseif trace_cursive and trace_details then
+ logprocess("%s, cursive %s is already done",pref(dataset,sequence),gref(getchar(start)),alreadydone)
+ end
+ end
+ return head,start,false
+end
+local function show_skip(dataset,sequence,char,ck,class)
+ logwarning("%s: skipping char %s, class %a, rule %a, lookuptype %a",cref(dataset,sequence),gref(char),class,ck[1],ck[8] or ck[2])
+end
+local userkern=nuts.pool and nuts.pool.newkern
+do if not userkern then
+ local thekern=nuts.new("kern",1)
+ local setkern=nuts.setkern
+ userkern=function(k)
+ local n=copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+end end
+local function checked(head)
+ local current=head
+ while current do
+ if getid(current)==glue_code then
+ local kern=userkern(getwidth(current))
+ if head==current then
+ local next=getnext(current)
+ if next then
+ setlink(kern,next)
+ end
+ flush_node(current)
+ head=kern
+ current=next
+ else
+ local prev,next=getboth(current)
+ setlink(prev,kern,next)
+ flush_node(current)
+ current=next
+ end
+ else
+ current=getnext(current)
+ end
+ end
+ return head
+end
+local function setdiscchecked(d,pre,post,replace)
+ if pre then pre=checked(pre) end
+ if post then post=checked(post) end
+ if replace then replace=checked(replace) end
+ setdisc(d,pre,post,replace)
+end
+local noflags={ false,false,false,false }
+local function chainrun(head,start,last,dataset,sequence,rlmode,skiphash,ck)
+ local size=ck[5]-ck[4]+1
+ local chainlookups=ck[6]
+ local done=false
+ if chainlookups then
+ if size==1 then
+ local chainlookup=chainlookups[1]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local chainkind=chainstep.type
+ local chainproc=chainprocs[chainkind]
+ if chainproc then
+ local ok
+ head,start,ok=chainproc(head,start,last,dataset,sequence,chainstep,rlmode,skiphash)
+ if ok then
+ done=true
+ end
+ else
+ logprocess("%s: %s is not yet supported (1)",cref(dataset,sequence),chainkind)
+ end
+ end
+ else
+ local i=1
+ local laststart=start
+ local nofchainlookups=#chainlookups
+ while start do
+ if skiphash then
+ while start do
+ local char=ischar(start,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ end
+ local chainlookup=chainlookups[i]
+ if chainlookup then
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local chainkind=chainstep.type
+ local chainproc=chainprocs[chainkind]
+ if chainproc then
+ local ok,n
+ head,start,ok,n=chainproc(head,start,last,dataset,sequence,chainstep,rlmode,skiphash,i)
+ if ok then
+ done=true
+ if n and n>1 and i+n>nofchainlookups then
+ i=size
+ break
+ end
+ end
+ else
+ logprocess("%s: %s is not yet supported (2)",cref(dataset,sequence),chainkind)
+ end
+ end
+ else
+ end
+ i=i+1
+ if i>size or not start then
+ break
+ elseif start then
+ laststart=start
+ start=getnext(start)
+ end
+ end
+ if not start then
+ start=laststart
+ end
+ end
+ else
+ local replacements=ck[7]
+ if replacements then
+ head,start,done=reversesub(head,start,last,dataset,sequence,replacements,rlmode,skiphash)
+ else
+ done=true
+ if trace_contexts then
+ logprocess("%s: skipping match",cref(dataset,sequence))
+ end
+ end
+ end
+ return head,start,done
+end
+local function chaindisk(head,start,dataset,sequence,rlmode,skiphash,ck)
+ if not start then
+ return head,start,false
+ end
+ local startishead=start==head
+ local seq=ck[3]
+ local f=ck[4]
+ local l=ck[5]
+ local s=#seq
+ local done=false
+ local sweepnode=sweepnode
+ local sweeptype=sweeptype
+ local sweepoverflow=false
+ local keepdisc=not sweepnode
+ local lookaheaddisc=nil
+ local backtrackdisc=nil
+ local current=start
+ local last=start
+ local prev=getprev(start)
+ local hasglue=false
+ local i=f
+ while i<=l do
+ local id=getid(current)
+ if id==glyph_code then
+ i=i+1
+ last=current
+ current=getnext(current)
+ elseif id==glue_code then
+ i=i+1
+ last=current
+ current=getnext(current)
+ hasglue=true
+ elseif id==disc_code then
+ if keepdisc then
+ keepdisc=false
+ lookaheaddisc=current
+ local replace=getfield(current,"replace")
+ if not replace then
+ sweepoverflow=true
+ sweepnode=current
+ current=getnext(current)
+ else
+ while replace and i<=l do
+ if getid(replace)==glyph_code then
+ i=i+1
+ end
+ replace=getnext(replace)
+ end
+ current=getnext(replace)
+ end
+ last=current
+ else
+ head,current=flattendisk(head,current)
+ end
+ else
+ last=current
+ current=getnext(current)
+ end
+ if current then
+ elseif sweepoverflow then
+ break
+ elseif sweeptype=="post" or sweeptype=="replace" then
+ current=getnext(sweepnode)
+ if current then
+ sweeptype=nil
+ sweepoverflow=true
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if sweepoverflow then
+ local prev=current and getprev(current)
+ if not current or prev~=sweepnode then
+ local head=getnext(sweepnode)
+ local tail=nil
+ if prev then
+ tail=prev
+ setprev(current,sweepnode)
+ else
+ tail=find_node_tail(head)
+ end
+ setnext(sweepnode,current)
+ setprev(head)
+ setnext(tail)
+ appenddisc(sweepnode,head)
+ end
+ end
+ if l<s then
+ local i=l
+ local t=sweeptype=="post" or sweeptype=="replace"
+ while current and i<s do
+ local id=getid(current)
+ if id==glyph_code then
+ i=i+1
+ current=getnext(current)
+ elseif id==glue_code then
+ i=i+1
+ current=getnext(current)
+ hasglue=true
+ elseif id==disc_code then
+ if keepdisc then
+ keepdisc=false
+ if notmatchpre[current]~=notmatchreplace[current] then
+ lookaheaddisc=current
+ end
+ local replace=getfield(current,"replace")
+ while replace and i<s do
+ if getid(replace)==glyph_code then
+ i=i+1
+ end
+ replace=getnext(replace)
+ end
+ current=getnext(current)
+ elseif notmatchpre[current]~=notmatchreplace[current] then
+ head,current=flattendisk(head,current)
+ else
+ current=getnext(current)
+ end
+ else
+ current=getnext(current)
+ end
+ if not current and t then
+ current=getnext(sweepnode)
+ if current then
+ sweeptype=nil
+ end
+ end
+ end
+ end
+ if f>1 then
+ local current=prev
+ local i=f
+ local t=sweeptype=="pre" or sweeptype=="replace"
+ if not current and t and current==checkdisk then
+ current=getprev(sweepnode)
+ end
+ while current and i>1 do
+ local id=getid(current)
+ if id==glyph_code then
+ i=i-1
+ elseif id==glue_code then
+ i=i-1
+ hasglue=true
+ elseif id==disc_code then
+ if keepdisc then
+ keepdisc=false
+ if notmatchpost[current]~=notmatchreplace[current] then
+ backtrackdisc=current
+ end
+ local replace=getfield(current,"replace")
+ while replace and i>1 do
+ if getid(replace)==glyph_code then
+ i=i-1
+ end
+ replace=getnext(replace)
+ end
+ elseif notmatchpost[current]~=notmatchreplace[current] then
+ head,current=flattendisk(head,current)
+ end
+ end
+ current=getprev(current)
+ if t and current==checkdisk then
+ current=getprev(sweepnode)
+ end
+ end
+ end
+ local done=false
+ if lookaheaddisc then
+ local cf=start
+ local cl=getprev(lookaheaddisc)
+ local cprev=getprev(start)
+ local insertedmarks=0
+ while cprev do
+ local char=ischar(cf,currentfont)
+ if char and marks[char] then
+ insertedmarks=insertedmarks+1
+ cf=cprev
+ startishead=cf==head
+ cprev=getprev(cprev)
+ else
+ break
+ end
+ end
+ setlink(cprev,lookaheaddisc)
+ setprev(cf)
+ setnext(cl)
+ if startishead then
+ head=lookaheaddisc
+ end
+ local pre,post,replace=getdisc(lookaheaddisc)
+ local new=copy_node_list(cf)
+ local cnew=new
+ if pre then
+ setlink(find_node_tail(cf),pre)
+ end
+ if replace then
+ local tail=find_node_tail(new)
+ setlink(tail,replace)
+ end
+ for i=1,insertedmarks do
+ cnew=getnext(cnew)
+ end
+ cl=start
+ local clast=cnew
+ for i=f,l do
+ cl=getnext(cl)
+ clast=getnext(clast)
+ end
+ if not notmatchpre[lookaheaddisc] then
+ local ok=false
+ cf,start,ok=chainrun(cf,start,cl,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if not notmatchreplace[lookaheaddisc] then
+ local ok=false
+ new,cnew,ok=chainrun(new,cnew,clast,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if hasglue then
+ setdiscchecked(lookaheaddisc,cf,post,new)
+ else
+ setdisc(lookaheaddisc,cf,post,new)
+ end
+ start=getprev(lookaheaddisc)
+ sweephead[cf]=getnext(clast) or false
+ sweephead[new]=getnext(cl) or false
+ elseif backtrackdisc then
+ local cf=getnext(backtrackdisc)
+ local cl=start
+ local cnext=getnext(start)
+ local insertedmarks=0
+ while cnext do
+ local char=ischar(cnext,currentfont)
+ if char and marks[char] then
+ insertedmarks=insertedmarks+1
+ cl=cnext
+ cnext=getnext(cnext)
+ else
+ break
+ end
+ end
+ setlink(backtrackdisc,cnext)
+ setprev(cf)
+ setnext(cl)
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(backtrackdisc,true)
+ local new=copy_node_list(cf)
+ local cnew=find_node_tail(new)
+ for i=1,insertedmarks do
+ cnew=getprev(cnew)
+ end
+ local clast=cnew
+ for i=f,l do
+ clast=getnext(clast)
+ end
+ if not notmatchpost[backtrackdisc] then
+ local ok=false
+ cf,start,ok=chainrun(cf,start,last,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if not notmatchreplace[backtrackdisc] then
+ local ok=false
+ new,cnew,ok=chainrun(new,cnew,clast,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if post then
+ setlink(posttail,cf)
+ else
+ post=cf
+ end
+ if replace then
+ setlink(replacetail,new)
+ else
+ replace=new
+ end
+ if hasglue then
+ setdiscchecked(backtrackdisc,pre,post,replace)
+ else
+ setdisc(backtrackdisc,pre,post,replace)
+ end
+ start=getprev(backtrackdisc)
+ sweephead[post]=getnext(clast) or false
+ sweephead[replace]=getnext(last) or false
+ else
+ local ok=false
+ head,start,ok=chainrun(head,start,last,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ return head,start,done
+end
+local function chaintrac(head,start,dataset,sequence,rlmode,skiphash,ck,match,discseen,sweepnode)
+ local rule=ck[1]
+ local lookuptype=ck[8] or ck[2]
+ local nofseq=#ck[3]
+ local first=ck[4]
+ local last=ck[5]
+ local char=getchar(start)
+ logwarning("%s: rule %s %s at char %s for (%s,%s,%s) chars, lookuptype %a, %sdisc seen, %ssweeping",
+ cref(dataset,sequence),rule,match and "matches" or "nomatch",
+ gref(char),first-1,last-first+1,nofseq-last,lookuptype,
+ discseen and "" or "no ",sweepnode and "" or "not ")
+end
+local function handle_contextchain(head,start,dataset,sequence,contexts,rlmode,skiphash)
+ local sweepnode=sweepnode
+ local sweeptype=sweeptype
+ local postreplace
+ local prereplace
+ local checkdisc
+ local discseen
+ if sweeptype then
+ if sweeptype=="replace" then
+ postreplace=true
+ prereplace=true
+ else
+ postreplace=sweeptype=="post"
+ prereplace=sweeptype=="pre"
+ end
+ checkdisc=getprev(head)
+ end
+ local currentfont=currentfont
+ local skipped
+ local startprev,
+ startnext=getboth(start)
+ local done
+ local nofcontexts=contexts.n
+ local startchar=nofcontext==1 or ischar(start,currentfont)
+ for k=1,nofcontexts do
+ local ck=contexts[k]
+ local seq=ck[3]
+ local f=ck[4]
+ if not startchar or not seq[f][startchar] then
+ goto next
+ end
+ local s=seq.n
+ local l=ck[5]
+ local current=start
+ local last=start
+ if l>f then
+ local discfound
+ local n=f+1
+ last=startnext
+ while n<=l do
+ if postreplace and not last then
+ last=getnext(sweepnode)
+ sweeptype=nil
+ end
+ if last then
+ local char,id=ischar(last,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped=true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ last=getnext(last)
+ elseif seq[n][char] then
+ if n<l then
+ last=getnext(last)
+ end
+ n=n+1
+ elseif discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char==false then
+ if discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif id==disc_code then
+ discseen=true
+ discfound=last
+ notmatchpre[last]=nil
+ notmatchpost[last]=true
+ notmatchreplace[last]=nil
+ local pre,post,replace=getdisc(last)
+ if pre then
+ local n=n
+ while pre do
+ if seq[n][getchar(pre)] then
+ n=n+1
+ if n>l then
+ break
+ end
+ pre=getnext(pre)
+ else
+ notmatchpre[last]=true
+ break
+ end
+ end
+ else
+ notmatchpre[last]=true
+ end
+ if replace then
+ while replace do
+ if seq[n][getchar(replace)] then
+ n=n+1
+ if n>l then
+ break
+ end
+ replace=getnext(replace)
+ else
+ notmatchreplace[last]=true
+ if notmatchpre[last] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ if notmatchpre[last] then
+ goto next
+ end
+ end
+ last=getnext(last)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ end
+ if f>1 then
+ if startprev then
+ local prev=startprev
+ if prereplace and prev==checkdisc then
+ prev=getprev(sweepnode)
+ end
+ if prev then
+ local discfound
+ local n=f-1
+ while n>=1 do
+ if prev then
+ local char,id=ischar(prev,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped=true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ prev=getprev(prev)
+ elseif seq[n][char] then
+ if n>1 then
+ prev=getprev(prev)
+ end
+ n=n-1
+ elseif discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpost[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char==false then
+ if discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpost[discfound] then
+ goto next
+ end
+ else
+ goto next
+ end
+ break
+ elseif id==disc_code then
+ discseen=true
+ discfound=prev
+ notmatchpre[prev]=true
+ notmatchpost[prev]=nil
+ notmatchreplace[prev]=nil
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(prev,true)
+ if pre~=start and post~=start and replace~=start then
+ if post then
+ local n=n
+ while posttail do
+ if seq[n][getchar(posttail)] then
+ n=n-1
+ if posttail==post or n<1 then
+ break
+ else
+ posttail=getprev(posttail)
+ end
+ else
+ notmatchpost[prev]=true
+ break
+ end
+ end
+ if n>=1 then
+ notmatchpost[prev]=true
+ end
+ else
+ notmatchpost[prev]=true
+ end
+ if replace then
+ while replacetail do
+ if seq[n][getchar(replacetail)] then
+ n=n-1
+ if replacetail==replace or n<1 then
+ break
+ else
+ replacetail=getprev(replacetail)
+ end
+ else
+ notmatchreplace[prev]=true
+ if notmatchpost[prev] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ else
+ end
+ end
+ prev=getprev(prev)
+ elseif id==glue_code then
+ local sn=seq[n]
+ if (sn[32] and spaces[prev]) or sn[0xFFFC] then
+ n=n-1
+ prev=getprev(prev)
+ else
+ goto next
+ end
+ elseif seq[n][0xFFFC] then
+ n=n-1
+ prev=getprev(prev)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ if s>l then
+ local current=last and getnext(last)
+ if not current and postreplace then
+ current=getnext(sweepnode)
+ end
+ if current then
+ local discfound
+ local n=l+1
+ while n<=s do
+ if current then
+ local char,id=ischar(current,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped=true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ current=getnext(current)
+ elseif seq[n][char] then
+ if n<s then
+ current=getnext(current)
+ end
+ n=n+1
+ elseif discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char==false then
+ if discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif id==disc_code then
+ discseen=true
+ discfound=current
+ notmatchpre[current]=nil
+ notmatchpost[current]=true
+ notmatchreplace[current]=nil
+ local pre,post,replace=getdisc(current)
+ if pre then
+ local n=n
+ while pre do
+ if seq[n][getchar(pre)] then
+ n=n+1
+ if n>s then
+ break
+ else
+ pre=getnext(pre)
+ end
+ else
+ notmatchpre[current]=true
+ break
+ end
+ end
+ if n<=s then
+ notmatchpre[current]=true
+ end
+ else
+ notmatchpre[current]=true
+ end
+ if replace then
+ while replace do
+ if seq[n][getchar(replace)] then
+ n=n+1
+ if n>s then
+ break
+ else
+ replace=getnext(replace)
+ end
+ else
+ notmatchreplace[current]=true
+ if notmatchpre[current] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ else
+ end
+ current=getnext(current)
+ elseif id==glue_code then
+ local sn=seq[n]
+ if (sn[32] and spaces[current]) or sn[0xFFFC] then
+ n=n+1
+ current=getnext(current)
+ else
+ goto next
+ end
+ elseif seq[n][0xFFFC] then
+ n=n+1
+ current=getnext(current)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ else
+ goto next
+ end
+ end
+ if trace_contexts then
+ chaintrac(head,start,dataset,sequence,rlmode,skipped and skiphash,ck,true,discseen,sweepnode)
+ end
+ if discseen or sweepnode then
+ head,start,done=chaindisk(head,start,dataset,sequence,rlmode,skipped and skiphash,ck)
+ else
+ head,start,done=chainrun(head,start,last,dataset,sequence,rlmode,skipped and skiphash,ck)
+ end
+ if done then
+ break
+ end
+ ::next::
+ end
+ if discseen then
+ notmatchpre={}
+ notmatchpost={}
+ notmatchreplace={}
+ end
+ return head,start,done
+end
+handlers.gsub_context=handle_contextchain
+handlers.gsub_contextchain=handle_contextchain
+handlers.gsub_reversecontextchain=handle_contextchain
+handlers.gpos_contextchain=handle_contextchain
+handlers.gpos_context=handle_contextchain
+local function chained_contextchain(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash)
+ local steps=currentlookup.steps
+ local nofsteps=currentlookup.nofsteps
+ if nofsteps>1 then
+ reportmoresteps(dataset,sequence)
+ end
+ local l=steps[1].coverage[getchar(start)]
+ if l then
+ return handle_contextchain(head,start,dataset,sequence,l,rlmode,skiphash)
+ else
+ return head,start,false
+ end
+end
+chainprocs.gsub_context=chained_contextchain
+chainprocs.gsub_contextchain=chained_contextchain
+chainprocs.gsub_reversecontextchain=chained_contextchain
+chainprocs.gpos_contextchain=chained_contextchain
+chainprocs.gpos_context=chained_contextchain
+local missing=setmetatableindex("table")
+local logwarning=report_process
+local resolved={}
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_process(...)
+end
+local sequencelists=setmetatableindex(function(t,font)
+ local sequences=fontdata[font].resources.sequences
+ if not sequences or not next(sequences) then
+ sequences=false
+ end
+ t[font]=sequences
+ return sequences
+end)
+do
+ local autofeatures=fonts.analyzers.features
+ local featuretypes=otf.tables.featuretypes
+ local defaultscript=otf.features.checkeddefaultscript
+ local defaultlanguage=otf.features.checkeddefaultlanguage
+ local wildcard="*"
+ local default="dflt"
+ local function initialize(sequence,script,language,enabled,autoscript,autolanguage)
+ local features=sequence.features
+ if features then
+ local order=sequence.order
+ if order then
+ local featuretype=featuretypes[sequence.type or "unknown"]
+ for i=1,#order do
+ local kind=order[i]
+ local valid=enabled[kind]
+ if valid then
+ local scripts=features[kind]
+ local languages=scripts and (
+ scripts[script] or
+ scripts[wildcard] or
+ (autoscript and defaultscript(featuretype,autoscript,scripts))
+ )
+ local enabled=languages and (
+ languages[language] or
+ languages[wildcard] or
+ (autolanguage and defaultlanguage(featuretype,autolanguage,languages))
+ )
+ if enabled then
+ return { valid,autofeatures[kind] or false,sequence,kind }
+ end
+ end
+ end
+ else
+ end
+ end
+ return false
+ end
+ function otf.dataset(tfmdata,font)
+ local shared=tfmdata.shared
+ local properties=tfmdata.properties
+ local language=properties.language or "dflt"
+ local script=properties.script or "dflt"
+ local enabled=shared.features
+ local autoscript=enabled and enabled.autoscript
+ local autolanguage=enabled and enabled.autolanguage
+ local res=resolved[font]
+ if not res then
+ res={}
+ resolved[font]=res
+ end
+ local rs=res[script]
+ if not rs then
+ rs={}
+ res[script]=rs
+ end
+ local rl=rs[language]
+ if not rl then
+ rl={
+ }
+ rs[language]=rl
+ local sequences=tfmdata.resources.sequences
+ if sequences then
+ for s=1,#sequences do
+ local v=enabled and initialize(sequences[s],script,language,enabled,autoscript,autolanguage)
+ if v then
+ rl[#rl+1]=v
+ end
+ end
+ end
+ end
+ return rl
+ end
+end
+local function report_disc(what,n)
+ report_run("%s: %s > %s",what,n,languages.serializediscretionary(n))
+end
+local function kernrun(disc,k_run,font,attr,...)
+ if trace_kernruns then
+ report_disc("kern",disc)
+ end
+ local prev,next=getboth(disc)
+ local nextstart=next
+ local done=false
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local prevmarks=prev
+ while prevmarks do
+ local char=ischar(prevmarks,font)
+ if char and marks[char] then
+ prevmarks=getprev(prevmarks)
+ else
+ break
+ end
+ end
+ if prev and not ischar(prev,font) then
+ prev=false
+ end
+ if next and not ischar(next,font) then
+ next=false
+ end
+ if pre then
+ if k_run(pre,"injections",nil,font,attr,...) then
+ done=true
+ end
+ if prev then
+ setlink(prev,pre)
+ if k_run(prevmarks,"preinjections",pre,font,attr,...) then
+ done=true
+ end
+ setprev(pre)
+ setlink(prev,disc)
+ end
+ end
+ if post then
+ if k_run(post,"injections",nil,font,attr,...) then
+ done=true
+ end
+ if next then
+ setlink(posttail,next)
+ if k_run(posttail,"postinjections",next,font,attr,...) then
+ done=true
+ end
+ setnext(posttail)
+ setlink(disc,next)
+ end
+ end
+ if replace then
+ if k_run(replace,"injections",nil,font,attr,...) then
+ done=true
+ end
+ if prev then
+ setlink(prev,replace)
+ if k_run(prevmarks,"replaceinjections",replace,font,attr,...) then
+ done=true
+ end
+ setprev(replace)
+ setlink(prev,disc)
+ end
+ if next then
+ setlink(replacetail,next)
+ if k_run(replacetail,"replaceinjections",next,font,attr,...) then
+ done=true
+ end
+ setnext(replacetail)
+ setlink(disc,next)
+ end
+ elseif prev and next then
+ setlink(prev,next)
+ if k_run(prevmarks,"emptyinjections",next,font,attr,...) then
+ done=true
+ end
+ setlink(prev,disc,next)
+ end
+ if done and trace_testruns then
+ report_disc("done",disc)
+ end
+ return nextstart,done
+end
+local function comprun(disc,c_run,...)
+ if trace_compruns then
+ report_disc("comp",disc)
+ end
+ local pre,post,replace=getdisc(disc)
+ local renewed=false
+ if pre then
+ sweepnode=disc
+ sweeptype="pre"
+ local new,done=c_run(pre,...)
+ if done then
+ pre=new
+ renewed=true
+ end
+ end
+ if post then
+ sweepnode=disc
+ sweeptype="post"
+ local new,done=c_run(post,...)
+ if done then
+ post=new
+ renewed=true
+ end
+ end
+ if replace then
+ sweepnode=disc
+ sweeptype="replace"
+ local new,done=c_run(replace,...)
+ if done then
+ replace=new
+ renewed=true
+ end
+ end
+ sweepnode=nil
+ sweeptype=nil
+ if renewed then
+ if trace_testruns then
+ report_disc("done",disc)
+ end
+ setdisc(disc,pre,post,replace)
+ end
+ return getnext(disc),renewed
+end
+local function testrun(disc,t_run,c_run,...)
+ if trace_testruns then
+ report_disc("test",disc)
+ end
+ local prev,next=getboth(disc)
+ if not next then
+ return
+ end
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local renewed=false
+ if (post or replace) then
+ if post then
+ setlink(posttail,next)
+ else
+ post=next
+ end
+ if replace then
+ setlink(replacetail,next)
+ else
+ replace=next
+ end
+ local d_post=t_run(post,next,...)
+ local d_replace=t_run(replace,next,...)
+ if d_post>0 or d_replace>0 then
+ local d=d_replace>d_post and d_replace or d_post
+ local head=getnext(disc)
+ local tail=head
+ for i=2,d do
+ local nx=getnext(tail)
+ local id=getid(nx)
+ if id==disc_code then
+ head,tail=flattendisk(head,nx)
+ elseif id==glyph_code then
+ tail=nx
+ else
+ break
+ end
+ end
+ next=getnext(tail)
+ setnext(tail)
+ setprev(head)
+ local new=copy_node_list(head)
+ if posttail then
+ setlink(posttail,head)
+ else
+ post=head
+ end
+ if replacetail then
+ setlink(replacetail,new)
+ else
+ replace=new
+ end
+ else
+ if posttail then
+ setnext(posttail)
+ else
+ post=nil
+ end
+ if replacetail then
+ setnext(replacetail)
+ else
+ replace=nil
+ end
+ end
+ setlink(disc,next)
+ end
+ if trace_testruns then
+ report_disc("more",disc)
+ end
+ if pre then
+ sweepnode=disc
+ sweeptype="pre"
+ local new,ok=c_run(pre,...)
+ if ok then
+ pre=new
+ renewed=true
+ end
+ end
+ if post then
+ sweepnode=disc
+ sweeptype="post"
+ local new,ok=c_run(post,...)
+ if ok then
+ post=new
+ renewed=true
+ end
+ end
+ if replace then
+ sweepnode=disc
+ sweeptype="replace"
+ local new,ok=c_run(replace,...)
+ if ok then
+ replace=new
+ renewed=true
+ end
+ end
+ sweepnode=nil
+ sweeptype=nil
+ if renewed then
+ setdisc(disc,pre,post,replace)
+ if trace_testruns then
+ report_disc("done",disc)
+ end
+ end
+ return getnext(disc),renewed
+end
+local nesting=0
+local function c_run_single(head,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ local done=false
+ local sweep=sweephead[head]
+ if sweep then
+ start=sweep
+ sweephead[head]=false
+ else
+ start=head
+ end
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ if not a or (a==attr) then
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ done=true
+ end
+ end
+ if start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif char==false then
+ return head,done
+ elseif sweep then
+ return head,done
+ else
+ start=getnext(start)
+ end
+ end
+ return head,done
+end
+local function t_run_single(start,stop,font,attr,lookupcache)
+ local lastd=nil
+ while start~=stop do
+ local char=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ local startnext=getnext(start)
+ if not a or (a==attr) then
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local s=startnext
+ local ss=nil
+ local sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+ local l=nil
+ local d=0
+ while s do
+ local char=ischar(s,font)
+ if char then
+ local lg=lookupmatch[char]
+ if lg then
+ if sstop then
+ d=1
+ elseif d>0 then
+ d=d+1
+ end
+ l=lg
+ s=getnext(s)
+ sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+lookupmatch=lg
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if l and l.ligature then
+ lastd=d
+ end
+ else
+ end
+ else
+ end
+ if lastd then
+ return lastd
+ end
+ start=startnext
+ else
+ break
+ end
+ end
+ return 0
+end
+local function k_run_single(sub,injection,last,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ local a
+ if attr then
+ a=getglyphdata(sub)
+ end
+ if not a or (a==attr) then
+ for n in nextnode,sub do
+ if n==last then
+ break
+ end
+ local char=ischar(n)
+ if char then
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local h,d,ok=handler(sub,n,dataset,sequence,lookupmatch,rlmode,skiphash,step,injection)
+ if ok then
+ return true
+ end
+ end
+ end
+ end
+ end
+end
+local function c_run_multiple(head,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ local done=false
+ local sweep=sweephead[head]
+ if sweep then
+ start=sweep
+ sweephead[head]=false
+ else
+ start=head
+ end
+ while start do
+ local char=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ if not a or (a==attr) then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ done=true
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif char==false then
+ return head,done
+ elseif sweep then
+ return head,done
+ else
+ start=getnext(start)
+ end
+ end
+ return head,done
+end
+local function t_run_multiple(start,stop,font,attr,steps,nofsteps)
+ local lastd=nil
+ while start~=stop do
+ local char=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ local startnext=getnext(start)
+ if not a or (a==attr) then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local s=startnext
+ local ss=nil
+ local sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+ local l=nil
+ local d=0
+ while s do
+ local char=ischar(s)
+ if char then
+ local lg=lookupmatch[char]
+ if lg then
+ if sstop then
+ d=1
+ elseif d>0 then
+ d=d+1
+ end
+ l=lg
+ s=getnext(s)
+ sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+lookupmatch=lg
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if l and l.ligature then
+ lastd=d
+ end
+ end
+ end
+ else
+ end
+ if lastd then
+ return lastd
+ end
+ start=startnext
+ else
+ break
+ end
+ end
+ return 0
+end
+local function k_run_multiple(sub,injection,last,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ local a
+ if attr then
+ a=getglyphdata(sub)
+ end
+ if not a or (a==attr) then
+ for n in nextnode,sub do
+ if n==last then
+ break
+ end
+ local char=ischar(n)
+ if char then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local h,d,ok=handler(sub,n,dataset,sequence,lookupmatch,rlmode,skiphash,step,injection)
+ if ok then
+ return true
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local txtdirstate,pardirstate do
+ local getdirection=nuts.getdirection
+ local lefttoright=0
+ local righttoleft=1
+ txtdirstate=function(start,stack,top,rlparmode)
+ local dir,pop=getdirection(start)
+ if pop then
+ if top==1 then
+ return 0,rlparmode
+ else
+ top=top-1
+ if stack[top]==righttoleft then
+ return top,-1
+ else
+ return top,1
+ end
+ end
+ elseif dir==lefttoright then
+ top=top+1
+ stack[top]=lefttoright
+ return top,1
+ elseif dir==righttoleft then
+ top=top+1
+ stack[top]=righttoleft
+ return top,-1
+ else
+ return top,rlparmode
+ end
+ end
+ pardirstate=function(start)
+ local dir=getdirection(start)
+ if dir==lefttoright then
+ return 1,1
+ elseif dir==righttoleft then
+ return -1,-1
+ elseif dir=="TLT" then
+ return 1,1
+ elseif dir=="TRT" then
+ return -1,-1
+ else
+ return 0,0
+ end
+ end
+end
+otf.helpers=otf.helpers or {}
+otf.helpers.txtdirstate=txtdirstate
+otf.helpers.pardirstate=pardirstate
+do
+ local fastdisc=true
+ local testdics=false
+ directives.register("otf.fastdisc",function(v) fastdisc=v end)
+ local otfdataset=nil
+ local getfastdisc={ __index=function(t,k)
+ local v=usesfont(k,currentfont)
+ t[k]=v
+ return v
+ end }
+ local getfastspace={ __index=function(t,k)
+ local v=isspace(k,threshold) or false
+ t[k]=v
+ return v
+ end }
+ function otf.featuresprocessor(head,font,attr,direction,n)
+ local sequences=sequencelists[font]
+ nesting=nesting+1
+ if nesting==1 then
+ currentfont=font
+ tfmdata=fontdata[font]
+ descriptions=tfmdata.descriptions
+ characters=tfmdata.characters
+ local resources=tfmdata.resources
+ marks=resources.marks
+ classes=resources.classes
+ threshold,
+ factor=getthreshold(font)
+ checkmarks=tfmdata.properties.checkmarks
+ if not otfdataset then
+ otfdataset=otf.dataset
+ end
+ discs=fastdisc and n and n>1 and setmetatable({},getfastdisc)
+ spaces=setmetatable({},getfastspace)
+ elseif currentfont~=font then
+ report_warning("nested call with a different font, level %s, quitting",nesting)
+ nesting=nesting-1
+ return head,false
+ end
+ if trace_steps then
+ checkstep(head)
+ end
+ local initialrl=0
+ if getid(head)==localpar_code and getsubtype(head)==0 then
+ initialrl=pardirstate(head)
+ elseif direction==1 or direction=="TRT" then
+ initialrl=-1
+ end
+ local datasets=otfdataset(tfmdata,font,attr)
+ local dirstack={ nil }
+ sweephead={}
+ for s=1,#datasets do
+ local dataset=datasets[s]
+ local attribute=dataset[2]
+ local sequence=dataset[3]
+ local rlparmode=initialrl
+ local topstack=0
+ local typ=sequence.type
+ local gpossing=typ=="gpos_single" or typ=="gpos_pair"
+ local forcetestrun=typ=="gsub_ligature"
+ local handler=handlers[typ]
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ local skiphash=sequence.skiphash
+ if not steps then
+ local h,ok=handler(head,dataset,sequence,initialrl,font,attr)
+ if h and h~=head then
+ head=h
+ end
+ elseif typ=="gsub_reversecontextchain" then
+ local start=find_node_tail(head)
+ local rlmode=0
+ local merged=steps.merged
+ while start do
+ local char=ischar(start,font)
+ if char then
+ local m=merged[char]
+ if m then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ if not a or (a==attr) then
+ for i=m[1],m[2] do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ break
+ end
+ end
+ end
+ if start then
+ start=getprev(start)
+ end
+ else
+ start=getprev(start)
+ end
+ else
+ start=getprev(start)
+ end
+ else
+ start=getprev(start)
+ end
+ end
+ else
+ local start=head
+ local rlmode=initialrl
+ if nofsteps==1 then
+ local step=steps[1]
+ local lookupcache=step.coverage
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local a
+ if attr then
+ if getglyphdata(start)==attr and (not attribute or getprop(start,a_state)==attribute) then
+ a=true
+ end
+ elseif not attribute or getprop(start,a_state)==attribute then
+ a=true
+ end
+ if a then
+ local ok,df
+ head,start,ok,df=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if df then
+ elseif start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ end
+ elseif char==false or id==glue_code then
+ start=getnext(start)
+ elseif id==disc_code then
+ if not discs or discs[start]==true then
+ local ok
+ if gpossing then
+ start,ok=kernrun(start,k_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ elseif forcetestrun then
+ start,ok=testrun(start,t_run_single,c_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ else
+ start,ok=comprun(start,c_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif id==math_code then
+ start=getnext(end_of_math(start))
+ elseif id==dir_code then
+ topstack,rlmode=txtdirstate(start,dirstack,topstack,rlparmode)
+ start=getnext(start)
+ else
+ start=getnext(start)
+ end
+ end
+ else
+ local merged=steps.merged
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ local m=merged[char]
+ if m then
+ local a
+ if attr then
+ if getglyphdata(start)==attr and (not attribute or getprop(start,a_state)==attribute) then
+ a=true
+ end
+ elseif not attribute or getprop(start,a_state)==attribute then
+ a=true
+ end
+ if a then
+ local ok,df
+ for i=m[1],m[2] do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ head,start,ok,df=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if df then
+ break
+ elseif ok then
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if df then
+ elseif start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ end
+ elseif char==false or id==glue_code then
+ start=getnext(start)
+ elseif id==disc_code then
+ if not discs or discs[start]==true then
+ local ok
+ if gpossing then
+ start,ok=kernrun(start,k_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ elseif forcetestrun then
+ start,ok=testrun(start,t_run_multiple,c_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ else
+ start,ok=comprun(start,c_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif id==math_code then
+ start=getnext(end_of_math(start))
+ elseif id==dir_code then
+ topstack,rlmode=txtdirstate(start,dirstack,topstack,rlparmode)
+ start=getnext(start)
+ else
+ start=getnext(start)
+ end
+ end
+ end
+ end
+ if trace_steps then
+ registerstep(head)
+ end
+ end
+ nesting=nesting-1
+ return head
+ end
+ function otf.datasetpositionprocessor(head,font,direction,dataset)
+ currentfont=font
+ tfmdata=fontdata[font]
+ descriptions=tfmdata.descriptions
+ characters=tfmdata.characters
+ local resources=tfmdata.resources
+ marks=resources.marks
+ classes=resources.classes
+ threshold,
+ factor=getthreshold(font)
+ checkmarks=tfmdata.properties.checkmarks
+ if type(dataset)=="number" then
+ dataset=otfdataset(tfmdata,font,0)[dataset]
+ end
+ local sequence=dataset[3]
+ local typ=sequence.type
+ local handler=handlers[typ]
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ local done=false
+ local dirstack={ nil }
+ local start=head
+ local initialrl=(direction==1 or direction=="TRT") and -1 or 0
+ local rlmode=initialrl
+ local rlparmode=initialrl
+ local topstack=0
+ local merged=steps.merged
+ local position=0
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ position=position+1
+ local m=merged[char]
+ if m then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ for i=m[1],m[2] do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if start then
+ start=getnext(start)
+ end
+ end
+ else
+ start=getnext(start)
+ end
+ elseif char==false or id==glue_code then
+ start=getnext(start)
+ elseif id==math_code then
+ start=getnext(end_of_math(start))
+ elseif id==dir_code then
+ topstack,rlmode=txtdirstate(start,dirstack,topstack,rlparmode)
+ start=getnext(start)
+ else
+ start=getnext(start)
+ end
+ end
+ return head
+ end
+end
+local plugins={}
+otf.plugins=plugins
+local report=logs.reporter("fonts")
+function otf.registerplugin(name,f)
+ if type(name)=="string" and type(f)=="function" then
+ plugins[name]={ name,f }
+ report()
+ report("plugin %a has been loaded, please be aware of possible side effects",name)
+ report()
+ if logs.pushtarget then
+ logs.pushtarget("log")
+ end
+ report("Plugins are not officially supported unless stated otherwise. This is because")
+ report("they bypass the regular font handling and therefore some features in ConTeXt")
+ report("(especially those related to fonts) might not work as expected or might not work")
+ report("at all. Some plugins are for testing and development only and might change")
+ report("whenever we feel the need for it.")
+ report()
+ if logs.poptarget then
+ logs.poptarget()
+ end
+ end
+end
+function otf.plugininitializer(tfmdata,value)
+ if type(value)=="string" then
+ tfmdata.shared.plugin=plugins[value]
+ end
+end
+function otf.pluginprocessor(head,font,attr,direction)
+ local s=fontdata[font].shared
+ local p=s and s.plugin
+ if p then
+ if trace_plugins then
+ report_process("applying plugin %a",p[1])
+ end
+ return p[2](head,font,attr,direction)
+ else
+ return head,false
+ end
+end
+function otf.featuresinitializer(tfmdata,value)
+end
+registerotffeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ position=1,
+ node=otf.featuresinitializer,
+ plug=otf.plugininitializer,
+ },
+ processors={
+ node=otf.featuresprocessor,
+ plug=otf.pluginprocessor,
+ }
+}
+otf.handlers=handlers
+local setspacekerns=nodes.injections.setspacekerns if not setspacekerns then os.exit() end
+local tag="kern"
+if fontfeatures then
+ function handlers.trigger_space_kerns(head,dataset,sequence,initialrl,font,attr)
+ local features=fontfeatures[font]
+ local enabled=features and features.spacekern and features[tag]
+ if enabled then
+ setspacekerns(font,sequence)
+ end
+ return head,enabled
+ end
+else
+ function handlers.trigger_space_kerns(head,dataset,sequence,initialrl,font,attr)
+ local shared=fontdata[font].shared
+ local features=shared and shared.features
+ local enabled=features and features.spacekern and features[tag]
+ if enabled then
+ setspacekerns(font,sequence)
+ end
+ return head,enabled
+ end
+end
+local function hasspacekerns(data)
+ local resources=data.resources
+ local sequences=resources.sequences
+ local validgpos=resources.features.gpos
+ if validgpos and sequences then
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ if steps and sequence.features[tag] then
+ local kind=sequence.type
+ if kind=="gpos_pair" or kind=="gpos_single" then
+ for i=1,#steps do
+ local step=steps[i]
+ local coverage=step.coverage
+ local rules=step.rules
+ if rules then
+ elseif not coverage then
+ elseif kind=="gpos_single" then
+ elseif kind=="gpos_pair" then
+ local format=step.format
+ if format=="move" or format=="kern" then
+ local kerns=coverage[32]
+ if kerns then
+ return true
+ end
+ for k,v in next,coverage do
+ if v[32] then
+ return true
+ end
+ end
+ elseif format=="pair" then
+ local kerns=coverage[32]
+ if kerns then
+ for k,v in next,kerns do
+ local one=v[1]
+ if one and one~=true then
+ return true
+ end
+ end
+ end
+ for k,v in next,coverage do
+ local kern=v[32]
+ if kern then
+ local one=kern[1]
+ if one and one~=true then
+ return true
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ return false
+end
+otf.readers.registerextender {
+ name="spacekerns",
+ action=function(data)
+ data.properties.hasspacekerns=hasspacekerns(data)
+ end
+}
+local function spaceinitializer(tfmdata,value)
+ local resources=tfmdata.resources
+ local spacekerns=resources and resources.spacekerns
+ if value and spacekerns==nil then
+ local rawdata=tfmdata.shared and tfmdata.shared.rawdata
+ local properties=rawdata.properties
+ if properties and properties.hasspacekerns then
+ local sequences=resources.sequences
+ local validgpos=resources.features.gpos
+ if validgpos and sequences then
+ local left={}
+ local right={}
+ local last=0
+ local feat=nil
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ if steps then
+ local kern=sequence.features[tag]
+ if kern then
+ local kind=sequence.type
+ if kind=="gpos_pair" or kind=="gpos_single" then
+ if feat then
+ for script,languages in next,kern do
+ local f=feat[script]
+ if f then
+ for l in next,languages do
+ f[l]=true
+ end
+ else
+ feat[script]=languages
+ end
+ end
+ else
+ feat=kern
+ end
+ for i=1,#steps do
+ local step=steps[i]
+ local coverage=step.coverage
+ local rules=step.rules
+ if rules then
+ elseif not coverage then
+ elseif kind=="gpos_single" then
+ elseif kind=="gpos_pair" then
+ local format=step.format
+ if format=="move" or format=="kern" then
+ local kerns=coverage[32]
+ if kerns then
+ for k,v in next,kerns do
+ right[k]=v
+ end
+ end
+ for k,v in next,coverage do
+ local kern=v[32]
+ if kern then
+ left[k]=kern
+ end
+ end
+ elseif format=="pair" then
+ local kerns=coverage[32]
+ if kerns then
+ for k,v in next,kerns do
+ local one=v[1]
+ if one and one~=true then
+ right[k]=one[3]
+ end
+ end
+ end
+ for k,v in next,coverage do
+ local kern=v[32]
+ if kern then
+ local one=kern[1]
+ if one and one~=true then
+ left[k]=one[3]
+ end
+ end
+ end
+ end
+ end
+ end
+ last=i
+ end
+ else
+ end
+ end
+ end
+ left=next(left) and left or false
+ right=next(right) and right or false
+ if left or right then
+ spacekerns={
+ left=left,
+ right=right,
+ }
+ if last>0 then
+ local triggersequence={
+ features={ [tag]=feat or { dflt={ dflt=true,} } },
+ flags=noflags,
+ name="trigger_space_kerns",
+ order={ tag },
+ type="trigger_space_kerns",
+ left=left,
+ right=right,
+ }
+ insert(sequences,last,triggersequence)
+ end
+ end
+ end
+ end
+ resources.spacekerns=spacekerns
+ end
+ return spacekerns
+end
+registerotffeature {
+ name="spacekern",
+ description="space kern injection",
+ default=true,
+ initializers={
+ node=spaceinitializer,
+ },
+}
+local function markinitializer(tfmdata,value)
+ local properties=tfmdata.properties
+ properties.checkmarks=value
+end
+registerotffeature {
+ name="checkmarks",
+ description="check mark widths",
+ default=true,
+ initializers={
+ node=markinitializer,
+ },
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ots”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-osd” 79eb2fc4a71364fd73c8b996a109f5df] ---
+
+if not modules then modules={} end modules ['font-osd']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Kai Eigner, TAT Zetwerk / Hans Hagen, PRAGMA ADE",
+ copyright="TAT Zetwerk / PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local insert,imerge,copy,tohash=table.insert,table.imerge,table.copy,table.tohash
+local next,type=next,type
+local report=logs.reporter("otf","devanagari")
+fonts=fonts or {}
+fonts.analyzers=fonts.analyzers or {}
+fonts.analyzers.methods=fonts.analyzers.methods or { node={ otf={} } }
+local otf=fonts.handlers.otf
+local handlers=otf.handlers
+local methods=fonts.analyzers.methods
+local otffeatures=fonts.constructors.features.otf
+local registerotffeature=otffeatures.register
+local nuts=nodes.nuts
+local getnext=nuts.getnext
+local getprev=nuts.getprev
+local getboth=nuts.getboth
+local getid=nuts.getid
+local getchar=nuts.getchar
+local getfont=nuts.getfont
+local getsubtype=nuts.getsubtype
+local setlink=nuts.setlink
+local setnext=nuts.setnext
+local setprev=nuts.setprev
+local setchar=nuts.setchar
+local getprop=nuts.getprop
+local setprop=nuts.setprop
+local ischar=nuts.ischar
+local insert_node_after=nuts.insert_after
+local copy_node=nuts.copy
+local remove_node=nuts.remove
+local flush_list=nuts.flush_list
+local flush_node=nuts.flush_node
+local copyinjection=nodes.injections.copy
+local unsetvalue=attributes.unsetvalue
+local fontdata=fonts.hashes.identifiers
+local a_state=attributes.private('state')
+local a_syllabe=attributes.private('syllabe')
+local dotted_circle=0x25CC
+local c_nbsp=0x00A0
+local c_zwnj=0x200C
+local c_zwj=0x200D
+local states=fonts.analyzers.states
+local s_rphf=states.rphf
+local s_half=states.half
+local s_pref=states.pref
+local s_blwf=states.blwf
+local s_pstf=states.pstf
+local s_init=states.init
+local replace_all_nbsp=nil
+replace_all_nbsp=function(head)
+ replace_all_nbsp=typesetters and typesetters.characters and typesetters.characters.replacenbspaces or function(head)
+ return head
+ end
+ return replace_all_nbsp(head)
+end
+local processcharacters=nil
+if context then
+ local fontprocesses=fonts.hashes.processes
+ function processcharacters(head,font)
+ local processors=fontprocesses[font]
+ for i=1,#processors do
+ head=processors[i](head,font,0)
+ end
+ return head
+ end
+else
+ function processcharacters(head,font)
+ local processors=fontdata[font].shared.processes
+ for i=1,#processors do
+ head=processors[i](head,font,0)
+ end
+ return head
+ end
+end
+local indicgroups=characters and characters.indicgroups
+if not indicgroups and characters then
+ local indic={
+ c={},
+ i={},
+ d={},
+ m={},
+ s={},
+ o={},
+ }
+ local indicmarks={
+ l={},
+ t={},
+ b={},
+ r={},
+ s={},
+ }
+ local indicclasses={
+ nukta={},
+ halant={},
+ ra={},
+ anudatta={},
+ }
+ local indicorders={
+ bp={},
+ ap={},
+ bs={},
+ as={},
+ bh={},
+ ah={},
+ bm={},
+ am={},
+ }
+ for k,v in next,characters.data do
+ local i=v.indic
+ if i then
+ indic[i][k]=true
+ i=v.indicmark
+ if i then
+ if i=="s" then
+ local s=v.specials
+ indicmarks[i][k]={ s[2],s[3] }
+ else
+ indicmarks[i][k]=true
+ end
+ end
+ i=v.indicclass
+ if i then
+ indicclasses[i][k]=true
+ end
+ i=v.indicorder
+ if i then
+ indicorders[i][k]=true
+ end
+ end
+ end
+ indicgroups={
+ consonant=indic.c,
+ independent_vowel=indic.i,
+ dependent_vowel=indic.d,
+ vowel_modifier=indic.m,
+ stress_tone_mark=indic.s,
+ pre_mark=indicmarks.l,
+ above_mark=indicmarks.t,
+ below_mark=indicmarks.b,
+ post_mark=indicmarks.r,
+ twopart_mark=indicmarks.s,
+ nukta=indicclasses.nukta,
+ halant=indicclasses.halant,
+ ra=indicclasses.ra,
+ anudatta=indicclasses.anudatta,
+ before_postscript=indicorders.bp,
+ after_postscript=indicorders.ap,
+ before_half=indicorders.bh,
+ after_half=indicorders.ah,
+ before_subscript=indicorders.bs,
+ after_subscript=indicorders.as,
+ before_main=indicorders.bm,
+ after_main=indicorders.am,
+ }
+ indic=nil
+ indicmarks=nil
+ indicclasses=nil
+ indicorders=nil
+ characters.indicgroups=indicgroups
+end
+local consonant=indicgroups.consonant
+local independent_vowel=indicgroups.independent_vowel
+local dependent_vowel=indicgroups.dependent_vowel
+local vowel_modifier=indicgroups.vowel_modifier
+local stress_tone_mark=indicgroups.stress_tone_mark
+local pre_mark=indicgroups.pre_mark
+local above_mark=indicgroups.above_mark
+local below_mark=indicgroups.below_mark
+local post_mark=indicgroups.post_mark
+local twopart_mark=indicgroups.twopart_mark
+local nukta=indicgroups.nukta
+local halant=indicgroups.halant
+local ra=indicgroups.ra
+local anudatta=indicgroups.anudatta
+local before_postscript=indicgroups.before_postscript
+local after_postscript=indicgroups.after_postscript
+local before_half=indicgroups.before_half
+local after_half=indicgroups.after_half
+local before_subscript=indicgroups.before_subscript
+local after_subscript=indicgroups.after_subscript
+local before_main=indicgroups.before_main
+local after_main=indicgroups.after_main
+local mark_four=table.merged (
+ pre_mark,
+ above_mark,
+ below_mark,
+ post_mark
+)
+local mark_above_below_post=table.merged (
+ above_mark,
+ below_mark,
+ post_mark
+)
+local zw_char={
+ [c_zwnj]=true,
+ [c_zwj ]=true,
+}
+local dflt_true={
+ dflt=true,
+}
+local two_defaults={}
+local one_defaults={}
+local false_flags={ false,false,false,false }
+local sequence_reorder_matras={
+ features={ dv01=two_defaults },
+ flags=false_flags,
+ name="dv01_reorder_matras",
+ order={ "dv01" },
+ type="devanagari_reorder_matras",
+ nofsteps=1,
+ steps={
+ {
+ coverage=pre_mark,
+ }
+ }
+}
+local sequence_reorder_reph={
+ features={ dv02=two_defaults },
+ flags=false_flags,
+ name="dv02_reorder_reph",
+ order={ "dv02" },
+ type="devanagari_reorder_reph",
+ nofsteps=1,
+ steps={
+ {
+ coverage={},
+ }
+ }
+}
+local sequence_reorder_pre_base_reordering_consonants={
+ features={ dv03=one_defaults },
+ flags=false_flags,
+ name="dv03_reorder_pre_base_reordering_consonants",
+ order={ "dv03" },
+ type="devanagari_reorder_pre_base_reordering_consonants",
+ nofsteps=1,
+ steps={
+ {
+ coverage={},
+ }
+ }
+}
+local sequence_remove_joiners={
+ features={ dv04=one_defaults },
+ flags=false_flags,
+ name="dv04_remove_joiners",
+ order={ "dv04" },
+ type="devanagari_remove_joiners",
+ nofsteps=1,
+ steps={
+ {
+ coverage=zw_char,
+ },
+ }
+}
+local basic_shaping_forms={
+ akhn=true,
+ blwf=true,
+ cjct=true,
+ half=true,
+ nukt=true,
+ pref=true,
+ pstf=true,
+ rkrf=true,
+ rphf=true,
+ vatu=true,
+ locl=true,
+}
+local valid={
+ abvs=true,
+ akhn=true,
+ blwf=true,
+ calt=true,
+ cjct=true,
+ half=true,
+ haln=true,
+ nukt=true,
+ pref=true,
+ pres=true,
+ pstf=true,
+ psts=true,
+ rkrf=true,
+ rphf=true,
+ vatu=true,
+ pres=true,
+ abvs=true,
+ blws=true,
+ psts=true,
+ haln=true,
+ calt=true,
+ locl=true,
+}
+local scripts={}
+local scripts_one={ "deva","mlym","beng","gujr","guru","knda","orya","taml","telu" }
+local scripts_two={ "dev2","mlm2","bng2","gjr2","gur2","knd2","ory2","tml2","tel2" }
+local nofscripts=#scripts_one
+for i=1,nofscripts do
+ local one=scripts_one[i]
+ local two=scripts_two[i]
+ scripts[one]=true
+ scripts[two]=true
+ two_defaults[two]=dflt_true
+ one_defaults[one]=dflt_true
+ one_defaults[two]=dflt_true
+end
+local function valid_one(s) for i=1,nofscripts do if s[scripts_one[i]] then return true end end end
+local function valid_two(s) for i=1,nofscripts do if s[scripts_two[i]] then return true end end end
+local function initializedevanagi(tfmdata)
+ local script,language=otf.scriptandlanguage(tfmdata,attr)
+ if scripts[script] then
+ local resources=tfmdata.resources
+ local devanagari=resources.devanagari
+ if not devanagari then
+ report("adding devanagari features to font")
+ local gsubfeatures=resources.features.gsub
+ local sequences=resources.sequences
+ local sharedfeatures=tfmdata.shared.features
+ gsubfeatures["dv01"]=two_defaults
+ gsubfeatures["dv02"]=two_defaults
+ gsubfeatures["dv03"]=one_defaults
+ gsubfeatures["dv04"]=one_defaults
+ local reorder_pre_base_reordering_consonants=copy(sequence_reorder_pre_base_reordering_consonants)
+ local reorder_reph=copy(sequence_reorder_reph)
+ local reorder_matras=copy(sequence_reorder_matras)
+ local remove_joiners=copy(sequence_remove_joiners)
+ local lastmatch=0
+ for s=1,#sequences do
+ local features=sequences[s].features
+ if features then
+ for k,v in next,features do
+ if k=="locl" then
+ local steps=sequences[s].steps
+ local nofsteps=sequences[s].nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,pre_mark do
+ local locl=coverage[k]
+ if locl then
+ if #locl>0 then
+ for j=1,#locl do
+ local ck=locl[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ locl=coverage[k]
+ end
+ end
+ end
+ end
+ end
+ end
+ if locl then
+ reorder_matras.steps[1].coverage[locl]=true
+ end
+ end
+ end
+ end
+ end
+ end
+ if basic_shaping_forms[k] then
+ lastmatch=lastmatch+1
+ if s~=lastmatch then
+ table.insert(sequences,lastmatch,table.remove(sequences,s))
+ end
+ end
+ end
+ end
+ end
+ local insertindex=lastmatch+1
+ if tfmdata.properties.language then
+ dflt_true[tfmdata.properties.language]=true
+ end
+ insert(sequences,insertindex,reorder_pre_base_reordering_consonants)
+ insert(sequences,insertindex,reorder_reph)
+ insert(sequences,insertindex,reorder_matras)
+ insert(sequences,insertindex,remove_joiners)
+ local blwfcache={}
+ local vatucache={}
+ local pstfcache={}
+ local seqsubset={}
+ local rephstep={
+ coverage={}
+ }
+ local devanagari={
+ reph=false,
+ vattu=false,
+ blwfcache=blwfcache,
+ vatucache=vatucache,
+ pstfcache=pstfcache,
+ seqsubset=seqsubset,
+ reorderreph=rephstep,
+ }
+ reorder_reph.steps={ rephstep }
+ local pre_base_reordering_consonants={}
+ reorder_pre_base_reordering_consonants.steps[1].coverage=pre_base_reordering_consonants
+ resources.devanagari=devanagari
+ for s=1,#sequences do
+ local sequence=sequences[s]
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ local features=sequence.features
+ local has_rphf=features.rphf
+ local has_blwf=features.blwf
+ local has_vatu=features.vatu
+ local has_pstf=features.pstf
+ if has_rphf and has_rphf[script] then
+ devanagari.reph=true
+ elseif (has_blwf and has_blwf[script] ) or (has_vatu and has_vatu[script] ) then
+ devanagari.vattu=true
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,coverage do
+ for h,w in next,halant do
+ if v[h] then
+ if not blwfcache[k] then
+ blwfcache[k]=v
+ end
+ end
+ if has_vatu and has_vatu[script] and not vatucache[k] then
+ vatucache[k]=v
+ end
+ end
+ end
+ end
+ end
+ elseif has_pstf and has_pstf[script] then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,coverage do
+ if not pstfcache[k] then
+ pstfcache[k]=v
+ end
+ end
+ for k,v in next,ra do
+ local r=coverage[k]
+ if r then
+ local found=false
+ if #r>0 then
+ for j=1,#r do
+ local ck=r[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups and chainlookups[f] then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local h=coverage[k]
+ if h then
+ for k,v in next,h do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k,v in next,r do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ for kind,spec in next,features do
+ if valid[kind] and valid_two(spec)then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local reph,rephbase=false,false
+ if kind=="rphf" then
+ for k,v in next,ra do
+ local r=coverage[k]
+ if r then
+ rephbase=k
+ local h=false
+ if #r>0 then
+ for j=1,#r do
+ local ck=r[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local r=coverage[k]
+ if r then
+ for k,v in next,halant do
+ local h=r[k]
+ if h then
+ reph=h.ligature or false
+ break
+ end
+ end
+ if h then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k,v in next,halant do
+ local h=r[k]
+ if h then
+ reph=h.ligature or false
+ break
+ end
+ end
+ end
+ if reph then
+ break
+ end
+ end
+ end
+ end
+ seqsubset[#seqsubset+1]={ kind,coverage,reph,rephbase }
+ end
+ end
+ end
+ if kind=="pref" then
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,halant do
+ local h=coverage[k]
+ if h then
+ local found=false
+ if #h>0 then
+ for j=1,#h do
+ local ck=h[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local h=coverage[k]
+ if h then
+ for k,v in next,h do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k,v in next,h do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if two_defaults[script] then
+ sharedfeatures["dv01"]=true
+ sharedfeatures["dv02"]=true
+ sharedfeatures["dv03"]=true
+ sharedfeatures["dv04"]=true
+ elseif one_defaults[script] then
+ sharedfeatures["dv03"]=true
+ sharedfeatures["dv04"]=true
+ end
+ if script=="mlym" or script=="taml" then
+ devanagari.left_matra_before_base=true
+ end
+ end
+ end
+end
+registerotffeature {
+ name="devanagari",
+ description="inject additional features",
+ default=true,
+ initializers={
+ node=initializedevanagi,
+ },
+}
+local show_syntax_errors=false
+local function inject_syntax_error(head,current,char)
+ local signal=copy_node(current)
+ copyinjection(signal,current)
+ if pre_mark[char] then
+ setchar(signal,dotted_circle)
+ else
+ setchar(current,dotted_circle)
+ end
+ return insert_node_after(head,current,signal)
+end
+local function initialize_one(font,attr)
+ local tfmdata=fontdata[font]
+ local datasets=otf.dataset(tfmdata,font,attr)
+ local devanagaridata=datasets.devanagari
+ if not devanagaridata then
+ devanagaridata={
+ reph=false,
+ vattu=false,
+ blwfcache={},
+ vatucache={},
+ pstfcache={},
+ }
+ datasets.devanagari=devanagaridata
+ local resources=tfmdata.resources
+ local devanagari=resources.devanagari
+ for s=1,#datasets do
+ local dataset=datasets[s]
+ if dataset and dataset[1] then
+ local kind=dataset[4]
+ if kind=="rphf" then
+ devanagaridata.reph=true
+ elseif kind=="blwf" or kind=="vatu" then
+ devanagaridata.vattu=true
+ devanagaridata.blwfcache=devanagari.blwfcache
+ devanagaridata.vatucache=devanagari.vatucache
+ devanagaridata.pstfcache=devanagari.pstfcache
+ end
+ end
+ end
+ end
+ return devanagaridata.reph,devanagaridata.vattu,devanagaridata.blwfcache,devanagaridata.vatucache,devanagaridata.pstfcache
+end
+local function contextchain(contexts,n)
+ local char=getchar(n)
+ for k=1,#contexts do
+ local ck=contexts[k]
+ local seq=ck[3]
+ local f=ck[4]
+ local l=ck[5]
+ if (l-f)==1 and seq[f+1][char] then
+ local ok=true
+ local c=n
+ for i=l+1,#seq do
+ c=getnext(c)
+ if not c or not seq[i][ischar(c)] then
+ ok=false
+ break
+ end
+ end
+ if ok then
+ c=getprev(n)
+ for i=1,f-1 do
+ c=getprev(c)
+ if not c or not seq[f-i][ischar(c)] then
+ ok=false
+ end
+ end
+ end
+ if ok then
+ return true
+ end
+ end
+ end
+ return false
+end
+local function order_matras(c)
+ local cn=getnext(c)
+ local char=getchar(cn)
+ while dependent_vowel[char] do
+ local next=getnext(cn)
+ local cc=c
+ local cchar=getchar(cc)
+ while cc~=cn do
+ if (above_mark[char] and (below_mark[cchar] or post_mark[cchar])) or (below_mark[char] and (post_mark[cchar])) then
+ local prev,next=getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ setnext(getprev(cc),cn)
+ setprev(cn,getprev(cc))
+ setnext(cn,cc)
+ setprev(cc,cn)
+ break
+ end
+ cc=getnext(cc)
+ cchar=getchar(cc)
+ end
+ cn=next
+ char=getchar(cn)
+ end
+end
+local function reorder_one(head,start,stop,font,attr,nbspaces)
+ local reph,vattu,blwfcache,vatucache,pstfcache=initialize_one(font,attr)
+ local devanagari=fontdata[font].resources.devanagari
+ local current=start
+ local n=getnext(start)
+ local base=nil
+ local firstcons=nil
+ local lastcons=nil
+ local basefound=false
+ if reph and ra[getchar(start)] and halant[getchar(n)] then
+ if n==stop then
+ return head,stop,nbspaces
+ end
+ if getchar(getnext(n))==c_zwj then
+ current=start
+ else
+ current=getnext(n)
+ setprop(start,a_state,s_rphf)
+ end
+ end
+ if getchar(current)==c_nbsp then
+ if current==stop then
+ stop=getprev(stop)
+ head=remove_node(head,current)
+ flush_node(current)
+ return head,stop,nbspaces
+ else
+ nbspaces=nbspaces+1
+ base=current
+ firstcons=current
+ lastcons=current
+ current=getnext(current)
+ if current~=stop then
+ local char=getchar(current)
+ if nukta[char] then
+ current=getnext(current)
+ char=getchar(current)
+ end
+ if char==c_zwj and current~=stop then
+ local next=getnext(current)
+ if next~=stop and halant[getchar(next)] then
+ current=next
+ next=getnext(current)
+ local tmp=next and getnext(next) or nil
+ local changestop=next==stop
+ local tempcurrent=copy_node(next)
+ copyinjection(tempcurrent,next)
+ local nextcurrent=copy_node(current)
+ copyinjection(nextcurrent,current)
+ setlink(tempcurrent,nextcurrent)
+ setprop(tempcurrent,a_state,s_blwf)
+ tempcurrent=processcharacters(tempcurrent,font)
+ setprop(tempcurrent,a_state,unsetvalue)
+ if getchar(next)==getchar(tempcurrent) then
+ flush_list(tempcurrent)
+ if show_syntax_errors then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ else
+ setchar(current,getchar(tempcurrent))
+ local freenode=getnext(current)
+ setlink(current,tmp)
+ flush_node(freenode)
+ flush_list(tempcurrent)
+ if changestop then
+ stop=current
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ while not basefound do
+ local char=getchar(current)
+ if consonant[char] then
+ setprop(current,a_state,s_half)
+ if not firstcons then
+ firstcons=current
+ end
+ lastcons=current
+ if not base then
+ base=current
+ elseif blwfcache[char] then
+ setprop(current,a_state,s_blwf)
+ elseif pstfcache[char] then
+ setprop(current,a_state,s_pstf)
+ else
+ base=current
+ end
+ end
+ basefound=current==stop
+ current=getnext(current)
+ end
+ if base~=lastcons then
+ local np=base
+ local n=getnext(base)
+ local ch=getchar(n)
+ if nukta[ch] then
+ np=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if halant[ch] then
+ if lastcons~=stop then
+ local ln=getnext(lastcons)
+ if nukta[getchar(ln)] then
+ lastcons=ln
+ end
+ end
+ local nn=getnext(n)
+ local ln=getnext(lastcons)
+ setlink(np,nn)
+ setnext(lastcons,n)
+ if ln then
+ setprev(ln,n)
+ end
+ setnext(n,ln)
+ setprev(n,lastcons)
+ if lastcons==stop then
+ stop=n
+ end
+ end
+ end
+ n=getnext(start)
+ if n~=stop and ra[getchar(start)] and halant[getchar(n)] and not zw_char[getchar(getnext(n))] then
+ local matra=base
+ if base~=stop then
+ local next=getnext(base)
+ if dependent_vowel[getchar(next)] then
+ matra=next
+ end
+ end
+ local sp=getprev(start)
+ local nn=getnext(n)
+ local mn=getnext(matra)
+ setlink(sp,nn)
+ setlink(matra,start)
+ setlink(n,mn)
+ if head==start then
+ head=nn
+ end
+ start=nn
+ if matra==stop then
+ stop=n
+ end
+ end
+ local current=start
+ while current~=stop do
+ local next=getnext(current)
+ if next~=stop and halant[getchar(next)] and getchar(getnext(next))==c_zwnj then
+ setprop(current,a_state,unsetvalue)
+ end
+ current=next
+ end
+ if base~=stop and getprop(base,a_state) then
+ local next=getnext(base)
+ if halant[getchar(next)] and not (next~=stop and getchar(getnext(next))==c_zwj) then
+ setprop(base,a_state,unsetvalue)
+ end
+ end
+ local current,allreordered,moved=start,false,{ [base]=true }
+ local a,b,p,bn=base,base,base,getnext(base)
+ if base~=stop and nukta[getchar(bn)] then
+ a,b,p=bn,bn,bn
+ end
+ while not allreordered do
+ local c=current
+ local n=getnext(current)
+ local l=nil
+ if c~=stop then
+ local ch=getchar(n)
+ if nukta[ch] then
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if c~=stop then
+ if halant[ch] then
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ local tpm=twopart_mark[ch]
+ while tpm do
+ local extra=copy_node(n)
+ copyinjection(extra,n)
+ ch=tpm[1]
+ setchar(n,ch)
+ setchar(extra,tpm[2])
+ head=insert_node_after(head,current,extra)
+ tpm=twopart_mark[ch]
+ end
+ while c~=stop and dependent_vowel[ch] do
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if c~=stop then
+ if vowel_modifier[ch] then
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if c~=stop and stress_tone_mark[ch] then
+ c=n
+ n=getnext(n)
+ end
+ end
+ end
+ end
+ local bp=getprev(firstcons)
+ local cn=getnext(current)
+ local last=getnext(c)
+ while cn~=last do
+ if pre_mark[getchar(cn)] then
+ if devanagari.left_matra_before_base then
+ local prev,next=getboth(cn)
+ setlink(prev,next)
+ if cn==stop then
+ stop=getprev(cn)
+ end
+ if base==start then
+ if head==start then
+ head=cn
+ end
+ start=cn
+ end
+ setlink(getprev(base),cn)
+ setlink(cn,base)
+ cn=next
+ else
+ if bp then
+ setnext(bp,cn)
+ end
+ local prev,next=getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ if cn==stop then
+ stop=prev
+ end
+ setprev(cn,bp)
+ setlink(cn,firstcons)
+ if firstcons==start then
+ if head==start then
+ head=cn
+ end
+ start=cn
+ end
+ cn=next
+ end
+ elseif current~=base and dependent_vowel[getchar(cn)] then
+ local prev,next=getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ if cn==stop then
+ stop=prev
+ end
+ setlink(b,cn,getnext(b))
+ order_matras(cn)
+ cn=next
+ elseif current==base and dependent_vowel[getchar(cn)] then
+ local cnn=getnext(cn)
+ order_matras(cn)
+ cn=cnn
+ while cn~=last and dependent_vowel[getchar(cn)] do
+ cn=getnext(cn)
+ end
+ else
+ cn=getnext(cn)
+ end
+ end
+ allreordered=c==stop
+ current=getnext(c)
+ end
+ if reph or vattu then
+ local current,cns=start,nil
+ while current~=stop do
+ local c=current
+ local n=getnext(current)
+ if ra[getchar(current)] and halant[getchar(n)] then
+ c=n
+ n=getnext(n)
+ local b,bn=base,base
+ while bn~=stop do
+ local next=getnext(bn)
+ if dependent_vowel[getchar(next)] then
+ b=next
+ end
+ bn=next
+ end
+ if getprop(current,a_state)==s_rphf then
+ if b~=current then
+ if current==start then
+ if head==start then
+ head=n
+ end
+ start=n
+ end
+ if b==stop then
+ stop=c
+ end
+ local prev=getprev(current)
+ setlink(prev,n)
+ local next=getnext(b)
+ setlink(c,next)
+ setlink(b,current)
+ end
+ elseif cns and getnext(cns)~=current then
+ local cp=getprev(current)
+ local cnsn=getnext(cns)
+ setlink(cp,n)
+ setlink(cns,current)
+ setlink(c,cnsn)
+ if c==stop then
+ stop=cp
+ break
+ end
+ current=getprev(n)
+ end
+ else
+ local char=getchar(current)
+ if consonant[char] then
+ cns=current
+ local next=getnext(cns)
+ if halant[getchar(next)] then
+ cns=next
+ end
+ if not vatucache[char] then
+ next=getnext(cns)
+ while dependent_vowel[getchar(next)] do
+ cns=next
+ next=getnext(cns)
+ end
+ end
+ elseif char==c_nbsp then
+ nbspaces=nbspaces+1
+ cns=current
+ local next=getnext(cns)
+ if halant[getchar(next)] then
+ cns=next
+ end
+ if not vatucache[char] then
+ next=getnext(cns)
+ while dependent_vowel[getchar(next)] do
+ cns=next
+ next=getnext(cns)
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ if getchar(base)==c_nbsp then
+ nbspaces=nbspaces-1
+ if base==stop then
+ stop=getprev(stop)
+ end
+ head=remove_node(head,base)
+ flush_node(base)
+ end
+ return head,stop,nbspaces
+end
+function handlers.devanagari_reorder_matras(head,start)
+ local current=start
+ local startfont=getfont(start)
+ local startattr=getprop(start,a_syllabe)
+ while current do
+ local char=ischar(current,startfont)
+ local next=getnext(current)
+ if char and getprop(current,a_syllabe)==startattr then
+ if halant[char] then
+ if next then
+ local char=ischar(next,startfont)
+ if char and zw_char[char] and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ end
+ end
+ local startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ start=startnext
+ break
+ end
+ else
+ break
+ end
+ current=next
+ end
+ return head,start,true
+end
+local rephbase={}
+function handlers.devanagari_reorder_reph(head,start)
+ local current=getnext(start)
+ local startnext=nil
+ local startprev=nil
+ local startfont=getfont(start)
+ local startattr=getprop(start,a_syllabe)
+ ::step_1::
+ local char=ischar(start,startfont)
+ local rephbase=rephbase[startfont][char]
+ if char and after_subscript[rephbase] then
+ goto step_5
+ end
+ ::step_2::
+ if char and not after_postscript[rephbase] then
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ if halant[char] then
+ local next=getnext(current)
+ if next then
+ local nextchar=ischar(next,startfont)
+ if nextchar and zw_char[nextchar] and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ end
+ end
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ break
+ end
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ end
+ ::step_3::
+ if not startnext then
+ if char and after_main[rephbase] then
+ current=getnext(start)
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ if consonant[char] and not getprop(current,a_state)==s_pref then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(current,start)
+ setlink(start,getnext(current))
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ break
+ end
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ end
+ end
+ ::step_4::
+ if not startnext then
+ if char and before_postscript[rephbase] then
+ current=getnext(start)
+ local c=nil
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ if getprop(current,a_state)==s_pstf then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(getprev(current),start)
+ setlink(start,current)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ break
+ elseif not c and (vowel_modifier[char] or stress_tone_mark[char] ) then
+ c=current
+ end
+ current=getnext(current)
+ else
+ if c then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(getprev(c),start)
+ setlink(start,c)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ end
+ break
+ end
+ end
+ end
+ end
+ ::step_5::
+ if not startnext then
+ current=getnext(start)
+ local c=nil
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ local state=getprop(current,a_state)
+ if before_subscript[rephbase] and (state==s_blwf or state==s_pstf) then
+ c=current
+ elseif after_subscript[rephbase] and (state==s_pstf) then
+ c=current
+ end
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ if c then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(getprev(c),start)
+ setlink(start,c)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ end
+ end
+ ::step_6::
+ if not startnext then
+ current=start
+ local next=getnext(current)
+ while next do
+ local nextchar=ischar(next,startfont)
+ if nextchar and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ else
+ break
+ end
+ end
+ if start~=current then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,getnext(current))
+ setlink(current,start)
+ start=startnext
+ end
+ end
+ return head,start,true
+end
+local reordered_pre_base_reordering_consonants={}
+function handlers.devanagari_reorder_pre_base_reordering_consonants(head,start)
+ if reordered_pre_base_reordering_consonants[start] then
+ return head,start,true
+ end
+ local current=start
+ local startfont=getfont(start)
+ local startattr=getprop(start,a_syllabe)
+ while current do
+ local char=ischar(current,startfont)
+ local next=getnext(current)
+ if char and getprop(current,a_syllabe)==startattr then
+ if halant[char] then
+ if next then
+ local char=ischar(next,startfont)
+ if char and zw_char[char] and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ end
+ end
+ local startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ reordered_pre_base_reordering_consonants[start]=true
+ start=startnext
+ return head,start,true
+ end
+ else
+ break
+ end
+ current=next
+ end
+ local startattr=getprop(start,a_syllabe)
+ local current=getprev(start)
+ while current and getprop(current,a_syllabe)==startattr do
+ local char=ischar(current)
+ if (not dependent_vowel[char] and not getprop(current,a_state) or getprop(current,a_state)==s_init) then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ if current==head then
+ setlink(start,current)
+ head=start
+ else
+ setlink(getprev(current),start)
+ setlink(start,current)
+ end
+ reordered_pre_base_reordering_consonants[start]=true
+ start=startnext
+ break
+ end
+ current=getprev(current)
+ end
+ return head,start,true
+end
+function handlers.devanagari_remove_joiners(head,start,kind,lookupname,replacement)
+ local stop=getnext(start)
+ local font=getfont(start)
+ local last=start
+ while stop do
+ local char=ischar(stop,font)
+ if char and (char==c_zwnj or char==c_zwj) then
+ last=stop
+ stop=getnext(stop)
+ else
+ break
+ end
+ end
+ local prev=getprev(start)
+ if stop then
+ setnext(last)
+ setlink(prev,stop)
+ elseif prev then
+ setnext(prev)
+ end
+ if head==start then
+ head=stop
+ end
+ flush_list(start)
+ return head,stop,true
+end
+local function initialize_two(font,attr)
+ local devanagari=fontdata[font].resources.devanagari
+ if devanagari then
+ return devanagari.seqsubset or {},devanagari.reorderreph or {}
+ else
+ return {},{}
+ end
+end
+local function reorder_two(head,start,stop,font,attr,nbspaces)
+ local seqsubset,reorderreph=initialize_two(font,attr)
+ local halfpos=nil
+ local basepos=nil
+ local subpos=nil
+ local postpos=nil
+ reorderreph.coverage={}
+ rephbase[font]={}
+ for i=1,#seqsubset do
+ local subset=seqsubset[i]
+ local kind=subset[1]
+ local lookupcache=subset[2]
+ if kind=="rphf" then
+ reorderreph.coverage[subset[3]]=true
+ rephbase[font][subset[3]]=subset[4]
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ local afternext=next~=stop and getnext(next)
+ if afternext and zw_char[getchar(afternext)] then
+ current=afternext
+ elseif current==start then
+ setprop(current,a_state,s_rphf)
+ current=next
+ else
+ current=next
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="pref" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then
+ setprop(current,a_state,s_pref)
+ setprop(next,a_state,s_pref)
+ current=next
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="half" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if next~=stop and getchar(getnext(next))==c_zwnj then
+ current=next
+ elseif (not getprop(current,a_state)) then
+ setprop(current,a_state,s_half)
+ if not halfpos then
+ halfpos=current
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="blwf" or kind=="vatu" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then
+ setprop(current,a_state,s_blwf)
+ setprop(next,a_state,s_blwf)
+ current=next
+ subpos=current
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="pstf" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then
+ setprop(current,a_state,s_pstf)
+ setprop(next,a_state,s_pstf)
+ current=next
+ postpos=current
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ end
+ local current,base,firstcons=start,nil,nil
+ if getprop(start,a_state)==s_rphf then
+ current=getnext(getnext(start))
+ end
+ if current~=getnext(stop) and getchar(current)==c_nbsp then
+ if current==stop then
+ stop=getprev(stop)
+ head=remove_node(head,current)
+ flush_node(current)
+ return head,stop,nbspaces
+ else
+ nbspaces=nbspaces+1
+ base=current
+ current=getnext(current)
+ if current~=stop then
+ local char=getchar(current)
+ if nukta[char] then
+ current=getnext(current)
+ char=getchar(current)
+ end
+ if char==c_zwj then
+ local next=getnext(current)
+ if current~=stop and next~=stop and halant[getchar(next)] then
+ current=next
+ next=getnext(current)
+ local tmp=getnext(next)
+ local changestop=next==stop
+ setnext(next)
+ setprop(current,a_state,s_pref)
+ current=processcharacters(current,font)
+ setprop(current,a_state,s_blwf)
+ current=processcharacters(current,font)
+ setprop(current,a_state,s_pstf)
+ current=processcharacters(current,font)
+ setprop(current,a_state,unsetvalue)
+ if halant[getchar(current)] then
+ setnext(getnext(current),tmp)
+ if show_syntax_errors then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ else
+ setnext(current,tmp)
+ if changestop then
+ stop=current
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ local last=getnext(stop)
+ while current~=last do
+ local next=getnext(current)
+ if consonant[getchar(current)] then
+ if not (current~=stop and next~=stop and halant[getchar(next)] and getchar(getnext(next))==c_zwj) then
+ if not firstcons then
+ firstcons=current
+ end
+ local a=getprop(current,a_state)
+ if not (a==s_blwf or a==s_pstf or (a~=s_rphf and a~=s_blwf and ra[getchar(current)])) then
+ base=current
+ end
+ end
+ end
+ current=next
+ end
+ if not base then
+ base=firstcons
+ end
+ end
+ if not base then
+ if getprop(start,a_state)==s_rphf then
+ setprop(start,a_state,unsetvalue)
+ end
+ return head,stop,nbspaces
+ else
+ if getprop(base,a_state) then
+ setprop(base,a_state,unsetvalue)
+ end
+ basepos=base
+ end
+ if not halfpos then
+ halfpos=base
+ end
+ if not subpos then
+ subpos=base
+ end
+ if not postpos then
+ postpos=subpos or base
+ end
+ local moved={}
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ local char=getchar(current)
+ local target=nil
+ local cn=getnext(current)
+ local tpm=twopart_mark[char]
+ while tpm do
+ local extra=copy_node(current)
+ copyinjection(extra,current)
+ char=tpm[1]
+ setchar(current,char)
+ setchar(extra,tpm[2])
+ head=insert_node_after(head,current,extra)
+ tpm=twopart_mark[char]
+ end
+ if not moved[current] and dependent_vowel[char] then
+ if pre_mark[char] then
+ moved[current]=true
+ local prev,next=getboth(current)
+ setlink(prev,next)
+ if current==stop then
+ stop=getprev(current)
+ end
+ local pos
+ if before_main[char] then
+ pos=basepos
+ else
+ pos=halfpos
+ end
+ local ppos=getprev(pos)
+ while ppos and getprop(ppos,a_syllabe)==getprop(pos,a_syllabe) do
+ if getprop(ppos,a_state)==s_pref then
+ pos=ppos
+ end
+ ppos=getprev(ppos)
+ end
+ local ppos=getprev(pos)
+ while ppos and getprop(ppos,a_syllabe)==getprop(pos,a_syllabe) and halant[ischar(ppos)] do
+ ppos=getprev(ppos)
+ if ppos and getprop(ppos,a_syllabe)==getprop(pos,a_syllabe) and consonant[ischar(ppos)] then
+ pos=ppos
+ ppos=getprev(ppos)
+ else
+ break
+ end
+ end
+ if pos==start then
+ if head==start then
+ head=current
+ end
+ start=current
+ end
+ setlink(getprev(pos),current)
+ setlink(current,pos)
+ elseif above_mark[char] then
+ target=basepos
+ if subpos==basepos then
+ subpos=current
+ end
+ if postpos==basepos then
+ postpos=current
+ end
+ basepos=current
+ elseif below_mark[char] then
+ target=subpos
+ if postpos==subpos then
+ postpos=current
+ end
+ subpos=current
+ elseif post_mark[char] then
+ local n=getnext(postpos)
+ while n do
+ local v=ischar(n,font)
+ if nukta[v] or stress_tone_mark[v] or vowel_modifier[v] then
+ postpos=n
+ else
+ break
+ end
+ n=getnext(n)
+ end
+ target=postpos
+ postpos=current
+ end
+ if mark_above_below_post[char] then
+ local prev=getprev(current)
+ if prev~=target then
+ local next=getnext(current)
+ setlink(prev,next)
+ if current==stop then
+ stop=prev
+ end
+ setlink(current,getnext(target))
+ setlink(target,current)
+ end
+ end
+ end
+ current=cn
+ end
+ local current=getnext(start)
+ local last=getnext(stop)
+ while current~=last do
+ local char=getchar(current)
+ local cn=getnext(current)
+ if halant[char] and ra[ischar(cn)] and getprop(cn,a_state)~=s_rphf and getprop(cn,a_state)~=s_blwf then
+ if after_main[ischar(cn)] then
+ local prev=getprev(current)
+ local next=getnext(cn)
+ local bpn=getnext(basepos)
+ while bpn and dependent_vowel[ischar(bpn)] do
+ basepos=bpn
+ bpn=getnext(bpn)
+ end
+ if basepos~=prev then
+ setlink(prev,next)
+ setlink(cn,getnext(basepos))
+ setlink(basepos,current)
+ if cn==stop then
+ stop=prev
+ end
+ cn=next
+ end
+ end
+ end
+ current=cn
+ end
+ local current=start
+ local c=nil
+ while current~=stop do
+ local char=getchar(current)
+ if halant[char] or stress_tone_mark[char] then
+ if not c then
+ c=current
+ end
+ else
+ c=nil
+ end
+ local next=getnext(current)
+ if c and nukta[getchar(next)] then
+ if head==c then
+ head=next
+ end
+ if stop==next then
+ stop=current
+ end
+ setlink(getprev(c),next)
+ local nextnext=getnext(next)
+ setnext(current,nextnext)
+ local nextnextnext=getnext(nextnext)
+ if nextnextnext then
+ setprev(nextnextnext,current)
+ end
+ setlink(nextnext,c)
+ end
+ if stop==current then break end
+ current=getnext(current)
+ end
+ if getchar(base)==c_nbsp then
+ if base==stop then
+ stop=getprev(stop)
+ end
+ nbspaces=nbspaces-1
+ head=remove_node(head,base)
+ flush_node(base)
+ end
+ return head,stop,nbspaces
+end
+local separator={}
+imerge(separator,consonant)
+imerge(separator,independent_vowel)
+imerge(separator,dependent_vowel)
+imerge(separator,vowel_modifier)
+imerge(separator,stress_tone_mark)
+for k,v in next,nukta do separator[k]=true end
+for k,v in next,halant do separator[k]=true end
+local function analyze_next_chars_one(c,font,variant)
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ if variant==1 then
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ n=getnext(n)
+ if n then
+ v=ischar(n,font)
+ end
+ end
+ if n and v then
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv then
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv then
+ if vv==c_zwj and consonant[vvv] then
+ c=nnn
+ elseif (vv==c_zwnj or vv==c_zwj) and halant[vvv] then
+ local nnnn=getnext(nnn)
+ if nnnn then
+ local vvvv=ischar(nnnn,font)
+ if vvvv and consonant[vvvv] then
+ c=nnnn
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ elseif variant==2 then
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ c=n
+ end
+ n=getnext(c)
+ if n then
+ v=ischar(n,font)
+ if v then
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv and zw_char[v] then
+ n=nn
+ v=vv
+ nn=getnext(nn)
+ vv=nn and ischar(nn,font)
+ end
+ if vv and halant[v] and consonant[vv] then
+ c=nn
+ end
+ end
+ end
+ end
+ end
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ local v=ischar(n,font)
+ if not v then
+ return c
+ end
+ local already_pre_mark
+ local already_above_mark
+ local already_below_mark
+ local already_post_mark
+ while dependent_vowel[v] do
+ local vowels=twopart_mark[v] or { v }
+ for k,v in next,vowels do
+ if pre_mark[v] and not already_pre_mark then
+ already_pre_mark=true
+ elseif above_mark[v] and not already_above_mark then
+ already_above_mark=true
+ elseif below_mark[v] and not already_below_mark then
+ already_below_mark=true
+ elseif post_mark[v] and not already_post_mark then
+ already_post_mark=true
+ else
+ return c
+ end
+ end
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if nukta[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if vowel_modifier[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ return n
+ else
+ return c
+ end
+end
+local function analyze_next_chars_two(c,font)
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ c=n
+ end
+ n=c
+ while true do
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv then
+ if halant[vv] then
+ n=nn
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv and zw_char[vvv] then
+ n=nnn
+ end
+ end
+ elseif vv==c_zwnj or vv==c_zwj then
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv and halant[vvv] then
+ n=nnn
+ end
+ end
+ else
+ break
+ end
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv and consonant[vv] then
+ n=nn
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv and nukta[vvv] then
+ n=nnn
+ end
+ end
+ c=n
+ else
+ break
+ end
+ else
+ break
+ end
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if not c then
+ return
+ end
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ local v=ischar(n,font)
+ if not v then
+ return c
+ end
+ if anudatta[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ if v==c_zwnj or v==c_zwj then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ else
+ local already_pre_mark
+ local already_above_mark
+ local already_below_mark
+ local already_post_mark
+ while dependent_vowel[v] do
+ local vowels=twopart_mark[v] or { v }
+ for k,v in next,vowels do
+ if pre_mark[v] and not already_pre_mark then
+ already_pre_mark=true
+ elseif above_mark[v] and not already_above_mark then
+ already_above_mark=true
+ elseif below_mark[v] and not already_below_mark then
+ already_below_mark=true
+ elseif post_mark[v] and not already_post_mark then
+ already_post_mark=true
+ else
+ return c
+ end
+ end
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if nukta[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ end
+ if vowel_modifier[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ return n
+ else
+ return c
+ end
+end
+local function method_one(head,font,attr)
+ local current=head
+ local start=true
+ local done=false
+ local nbspaces=0
+ local syllabe=0
+ while current do
+ local char=ischar(current,font)
+ if char then
+ done=true
+ local syllablestart=current
+ local syllableend=nil
+ local c=current
+ local n=getnext(c)
+ local first=char
+ if n and ra[first] then
+ local second=ischar(n,font)
+ if second and halant[second] then
+ local n=getnext(n)
+ if n then
+ local third=ischar(n,font)
+ if third then
+ c=n
+ first=third
+ end
+ end
+ end
+ end
+ local standalone=first==c_nbsp
+ if standalone then
+ local prev=getprev(current)
+ if prev then
+ local prevchar=ischar(prev,font)
+ if not prevchar then
+ elseif not separator[prevchar] then
+ else
+ standalone=false
+ end
+ else
+ end
+ end
+ if standalone then
+ local syllableend=analyze_next_chars_one(c,font,2)
+ current=getnext(syllableend)
+ if syllablestart~=syllableend then
+ head,current,nbspaces=reorder_one(head,syllablestart,syllableend,font,attr,nbspaces)
+ current=getnext(current)
+ end
+ else
+ if consonant[char] then
+ local prevc=true
+ while prevc do
+ prevc=false
+ local n=getnext(current)
+ if not n then
+ break
+ end
+ local v=ischar(n,font)
+ if not v then
+ break
+ end
+ if nukta[v] then
+ n=getnext(n)
+ if not n then
+ break
+ end
+ v=ischar(n,font)
+ if not v then
+ break
+ end
+ end
+ if halant[v] then
+ n=getnext(n)
+ if not n then
+ break
+ end
+ v=ischar(n,font)
+ if not v then
+ break
+ end
+ if v==c_zwnj or v==c_zwj then
+ n=getnext(n)
+ if not n then
+ break
+ end
+ v=ischar(n,font)
+ if not v then
+ break
+ end
+ end
+ if consonant[v] then
+ prevc=true
+ current=n
+ end
+ end
+ end
+ local n=getnext(current)
+ if n then
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ current=n
+ n=getnext(current)
+ end
+ end
+ syllableend=current
+ current=n
+ if current then
+ local v=ischar(current,font)
+ if not v then
+ elseif halant[v] then
+ local n=getnext(current)
+ if n then
+ local v=ischar(n,font)
+ if v and zw_char[v] then
+ syllableend=n
+ current=getnext(n)
+ else
+ syllableend=current
+ current=n
+ end
+ else
+ syllableend=current
+ current=n
+ end
+ else
+ if dependent_vowel[v] then
+ syllableend=current
+ current=getnext(current)
+ v=ischar(current,font)
+ end
+ if v and vowel_modifier[v] then
+ syllableend=current
+ current=getnext(current)
+ v=ischar(current,font)
+ end
+ if v and stress_tone_mark[v] then
+ syllableend=current
+ current=getnext(current)
+ end
+ end
+ end
+ if syllablestart~=syllableend then
+ if syllableend then
+ syllabe=syllabe+1
+ local c=syllablestart
+ local n=getnext(syllableend)
+ while c~=n do
+ setprop(c,a_syllabe,syllabe)
+ c=getnext(c)
+ end
+ end
+ head,current,nbspaces=reorder_one(head,syllablestart,syllableend,font,attr,nbspaces)
+ current=getnext(current)
+ end
+ elseif independent_vowel[char] then
+ syllableend=current
+ current=getnext(current)
+ if current then
+ local v=ischar(current,font)
+ if v then
+ if vowel_modifier[v] then
+ syllableend=current
+ current=getnext(current)
+ v=ischar(current,font)
+ end
+ if v and stress_tone_mark[v] then
+ syllableend=current
+ current=getnext(current)
+ end
+ end
+ end
+ else
+ if show_syntax_errors then
+ local mark=mark_four[char]
+ if mark then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ else
+ current=getnext(current)
+ end
+ start=false
+ end
+ if nbspaces>0 then
+ head=replace_all_nbsp(head)
+ end
+ current=head
+ local n=0
+ while current do
+ local char=ischar(current,font)
+ if char then
+ if n==0 and not getprop(current,a_state) then
+ setprop(current,a_state,s_init)
+ end
+ n=n+1
+ else
+ n=0
+ end
+ current=getnext(current)
+ end
+ return head,done
+end
+local function method_two(head,font,attr)
+ local current=head
+ local start=true
+ local done=false
+ local syllabe=0
+ local nbspaces=0
+ while current do
+ local syllablestart=nil
+ local syllableend=nil
+ local char=ischar(current,font)
+ if char then
+ done=true
+ syllablestart=current
+ local c=current
+ local n=getnext(current)
+ if n and ra[char] then
+ local nextchar=ischar(n,font)
+ if nextchar and halant[nextchar] then
+ local n=getnext(n)
+ if n then
+ local nextnextchar=ischar(n,font)
+ if nextnextchar then
+ c=n
+ char=nextnextchar
+ end
+ end
+ end
+ end
+ if independent_vowel[char] then
+ current=analyze_next_chars_one(c,font,1)
+ syllableend=current
+ else
+ local standalone=char==c_nbsp
+ if standalone then
+ nbspaces=nbspaces+1
+ local p=getprev(current)
+ if not p then
+ elseif ischar(p,font) then
+ elseif not separator[getchar(p)] then
+ else
+ standalone=false
+ end
+ end
+ if standalone then
+ current=analyze_next_chars_one(c,font,2)
+ syllableend=current
+ elseif consonant[getchar(current)] then
+ current=analyze_next_chars_two(current,font)
+ syllableend=current
+ end
+ end
+ end
+ if syllableend then
+ syllabe=syllabe+1
+ local c=syllablestart
+ local n=getnext(syllableend)
+ while c~=n do
+ setprop(c,a_syllabe,syllabe)
+ c=getnext(c)
+ end
+ end
+ if syllableend and syllablestart~=syllableend then
+ head,current,nbspaces=reorder_two(head,syllablestart,syllableend,font,attr,nbspaces)
+ end
+ if not syllableend and show_syntax_errors then
+ local char=ischar(current,font)
+ if char and not getprop(current,a_state) then
+ local mark=mark_four[char]
+ if mark then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ end
+ end
+ start=false
+ current=getnext(current)
+ end
+ if nbspaces>0 then
+ head=replace_all_nbsp(head)
+ end
+ current=head
+ local n=0
+ while current do
+ local char=ischar(current,font)
+ if char then
+ if n==0 and not getprop(current,a_state) then
+ setprop(current,a_state,s_init)
+ end
+ n=n+1
+ else
+ n=0
+ end
+ current=getnext(current)
+ end
+ return head,done
+end
+for i=1,nofscripts do
+ methods[scripts_one[i]]=method_one
+ methods[scripts_two[i]]=method_two
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-osd”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ocl” b720867fb19a23f0b50377efd2a3c54a] ---
+
+if not modules then modules={} end modules ['font-ocl']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local tostring,tonumber,next=tostring,tonumber,next
+local round,max=math.round,math.round
+local sortedkeys,sortedhash=table.sortedkeys,table.sortedhash
+local setmetatableindex=table.setmetatableindex
+local formatters=string.formatters
+local tounicode=fonts.mappings.tounicode
+local helpers=fonts.helpers
+local charcommand=helpers.commands.char
+local rightcommand=helpers.commands.right
+local leftcommand=helpers.commands.left
+local downcommand=helpers.commands.down
+local otf=fonts.handlers.otf
+local f_color=formatters["%.3f %.3f %.3f rg"]
+local f_gray=formatters["%.3f g"]
+if context then
+ local startactualtext=nil
+ local stopactualtext=nil
+ function otf.getactualtext(s)
+ if not startactualtext then
+ startactualtext=backends.codeinjections.startunicodetoactualtextdirect
+ stopactualtext=backends.codeinjections.stopunicodetoactualtextdirect
+ end
+ return startactualtext(s),stopactualtext()
+ end
+else
+ local tounicode=fonts.mappings.tounicode16
+ function otf.getactualtext(s)
+ return
+ "/Span << /ActualText <feff"..s.."> >> BDC",
+ "EMC"
+ end
+end
+local sharedpalettes={}
+local hash=setmetatableindex(function(t,k)
+ local v={ "pdf","direct",k }
+ t[k]=v
+ return v
+end)
+if context then
+ local colors=attributes.list[attributes.private('color')] or {}
+ local transparencies=attributes.list[attributes.private('transparency')] or {}
+ function otf.registerpalette(name,values)
+ sharedpalettes[name]=values
+ local color=lpdf.color
+ local transparency=lpdf.transparency
+ local register=colors.register
+ for i=1,#values do
+ local v=values[i]
+ if v=="textcolor" then
+ values[i]=false
+ else
+ local c=nil
+ local t=nil
+ if type(v)=="table" then
+ c=register(name,"rgb",
+ max(round((v.r or 0)*255),255)/255,
+ max(round((v.g or 0)*255),255)/255,
+ max(round((v.b or 0)*255),255)/255
+ )
+ else
+ c=colors[v]
+ t=transparencies[v]
+ end
+ if c and t then
+ values[i]=hash[color(1,c).." "..transparency(t)]
+ elseif c then
+ values[i]=hash[color(1,c)]
+ elseif t then
+ values[i]=hash[color(1,t)]
+ end
+ end
+ end
+ end
+else
+ function otf.registerpalette(name,values)
+ sharedpalettes[name]=values
+ for i=1,#values do
+ local v=values[i]
+ if v then
+ values[i]=hash[f_color(
+ max(round((v.r or 0)*255),255)/255,
+ max(round((v.g or 0)*255),255)/255,
+ max(round((v.b or 0)*255),255)/255
+ )]
+ end
+ end
+ end
+end
+local function convert(t,k)
+ local v={}
+ for i=1,#k do
+ local p=k[i]
+ local r,g,b=p[1],p[2],p[3]
+ if r==g and g==b then
+ v[i]=hash[f_gray(r/255)]
+ else
+ v[i]=hash[f_color(r/255,g/255,b/255)]
+ end
+ end
+ t[k]=v
+ return v
+end
+local start={ "pdf","mode","font" }
+local push={ "pdf","page","q" }
+local pop={ "pdf","page","Q" }
+local function initialize(tfmdata,kind,value)
+ if value then
+ local resources=tfmdata.resources
+ local palettes=resources.colorpalettes
+ if palettes then
+ local converted=resources.converted
+ if not converted then
+ converted=setmetatableindex(convert)
+ resources.converted=converted
+ end
+ local colorvalues=sharedpalettes[value]
+ local default=false
+ if colorvalues then
+ default=colorvalues[#colorvalues]
+ else
+ colorvalues=converted[palettes[tonumber(value) or 1] or palettes[1]] or {}
+ end
+ local classes=#colorvalues
+ if classes==0 then
+ return
+ end
+ local characters=tfmdata.characters
+ local descriptions=tfmdata.descriptions
+ local properties=tfmdata.properties
+ properties.virtualized=true
+ tfmdata.fonts={
+ { id=0 }
+ }
+ local getactualtext=otf.getactualtext
+ local b,e=getactualtext(tounicode(0xFFFD))
+ local actualb={ "pdf","page",b }
+ local actuale={ "pdf","page",e }
+ for unicode,character in next,characters do
+ local description=descriptions[unicode]
+ if description then
+ local colorlist=description.colors
+ if colorlist then
+ local u=description.unicode or characters[unicode].unicode
+ local w=character.width or 0
+ local s=#colorlist
+ local goback=w~=0 and leftcommand[w] or nil
+ local t={
+ start,
+ not u and actualb or { "pdf","page",(getactualtext(tounicode(u))) }
+ }
+ local n=2
+ local l=nil
+ local f=false
+ for i=1,s do
+ local entry=colorlist[i]
+ local v=colorvalues[entry.class] or default
+ if v and l~=v then
+ if f then
+ n=n+1 t[n]=pop
+ end
+ n=n+1 t[n]=push
+ f=true
+ n=n+1 t[n]=v
+ l=v
+ else
+ if f then
+ n=n+1 t[n]=pop
+ end
+ f=false
+ l=nil
+ end
+ n=n+1 t[n]=charcommand[entry.slot]
+ if s>1 and i<s and goback then
+ n=n+1 t[n]=goback
+ end
+ end
+ if f then
+ n=n+1 t[n]=pop
+ end
+ n=n+1 t[n]=actuale
+ character.commands=t
+ end
+ end
+ end
+ end
+ end
+end
+fonts.handlers.otf.features.register {
+ name="colr",
+ description="color glyphs",
+ manipulators={
+ base=initialize,
+ node=initialize,
+ }
+}
+do
+ local nofstreams=0
+ local f_name=formatters[ [[pdf-glyph-%05i]] ]
+ local f_used=context and formatters[ [[original:///%s]] ] or formatters[ [[%s]] ]
+ local hashed={}
+ local cache={}
+ local openpdf=pdfe.new
+ function otf.storepdfdata(pdf)
+ local done=hashed[pdf]
+ if not done then
+ nofstreams=nofstreams+1
+ local f=f_name(nofstreams)
+ local n=openpdf(pdf,#pdf,f)
+ done=f_used(n)
+ hashed[pdf]=done
+ end
+ return done
+ end
+end
+local function pdftovirtual(tfmdata,pdfshapes,kind)
+ if not tfmdata or not pdfshapes or not kind then
+ return
+ end
+ local characters=tfmdata.characters
+ local properties=tfmdata.properties
+ local parameters=tfmdata.parameters
+ local hfactor=parameters.hfactor
+ properties.virtualized=true
+ tfmdata.fonts={
+ { id=0 }
+ }
+ local getactualtext=otf.getactualtext
+ local storepdfdata=otf.storepdfdata
+ local b,e=getactualtext(tounicode(0xFFFD))
+ local actualb={ "pdf","page",b }
+ local actuale={ "pdf","page",e }
+ local vfimage=lpdf and lpdf.vfimage or function(wd,ht,dp,data,name)
+ local name=storepdfdata(data)
+ return { "image",{ filename=name,width=wd,height=ht,depth=dp } }
+ end
+ for unicode,character in sortedhash(characters) do
+ local index=character.index
+ if index then
+ local pdf=pdfshapes[index]
+ local typ=type(pdf)
+ local data=nil
+ local dx=nil
+ local dy=nil
+ if typ=="table" then
+ data=pdf.data
+ dx=pdf.dx or 0
+ dy=pdf.dy or 0
+ elseif typ=="string" then
+ data=pdf
+ dx=0
+ dy=0
+ end
+ if data then
+ local bt=unicode and getactualtext(unicode)
+ local wd=character.width or 0
+ local ht=character.height or 0
+ local dp=character.depth or 0
+ character.commands={
+ not unicode and actualb or { "pdf","page",(getactualtext(unicode)) },
+ downcommand[dp+dy*hfactor],
+ rightcommand[dx*hfactor],
+ vfimage(wd,ht,dp,data,name),
+ actuale,
+ }
+ character[kind]=true
+ end
+ end
+ end
+end
+local otfsvg=otf.svg or {}
+otf.svg=otfsvg
+otf.svgenabled=true
+do
+ local report_svg=logs.reporter("fonts","svg conversion")
+ local loaddata=io.loaddata
+ local savedata=io.savedata
+ local remove=os.remove
+ if context and xml.convert then
+ local xmlconvert=xml.convert
+ local xmlfirst=xml.first
+ function otfsvg.filterglyph(entry,index)
+ local svg=xmlconvert(entry.data)
+ local root=svg and xmlfirst(svg,"/svg[@id='glyph"..index.."']")
+ local data=root and tostring(root)
+ return data
+ end
+ else
+ function otfsvg.filterglyph(entry,index)
+ return entry.data
+ end
+ end
+ local runner=sandbox and sandbox.registerrunner {
+ name="otfsvg",
+ program="inkscape",
+ method="pipeto",
+ template="--shell > temp-otf-svg-shape.log",
+ reporter=report_svg,
+ }
+ if not runner then
+ runner=function()
+ return io.open("inkscape --shell > temp-otf-svg-shape.log","w")
+ end
+ end
+ function otfsvg.topdf(svgshapes)
+ local pdfshapes={}
+ local inkscape=runner()
+ if inkscape then
+ local nofshapes=#svgshapes
+ local f_svgfile=formatters["temp-otf-svg-shape-%i.svg"]
+ local f_pdffile=formatters["temp-otf-svg-shape-%i.pdf"]
+ local f_convert=formatters["%s --export-pdf=%s\n"]
+ local filterglyph=otfsvg.filterglyph
+ local nofdone=0
+ report_svg("processing %i svg containers",nofshapes)
+ statistics.starttiming()
+ for i=1,nofshapes do
+ local entry=svgshapes[i]
+ for index=entry.first,entry.last do
+ local data=filterglyph(entry,index)
+ if data and data~="" then
+ local svgfile=f_svgfile(index)
+ local pdffile=f_pdffile(index)
+ savedata(svgfile,data)
+ inkscape:write(f_convert(svgfile,pdffile))
+ pdfshapes[index]=true
+ nofdone=nofdone+1
+ if nofdone%100==0 then
+ report_svg("%i shapes processed",nofdone)
+ end
+ end
+ end
+ end
+ inkscape:write("quit\n")
+ inkscape:close()
+ report_svg("processing %i pdf results",nofshapes)
+ for index in next,pdfshapes do
+ local svgfile=f_svgfile(index)
+ local pdffile=f_pdffile(index)
+ pdfshapes[index]=loaddata(pdffile)
+ remove(svgfile)
+ remove(pdffile)
+ end
+ statistics.stoptiming()
+ if statistics.elapsedseconds then
+ report_svg("svg conversion time %s",statistics.elapsedseconds() or "-")
+ end
+ end
+ return pdfshapes
+ end
+end
+local function initializesvg(tfmdata,kind,value)
+ if value and otf.svgenabled then
+ local svg=tfmdata.properties.svg
+ local hash=svg and svg.hash
+ local timestamp=svg and svg.timestamp
+ if not hash then
+ return
+ end
+ local pdffile=containers.read(otf.pdfcache,hash)
+ local pdfshapes=pdffile and pdffile.pdfshapes
+ if not pdfshapes or pdffile.timestamp~=timestamp then
+ local svgfile=containers.read(otf.svgcache,hash)
+ local svgshapes=svgfile and svgfile.svgshapes
+ pdfshapes=svgshapes and otfsvg.topdf(svgshapes) or {}
+ containers.write(otf.pdfcache,hash,{
+ pdfshapes=pdfshapes,
+ timestamp=timestamp,
+ })
+ end
+ pdftovirtual(tfmdata,pdfshapes,"svg")
+ end
+end
+fonts.handlers.otf.features.register {
+ name="svg",
+ description="svg glyphs",
+ manipulators={
+ base=initializesvg,
+ node=initializesvg,
+ }
+}
+local otfpng=otf.png or {}
+otf.png=otfpng
+otf.pngenabled=true
+do
+ local report_png=logs.reporter("fonts","png conversion")
+ local loaddata=io.loaddata
+ local savedata=io.savedata
+ local remove=os.remove
+ local runner=sandbox and sandbox.registerrunner {
+ name="otfpng",
+ program="gm",
+ template="convert -quality 100 temp-otf-png-shape.png temp-otf-png-shape.pdf > temp-otf-svg-shape.log",
+ }
+ if not runner then
+ runner=function()
+ return os.execute("gm convert -quality 100 temp-otf-png-shape.png temp-otf-png-shape.pdf > temp-otf-svg-shape.log")
+ end
+ end
+ function otfpng.topdf(pngshapes)
+ local pdfshapes={}
+ local pngfile="temp-otf-png-shape.png"
+ local pdffile="temp-otf-png-shape.pdf"
+ local nofdone=0
+ local indices=sortedkeys(pngshapes)
+ local nofindices=#indices
+ report_png("processing %i png containers",nofindices)
+ statistics.starttiming()
+ for i=1,nofindices do
+ local index=indices[i]
+ local entry=pngshapes[index]
+ local data=entry.data
+ local x=entry.x
+ local y=entry.y
+ savedata(pngfile,data)
+ runner()
+ pdfshapes[index]={
+ x=x~=0 and x or nil,
+ y=y~=0 and y or nil,
+ data=loaddata(pdffile),
+ }
+ nofdone=nofdone+1
+ if nofdone%100==0 then
+ report_png("%i shapes processed",nofdone)
+ end
+ end
+ report_png("processing %i pdf results",nofindices)
+ remove(pngfile)
+ remove(pdffile)
+ statistics.stoptiming()
+ if statistics.elapsedseconds then
+ report_png("png conversion time %s",statistics.elapsedseconds() or "-")
+ end
+ return pdfshapes
+ end
+end
+local function initializepng(tfmdata,kind,value)
+ if value and otf.pngenabled then
+ local png=tfmdata.properties.png
+ local hash=png and png.hash
+ local timestamp=png and png.timestamp
+ if not hash then
+ return
+ end
+ local pdffile=containers.read(otf.pdfcache,hash)
+ local pdfshapes=pdffile and pdffile.pdfshapes
+ if not pdfshapes or pdffile.timestamp~=timestamp then
+ local pngfile=containers.read(otf.pngcache,hash)
+ local pngshapes=pngfile and pngfile.pngshapes
+ pdfshapes=pngshapes and otfpng.topdf(pngshapes) or {}
+ containers.write(otf.pdfcache,hash,{
+ pdfshapes=pdfshapes,
+ timestamp=timestamp,
+ })
+ end
+ pdftovirtual(tfmdata,pdfshapes,"png")
+ end
+end
+fonts.handlers.otf.features.register {
+ name="sbix",
+ description="sbix glyphs",
+ manipulators={
+ base=initializepng,
+ node=initializepng,
+ }
+}
+fonts.handlers.otf.features.register {
+ name="cblc",
+ description="cblc glyphs",
+ manipulators={
+ base=initializepng,
+ node=initializepng,
+ }
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-ocl”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otc” 95a4ff28ba4afb55a978a4aecfd688bf] ---
+
+if not modules then modules={} end modules ['font-otc']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local insert,sortedkeys,sortedhash,tohash=table.insert,table.sortedkeys,table.sortedhash,table.tohash
+local type,next,tonumber=type,next,tonumber
+local lpegmatch=lpeg.match
+local utfbyte,utflen=utf.byte,utf.len
+local sortedhash=table.sortedhash
+local trace_loading=false trackers.register("otf.loading",function(v) trace_loading=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local fonts=fonts
+local otf=fonts.handlers.otf
+local registerotffeature=otf.features.register
+local setmetatableindex=table.setmetatableindex
+local checkmerge=fonts.helpers.checkmerge
+local checkflags=fonts.helpers.checkflags
+local checksteps=fonts.helpers.checksteps
+local normalized={
+ substitution="substitution",
+ single="substitution",
+ ligature="ligature",
+ alternate="alternate",
+ multiple="multiple",
+ kern="kern",
+ pair="pair",
+ single="single",
+ chainsubstitution="chainsubstitution",
+ chainposition="chainposition",
+}
+local types={
+ substitution="gsub_single",
+ ligature="gsub_ligature",
+ alternate="gsub_alternate",
+ multiple="gsub_multiple",
+ kern="gpos_pair",
+ pair="gpos_pair",
+ single="gpos_single",
+ chainsubstitution="gsub_contextchain",
+ chainposition="gpos_contextchain",
+}
+local names={
+ gsub_single="gsub",
+ gsub_multiple="gsub",
+ gsub_alternate="gsub",
+ gsub_ligature="gsub",
+ gsub_context="gsub",
+ gsub_contextchain="gsub",
+ gsub_reversecontextchain="gsub",
+ gpos_single="gpos",
+ gpos_pair="gpos",
+ gpos_cursive="gpos",
+ gpos_mark2base="gpos",
+ gpos_mark2ligature="gpos",
+ gpos_mark2mark="gpos",
+ gpos_context="gpos",
+ gpos_contextchain="gpos",
+}
+setmetatableindex(types,function(t,k) t[k]=k return k end)
+local everywhere={ ["*"]={ ["*"]=true } }
+local noflags={ false,false,false,false }
+local function getrange(sequences,category)
+ local count=#sequences
+ local first=nil
+ local last=nil
+ for i=1,count do
+ local t=sequences[i].type
+ if t and names[t]==category then
+ if not first then
+ first=i
+ end
+ last=i
+ end
+ end
+ return first or 1,last or count
+end
+local function validspecification(specification,name)
+ local dataset=specification.dataset
+ if dataset then
+ elseif specification[1] then
+ dataset=specification
+ specification={ dataset=dataset }
+ else
+ dataset={ { data=specification.data } }
+ specification.data=nil
+ specification.dataset=dataset
+ end
+ local first=dataset[1]
+ if first then
+ first=first.data
+ end
+ if not first then
+ report_otf("invalid feature specification, no dataset")
+ return
+ end
+ if type(name)~="string" then
+ name=specification.name or first.name
+ end
+ if type(name)~="string" then
+ report_otf("invalid feature specification, no name")
+ return
+ end
+ local n=#dataset
+ if n>0 then
+ for i=1,n do
+ setmetatableindex(dataset[i],specification)
+ end
+ return specification,name
+ end
+end
+local function addfeature(data,feature,specifications)
+ if not specifications then
+ report_otf("missing specification")
+ return
+ end
+ local descriptions=data.descriptions
+ local resources=data.resources
+ local features=resources.features
+ local sequences=resources.sequences
+ if not features or not sequences then
+ report_otf("missing specification")
+ return
+ end
+ local alreadydone=resources.alreadydone
+ if not alreadydone then
+ alreadydone={}
+ resources.alreadydone=alreadydone
+ end
+ if alreadydone[specifications] then
+ return
+ else
+ alreadydone[specifications]=true
+ end
+ local fontfeatures=resources.features or everywhere
+ local unicodes=resources.unicodes
+ local splitter=lpeg.splitter(" ",unicodes)
+ local done=0
+ local skip=0
+ local aglunicodes=false
+ local specifications=validspecification(specifications,feature)
+ if not specifications then
+ return
+ end
+ local p=lpeg.P("P")*(lpeg.patterns.hexdigit^1/function(s) return tonumber(s,16) end)*lpeg.P(-1)
+ local function tounicode(code)
+ if not code then
+ return
+ end
+ if type(code)=="number" then
+ return code
+ end
+ local u=unicodes[code]
+ if u then
+ return u
+ end
+ if utflen(code)==1 then
+ u=utfbyte(code)
+ if u then
+ return u
+ end
+ end
+ local u=lpegmatch(p,code)
+ if u then
+ return u
+ end
+ if not aglunicodes then
+ aglunicodes=fonts.encodings.agl.unicodes
+ end
+ local u=aglunicodes[code]
+ if u then
+ return u
+ end
+ end
+ local coverup=otf.coverup
+ local coveractions=coverup.actions
+ local stepkey=coverup.stepkey
+ local register=coverup.register
+ local function prepare_substitution(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ else
+ if type(replacement)=="table" then
+ replacement=replacement[1]
+ end
+ replacement=tounicode(replacement)
+ if replacement and descriptions[replacement] then
+ cover(coverage,unicode,replacement)
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function prepare_alternate(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ elseif type(replacement)=="table" then
+ local r={}
+ for i=1,#replacement do
+ local u=tounicode(replacement[i])
+ r[i]=(nocheck or descriptions[u]) and u or unicode
+ end
+ cover(coverage,unicode,r)
+ done=done+1
+ else
+ local u=tounicode(replacement)
+ if u then
+ cover(coverage,unicode,{ u })
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function prepare_multiple(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ elseif type(replacement)=="table" then
+ local r={}
+ local n=0
+ for i=1,#replacement do
+ local u=tounicode(replacement[i])
+ if nocheck or descriptions[u] then
+ n=n+1
+ r[n]=u
+ end
+ end
+ if n>0 then
+ cover(coverage,unicode,r)
+ done=done+1
+ else
+ skip=skip+1
+ end
+ else
+ local u=tounicode(replacement)
+ if u then
+ cover(coverage,unicode,{ u })
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function prepare_ligature(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,ligature in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ else
+ if type(ligature)=="string" then
+ ligature={ lpegmatch(splitter,ligature) }
+ end
+ local present=true
+ for i=1,#ligature do
+ local l=ligature[i]
+ local u=tounicode(l)
+ if nocheck or descriptions[u] then
+ ligature[i]=u
+ else
+ present=false
+ break
+ end
+ end
+ if present then
+ cover(coverage,unicode,ligature)
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function resetspacekerns()
+ data.properties.hasspacekerns=true
+ data.resources .spacekerns=nil
+ end
+ local function prepare_kern(list,featuretype)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ local isspace=false
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if description and type(replacement)=="table" then
+ local r={}
+ for k,v in next,replacement do
+ local u=tounicode(k)
+ if u then
+ r[u]=v
+ if u==32 then
+ isspace=true
+ end
+ end
+ end
+ if next(r) then
+ cover(coverage,unicode,r)
+ done=done+1
+ if unicode==32 then
+ isspace=true
+ end
+ else
+ skip=skip+1
+ end
+ else
+ skip=skip+1
+ end
+ end
+ if isspace then
+ resetspacekerns()
+ end
+ return coverage
+ end
+ local function prepare_pair(list,featuretype)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ if cover then
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if description and type(replacement)=="table" then
+ local r={}
+ for k,v in next,replacement do
+ local u=tounicode(k)
+ if u then
+ r[u]=v
+ if u==32 then
+ isspace=true
+ end
+ end
+ end
+ if next(r) then
+ cover(coverage,unicode,r)
+ done=done+1
+ if unicode==32 then
+ isspace=true
+ end
+ else
+ skip=skip+1
+ end
+ else
+ skip=skip+1
+ end
+ end
+ if isspace then
+ resetspacekerns()
+ end
+ else
+ report_otf("unknown cover type %a",featuretype)
+ end
+ return coverage
+ end
+ local prepare_single=prepare_pair
+ local function prepare_chain(list,featuretype,sublookups)
+ local rules=list.rules
+ local coverage={}
+ if rules then
+ local rulehash={}
+ local rulesize=0
+ local lookuptype=types[featuretype]
+ for nofrules=1,#rules do
+ local rule=rules[nofrules]
+ local current=rule.current
+ local before=rule.before
+ local after=rule.after
+ local replacements=rule.replacements or false
+ local sequence={}
+ local nofsequences=0
+ if before then
+ for n=1,#before do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=before[n]
+ end
+ end
+ local start=nofsequences+1
+ for n=1,#current do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=current[n]
+ end
+ local stop=nofsequences
+ if after then
+ for n=1,#after do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=after[n]
+ end
+ end
+ local lookups=rule.lookups or false
+ local subtype=nil
+ if lookups and sublookups then
+ for k,v in sortedhash(lookups) do
+ local t=type(v)
+ if t=="table" then
+ for i=1,#v do
+ local vi=v[i]
+ if type(vi)~="table" then
+ v[i]={ vi }
+ end
+ end
+ elseif t=="number" then
+ local lookup=sublookups[v]
+ if lookup then
+ lookups[k]={ lookup }
+ if not subtype then
+ subtype=lookup.type
+ end
+ elseif v==0 then
+ lookups[k]={ { type="gsub_remove" } }
+ else
+ lookups[k]=false
+ end
+ else
+ lookups[k]=false
+ end
+ end
+ end
+ if nofsequences>0 then
+ local hashed={}
+ for i=1,nofsequences do
+ local t={}
+ local s=sequence[i]
+ for i=1,#s do
+ local u=tounicode(s[i])
+ if u then
+ t[u]=true
+ end
+ end
+ hashed[i]=t
+ end
+ sequence=hashed
+ rulesize=rulesize+1
+ rulehash[rulesize]={
+ nofrules,
+ lookuptype,
+ sequence,
+ start,
+ stop,
+ lookups,
+ replacements,
+ subtype,
+ }
+ for unic in sortedhash(sequence[start]) do
+ local cu=coverage[unic]
+ if not cu then
+ coverage[unic]=rulehash
+ end
+ end
+ sequence.n=nofsequences
+ end
+ end
+ rulehash.n=rulesize
+ end
+ return coverage
+ end
+ local dataset=specifications.dataset
+ local function report(name,category,position,first,last,sequences)
+ report_otf("injecting name %a of category %a at position %i in [%i,%i] of [%i,%i]",
+ name,category,position,first,last,1,#sequences)
+ end
+ local function inject(specification,sequences,sequence,first,last,category,name)
+ local position=specification.position or false
+ if not position then
+ position=specification.prepend
+ if position==true then
+ if trace_loading then
+ report(name,category,first,first,last,sequences)
+ end
+ insert(sequences,first,sequence)
+ return
+ end
+ end
+ if not position then
+ position=specification.append
+ if position==true then
+ if trace_loading then
+ report(name,category,last+1,first,last,sequences)
+ end
+ insert(sequences,last+1,sequence)
+ return
+ end
+ end
+ local kind=type(position)
+ if kind=="string" then
+ local index=false
+ for i=first,last do
+ local s=sequences[i]
+ local f=s.features
+ if f then
+ for k in sortedhash(f) do
+ if k==position then
+ index=i
+ break
+ end
+ end
+ if index then
+ break
+ end
+ end
+ end
+ if index then
+ position=index
+ else
+ position=last+1
+ end
+ elseif kind=="number" then
+ if position<0 then
+ position=last-position+1
+ end
+ if position>last then
+ position=last+1
+ elseif position<first then
+ position=first
+ end
+ else
+ position=last+1
+ end
+ if trace_loading then
+ report(name,category,position,first,last,sequences)
+ end
+ insert(sequences,position,sequence)
+ end
+ for s=1,#dataset do
+ local specification=dataset[s]
+ local valid=specification.valid
+ local feature=specification.name or feature
+ if not feature or feature=="" then
+ report_otf("no valid name given for extra feature")
+ elseif not valid or valid(data,specification,feature) then
+ local initialize=specification.initialize
+ if initialize then
+ specification.initialize=initialize(specification,data) and initialize or nil
+ end
+ local askedfeatures=specification.features or everywhere
+ local askedsteps=specification.steps or specification.subtables or { specification.data } or {}
+ local featuretype=normalized[specification.type or "substitution"] or "substitution"
+ local featureflags=specification.flags or noflags
+ local nocheck=specification.nocheck
+ local futuresteps=specification.futuresteps
+ local featureorder=specification.order or { feature }
+ local featurechain=(featuretype=="chainsubstitution" or featuretype=="chainposition") and 1 or 0
+ local nofsteps=0
+ local steps={}
+ local sublookups=specification.lookups
+ local category=nil
+ checkflags(specification,resources)
+ if sublookups then
+ local s={}
+ for i=1,#sublookups do
+ local specification=sublookups[i]
+ local askedsteps=specification.steps or specification.subtables or { specification.data } or {}
+ local featuretype=normalized[specification.type or "substitution"] or "substitution"
+ local featureflags=specification.flags or noflags
+ local nofsteps=0
+ local steps={}
+ for i=1,#askedsteps do
+ local list=askedsteps[i]
+ local coverage=nil
+ local format=nil
+ if featuretype=="substitution" then
+ coverage=prepare_substitution(list,featuretype,nocheck)
+ elseif featuretype=="ligature" then
+ coverage=prepare_ligature(list,featuretype,nocheck)
+ elseif featuretype=="alternate" then
+ coverage=prepare_alternate(list,featuretype,nocheck)
+ elseif featuretype=="multiple" then
+ coverage=prepare_multiple(list,featuretype,nocheck)
+ elseif featuretype=="kern" or featuretype=="move" then
+ format=featuretype
+ coverage=prepare_kern(list,featuretype)
+ elseif featuretype=="pair" then
+ format="pair"
+ coverage=prepare_pair(list,featuretype)
+ elseif featuretype=="single" then
+ format="single"
+ coverage=prepare_single(list,featuretype)
+ end
+ if coverage and next(coverage) then
+ nofsteps=nofsteps+1
+ steps[nofsteps]=register(coverage,featuretype,format,feature,nofsteps,descriptions,resources)
+ end
+ end
+ checkmerge(specification)
+ checksteps(specification)
+ s[i]={
+ [stepkey]=steps,
+ nofsteps=nofsteps,
+ flags=featureflags,
+ type=types[featuretype],
+ }
+ end
+ sublookups=s
+ end
+ for i=1,#askedsteps do
+ local list=askedsteps[i]
+ local coverage=nil
+ local format=nil
+ if featuretype=="substitution" then
+ category="gsub"
+ coverage=prepare_substitution(list,featuretype,nocheck)
+ elseif featuretype=="ligature" then
+ category="gsub"
+ coverage=prepare_ligature(list,featuretype,nocheck)
+ elseif featuretype=="alternate" then
+ category="gsub"
+ coverage=prepare_alternate(list,featuretype,nocheck)
+ elseif featuretype=="multiple" then
+ category="gsub"
+ coverage=prepare_multiple(list,featuretype,nocheck)
+ elseif featuretype=="kern" or featuretype=="move" then
+ category="gpos"
+ format=featuretype
+ coverage=prepare_kern(list,featuretype)
+ elseif featuretype=="pair" then
+ category="gpos"
+ format="pair"
+ coverage=prepare_pair(list,featuretype)
+ elseif featuretype=="single" then
+ category="gpos"
+ format="single"
+ coverage=prepare_single(list,featuretype)
+ elseif featuretype=="chainsubstitution" then
+ category="gsub"
+ coverage=prepare_chain(list,featuretype,sublookups)
+ elseif featuretype=="chainposition" then
+ category="gpos"
+ coverage=prepare_chain(list,featuretype,sublookups)
+ else
+ report_otf("not registering feature %a, unknown category",feature)
+ return
+ end
+ if coverage and next(coverage) then
+ nofsteps=nofsteps+1
+ steps[nofsteps]=register(coverage,featuretype,format,feature,nofsteps,descriptions,resources)
+ end
+ end
+ if nofsteps>0 then
+ for k,v in next,askedfeatures do
+ if v[1] then
+ askedfeatures[k]=tohash(v)
+ end
+ end
+ if featureflags[1] then featureflags[1]="mark" end
+ if featureflags[2] then featureflags[2]="ligature" end
+ if featureflags[3] then featureflags[3]="base" end
+ local steptype=types[featuretype]
+ local sequence={
+ chain=featurechain,
+ features={ [feature]=askedfeatures },
+ flags=featureflags,
+ name=feature,
+ order=featureorder,
+ [stepkey]=steps,
+ nofsteps=nofsteps,
+ type=steptype,
+ }
+ checkflags(sequence,resources)
+ checkmerge(sequence)
+ checksteps(sequence)
+ local first,last=getrange(sequences,category)
+ inject(specification,sequences,sequence,first,last,category,feature)
+ local features=fontfeatures[category]
+ if not features then
+ features={}
+ fontfeatures[category]=features
+ end
+ local k=features[feature]
+ if not k then
+ k={}
+ features[feature]=k
+ end
+ for script,languages in next,askedfeatures do
+ local kk=k[script]
+ if not kk then
+ kk={}
+ k[script]=kk
+ end
+ for language,value in next,languages do
+ kk[language]=value
+ end
+ end
+ end
+ end
+ end
+ if trace_loading then
+ report_otf("registering feature %a, affected glyphs %a, skipped glyphs %a",feature,done,skip)
+ end
+end
+otf.enhancers.addfeature=addfeature
+local extrafeatures={}
+local knownfeatures={}
+function otf.addfeature(name,specification)
+ if type(name)=="table" then
+ specification=name
+ end
+ if type(specification)~="table" then
+ report_otf("invalid feature specification, no valid table")
+ return
+ end
+ specification,name=validspecification(specification,name)
+ if name and specification then
+ local slot=knownfeatures[name]
+ if not slot then
+ slot=#extrafeatures+1
+ knownfeatures[name]=slot
+ elseif specification.overload==false then
+ slot=#extrafeatures+1
+ knownfeatures[name]=slot
+ else
+ end
+ specification.name=name
+ extrafeatures[slot]=specification
+ end
+end
+local function enhance(data,filename,raw)
+ for slot=1,#extrafeatures do
+ local specification=extrafeatures[slot]
+ addfeature(data,specification.name,specification)
+ end
+end
+otf.enhancers.enhance=enhance
+otf.enhancers.register("check extra features",enhance)
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-otc”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-onr” d4d2449b4084e6afb1837ae5835082cc] ---
+
+if not modules then modules={} end modules ['font-onr']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local fonts,logs,trackers,resolvers=fonts,logs,trackers,resolvers
+local next,type,tonumber,rawget,rawset=next,type,tonumber,rawget,rawset
+local match,lower,gsub,strip,find=string.match,string.lower,string.gsub,string.strip,string.find
+local char,byte,sub=string.char,string.byte,string.sub
+local abs=math.abs
+local bxor,rshift=bit32.bxor,bit32.rshift
+local P,S,R,V,Cmt,C,Ct,Cs,Carg,Cf,Cg,Cc=lpeg.P,lpeg.S,lpeg.R,lpeg.V,lpeg.Cmt,lpeg.C,lpeg.Ct,lpeg.Cs,lpeg.Carg,lpeg.Cf,lpeg.Cg,lpeg.Cc
+local lpegmatch,patterns=lpeg.match,lpeg.patterns
+local trace_indexing=false trackers.register("afm.indexing",function(v) trace_indexing=v end)
+local trace_loading=false trackers.register("afm.loading",function(v) trace_loading=v end)
+local report_afm=logs.reporter("fonts","afm loading")
+local report_pfb=logs.reporter("fonts","pfb loading")
+local handlers=fonts.handlers
+local afm=handlers.afm or {}
+handlers.afm=afm
+local readers=afm.readers or {}
+afm.readers=readers
+afm.version=1.513
+local get_indexes,get_shapes
+do
+ local decrypt
+ do
+ local r,c1,c2,n=0,0,0,0
+ local function step(c)
+ local cipher=byte(c)
+ local plain=bxor(cipher,rshift(r,8))
+ r=((cipher+r)*c1+c2)%65536
+ return char(plain)
+ end
+ decrypt=function(binary,initial,seed)
+ r,c1,c2,n=initial,52845,22719,seed
+ binary=gsub(binary,".",step)
+ return sub(binary,n+1)
+ end
+ end
+ local charstrings=P("/CharStrings")
+ local subroutines=P("/Subrs")
+ local encoding=P("/Encoding")
+ local dup=P("dup")
+ local put=P("put")
+ local array=P("array")
+ local name=P("/")*C((R("az","AZ","09")+S("-_."))^1)
+ local digits=R("09")^1
+ local cardinal=digits/tonumber
+ local spaces=P(" ")^1
+ local spacing=patterns.whitespace^0
+ local routines,vector,chars,n,m
+ local initialize=function(str,position,size)
+ n=0
+ m=size
+ return position+1
+ end
+ local setroutine=function(str,position,index,size,filename)
+ if routines[index] then
+ return false
+ end
+ local forward=position+size
+ local stream=decrypt(sub(str,position+1,forward),4330,4)
+ routines[index]={ byte(stream,1,#stream) }
+ n=n+1
+ if n>=m then
+ return #str
+ end
+ return forward+1
+ end
+ local setvector=function(str,position,name,size,filename)
+ local forward=position+tonumber(size)
+ if n>=m then
+ return #str
+ elseif forward<#str then
+ if n==0 and name~=".notdef" then
+ report_pfb("reserving .notdef at index 0 in %a",filename)
+ n=n+1
+ end
+ vector[n]=name
+ n=n+1
+ return forward
+ else
+ return #str
+ end
+ end
+ local setshapes=function(str,position,name,size,filename)
+ local forward=position+tonumber(size)
+ local stream=sub(str,position+1,forward)
+ if n>m then
+ return #str
+ elseif forward<#str then
+ if n==0 and name~=".notdef" then
+ report_pfb("reserving .notdef at index 0 in %a",filename)
+ n=n+1
+ end
+ vector[n]=name
+ n=n+1
+ chars [n]=decrypt(stream,4330,4)
+ return forward
+ else
+ return #str
+ end
+ end
+ local p_rd=spacing*(P("RD")+P("-|"))
+ local p_np=spacing*(P("NP")+P("|"))
+ local p_nd=spacing*(P("ND")+P("|"))
+ local p_filterroutines=
+ (1-subroutines)^0*subroutines*spaces*Cmt(cardinal,initialize)*(Cmt(cardinal*spaces*cardinal*p_rd*Carg(1),setroutine)*p_np+(1-p_nd))^1
+ local p_filtershapes=
+ (1-charstrings)^0*charstrings*spaces*Cmt(cardinal,initialize)*(Cmt(name*spaces*cardinal*p_rd*Carg(1),setshapes)*p_nd+P(1))^1
+ local p_filternames=Ct (
+ (1-charstrings)^0*charstrings*spaces*Cmt(cardinal,initialize)*(Cmt(name*spaces*cardinal*Carg(1),setvector)+P(1))^1
+ )
+ local p_filterencoding=(1-encoding)^0*encoding*spaces*digits*spaces*array*(1-dup)^0*Cf(
+ Ct("")*Cg(spacing*dup*spaces*cardinal*spaces*name*spaces*put)^1
+,rawset)
+ local key=spacing*P("/")*R("az","AZ")
+ local str=spacing*Cs { (P("(")/"")*((1-P("\\(")-P("\\)")-S("()"))+V(1))^0*(P(")")/"") }
+ local num=spacing*(R("09")+S("+-."))^1/tonumber
+ local arr=spacing*Ct (S("[{")*(num)^0*spacing*S("]}"))
+ local boo=spacing*(P("true")*Cc(true)+P("false")*Cc(false))
+ local nam=spacing*P("/")*Cs(R("az","AZ")^1)
+ local p_filtermetadata=(
+ P("/")*Carg(1)*((
+ C("version")*str+C("Copyright")*str+C("Notice")*str+C("FullName")*str+C("FamilyName")*str+C("Weight")*str+C("ItalicAngle")*num+C("isFixedPitch")*boo+C("UnderlinePosition")*num+C("UnderlineThickness")*num+C("FontName")*nam+C("FontMatrix")*arr+C("FontBBox")*arr
+ ) )/function(t,k,v) t[lower(k)]=v end+P(1)
+ )^0*Carg(1)
+ local function loadpfbvector(filename,shapestoo,streams)
+ local data=io.loaddata(resolvers.findfile(filename))
+ if not data then
+ report_pfb("no data in %a",filename)
+ return
+ end
+ if not (find(data,"!PS-AdobeFont-",1,true) or find(data,"%!FontType1",1,true)) then
+ report_pfb("no font in %a",filename)
+ return
+ end
+ local ascii,binary=match(data,"(.*)eexec%s+......(.*)")
+ if not binary then
+ report_pfb("no binary data in %a",filename)
+ return
+ end
+ binary=decrypt(binary,55665,4)
+ local names={}
+ local encoding=lpegmatch(p_filterencoding,ascii)
+ local metadata=lpegmatch(p_filtermetadata,ascii,1,{})
+ local glyphs={}
+ routines,vector,chars={},{},{}
+ if shapestoo or streams then
+ lpegmatch(p_filterroutines,binary,1,filename)
+ lpegmatch(p_filtershapes,binary,1,filename)
+ local data={
+ dictionaries={
+ {
+ charstrings=chars,
+ charset=vector,
+ subroutines=routines,
+ }
+ },
+ }
+ fonts.handlers.otf.readers.parsecharstrings(false,data,glyphs,true,"cff",streams,true)
+ else
+ lpegmatch(p_filternames,binary,1,filename)
+ end
+ names=vector
+ routines,vector,chars=nil,nil,nil
+ return names,encoding,glyphs,metadata
+ end
+ local pfb=handlers.pfb or {}
+ handlers.pfb=pfb
+ pfb.loadvector=loadpfbvector
+ get_indexes=function(data,pfbname)
+ local vector=loadpfbvector(pfbname)
+ if vector then
+ local characters=data.characters
+ if trace_loading then
+ report_afm("getting index data from %a",pfbname)
+ end
+ for index=0,#vector do
+ local name=vector[index]
+ local char=characters[name]
+ if char then
+ if trace_indexing then
+ report_afm("glyph %a has index %a",name,index)
+ end
+ char.index=index
+ else
+ if trace_indexing then
+ report_afm("glyph %a has index %a but no data",name,index)
+ end
+ end
+ end
+ end
+ end
+ get_shapes=function(pfbname)
+ local vector,encoding,glyphs=loadpfbvector(pfbname,true)
+ return glyphs
+ end
+end
+local spacer=patterns.spacer
+local whitespace=patterns.whitespace
+local lineend=patterns.newline
+local spacing=spacer^0
+local number=spacing*S("+-")^-1*(R("09")+S("."))^1/tonumber
+local name=spacing*C((1-whitespace)^1)
+local words=spacing*((1-lineend)^1/strip)
+local rest=(1-lineend)^0
+local fontdata=Carg(1)
+local semicolon=spacing*P(";")
+local plus=spacing*P("plus")*number
+local minus=spacing*P("minus")*number
+local function addkernpair(data,one,two,value)
+ local chr=data.characters[one]
+ if chr then
+ local kerns=chr.kerns
+ if kerns then
+ kerns[two]=tonumber(value)
+ else
+ chr.kerns={ [two]=tonumber(value) }
+ end
+ end
+end
+local p_kernpair=(fontdata*P("KPX")*name*name*number)/addkernpair
+local chr=false
+local ind=0
+local function start(data,version)
+ data.metadata.afmversion=version
+ ind=0
+ chr={}
+end
+local function stop()
+ ind=0
+ chr=false
+end
+local function setindex(i)
+ if i<0 then
+ ind=ind+1
+ else
+ ind=i
+ end
+ chr={
+ index=ind
+ }
+end
+local function setwidth(width)
+ chr.width=width
+end
+local function setname(data,name)
+ data.characters[name]=chr
+end
+local function setboundingbox(boundingbox)
+ chr.boundingbox=boundingbox
+end
+local function setligature(plus,becomes)
+ local ligatures=chr.ligatures
+ if ligatures then
+ ligatures[plus]=becomes
+ else
+ chr.ligatures={ [plus]=becomes }
+ end
+end
+local p_charmetric=((
+ P("C")*number/setindex+P("WX")*number/setwidth+P("N")*fontdata*name/setname+P("B")*Ct((number)^4)/setboundingbox+P("L")*(name)^2/setligature
+ )*semicolon )^1
+local p_charmetrics=P("StartCharMetrics")*number*(p_charmetric+(1-P("EndCharMetrics")))^0*P("EndCharMetrics")
+local p_kernpairs=P("StartKernPairs")*number*(p_kernpair+(1-P("EndKernPairs" )))^0*P("EndKernPairs" )
+local function set_1(data,key,a) data.metadata[lower(key)]=a end
+local function set_2(data,key,a,b) data.metadata[lower(key)]={ a,b } end
+local function set_3(data,key,a,b,c) data.metadata[lower(key)]={ a,b,c } end
+local p_parameters=P(false)+fontdata*((P("FontName")+P("FullName")+P("FamilyName"))/lower)*words/function(data,key,value)
+ data.metadata[key]=value
+ end+fontdata*((P("Weight")+P("Version"))/lower)*name/function(data,key,value)
+ data.metadata[key]=value
+ end+fontdata*P("IsFixedPitch")*name/function(data,pitch)
+ data.metadata.monospaced=toboolean(pitch,true)
+ end+fontdata*P("FontBBox")*Ct(number^4)/function(data,boundingbox)
+ data.metadata.boundingbox=boundingbox
+ end+fontdata*((P("CharWidth")+P("CapHeight")+P("XHeight")+P("Descender")+P("Ascender")+P("ItalicAngle"))/lower)*number/function(data,key,value)
+ data.metadata[key]=value
+ end+P("Comment")*spacing*(P(false)+(fontdata*C("DESIGNSIZE")*number*rest)/set_1
++(fontdata*C("TFM designsize")*number*rest)/set_1+(fontdata*C("DesignSize")*number*rest)/set_1+(fontdata*C("CODINGSCHEME")*words*rest)/set_1
++(fontdata*C("CHECKSUM")*number*words*rest)/set_1
++(fontdata*C("SPACE")*number*plus*minus*rest)/set_3
++(fontdata*C("QUAD")*number*rest)/set_1
++(fontdata*C("EXTRASPACE")*number*rest)/set_1
++(fontdata*C("NUM")*number*number*number*rest)/set_3
++(fontdata*C("DENOM")*number*number*rest)/set_2
++(fontdata*C("SUP")*number*number*number*rest)/set_3
++(fontdata*C("SUB")*number*number*rest)/set_2
++(fontdata*C("SUPDROP")*number*rest)/set_1
++(fontdata*C("SUBDROP")*number*rest)/set_1
++(fontdata*C("DELIM")*number*number*rest)/set_2
++(fontdata*C("AXISHEIGHT")*number*rest)/set_1
+ )
+local fullparser=(P("StartFontMetrics")*fontdata*name/start )*(p_charmetrics+p_kernpairs+p_parameters+(1-P("EndFontMetrics")) )^0*(P("EndFontMetrics")/stop )
+local infoparser=(P("StartFontMetrics")*fontdata*name/start )*(p_parameters+(1-P("EndFontMetrics")) )^0*(P("EndFontMetrics")/stop )
+local function read(filename,parser)
+ local afmblob=io.loaddata(filename)
+ if afmblob then
+ local data={
+ resources={
+ filename=resolvers.unresolve(filename),
+ version=afm.version,
+ creator="context mkiv",
+ },
+ properties={
+ hasitalics=false,
+ },
+ goodies={},
+ metadata={
+ filename=file.removesuffix(file.basename(filename))
+ },
+ characters={
+ },
+ descriptions={
+ },
+ }
+ if trace_loading then
+ report_afm("parsing afm file %a",filename)
+ end
+ lpegmatch(parser,afmblob,1,data)
+ return data
+ else
+ if trace_loading then
+ report_afm("no valid afm file %a",filename)
+ end
+ return nil
+ end
+end
+function readers.loadfont(afmname,pfbname)
+ local data=read(resolvers.findfile(afmname),fullparser)
+ if data then
+ if not pfbname or pfbname=="" then
+ pfbname=resolvers.findfile(file.replacesuffix(file.nameonly(afmname),"pfb"))
+ end
+ if pfbname and pfbname~="" then
+ data.resources.filename=resolvers.unresolve(pfbname)
+ get_indexes(data,pfbname)
+ return data
+ else
+ report_afm("no pfb file for %a",afmname)
+ end
+ end
+end
+function readers.loadshapes(filename)
+ local fullname=resolvers.findfile(filename) or ""
+ if fullname=="" then
+ return {
+ filename="not found: "..filename,
+ glyphs={}
+ }
+ else
+ return {
+ filename=fullname,
+ format="opentype",
+ glyphs=get_shapes(fullname) or {},
+ units=1000,
+ }
+ end
+end
+function readers.getinfo(filename)
+ local data=read(resolvers.findfile(filename),infoparser)
+ if data then
+ return data.metadata
+ end
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-onr”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-one” 987c5c5ed3754ad2feab80985067d59e] ---
+
+if not modules then modules={} end modules ['font-one']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local fonts,logs,trackers,containers,resolvers=fonts,logs,trackers,containers,resolvers
+local next,type,tonumber,rawget=next,type,tonumber,rawget
+local match,gsub=string.match,string.gsub
+local abs=math.abs
+local P,S,R,Cmt,C,Ct,Cs,Carg=lpeg.P,lpeg.S,lpeg.R,lpeg.Cmt,lpeg.C,lpeg.Ct,lpeg.Cs,lpeg.Carg
+local lpegmatch,patterns=lpeg.match,lpeg.patterns
+local sortedhash=table.sortedhash
+local trace_features=false trackers.register("afm.features",function(v) trace_features=v end)
+local trace_indexing=false trackers.register("afm.indexing",function(v) trace_indexing=v end)
+local trace_loading=false trackers.register("afm.loading",function(v) trace_loading=v end)
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local report_afm=logs.reporter("fonts","afm loading")
+local setmetatableindex=table.setmetatableindex
+local derivetable=table.derive
+local findbinfile=resolvers.findbinfile
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local definers=fonts.definers
+local readers=fonts.readers
+local constructors=fonts.constructors
+local afm=constructors.handlers.afm
+local pfb=constructors.handlers.pfb
+local otf=fonts.handlers.otf
+local otfreaders=otf.readers
+local otfenhancers=otf.enhancers
+local afmfeatures=constructors.features.afm
+local registerafmfeature=afmfeatures.register
+local afmenhancers=constructors.enhancers.afm
+local registerafmenhancer=afmenhancers.register
+afm.version=1.513
+afm.cache=containers.define("fonts","one",afm.version,true)
+afm.autoprefixed=true
+afm.helpdata={}
+afm.syncspace=true
+local overloads=fonts.mappings.overloads
+local applyruntimefixes=fonts.treatments and fonts.treatments.applyfixes
+function afm.load(filename)
+ filename=resolvers.findfile(filename,'afm') or ""
+ if filename~="" and not fonts.names.ignoredfile(filename) then
+ local name=file.removesuffix(file.basename(filename))
+ local data=containers.read(afm.cache,name)
+ local attr=lfs.attributes(filename)
+ local size=attr and attr.size or 0
+ local time=attr and attr.modification or 0
+ local pfbfile=file.replacesuffix(name,"pfb")
+ local pfbname=resolvers.findfile(pfbfile,"pfb") or ""
+ if pfbname=="" then
+ pfbname=resolvers.findfile(file.basename(pfbfile),"pfb") or ""
+ end
+ local pfbsize=0
+ local pfbtime=0
+ if pfbname~="" then
+ local attr=lfs.attributes(pfbname)
+ pfbsize=attr.size or 0
+ pfbtime=attr.modification or 0
+ end
+ if not data or data.size~=size or data.time~=time or data.pfbsize~=pfbsize or data.pfbtime~=pfbtime then
+ report_afm("reading %a",filename)
+ data=afm.readers.loadfont(filename,pfbname)
+ if data then
+ afmenhancers.apply(data,filename)
+ fonts.mappings.addtounicode(data,filename)
+ otfreaders.stripredundant(data)
+ otfreaders.pack(data)
+ data.size=size
+ data.time=time
+ data.pfbsize=pfbsize
+ data.pfbtime=pfbtime
+ report_afm("saving %a in cache",name)
+ data=containers.write(afm.cache,name,data)
+ data=containers.read(afm.cache,name)
+ end
+ end
+ if data then
+ otfreaders.unpack(data)
+ otfreaders.expand(data)
+ otfreaders.addunicodetable(data)
+ otfenhancers.apply(data,filename,data)
+ if applyruntimefixes then
+ applyruntimefixes(filename,data)
+ end
+ end
+ return data
+ end
+end
+local uparser=fonts.mappings.makenameparser()
+local function enhance_unify_names(data,filename)
+ local unicodevector=fonts.encodings.agl.unicodes
+ local unicodes={}
+ local names={}
+ local private=data.private or privateoffset
+ local descriptions=data.descriptions
+ for name,blob in sortedhash(data.characters) do
+ local code=unicodevector[name]
+ if not code then
+ code=lpegmatch(uparser,name)
+ if type(code)~="number" then
+ code=private
+ private=private+1
+ report_afm("assigning private slot %U for unknown glyph name %a",code,name)
+ end
+ end
+ local index=blob.index
+ unicodes[name]=code
+ names[name]=index
+ blob.name=name
+ descriptions[code]={
+ boundingbox=blob.boundingbox,
+ width=blob.width,
+ kerns=blob.kerns,
+ index=index,
+ name=name,
+ }
+ end
+ for unicode,description in next,descriptions do
+ local kerns=description.kerns
+ if kerns then
+ local krn={}
+ for name,kern in next,kerns do
+ local unicode=unicodes[name]
+ if unicode then
+ krn[unicode]=kern
+ else
+ end
+ end
+ description.kerns=krn
+ end
+ end
+ data.characters=nil
+ data.private=private
+ local resources=data.resources
+ local filename=resources.filename or file.removesuffix(file.basename(filename))
+ resources.filename=resolvers.unresolve(filename)
+ resources.unicodes=unicodes
+ resources.marks={}
+end
+local everywhere={ ["*"]={ ["*"]=true } }
+local noflags={ false,false,false,false }
+local function enhance_normalize_features(data)
+ local ligatures=setmetatableindex("table")
+ local kerns=setmetatableindex("table")
+ local extrakerns=setmetatableindex("table")
+ for u,c in next,data.descriptions do
+ local l=c.ligatures
+ local k=c.kerns
+ local e=c.extrakerns
+ if l then
+ ligatures[u]=l
+ for u,v in next,l do
+ l[u]={ ligature=v }
+ end
+ c.ligatures=nil
+ end
+ if k then
+ kerns[u]=k
+ for u,v in next,k do
+ k[u]=v
+ end
+ c.kerns=nil
+ end
+ if e then
+ extrakerns[u]=e
+ for u,v in next,e do
+ e[u]=v
+ end
+ c.extrakerns=nil
+ end
+ end
+ local features={
+ gpos={},
+ gsub={},
+ }
+ local sequences={
+ }
+ if next(ligatures) then
+ features.gsub.liga=everywhere
+ data.properties.hasligatures=true
+ sequences[#sequences+1]={
+ features={
+ liga=everywhere,
+ },
+ flags=noflags,
+ name="s_s_0",
+ nofsteps=1,
+ order={ "liga" },
+ type="gsub_ligature",
+ steps={
+ {
+ coverage=ligatures,
+ },
+ },
+ }
+ end
+ if next(kerns) then
+ features.gpos.kern=everywhere
+ data.properties.haskerns=true
+ sequences[#sequences+1]={
+ features={
+ kern=everywhere,
+ },
+ flags=noflags,
+ name="p_s_0",
+ nofsteps=1,
+ order={ "kern" },
+ type="gpos_pair",
+ steps={
+ {
+ format="kern",
+ coverage=kerns,
+ },
+ },
+ }
+ end
+ if next(extrakerns) then
+ features.gpos.extrakerns=everywhere
+ data.properties.haskerns=true
+ sequences[#sequences+1]={
+ features={
+ extrakerns=everywhere,
+ },
+ flags=noflags,
+ name="p_s_1",
+ nofsteps=1,
+ order={ "extrakerns" },
+ type="gpos_pair",
+ steps={
+ {
+ format="kern",
+ coverage=extrakerns,
+ },
+ },
+ }
+ end
+ data.resources.features=features
+ data.resources.sequences=sequences
+end
+local function enhance_fix_names(data)
+ for k,v in next,data.descriptions do
+ local n=v.name
+ local r=overloads[n]
+ if r then
+ local name=r.name
+ if trace_indexing then
+ report_afm("renaming characters %a to %a",n,name)
+ end
+ v.name=name
+ v.unicode=r.unicode
+ end
+ end
+end
+local addthem=function(rawdata,ligatures)
+ if ligatures then
+ local descriptions=rawdata.descriptions
+ local resources=rawdata.resources
+ local unicodes=resources.unicodes
+ for ligname,ligdata in next,ligatures do
+ local one=descriptions[unicodes[ligname]]
+ if one then
+ for _,pair in next,ligdata do
+ local two=unicodes[pair[1]]
+ local three=unicodes[pair[2]]
+ if two and three then
+ local ol=one.ligatures
+ if ol then
+ if not ol[two] then
+ ol[two]=three
+ end
+ else
+ one.ligatures={ [two]=three }
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local function enhance_add_ligatures(rawdata)
+ addthem(rawdata,afm.helpdata.ligatures)
+end
+local function enhance_add_extra_kerns(rawdata)
+ local descriptions=rawdata.descriptions
+ local resources=rawdata.resources
+ local unicodes=resources.unicodes
+ local function do_it_left(what)
+ if what then
+ for unicode,description in next,descriptions do
+ local kerns=description.kerns
+ if kerns then
+ local extrakerns
+ for complex,simple in next,what do
+ complex=unicodes[complex]
+ simple=unicodes[simple]
+ if complex and simple then
+ local ks=kerns[simple]
+ if ks and not kerns[complex] then
+ if extrakerns then
+ extrakerns[complex]=ks
+ else
+ extrakerns={ [complex]=ks }
+ end
+ end
+ end
+ end
+ if extrakerns then
+ description.extrakerns=extrakerns
+ end
+ end
+ end
+ end
+ end
+ local function do_it_copy(what)
+ if what then
+ for complex,simple in next,what do
+ complex=unicodes[complex]
+ simple=unicodes[simple]
+ if complex and simple then
+ local complexdescription=descriptions[complex]
+ if complexdescription then
+ local simpledescription=descriptions[complex]
+ if simpledescription then
+ local extrakerns
+ local kerns=simpledescription.kerns
+ if kerns then
+ for unicode,kern in next,kerns do
+ if extrakerns then
+ extrakerns[unicode]=kern
+ else
+ extrakerns={ [unicode]=kern }
+ end
+ end
+ end
+ local extrakerns=simpledescription.extrakerns
+ if extrakerns then
+ for unicode,kern in next,extrakerns do
+ if extrakerns then
+ extrakerns[unicode]=kern
+ else
+ extrakerns={ [unicode]=kern }
+ end
+ end
+ end
+ if extrakerns then
+ complexdescription.extrakerns=extrakerns
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ do_it_left(afm.helpdata.leftkerned)
+ do_it_left(afm.helpdata.bothkerned)
+ do_it_copy(afm.helpdata.bothkerned)
+ do_it_copy(afm.helpdata.rightkerned)
+end
+local function adddimensions(data)
+ if data then
+ for unicode,description in next,data.descriptions do
+ local bb=description.boundingbox
+ if bb then
+ local ht=bb[4]
+ local dp=-bb[2]
+ if ht==0 or ht<0 then
+ else
+ description.height=ht
+ end
+ if dp==0 or dp<0 then
+ else
+ description.depth=dp
+ end
+ end
+ end
+ end
+end
+local function copytotfm(data)
+ if data and data.descriptions then
+ local metadata=data.metadata
+ local resources=data.resources
+ local properties=derivetable(data.properties)
+ local descriptions=derivetable(data.descriptions)
+ local goodies=derivetable(data.goodies)
+ local characters={}
+ local parameters={}
+ local unicodes=resources.unicodes
+ for unicode,description in next,data.descriptions do
+ characters[unicode]={}
+ end
+ local filename=constructors.checkedfilename(resources)
+ local fontname=metadata.fontname or metadata.fullname
+ local fullname=metadata.fullname or metadata.fontname
+ local endash=0x2013
+ local emdash=0x2014
+ local space=0x0020
+ local spacer="space"
+ local spaceunits=500
+ local monospaced=metadata.monospaced
+ local charwidth=metadata.charwidth
+ local italicangle=metadata.italicangle
+ local charxheight=metadata.xheight and metadata.xheight>0 and metadata.xheight
+ properties.monospaced=monospaced
+ parameters.italicangle=italicangle
+ parameters.charwidth=charwidth
+ parameters.charxheight=charxheight
+ local d_endash=descriptions[endash]
+ local d_emdash=descriptions[emdash]
+ local d_space=descriptions[space]
+ if not d_space or d_space==0 then
+ d_space=d_endash
+ end
+ if d_space then
+ spaceunits,spacer=d_space.width or 0,"space"
+ end
+ if properties.monospaced then
+ if spaceunits==0 and d_emdash then
+ spaceunits,spacer=d_emdash.width or 0,"emdash"
+ end
+ else
+ if spaceunits==0 and d_endash then
+ spaceunits,spacer=d_emdash.width or 0,"endash"
+ end
+ end
+ if spaceunits==0 and charwidth then
+ spaceunits,spacer=charwidth or 0,"charwidth"
+ end
+ if spaceunits==0 then
+ spaceunits=tonumber(spaceunits) or 500
+ end
+ if spaceunits==0 then
+ spaceunits=500
+ end
+ parameters.slant=0
+ parameters.space=spaceunits
+ parameters.space_stretch=500
+ parameters.space_shrink=333
+ parameters.x_height=400
+ parameters.quad=1000
+ if italicangle and italicangle~=0 then
+ parameters.italicangle=italicangle
+ parameters.italicfactor=math.cos(math.rad(90+italicangle))
+ parameters.slant=- math.tan(italicangle*math.pi/180)
+ end
+ if monospaced then
+ parameters.space_stretch=0
+ parameters.space_shrink=0
+ elseif afm.syncspace then
+ parameters.space_stretch=spaceunits/2
+ parameters.space_shrink=spaceunits/3
+ end
+ parameters.extra_space=parameters.space_shrink
+ if charxheight then
+ parameters.x_height=charxheight
+ else
+ local x=0x0078
+ if x then
+ local x=descriptions[x]
+ if x then
+ parameters.x_height=x.height
+ end
+ end
+ end
+ if metadata.sup then
+ local dummy={ 0,0,0 }
+ parameters[ 1]=metadata.designsize or 0
+ parameters[ 2]=metadata.checksum or 0
+ parameters[ 3],
+ parameters[ 4],
+ parameters[ 5]=unpack(metadata.space or dummy)
+ parameters[ 6]=metadata.quad or 0
+ parameters[ 7]=metadata.extraspace or 0
+ parameters[ 8],
+ parameters[ 9],
+ parameters[10]=unpack(metadata.num or dummy)
+ parameters[11],
+ parameters[12]=unpack(metadata.denom or dummy)
+ parameters[13],
+ parameters[14],
+ parameters[15]=unpack(metadata.sup or dummy)
+ parameters[16],
+ parameters[17]=unpack(metadata.sub or dummy)
+ parameters[18]=metadata.supdrop or 0
+ parameters[19]=metadata.subdrop or 0
+ parameters[20],
+ parameters[21]=unpack(metadata.delim or dummy)
+ parameters[22]=metadata.axisheight or 0
+ end
+ parameters.designsize=(metadata.designsize or 10)*65536
+ parameters.ascender=abs(metadata.ascender or 0)
+ parameters.descender=abs(metadata.descender or 0)
+ parameters.units=1000
+ properties.spacer=spacer
+ properties.encodingbytes=2
+ properties.format=fonts.formats[filename] or "type1"
+ properties.filename=filename
+ properties.fontname=fontname
+ properties.fullname=fullname
+ properties.psname=fullname
+ properties.name=filename or fullname or fontname
+ properties.private=properties.private or data.private or privateoffset
+ if next(characters) then
+ return {
+ characters=characters,
+ descriptions=descriptions,
+ parameters=parameters,
+ resources=resources,
+ properties=properties,
+ goodies=goodies,
+ }
+ end
+ end
+ return nil
+end
+function afm.setfeatures(tfmdata,features)
+ local okay=constructors.initializefeatures("afm",tfmdata,features,trace_features,report_afm)
+ if okay then
+ return constructors.collectprocessors("afm",tfmdata,features,trace_features,report_afm)
+ else
+ return {}
+ end
+end
+local function addtables(data)
+ local resources=data.resources
+ local lookuptags=resources.lookuptags
+ local unicodes=resources.unicodes
+ if not lookuptags then
+ lookuptags={}
+ resources.lookuptags=lookuptags
+ end
+ setmetatableindex(lookuptags,function(t,k)
+ local v=type(k)=="number" and ("lookup "..k) or k
+ t[k]=v
+ return v
+ end)
+ if not unicodes then
+ unicodes={}
+ resources.unicodes=unicodes
+ setmetatableindex(unicodes,function(t,k)
+ setmetatableindex(unicodes,nil)
+ for u,d in next,data.descriptions do
+ local n=d.name
+ if n then
+ t[n]=u
+ end
+ end
+ return rawget(t,k)
+ end)
+ end
+ constructors.addcoreunicodes(unicodes)
+end
+local function afmtotfm(specification)
+ local afmname=specification.filename or specification.name
+ if specification.forced=="afm" or specification.format=="afm" then
+ if trace_loading then
+ report_afm("forcing afm format for %a",afmname)
+ end
+ else
+ local tfmname=findbinfile(afmname,"ofm") or ""
+ if tfmname~="" then
+ if trace_loading then
+ report_afm("fallback from afm to tfm for %a",afmname)
+ end
+ return
+ end
+ end
+ if afmname~="" then
+ local features=constructors.checkedfeatures("afm",specification.features.normal)
+ specification.features.normal=features
+ constructors.hashinstance(specification,true)
+ specification=definers.resolve(specification)
+ local cache_id=specification.hash
+ local tfmdata=containers.read(constructors.cache,cache_id)
+ if not tfmdata then
+ local rawdata=afm.load(afmname)
+ if rawdata and next(rawdata) then
+ addtables(rawdata)
+ adddimensions(rawdata)
+ tfmdata=copytotfm(rawdata)
+ if tfmdata and next(tfmdata) then
+ local shared=tfmdata.shared
+ if not shared then
+ shared={}
+ tfmdata.shared=shared
+ end
+ shared.rawdata=rawdata
+ shared.dynamics={}
+ tfmdata.changed={}
+ shared.features=features
+ shared.processes=afm.setfeatures(tfmdata,features)
+ end
+ elseif trace_loading then
+ report_afm("no (valid) afm file found with name %a",afmname)
+ end
+ tfmdata=containers.write(constructors.cache,cache_id,tfmdata)
+ end
+ return tfmdata
+ end
+end
+local function read_from_afm(specification)
+ local tfmdata=afmtotfm(specification)
+ if tfmdata then
+ tfmdata.properties.name=specification.name
+ tfmdata=constructors.scale(tfmdata,specification)
+ local allfeatures=tfmdata.shared.features or specification.features.normal
+ constructors.applymanipulators("afm",tfmdata,allfeatures,trace_features,report_afm)
+ fonts.loggers.register(tfmdata,'afm',specification)
+ end
+ return tfmdata
+end
+registerafmfeature {
+ name="mode",
+ description="mode",
+ initializers={
+ base=otf.modeinitializer,
+ node=otf.modeinitializer,
+ }
+}
+registerafmfeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ node=otf.nodemodeinitializer,
+ base=otf.basemodeinitializer,
+ },
+ processors={
+ node=otf.featuresprocessor,
+ }
+}
+fonts.formats.afm="type1"
+fonts.formats.pfb="type1"
+local function check_afm(specification,fullname)
+ local foundname=findbinfile(fullname,'afm') or ""
+ if foundname=="" then
+ foundname=fonts.names.getfilename(fullname,"afm") or ""
+ end
+ if fullname and foundname=="" and afm.autoprefixed then
+ local encoding,shortname=match(fullname,"^(.-)%-(.*)$")
+ if encoding and shortname and fonts.encodings.known[encoding] then
+ shortname=findbinfile(shortname,'afm') or ""
+ if shortname~="" then
+ foundname=shortname
+ if trace_defining then
+ report_afm("stripping encoding prefix from filename %a",afmname)
+ end
+ end
+ end
+ end
+ if foundname~="" then
+ specification.filename=foundname
+ specification.format="afm"
+ return read_from_afm(specification)
+ end
+end
+function readers.afm(specification,method)
+ local fullname=specification.filename or ""
+ local tfmdata=nil
+ if fullname=="" then
+ local forced=specification.forced or ""
+ if forced~="" then
+ tfmdata=check_afm(specification,specification.name.."."..forced)
+ end
+ if not tfmdata then
+ local check_tfm=readers.check_tfm
+ method=(check_tfm and (method or definers.method or "afm or tfm")) or "afm"
+ if method=="tfm" then
+ tfmdata=check_tfm(specification,specification.name)
+ elseif method=="afm" then
+ tfmdata=check_afm(specification,specification.name)
+ elseif method=="tfm or afm" then
+ tfmdata=check_tfm(specification,specification.name) or check_afm(specification,specification.name)
+ else
+ tfmdata=check_afm(specification,specification.name) or check_tfm(specification,specification.name)
+ end
+ end
+ else
+ tfmdata=check_afm(specification,fullname)
+ end
+ return tfmdata
+end
+function readers.pfb(specification,method)
+ local original=specification.specification
+ if trace_defining then
+ report_afm("using afm reader for %a",original)
+ end
+ specification.forced="afm"
+ local function swap(name)
+ local value=specification[swap]
+ if value then
+ specification[swap]=gsub("%.pfb",".afm",1)
+ end
+ end
+ swap("filename")
+ swap("fullname")
+ swap("forcedname")
+ swap("specification")
+ return readers.afm(specification,method)
+end
+registerafmenhancer("unify names",enhance_unify_names)
+registerafmenhancer("add ligatures",enhance_add_ligatures)
+registerafmenhancer("add extra kerns",enhance_add_extra_kerns)
+registerafmenhancer("normalize features",enhance_normalize_features)
+registerafmenhancer("check extra features",otfenhancers.enhance)
+registerafmenhancer("fix names",enhance_fix_names)
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-one”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-afk” 54d554530e75c57c56ee76234724e26d] ---
+
+if not modules then modules={} end modules ['font-afk']={
+ version=1.001,
+ comment="companion to font-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+ dataonly=true,
+}
+local allocate=utilities.storage.allocate
+fonts.handlers.afm.helpdata={
+ ligatures=allocate {
+ ['f']={
+ { 'f','ff' },
+ { 'i','fi' },
+ { 'l','fl' },
+ },
+ ['ff']={
+ { 'i','ffi' }
+ },
+ ['fi']={
+ { 'i','fii' }
+ },
+ ['fl']={
+ { 'i','fli' }
+ },
+ ['s']={
+ { 't','st' }
+ },
+ ['i']={
+ { 'j','ij' }
+ },
+ },
+ texligatures=allocate {
+ ['quoteleft']={
+ { 'quoteleft','quotedblleft' }
+ },
+ ['quoteright']={
+ { 'quoteright','quotedblright' }
+ },
+ ['hyphen']={
+ { 'hyphen','endash' }
+ },
+ ['endash']={
+ { 'hyphen','emdash' }
+ }
+ },
+ leftkerned=allocate {
+ AEligature="A",aeligature="a",
+ OEligature="O",oeligature="o",
+ IJligature="I",ijligature="i",
+ AE="A",ae="a",
+ OE="O",oe="o",
+ IJ="I",ij="i",
+ Ssharp="S",ssharp="s",
+ },
+ rightkerned=allocate {
+ AEligature="E",aeligature="e",
+ OEligature="E",oeligature="e",
+ IJligature="J",ijligature="j",
+ AE="E",ae="e",
+ OE="E",oe="e",
+ IJ="J",ij="j",
+ Ssharp="S",ssharp="s",
+ },
+ bothkerned=allocate {
+ Acircumflex="A",acircumflex="a",
+ Ccircumflex="C",ccircumflex="c",
+ Ecircumflex="E",ecircumflex="e",
+ Gcircumflex="G",gcircumflex="g",
+ Hcircumflex="H",hcircumflex="h",
+ Icircumflex="I",icircumflex="i",
+ Jcircumflex="J",jcircumflex="j",
+ Ocircumflex="O",ocircumflex="o",
+ Scircumflex="S",scircumflex="s",
+ Ucircumflex="U",ucircumflex="u",
+ Wcircumflex="W",wcircumflex="w",
+ Ycircumflex="Y",ycircumflex="y",
+ Agrave="A",agrave="a",
+ Egrave="E",egrave="e",
+ Igrave="I",igrave="i",
+ Ograve="O",ograve="o",
+ Ugrave="U",ugrave="u",
+ Ygrave="Y",ygrave="y",
+ Atilde="A",atilde="a",
+ Itilde="I",itilde="i",
+ Otilde="O",otilde="o",
+ Utilde="U",utilde="u",
+ Ntilde="N",ntilde="n",
+ Adiaeresis="A",adiaeresis="a",Adieresis="A",adieresis="a",
+ Ediaeresis="E",ediaeresis="e",Edieresis="E",edieresis="e",
+ Idiaeresis="I",idiaeresis="i",Idieresis="I",idieresis="i",
+ Odiaeresis="O",odiaeresis="o",Odieresis="O",odieresis="o",
+ Udiaeresis="U",udiaeresis="u",Udieresis="U",udieresis="u",
+ Ydiaeresis="Y",ydiaeresis="y",Ydieresis="Y",ydieresis="y",
+ Aacute="A",aacute="a",
+ Cacute="C",cacute="c",
+ Eacute="E",eacute="e",
+ Iacute="I",iacute="i",
+ Lacute="L",lacute="l",
+ Nacute="N",nacute="n",
+ Oacute="O",oacute="o",
+ Racute="R",racute="r",
+ Sacute="S",sacute="s",
+ Uacute="U",uacute="u",
+ Yacute="Y",yacute="y",
+ Zacute="Z",zacute="z",
+ Dstroke="D",dstroke="d",
+ Hstroke="H",hstroke="h",
+ Tstroke="T",tstroke="t",
+ Cdotaccent="C",cdotaccent="c",
+ Edotaccent="E",edotaccent="e",
+ Gdotaccent="G",gdotaccent="g",
+ Idotaccent="I",idotaccent="i",
+ Zdotaccent="Z",zdotaccent="z",
+ Amacron="A",amacron="a",
+ Emacron="E",emacron="e",
+ Imacron="I",imacron="i",
+ Omacron="O",omacron="o",
+ Umacron="U",umacron="u",
+ Ccedilla="C",ccedilla="c",
+ Kcedilla="K",kcedilla="k",
+ Lcedilla="L",lcedilla="l",
+ Ncedilla="N",ncedilla="n",
+ Rcedilla="R",rcedilla="r",
+ Scedilla="S",scedilla="s",
+ Tcedilla="T",tcedilla="t",
+ Ohungarumlaut="O",ohungarumlaut="o",
+ Uhungarumlaut="U",uhungarumlaut="u",
+ Aogonek="A",aogonek="a",
+ Eogonek="E",eogonek="e",
+ Iogonek="I",iogonek="i",
+ Uogonek="U",uogonek="u",
+ Aring="A",aring="a",
+ Uring="U",uring="u",
+ Abreve="A",abreve="a",
+ Ebreve="E",ebreve="e",
+ Gbreve="G",gbreve="g",
+ Ibreve="I",ibreve="i",
+ Obreve="O",obreve="o",
+ Ubreve="U",ubreve="u",
+ Ccaron="C",ccaron="c",
+ Dcaron="D",dcaron="d",
+ Ecaron="E",ecaron="e",
+ Lcaron="L",lcaron="l",
+ Ncaron="N",ncaron="n",
+ Rcaron="R",rcaron="r",
+ Scaron="S",scaron="s",
+ Tcaron="T",tcaron="t",
+ Zcaron="Z",zcaron="z",
+ dotlessI="I",dotlessi="i",
+ dotlessJ="J",dotlessj="j",
+ AEligature="AE",aeligature="ae",AE="AE",ae="ae",
+ OEligature="OE",oeligature="oe",OE="OE",oe="oe",
+ IJligature="IJ",ijligature="ij",IJ="IJ",ij="ij",
+ Lstroke="L",lstroke="l",Lslash="L",lslash="l",
+ Ostroke="O",ostroke="o",Oslash="O",oslash="o",
+ Ssharp="SS",ssharp="ss",
+ Aumlaut="A",aumlaut="a",
+ Eumlaut="E",eumlaut="e",
+ Iumlaut="I",iumlaut="i",
+ Oumlaut="O",oumlaut="o",
+ Uumlaut="U",uumlaut="u",
+ }
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-afk”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-tfm” 3bbba3214fd0b8c6f35ad85592fc2917] ---
+
+if not modules then modules={} end modules ['luatex-fonts-tfm']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type=next,type
+local match,format=string.match,string.format
+local concat,sortedhash=table.concat,table.sortedhash
+local idiv=number.idiv
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local trace_features=false trackers.register("tfm.features",function(v) trace_features=v end)
+local report_defining=logs.reporter("fonts","defining")
+local report_tfm=logs.reporter("fonts","tfm loading")
+local findbinfile=resolvers.findbinfile
+local setmetatableindex=table.setmetatableindex
+local fonts=fonts
+local handlers=fonts.handlers
+local helpers=fonts.helpers
+local readers=fonts.readers
+local constructors=fonts.constructors
+local encodings=fonts.encodings
+local tfm=constructors.handlers.tfm
+tfm.version=1.000
+tfm.maxnestingdepth=5
+tfm.maxnestingsize=65536*1024
+local otf=fonts.handlers.otf
+local otfenhancers=otf.enhancers
+local tfmfeatures=constructors.features.tfm
+local registertfmfeature=tfmfeatures.register
+local tfmenhancers=constructors.enhancers.tfm
+local registertfmenhancer=tfmenhancers.register
+local charcommand=helpers.commands.char
+constructors.resolvevirtualtoo=false
+fonts.formats.tfm="type1"
+fonts.formats.ofm="type1"
+function tfm.setfeatures(tfmdata,features)
+ local okay=constructors.initializefeatures("tfm",tfmdata,features,trace_features,report_tfm)
+ if okay then
+ return constructors.collectprocessors("tfm",tfmdata,features,trace_features,report_tfm)
+ else
+ return {}
+ end
+end
+local depth={}
+local loadtfm=font.read_tfm
+local loadvf=font.read_vf
+local function read_from_tfm(specification)
+ local filename=specification.filename
+ local size=specification.size
+ depth[filename]=(depth[filename] or 0)+1
+ if trace_defining then
+ report_defining("loading tfm file %a at size %s",filename,size)
+ end
+ local tfmdata=loadtfm(filename,size)
+ if tfmdata then
+ local features=specification.features and specification.features.normal or {}
+ local features=constructors.checkedfeatures("tfm",features)
+ specification.features.normal=features
+ local newtfmdata=(depth[filename]==1) and tfm.reencode(tfmdata,specification)
+ if newtfmdata then
+ tfmdata=newtfmdata
+ end
+ local resources=tfmdata.resources or {}
+ local properties=tfmdata.properties or {}
+ local parameters=tfmdata.parameters or {}
+ local shared=tfmdata.shared or {}
+ shared.features=features
+ shared.resources=resources
+ properties.name=tfmdata.name
+ properties.fontname=tfmdata.fontname
+ properties.psname=tfmdata.psname
+ properties.fullname=tfmdata.fullname
+ properties.filename=specification.filename
+ properties.format=tfmdata.format or fonts.formats.tfm
+ properties.usedbitmap=tfmdata.usedbitmap
+ tfmdata.properties=properties
+ tfmdata.resources=resources
+ tfmdata.parameters=parameters
+ tfmdata.shared=shared
+ shared.rawdata={ resources=resources }
+ shared.features=features
+ if newtfmdata then
+ if not resources.marks then
+ resources.marks={}
+ end
+ if not resources.sequences then
+ resources.sequences={}
+ end
+ if not resources.features then
+ resources.features={
+ gsub={},
+ gpos={},
+ }
+ end
+ if not tfmdata.changed then
+ tfmdata.changed={}
+ end
+ if not tfmdata.descriptions then
+ tfmdata.descriptions=tfmdata.characters
+ end
+ otf.readers.addunicodetable(tfmdata)
+ tfmenhancers.apply(tfmdata,filename)
+ constructors.applymanipulators("tfm",tfmdata,features,trace_features,report_tfm)
+ otf.readers.unifymissing(tfmdata)
+ fonts.mappings.addtounicode(tfmdata,filename)
+ tfmdata.tounicode=1
+ local tounicode=fonts.mappings.tounicode
+ for unicode,v in next,tfmdata.characters do
+ local u=v.unicode
+ if u then
+ v.tounicode=tounicode(u)
+ end
+ end
+ if tfmdata.usedbitmap then
+ tfm.addtounicode(tfmdata)
+ end
+ end
+ shared.processes=next(features) and tfm.setfeatures(tfmdata,features) or nil
+ if size<0 then
+ size=idiv(65536*-size,100)
+ end
+ parameters.factor=1
+ parameters.units=1000
+ parameters.size=size
+ parameters.slant=parameters.slant or parameters[1] or 0
+ parameters.space=parameters.space or parameters[2] or 0
+ parameters.space_stretch=parameters.space_stretch or parameters[3] or 0
+ parameters.space_shrink=parameters.space_shrink or parameters[4] or 0
+ parameters.x_height=parameters.x_height or parameters[5] or 0
+ parameters.quad=parameters.quad or parameters[6] or 0
+ parameters.extra_space=parameters.extra_space or parameters[7] or 0
+ constructors.enhanceparameters(parameters)
+ properties.private=properties.private or tfmdata.private or privateoffset
+ if newtfmdata then
+ elseif constructors.resolvevirtualtoo then
+ fonts.loggers.register(tfmdata,file.suffix(filename),specification)
+ local vfname=findbinfile(specification.name,'ovf')
+ if vfname and vfname~="" then
+ local vfdata=loadvf(vfname,size)
+ if vfdata then
+ local chars=tfmdata.characters
+ for k,v in next,vfdata.characters do
+ chars[k].commands=v.commands
+ end
+ properties.virtualized=true
+ tfmdata.fonts=vfdata.fonts
+ tfmdata.type="virtual"
+ local fontlist=vfdata.fonts
+ local name=file.nameonly(filename)
+ for i=1,#fontlist do
+ local n=fontlist[i].name
+ local s=fontlist[i].size
+ local d=depth[filename]
+ s=constructors.scaled(s,vfdata.designsize)
+ if d>tfm.maxnestingdepth then
+ report_defining("too deeply nested virtual font %a with size %a, max nesting depth %s",n,s,tfm.maxnestingdepth)
+ fontlist[i]={ id=0 }
+ elseif (d>1) and (s>tfm.maxnestingsize) then
+ report_defining("virtual font %a exceeds size %s",n,s)
+ fontlist[i]={ id=0 }
+ else
+ local t,id=constructors.readanddefine(n,s)
+ fontlist[i]={ id=id }
+ end
+ end
+ end
+ end
+ end
+ properties.haskerns=true
+ properties.hasligatures=true
+ properties.hasitalics=true
+ resources.unicodes={}
+ resources.lookuptags={}
+ depth[filename]=depth[filename]-1
+ return tfmdata
+ else
+ depth[filename]=depth[filename]-1
+ end
+end
+local function check_tfm(specification,fullname)
+ local foundname=findbinfile(fullname,'tfm') or ""
+ if foundname=="" then
+ foundname=findbinfile(fullname,'ofm') or ""
+ end
+ if foundname=="" then
+ foundname=fonts.names.getfilename(fullname,"tfm") or ""
+ end
+ if foundname~="" then
+ specification.filename=foundname
+ specification.format="ofm"
+ return read_from_tfm(specification)
+ elseif trace_defining then
+ report_defining("loading tfm with name %a fails",specification.name)
+ end
+end
+readers.check_tfm=check_tfm
+function readers.tfm(specification)
+ local fullname=specification.filename or ""
+ if fullname=="" then
+ local forced=specification.forced or ""
+ if forced~="" then
+ fullname=specification.name.."."..forced
+ else
+ fullname=specification.name
+ end
+ end
+ return check_tfm(specification,fullname)
+end
+readers.ofm=readers.tfm
+do
+ local outfiles={}
+ local tfmcache=table.setmetatableindex(function(t,tfmdata)
+ local id=font.define(tfmdata)
+ t[tfmdata]=id
+ return id
+ end)
+ local encdone=table.setmetatableindex("table")
+ function tfm.reencode(tfmdata,specification)
+ local features=specification.features
+ if not features then
+ return
+ end
+ local features=features.normal
+ if not features then
+ return
+ end
+ local tfmfile=file.basename(tfmdata.name)
+ local encfile=features.reencode
+ local pfbfile=features.pfbfile
+ local bitmap=features.bitmap
+ if not encfile then
+ return
+ end
+ local pfbfile=outfiles[tfmfile]
+ if pfbfile==nil then
+ if bitmap then
+ pfbfile=false
+ elseif type(pfbfile)~="string" then
+ pfbfile=tfmfile
+ end
+ if type(pfbfile)=="string" then
+ pfbfile=file.addsuffix(pfbfile,"pfb")
+ report_tfm("using type1 shapes from %a for %a",pfbfile,tfmfile)
+ else
+ report_tfm("using bitmap shapes for %a",tfmfile)
+ pfbfile=false
+ end
+ outfiles[tfmfile]=pfbfile
+ end
+ local encoding=false
+ local vector=false
+ if type(pfbfile)=="string" then
+ local pfb=constructors.handlers.pfb
+ if pfb and pfb.loadvector then
+ local v,e=pfb.loadvector(pfbfile)
+ if v then
+ vector=v
+ end
+ if e then
+ encoding=e
+ end
+ end
+ end
+ if type(encfile)=="string" and encfile~="auto" then
+ encoding=fonts.encodings.load(file.addsuffix(encfile,"enc"))
+ if encoding then
+ encoding=encoding.vector
+ end
+ end
+ if not encoding then
+ report_tfm("bad encoding for %a, quitting",tfmfile)
+ return
+ end
+ local unicoding=fonts.encodings.agl and fonts.encodings.agl.unicodes
+ local virtualid=tfmcache[tfmdata]
+ local tfmdata=table.copy(tfmdata)
+ local characters={}
+ local originals=tfmdata.characters
+ local indices={}
+ local parentfont={ "font",1 }
+ local private=tfmdata.privateoffset or constructors.privateoffset
+ local reported=encdone[tfmfile][encfile]
+ local backmap=vector and table.swapped(vector)
+ local done={}
+ for index,name in sortedhash(encoding) do
+ local unicode=unicoding[name]
+ local original=originals[index]
+ if original then
+ if unicode then
+ original.unicode=unicode
+ else
+ unicode=private
+ private=private+1
+ if not reported then
+ report_tfm("glyph %a in font %a with encoding %a gets unicode %U",name,tfmfile,encfile,unicode)
+ end
+ end
+ characters[unicode]=original
+ indices[index]=unicode
+ original.name=name
+ if backmap then
+ original.index=backmap[name]
+ else
+ original.commands={ parentfont,charcommand[index] }
+ original.oindex=index
+ end
+ done[name]=true
+ elseif not done[name] then
+ report_tfm("bad index %a in font %a with name %a",index,tfmfile,name)
+ end
+ end
+ encdone[tfmfile][encfile]=true
+ for k,v in next,characters do
+ local kerns=v.kerns
+ if kerns then
+ local t={}
+ for k,v in next,kerns do
+ local i=indices[k]
+ if i then
+ t[i]=v
+ end
+ end
+ v.kerns=next(t) and t or nil
+ end
+ local ligatures=v.ligatures
+ if ligatures then
+ local t={}
+ for k,v in next,ligatures do
+ local i=indices[k]
+ if i then
+ t[i]=v
+ v.char=indices[v.char]
+ end
+ end
+ v.ligatures=next(t) and t or nil
+ end
+ end
+ tfmdata.fonts={ { id=virtualid } }
+ tfmdata.characters=characters
+ tfmdata.fullname=tfmdata.fullname or tfmdata.name
+ tfmdata.psname=file.nameonly(pfbfile or tfmdata.name)
+ tfmdata.filename=pfbfile
+ tfmdata.encodingbytes=2
+ tfmdata.format="type1"
+ tfmdata.tounicode=1
+ tfmdata.embedding="subset"
+ tfmdata.usedbitmap=bitmap and virtualid
+ tfmdata.private=private
+ return tfmdata
+ end
+end
+do
+ local template=[[
+/CIDInit /ProcSet findresource begin
+ 12 dict begin
+ begincmap
+ /CIDSystemInfo << /Registry (TeX) /Ordering (bitmap-%s) /Supplement 0 >> def
+ /CMapName /TeX-bitmap-%s def
+ /CMapType 2 def
+ 1 begincodespacerange
+ <00> <FF>
+ endcodespacerange
+ %s beginbfchar
+%s
+ endbfchar
+ endcmap
+CMapName currentdict /CMap defineresource pop end
+end
+end
+]]
+ local flushstreamobject=lpdf and lpdf.flushstreamobject
+ local setfontattributes=lpdf and lpdf.setfontattributes
+ if not flushstreamobject then
+ flushstreamobject=function(data)
+ return pdf.obj { immediate=true,type="stream",string=data }
+ end
+ end
+ if not setfontattributes then
+ setfontattributes=function(id,data)
+ return pdf.setfontattributes(id,data)
+ end
+ end
+ function tfm.addtounicode(tfmdata)
+ local id=tfmdata.usedbitmap
+ local map={}
+ local char={}
+ for k,v in next,tfmdata.characters do
+ local index=v.oindex
+ local tounicode=v.tounicode
+ if index and tounicode then
+ map[index]=tounicode
+ end
+ end
+ for k,v in sortedhash(map) do
+ char[#char+1]=format("<%02X> <%s>",k,v)
+ end
+ char=concat(char,"\n")
+ local stream=format(template,id,id,#char,char)
+ local reference=flushstreamobject(stream,nil,true)
+ setfontattributes(id,format("/ToUnicode %i 0 R",reference))
+ end
+end
+do
+ local everywhere={ ["*"]={ ["*"]=true } }
+ local noflags={ false,false,false,false }
+ local function enhance_normalize_features(data)
+ local ligatures=setmetatableindex("table")
+ local kerns=setmetatableindex("table")
+ local characters=data.characters
+ for u,c in next,characters do
+ local l=c.ligatures
+ local k=c.kerns
+ if l then
+ ligatures[u]=l
+ for u,v in next,l do
+ l[u]={ ligature=v.char }
+ end
+ c.ligatures=nil
+ end
+ if k then
+ kerns[u]=k
+ for u,v in next,k do
+ k[u]=v
+ end
+ c.kerns=nil
+ end
+ end
+ for u,l in next,ligatures do
+ for k,v in next,l do
+ local vl=v.ligature
+ local dl=ligatures[vl]
+ if dl then
+ for kk,vv in next,dl do
+ v[kk]=vv
+ end
+ end
+ end
+ end
+ local features={
+ gpos={},
+ gsub={},
+ }
+ local sequences={
+ }
+ if next(ligatures) then
+ features.gsub.liga=everywhere
+ data.properties.hasligatures=true
+ sequences[#sequences+1]={
+ features={
+ liga=everywhere,
+ },
+ flags=noflags,
+ name="s_s_0",
+ nofsteps=1,
+ order={ "liga" },
+ type="gsub_ligature",
+ steps={
+ {
+ coverage=ligatures,
+ },
+ },
+ }
+ end
+ if next(kerns) then
+ features.gpos.kern=everywhere
+ data.properties.haskerns=true
+ sequences[#sequences+1]={
+ features={
+ kern=everywhere,
+ },
+ flags=noflags,
+ name="p_s_0",
+ nofsteps=1,
+ order={ "kern" },
+ type="gpos_pair",
+ steps={
+ {
+ format="kern",
+ coverage=kerns,
+ },
+ },
+ }
+ end
+ data.resources.features=features
+ data.resources.sequences=sequences
+ data.shared.resources=data.shared.resources or resources
+ end
+ registertfmenhancer("normalize features",enhance_normalize_features)
+ registertfmenhancer("check extra features",otfenhancers.enhance)
+end
+registertfmfeature {
+ name="mode",
+ description="mode",
+ initializers={
+ base=otf.modeinitializer,
+ node=otf.modeinitializer,
+ }
+}
+registertfmfeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ base=otf.basemodeinitializer,
+ node=otf.nodemodeinitializer,
+ },
+ processors={
+ node=otf.featuresprocessor,
+ }
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-tfm”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-lua” 55b281fb98f7bd848fc19928f376f647] ---
+
+if not modules then modules={} end modules ['font-lua']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local report_lua=logs.reporter("fonts","lua loading")
+local fonts=fonts
+local readers=fonts.readers
+fonts.formats.lua="lua"
+local function check_lua(specification,fullname)
+ local fullname=resolvers.findfile(fullname) or ""
+ if fullname~="" then
+ local loader=loadfile(fullname)
+ loader=loader and loader()
+ return loader and loader(specification)
+ end
+end
+readers.check_lua=check_lua
+function readers.lua(specification)
+ local original=specification.specification
+ if trace_defining then
+ report_lua("using lua reader for %a",original)
+ end
+ local fullname=specification.filename or ""
+ if fullname=="" then
+ local forced=specification.forced or ""
+ if forced~="" then
+ fullname=specification.name.."."..forced
+ else
+ fullname=specification.name
+ end
+ end
+ return check_lua(specification,fullname)
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-lua”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-def” f66c365dae4499f982d8bf16e5d37de3] ---
+
+if not modules then modules={} end modules ['font-def']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local lower,gsub=string.lower,string.gsub
+local tostring,next=tostring,next
+local lpegmatch=lpeg.match
+local suffixonly,removesuffix,basename=file.suffix,file.removesuffix,file.basename
+local formatters=string.formatters
+local sortedhash,sortedkeys=table.sortedhash,table.sortedkeys
+local allocate=utilities.storage.allocate
+local trace_defining=false trackers .register("fonts.defining",function(v) trace_defining=v end)
+local directive_embedall=false directives.register("fonts.embedall",function(v) directive_embedall=v end)
+trackers.register("fonts.loading","fonts.defining","otf.loading","afm.loading","tfm.loading")
+local report_defining=logs.reporter("fonts","defining")
+local fonts=fonts
+local fontdata=fonts.hashes.identifiers
+local readers=fonts.readers
+local definers=fonts.definers
+local specifiers=fonts.specifiers
+local constructors=fonts.constructors
+local fontgoodies=fonts.goodies
+readers.sequence=allocate { 'otf','ttf','afm','tfm','lua' }
+local variants=allocate()
+specifiers.variants=variants
+definers.methods=definers.methods or {}
+local internalized=allocate()
+local lastdefined=nil
+local loadedfonts=constructors.loadedfonts
+local designsizes=constructors.designsizes
+local resolvefile=fontgoodies and fontgoodies.filenames and fontgoodies.filenames.resolve or function(s) return s end
+local function makespecification(specification,lookup,name,sub,method,detail,size)
+ size=size or 655360
+ if not lookup or lookup=="" then
+ lookup=definers.defaultlookup
+ end
+ if trace_defining then
+ report_defining("specification %a, lookup %a, name %a, sub %a, method %a, detail %a",
+ specification,lookup,name,sub,method,detail)
+ end
+ local t={
+ lookup=lookup,
+ specification=specification,
+ size=size,
+ name=name,
+ sub=sub,
+ method=method,
+ detail=detail,
+ resolved="",
+ forced="",
+ features={},
+ }
+ return t
+end
+definers.makespecification=makespecification
+if context then
+ local splitter,splitspecifiers=nil,""
+ local P,C,S,Cc,Cs=lpeg.P,lpeg.C,lpeg.S,lpeg.Cc,lpeg.Cs
+ local left=P("(")
+ local right=P(")")
+ local colon=P(":")
+ local space=P(" ")
+ local lbrace=P("{")
+ local rbrace=P("}")
+ definers.defaultlookup="file"
+ local prefixpattern=P(false)
+ local function addspecifier(symbol)
+ splitspecifiers=splitspecifiers..symbol
+ local method=S(splitspecifiers)
+ local lookup=C(prefixpattern)*colon
+ local sub=left*C(P(1-left-right-method)^1)*right
+ local specification=C(method)*C(P(1)^1)
+ local name=Cs((lbrace/"")*(1-rbrace)^1*(rbrace/"")+(1-sub-specification)^1)
+ splitter=P((lookup+Cc(""))*name*(sub+Cc(""))*(specification+Cc("")))
+ end
+ local function addlookup(str)
+ prefixpattern=prefixpattern+P(str)
+ end
+ definers.addlookup=addlookup
+ addlookup("file")
+ addlookup("name")
+ addlookup("spec")
+ local function getspecification(str)
+ return lpegmatch(splitter,str or "")
+ end
+ definers.getspecification=getspecification
+ function definers.registersplit(symbol,action,verbosename)
+ addspecifier(symbol)
+ variants[symbol]=action
+ if verbosename then
+ variants[verbosename]=action
+ end
+ end
+ function definers.analyze(specification,size)
+ local lookup,name,sub,method,detail=getspecification(specification or "")
+ return makespecification(specification,lookup,name,sub,method,detail,size)
+ end
+end
+definers.resolvers=definers.resolvers or {}
+local resolvers=definers.resolvers
+function resolvers.file(specification)
+ local name=resolvefile(specification.name)
+ local suffix=lower(suffixonly(name))
+ if fonts.formats[suffix] then
+ specification.forced=suffix
+ specification.forcedname=name
+ specification.name=removesuffix(name)
+ else
+ specification.name=name
+ end
+end
+function resolvers.name(specification)
+ local resolve=fonts.names.resolve
+ if resolve then
+ local resolved,sub,subindex,instance=resolve(specification.name,specification.sub,specification)
+ if resolved then
+ specification.resolved=resolved
+ specification.sub=sub
+ specification.subindex=subindex
+ if instance then
+ specification.instance=instance
+ local features=specification.features
+ if not features then
+ features={}
+ specification.features=features
+ end
+ local normal=features.normal
+ if not normal then
+ normal={}
+ features.normal=normal
+ end
+ normal.instance=instance
+ end
+ local suffix=lower(suffixonly(resolved))
+ if fonts.formats[suffix] then
+ specification.forced=suffix
+ specification.forcedname=resolved
+ specification.name=removesuffix(resolved)
+ else
+ specification.name=resolved
+ end
+ end
+ else
+ resolvers.file(specification)
+ end
+end
+function resolvers.spec(specification)
+ local resolvespec=fonts.names.resolvespec
+ if resolvespec then
+ local resolved,sub,subindex=resolvespec(specification.name,specification.sub,specification)
+ if resolved then
+ specification.resolved=resolved
+ specification.sub=sub
+ specification.subindex=subindex
+ specification.forced=lower(suffixonly(resolved))
+ specification.forcedname=resolved
+ specification.name=removesuffix(resolved)
+ end
+ else
+ resolvers.name(specification)
+ end
+end
+function definers.resolve(specification)
+ if not specification.resolved or specification.resolved=="" then
+ local r=resolvers[specification.lookup]
+ if r then
+ r(specification)
+ end
+ end
+ if specification.forced=="" then
+ specification.forced=nil
+ specification.forcedname=nil
+ end
+ specification.hash=lower(specification.name..' @ '..constructors.hashfeatures(specification))
+ if specification.sub and specification.sub~="" then
+ specification.hash=specification.sub..' @ '..specification.hash
+ end
+ return specification
+end
+function definers.applypostprocessors(tfmdata)
+ local postprocessors=tfmdata.postprocessors
+ if postprocessors then
+ local properties=tfmdata.properties
+ for i=1,#postprocessors do
+ local extrahash=postprocessors[i](tfmdata)
+ if type(extrahash)=="string" and extrahash~="" then
+ extrahash=gsub(lower(extrahash),"[^a-z]","-")
+ properties.fullname=formatters["%s-%s"](properties.fullname,extrahash)
+ end
+ end
+ end
+ return tfmdata
+end
+local function checkembedding(tfmdata)
+ local properties=tfmdata.properties
+ local embedding
+ if directive_embedall then
+ embedding="full"
+ elseif properties and properties.filename and constructors.dontembed[properties.filename] then
+ embedding="no"
+ else
+ embedding="subset"
+ end
+ if properties then
+ properties.embedding=embedding
+ else
+ tfmdata.properties={ embedding=embedding }
+ end
+ tfmdata.embedding=embedding
+end
+local function checkfeatures(tfmdata)
+ local resources=tfmdata.resources
+ local shared=tfmdata.shared
+ if resources and shared then
+ local features=resources.features
+ local usedfeatures=shared.features
+ if features and usedfeatures then
+ local usedlanguage=usedfeatures.language or "dflt"
+ local usedscript=usedfeatures.script or "dflt"
+ local function check(what)
+ if what then
+ local foundlanguages={}
+ for feature,scripts in next,what do
+ if usedscript=="auto" or scripts["*"] then
+ elseif not scripts[usedscript] then
+ else
+ for script,languages in next,scripts do
+ if languages["*"] then
+ elseif context and not languages[usedlanguage] then
+ report_defining("font %!font:name!, feature %a, script %a, no language %a",
+ tfmdata,feature,script,usedlanguage)
+ end
+ end
+ end
+ for script,languages in next,scripts do
+ for language in next,languages do
+ foundlanguages[language]=true
+ end
+ end
+ end
+ if false then
+ foundlanguages["*"]=nil
+ foundlanguages=sortedkeys(foundlanguages)
+ for feature,scripts in sortedhash(what) do
+ for script,languages in next,scripts do
+ if not languages["*"] then
+ for i=1,#foundlanguages do
+ local language=foundlanguages[i]
+ if context and not languages[language] then
+ report_defining("font %!font:name!, feature %a, script %a, no language %a",
+ tfmdata,feature,script,language)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ check(features.gsub)
+ check(features.gpos)
+ end
+ end
+end
+function definers.loadfont(specification)
+ local hash=constructors.hashinstance(specification)
+ local tfmdata=loadedfonts[hash]
+ if not tfmdata then
+ local forced=specification.forced or ""
+ if forced~="" then
+ local reader=readers[lower(forced)]
+ tfmdata=reader and reader(specification)
+ if not tfmdata then
+ report_defining("forced type %a of %a not found",forced,specification.name)
+ end
+ else
+ local sequence=readers.sequence
+ for s=1,#sequence do
+ local reader=sequence[s]
+ if readers[reader] then
+ if trace_defining then
+ report_defining("trying (reader sequence driven) type %a for %a with file %a",reader,specification.name,specification.filename)
+ end
+ tfmdata=readers[reader](specification)
+ if tfmdata then
+ break
+ else
+ specification.filename=nil
+ end
+ end
+ end
+ end
+ if tfmdata then
+ tfmdata=definers.applypostprocessors(tfmdata)
+ checkembedding(tfmdata)
+ loadedfonts[hash]=tfmdata
+ designsizes[specification.hash]=tfmdata.parameters.designsize
+ checkfeatures(tfmdata)
+ end
+ end
+ if not tfmdata then
+ report_defining("font with asked name %a is not found using lookup %a",specification.name,specification.lookup)
+ end
+ return tfmdata
+end
+function constructors.readanddefine(name,size)
+ local specification=definers.analyze(name,size)
+ local method=specification.method
+ if method and variants[method] then
+ specification=variants[method](specification)
+ end
+ specification=definers.resolve(specification)
+ local hash=constructors.hashinstance(specification)
+ local id=definers.registered(hash)
+ if not id then
+ local tfmdata=definers.loadfont(specification)
+ if tfmdata then
+ tfmdata.properties.hash=hash
+ id=font.define(tfmdata)
+ definers.register(tfmdata,id)
+ else
+ id=0
+ end
+ end
+ return fontdata[id],id
+end
+function definers.current()
+ return lastdefined
+end
+function definers.registered(hash)
+ local id=internalized[hash]
+ return id,id and fontdata[id]
+end
+function definers.register(tfmdata,id)
+ if tfmdata and id then
+ local hash=tfmdata.properties.hash
+ if not hash then
+ report_defining("registering font, id %a, name %a, invalid hash",id,tfmdata.properties.filename or "?")
+ elseif not internalized[hash] then
+ internalized[hash]=id
+ if trace_defining then
+ report_defining("registering font, id %s, hash %a",id,hash)
+ end
+ fontdata[id]=tfmdata
+ end
+ end
+end
+function definers.read(specification,size,id)
+ statistics.starttiming(fonts)
+ if type(specification)=="string" then
+ specification=definers.analyze(specification,size)
+ end
+ local method=specification.method
+ if method and variants[method] then
+ specification=variants[method](specification)
+ end
+ specification=definers.resolve(specification)
+ local hash=constructors.hashinstance(specification)
+ local tfmdata=definers.registered(hash)
+ if tfmdata then
+ if trace_defining then
+ report_defining("already hashed: %s",hash)
+ end
+ else
+ tfmdata=definers.loadfont(specification)
+ if tfmdata then
+ if trace_defining then
+ report_defining("loaded and hashed: %s",hash)
+ end
+ tfmdata.properties.hash=hash
+ if id then
+ definers.register(tfmdata,id)
+ end
+ else
+ if trace_defining then
+ report_defining("not loaded and hashed: %s",hash)
+ end
+ end
+ end
+ lastdefined=tfmdata or id
+ if not tfmdata then
+ report_defining("unknown font %a, loading aborted",specification.name)
+ elseif trace_defining and type(tfmdata)=="table" then
+ local properties=tfmdata.properties or {}
+ local parameters=tfmdata.parameters or {}
+ report_defining("using %a font with id %a, name %a, size %a, bytes %a, encoding %a, fullname %a, filename %a",
+ properties.format or "unknown",id or "-",properties.name,parameters.size,properties.encodingbytes,
+ properties.encodingname,properties.fullname,basename(properties.filename))
+ end
+ statistics.stoptiming(fonts)
+ return tfmdata
+end
+function font.getfont(id)
+ return fontdata[id]
+end
+callbacks.register('define_font',definers.read,"definition of fonts (tfmdata preparation)")
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-def”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-def” 5ad79120ebc5e60f4d322fb3ee13bffe] ---
+
+if not modules then modules={} end modules ['luatex-fonts-def']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+ os.exit()
+end
+local fonts=fonts
+fonts.constructors.namemode="specification"
+function fonts.definers.getspecification(str)
+ return "",str,"",":",str
+end
+local list={}
+local function issome () list.lookup='name' end
+local function isfile () list.lookup='file' end
+local function isname () list.lookup='name' end
+local function thename(s) list.name=s end
+local function issub (v) list.sub=v end
+local function iscrap (s) list.crap=string.lower(s) end
+local function iskey (k,v) list[k]=v end
+local function istrue (s) list[s]=true end
+local function isfalse(s) list[s]=false end
+local P,S,R,C,Cs=lpeg.P,lpeg.S,lpeg.R,lpeg.C,lpeg.Cs
+local spaces=P(" ")^0
+local namespec=Cs((P("{")/"")*(1-S("}"))^0*(P("}")/"")+(1-S("/:("))^0)
+local crapspec=spaces*P("/")*(((1-P(":"))^0)/iscrap)*spaces
+local filename_1=P("file:")/isfile*(namespec/thename)
+local filename_2=P("[")*P(true)/isfile*(((1-P("]"))^0)/thename)*P("]")
+local fontname_1=P("name:")/isname*(namespec/thename)
+local fontname_2=P(true)/issome*(namespec/thename)
+local sometext=R("az","AZ","09")^1
+local somekey=R("az","AZ","09")^1
+local somevalue=(P("{")/"")*(1-P("}"))^0*(P("}")/"")+(1-S(";"))^1
+local truevalue=P("+")*spaces*(sometext/istrue)
+local falsevalue=P("-")*spaces*(sometext/isfalse)
+local keyvalue=(C(somekey)*spaces*P("=")*spaces*C(somevalue))/iskey
+local somevalue=sometext/istrue
+local subvalue=P("(")*(C(P(1-S("()"))^1)/issub)*P(")")
+local option=spaces*(keyvalue+falsevalue+truevalue+somevalue)*spaces
+local options=P(":")*spaces*(P(";")^0*option)^0
+local pattern=(filename_1+filename_2+fontname_1+fontname_2)*subvalue^0*crapspec^0*options^0
+function fonts.definers.analyze(str,size)
+ local specification=fonts.definers.makespecification(str,nil,nil,nil,":",nil,size)
+ list={}
+ lpeg.match(pattern,str)
+ list.crap=nil
+ if list.name then
+ specification.name=list.name
+ list.name=nil
+ end
+ if list.lookup then
+ specification.lookup=list.lookup
+ list.lookup=nil
+ end
+ if list.sub then
+ specification.sub=list.sub
+ list.sub=nil
+ end
+ specification.features.normal=fonts.handlers.otf.features.normalize(list)
+ list=nil
+ return specification
+end
+function fonts.definers.applypostprocessors(tfmdata)
+ local postprocessors=tfmdata.postprocessors
+ if postprocessors then
+ for i=1,#postprocessors do
+ local extrahash=postprocessors[i](tfmdata)
+ if type(extrahash)=="string" and extrahash~="" then
+ extrahash=string.gsub(lower(extrahash),"[^a-z]","-")
+ tfmdata.properties.fullname=format("%s-%s",tfmdata.properties.fullname,extrahash)
+ end
+ end
+ end
+ return tfmdata
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-def”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-ext” 01015ab3758cdc2af29394e6d502a91a] ---
+
+if not modules then modules={} end modules ['luatex-fonts-ext']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+ os.exit()
+end
+local byte=string.byte
+local fonts=fonts
+local handlers=fonts.handlers
+local otf=handlers.otf
+local afm=handlers.afm
+local registerotffeature=otf.features.register
+local registerafmfeature=afm.features.register
+function fonts.loggers.onetimemessage() end
+fonts.protrusions=fonts.protrusions or {}
+fonts.protrusions.setups=fonts.protrusions.setups or {}
+local setups=fonts.protrusions.setups
+setups['default']={
+ factor=1,
+ left=1,
+ right=1,
+ [0x002C]={ 0,1 },
+ [0x002E]={ 0,1 },
+ [0x003A]={ 0,1 },
+ [0x003B]={ 0,1 },
+ [0x002D]={ 0,1 },
+ [0x2013]={ 0,0.50 },
+ [0x2014]={ 0,0.33 },
+ [0x3001]={ 0,1 },
+ [0x3002]={ 0,1 },
+ [0x060C]={ 0,1 },
+ [0x061B]={ 0,1 },
+ [0x06D4]={ 0,1 },
+}
+local function initializeprotrusion(tfmdata,value)
+ if value then
+ local setup=setups[value]
+ if setup then
+ local factor,left,right=setup.factor or 1,setup.left or 1,setup.right or 1
+ local emwidth=tfmdata.parameters.quad
+ tfmdata.parameters.protrusion={
+ auto=true,
+ }
+ for i,chr in next,tfmdata.characters do
+ local v,pl,pr=setup[i],nil,nil
+ if v then
+ pl,pr=v[1],v[2]
+ end
+ if pl and pl~=0 then chr.left_protruding=left*pl*factor end
+ if pr and pr~=0 then chr.right_protruding=right*pr*factor end
+ end
+ end
+ end
+end
+local specification={
+ name="protrusion",
+ description="shift characters into the left and or right margin",
+ initializers={
+ base=initializeprotrusion,
+ node=initializeprotrusion,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+fonts.expansions=fonts.expansions or {}
+fonts.expansions.setups=fonts.expansions.setups or {}
+local setups=fonts.expansions.setups
+setups['default']={
+ stretch=2,
+ shrink=2,
+ step=.5,
+ factor=1,
+ [byte('A')]=0.5,[byte('B')]=0.7,[byte('C')]=0.7,[byte('D')]=0.5,[byte('E')]=0.7,
+ [byte('F')]=0.7,[byte('G')]=0.5,[byte('H')]=0.7,[byte('K')]=0.7,[byte('M')]=0.7,
+ [byte('N')]=0.7,[byte('O')]=0.5,[byte('P')]=0.7,[byte('Q')]=0.5,[byte('R')]=0.7,
+ [byte('S')]=0.7,[byte('U')]=0.7,[byte('W')]=0.7,[byte('Z')]=0.7,
+ [byte('a')]=0.7,[byte('b')]=0.7,[byte('c')]=0.7,[byte('d')]=0.7,[byte('e')]=0.7,
+ [byte('g')]=0.7,[byte('h')]=0.7,[byte('k')]=0.7,[byte('m')]=0.7,[byte('n')]=0.7,
+ [byte('o')]=0.7,[byte('p')]=0.7,[byte('q')]=0.7,[byte('s')]=0.7,[byte('u')]=0.7,
+ [byte('w')]=0.7,[byte('z')]=0.7,
+ [byte('2')]=0.7,[byte('3')]=0.7,[byte('6')]=0.7,[byte('8')]=0.7,[byte('9')]=0.7,
+}
+local function initializeexpansion(tfmdata,value)
+ if value then
+ local setup=setups[value]
+ if setup then
+ local factor=setup.factor or 1
+ tfmdata.parameters.expansion={
+ stretch=10*(setup.stretch or 0),
+ shrink=10*(setup.shrink or 0),
+ step=10*(setup.step or 0),
+ auto=true,
+ }
+ for i,chr in next,tfmdata.characters do
+ local v=setup[i]
+ if v and v~=0 then
+ chr.expansion_factor=v*factor
+ else
+ chr.expansion_factor=factor
+ end
+ end
+ end
+ end
+end
+local specification={
+ name="expansion",
+ description="apply hz optimization",
+ initializers={
+ base=initializeexpansion,
+ node=initializeexpansion,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+if not otf.features.normalize then
+ otf.features.normalize=function(t)
+ if t.rand then
+ t.rand="random"
+ end
+ return t
+ end
+end
+function fonts.helpers.nametoslot(name)
+ local t=type(name)
+ if t=="string" then
+ local tfmdata=fonts.hashes.identifiers[currentfont()]
+ local shared=tfmdata and tfmdata.shared
+ local fntdata=shared and shared.rawdata
+ return fntdata and fntdata.resources.unicodes[name]
+ elseif t=="number" then
+ return n
+ end
+end
+fonts.encodings=fonts.encodings or {}
+local reencodings={}
+fonts.encodings.reencodings=reencodings
+local function specialreencode(tfmdata,value)
+ local encoding=value and reencodings[value]
+ if encoding then
+ local temp={}
+ local char=tfmdata.characters
+ for k,v in next,encoding do
+ temp[k]=char[v]
+ end
+ for k,v in next,temp do
+ char[k]=temp[k]
+ end
+ return string.format("reencoded:%s",value)
+ end
+end
+local function initialize(tfmdata,value)
+ tfmdata.postprocessors=tfmdata.postprocessors or {}
+ table.insert(tfmdata.postprocessors,
+ function(tfmdata)
+ return specialreencode(tfmdata,value)
+ end
+ )
+end
+registerotffeature {
+ name="reencode",
+ description="reencode characters",
+ manipulators={
+ base=initialize,
+ node=initialize,
+ }
+}
+local function initialize(tfmdata,key,value)
+ if value then
+ tfmdata.mathparameters=nil
+ end
+end
+registerotffeature {
+ name="ignoremathconstants",
+ description="ignore math constants table",
+ initializers={
+ base=initialize,
+ node=initialize,
+ }
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-ext”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-tex” 77c374b0ef00c2fb12188ec42beb4257] ---
+
+if not modules then modules={} end modules ['font-imp-tex']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next=next
+local fonts=fonts
+local otf=fonts.handlers.otf
+local registerotffeature=otf.features.register
+local addotffeature=otf.addfeature
+local specification={
+ type="ligature",
+ order={ "tlig" },
+ prepend=true,
+ data={
+ [0x2013]={ 0x002D,0x002D },
+ [0x2014]={ 0x002D,0x002D,0x002D },
+ },
+}
+addotffeature("tlig",specification)
+registerotffeature {
+ name="tlig",
+ description="tex ligatures",
+}
+local specification={
+ type="substitution",
+ order={ "trep" },
+ prepend=true,
+ data={
+ [0x0027]=0x2019,
+ },
+}
+addotffeature("trep",specification)
+registerotffeature {
+ name="trep",
+ description="tex replacements",
+}
+local anum_arabic={
+ [0x0030]=0x0660,
+ [0x0031]=0x0661,
+ [0x0032]=0x0662,
+ [0x0033]=0x0663,
+ [0x0034]=0x0664,
+ [0x0035]=0x0665,
+ [0x0036]=0x0666,
+ [0x0037]=0x0667,
+ [0x0038]=0x0668,
+ [0x0039]=0x0669,
+}
+local anum_persian={
+ [0x0030]=0x06F0,
+ [0x0031]=0x06F1,
+ [0x0032]=0x06F2,
+ [0x0033]=0x06F3,
+ [0x0034]=0x06F4,
+ [0x0035]=0x06F5,
+ [0x0036]=0x06F6,
+ [0x0037]=0x06F7,
+ [0x0038]=0x06F8,
+ [0x0039]=0x06F9,
+}
+local function valid(data)
+ local features=data.resources.features
+ if features then
+ for k,v in next,features do
+ for k,v in next,v do
+ if v.arab then
+ return true
+ end
+ end
+ end
+ end
+end
+local specification={
+ {
+ type="substitution",
+ features={ arab={ urd=true,dflt=true } },
+ order={ "anum" },
+ data=anum_arabic,
+ valid=valid,
+ },
+ {
+ type="substitution",
+ features={ arab={ urd=true } },
+ order={ "anum" },
+ data=anum_persian,
+ valid=valid,
+ },
+}
+addotffeature("anum",specification)
+registerotffeature {
+ name="anum",
+ description="arabic digits",
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-tex”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-ligatures” 043daa4fcccf2560868da359d71d3a4a] ---
+
+if not modules then modules={} end modules ['font-imp-ligatures']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local lpegmatch=lpeg.match
+local utfsplit=utf.split
+local settings_to_array=utilities.parsers.settings_to_array
+local fonts=fonts
+local otf=fonts.handlers.otf
+local registerotffeature=otf.features.register
+local addotffeature=otf.addfeature
+local lookups={}
+local protect={}
+local revert={}
+local zwjchar=0x200C
+local zwj={ zwjchar }
+addotffeature {
+ name="blockligatures",
+ type="chainsubstitution",
+ nocheck=true,
+ prepend=true,
+ future=true,
+ lookups={
+ {
+ type="multiple",
+ data=lookups,
+ },
+ },
+ data={
+ rules=protect,
+ }
+}
+addotffeature {
+ name="blockligatures",
+ type="chainsubstitution",
+ nocheck=true,
+ append=true,
+ overload=false,
+ lookups={
+ {
+ type="ligature",
+ data=lookups,
+ },
+ },
+ data={
+ rules=revert,
+ }
+}
+registerotffeature {
+ name='blockligatures',
+ description='block certain ligatures',
+}
+local splitter=lpeg.splitat(":")
+local function blockligatures(str)
+ local t=settings_to_array(str)
+ for i=1,#t do
+ local ti=t[i]
+ local before,current,after=lpegmatch(splitter,ti)
+ if current and after then
+ if before then
+ before=utfsplit(before)
+ for i=1,#before do
+ before[i]={ before[i] }
+ end
+ end
+ if current then
+ current=utfsplit(current)
+ end
+ if after then
+ after=utfsplit(after)
+ for i=1,#after do
+ after[i]={ after[i] }
+ end
+ end
+ else
+ before=nil
+ current=utfsplit(ti)
+ after=nil
+ end
+ if #current>1 then
+ local one=current[1]
+ local two=current[2]
+ lookups[one]={ one,zwjchar }
+ local one={ one }
+ local two={ two }
+ local new=#protect+1
+ protect[new]={
+ before=before,
+ current={ one,two },
+ after=after,
+ lookups={ 1 },
+ }
+ revert[new]={
+ current={ one,zwj },
+ after={ two },
+ lookups={ 1 },
+ }
+ end
+ end
+end
+otf.helpers.blockligatures=blockligatures
+if context then
+ interfaces.implement {
+ name="blockligatures",
+ arguments="string",
+ actions=blockligatures,
+ }
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-ligatures”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-italics” fe1ca80fb5ea4a2f8d2d5c484e7ba913] ---
+
+if not modules then modules={} end modules ['font-imp-italics']={
+ version=1.001,
+ comment="companion to font-ini.mkiv and hand-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next=next
+local fonts=fonts
+local handlers=fonts.handlers
+local registerotffeature=handlers.otf.features.register
+local registerafmfeature=handlers.afm.features.register
+local function initialize(tfmdata,key,value)
+ for unicode,character in next,tfmdata.characters do
+ local olditalic=character.italic
+ if olditalic and olditalic~=0 then
+ character.width=character.width+olditalic
+ character.italic=0
+ end
+ end
+end
+local specification={
+ name="italicwidths",
+ description="add italic to width",
+ manipulators={
+ base=initialize,
+ node=initialize,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initialize(tfmdata,value)
+ if value then
+ local parameters=tfmdata.parameters
+ local italicangle=parameters.italicangle
+ if italicangle and italicangle~=0 then
+ local properties=tfmdata.properties
+ local factor=tonumber(value) or 1
+ properties.hasitalics=true
+ properties.autoitalicamount=factor*(parameters.uwidth or 40)/2
+ end
+ end
+end
+local specification={
+ name="itlc",
+ description="italic correction",
+ initializers={
+ base=initialize,
+ node=initialize,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+if context then
+ local function initialize(tfmdata,value)
+ tfmdata.properties.textitalics=toboolean(value)
+ end
+ local specification={
+ name="textitalics",
+ description="use alternative text italic correction",
+ initializers={
+ base=initialize,
+ node=initialize,
+ }
+ }
+ registerotffeature(specification)
+ registerafmfeature(specification)
+end
+if context then
+ local letter=characters.is_letter
+ local always=true
+ local function collapseitalics(tfmdata,key,value)
+ local threshold=value==true and 100 or tonumber(value)
+ if threshold and threshold>0 then
+ if threshold>100 then
+ threshold=100
+ end
+ for unicode,data in next,tfmdata.characters do
+ if always or letter[unicode] or letter[data.unicode] then
+ local italic=data.italic
+ if italic and italic~=0 then
+ local width=data.width
+ if width and width~=0 then
+ local delta=threshold*italic/100
+ data.width=width+delta
+ data.italic=italic-delta
+ end
+ end
+ end
+ end
+ end
+ end
+ local dimensions_specification={
+ name="collapseitalics",
+ description="collapse italics",
+ manipulators={
+ base=collapseitalics,
+ node=collapseitalics,
+ }
+ }
+ registerotffeature(dimensions_specification)
+ registerafmfeature(dimensions_specification)
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-italics”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-effects” 73a660359a0ec71e44cc2b7225a715ac] ---
+
+if not modules then modules={} end modules ['font-imp-effects']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+local is_boolean=string.is_boolean
+local fonts=fonts
+local handlers=fonts.handlers
+local registerotffeature=handlers.otf.features.register
+local registerafmfeature=handlers.afm.features.register
+local settings_to_hash=utilities.parsers.settings_to_hash_colon_too
+local helpers=fonts.helpers
+local prependcommands=helpers.prependcommands
+local charcommand=helpers.commands.char
+local leftcommand=helpers.commands.left
+local rightcommand=helpers.commands.right
+local upcommand=helpers.commands.up
+local downcommand=helpers.commands.down
+local dummycommand=helpers.commands.dummy
+local report_effect=logs.reporter("fonts","effect")
+local report_slant=logs.reporter("fonts","slant")
+local report_extend=logs.reporter("fonts","extend")
+local report_squeeze=logs.reporter("fonts","squeeze")
+local trace=false
+trackers.register("fonts.effect",function(v) trace=v end)
+trackers.register("fonts.slant",function(v) trace=v end)
+trackers.register("fonts.extend",function(v) trace=v end)
+trackers.register("fonts.squeeze",function(v) trace=v end)
+local function initializeslant(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ elseif value>1 then
+ value=1
+ elseif value<-1 then
+ value=-1
+ end
+ if trace then
+ report_slant("applying %0.3f",value)
+ end
+ tfmdata.parameters.slantfactor=value
+end
+local specification={
+ name="slant",
+ description="slant glyphs",
+ initializers={
+ base=initializeslant,
+ node=initializeslant,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initializeextend(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ elseif value>10 then
+ value=10
+ elseif value<-10 then
+ value=-10
+ end
+ if trace then
+ report_extend("applying %0.3f",value)
+ end
+ tfmdata.parameters.extendfactor=value
+end
+local specification={
+ name="extend",
+ description="scale glyphs horizontally",
+ initializers={
+ base=initializeextend,
+ node=initializeextend,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initializesqueeze(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ elseif value>10 then
+ value=10
+ elseif value<-10 then
+ value=-10
+ end
+ if trace then
+ report_squeeze("applying %0.3f",value)
+ end
+ tfmdata.parameters.squeezefactor=value
+end
+local specification={
+ name="squeeze",
+ description="scale glyphs vertically",
+ initializers={
+ base=initializesqueeze,
+ node=initializesqueeze,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local effects={
+ inner=0,
+ normal=0,
+ outer=1,
+ outline=1,
+ both=2,
+ hidden=3,
+}
+local function initializeeffect(tfmdata,value)
+ local spec
+ if type(value)=="number" then
+ spec={ width=value }
+ else
+ spec=settings_to_hash(value)
+ end
+ local effect=spec.effect or "both"
+ local width=tonumber(spec.width) or 0
+ local mode=effects[effect]
+ if not mode then
+ report_effect("invalid effect %a",effect)
+ elseif width==0 and mode==0 then
+ report_effect("invalid width %a for effect %a",width,effect)
+ else
+ local parameters=tfmdata.parameters
+ local properties=tfmdata.properties
+ parameters.mode=mode
+ parameters.width=width*1000
+ if is_boolean(spec.auto)==true then
+ local squeeze=1-width/20
+ local average=(1-squeeze)*width*100
+ spec.squeeze=squeeze
+ spec.extend=1+width/2
+ spec.wdelta=average
+ spec.hdelta=average/2
+ spec.ddelta=average/2
+ spec.vshift=average/2
+ end
+ local factor=tonumber(spec.factor) or 0
+ local hfactor=tonumber(spec.hfactor) or factor
+ local vfactor=tonumber(spec.vfactor) or factor
+ local delta=tonumber(spec.delta) or 1
+ local wdelta=tonumber(spec.wdelta) or delta
+ local hdelta=tonumber(spec.hdelta) or delta
+ local ddelta=tonumber(spec.ddelta) or hdelta
+ local vshift=tonumber(spec.vshift) or 0
+ local slant=spec.slant
+ local extend=spec.extend
+ local squeeze=spec.squeeze
+ if slant then
+ initializeslant(tfmdata,slant)
+ end
+ if extend then
+ initializeextend(tfmdata,extend)
+ end
+ if squeeze then
+ initializesqueeze(tfmdata,squeeze)
+ end
+ properties.effect={
+ effect=effect,
+ width=width,
+ factor=factor,
+ hfactor=hfactor,
+ vfactor=vfactor,
+ wdelta=wdelta,
+ hdelta=hdelta,
+ ddelta=ddelta,
+ vshift=vshift,
+ slant=tfmdata.parameters.slantfactor,
+ extend=tfmdata.parameters.extendfactor,
+ squeeze=tfmdata.parameters.squeezefactor,
+ }
+ end
+end
+local rules={
+ "RadicalRuleThickness",
+ "OverbarRuleThickness",
+ "FractionRuleThickness",
+ "UnderbarRuleThickness",
+}
+local function setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze)
+ if delta~=0 then
+ for i=1,#rules do
+ local name=rules[i]
+ local value=mathparameters[name]
+ if value then
+ mathparameters[name]=(squeeze or 1)*(value+dx)
+ end
+ end
+ end
+end
+local function setmathcharacters(tfmdata,characters,mathparameters,dx,dy,squeeze,wdelta,hdelta,ddelta)
+ local function wdpatch(char)
+ if wsnap~=0 then
+ char.width=char.width+wdelta/2
+ end
+ end
+ local function htpatch(char)
+ if hsnap~=0 then
+ local height=char.height
+ if height then
+ char.height=char.height+2*dy
+ end
+ end
+ end
+ local character=characters[0x221A]
+ if character and character.next then
+ local char=character
+ local next=character.next
+ wdpatch(char)
+ htpatch(char)
+ while next do
+ char=characters[next]
+ wdpatch(char)
+ htpatch(char)
+ next=char.next
+ end
+ if char then
+ local v=char.vert_variants
+ if v then
+ local top=v[#v]
+ if top then
+ local char=characters[top.glyph]
+ htpatch(char)
+ end
+ end
+ end
+ end
+end
+local function manipulateeffect(tfmdata)
+ local effect=tfmdata.properties.effect
+ if effect then
+ local characters=tfmdata.characters
+ local parameters=tfmdata.parameters
+ local mathparameters=tfmdata.mathparameters
+ local multiplier=effect.width*100
+ local factor=parameters.factor
+ local hfactor=parameters.hfactor
+ local vfactor=parameters.vfactor
+ local wdelta=effect.wdelta*hfactor*multiplier
+ local hdelta=effect.hdelta*vfactor*multiplier
+ local ddelta=effect.ddelta*vfactor*multiplier
+ local vshift=effect.vshift*vfactor*multiplier
+ local squeeze=effect.squeeze
+ local hshift=wdelta/2
+ local dx=multiplier*vfactor
+ local dy=vshift
+ local factor=(1+effect.factor)*factor
+ local hfactor=(1+effect.hfactor)*hfactor
+ local vfactor=(1+effect.vfactor)*vfactor
+ local vshift=vshift~=0 and upcommand[vshift] or false
+ for unicode,character in next,characters do
+ local oldwidth=character.width
+ local oldheight=character.height
+ local olddepth=character.depth
+ if oldwidth and oldwidth>0 then
+ character.width=oldwidth+wdelta
+ local commands=character.commands
+ local hshift=rightcommand[hshift]
+ if vshift then
+ if commands then
+ prependcommands (commands,
+ hshift,
+ vshift
+ )
+ else
+ character.commands={
+ hshift,
+ vshift,
+ charcommand[unicode]
+ }
+ end
+ else
+ if commands then
+ prependcommands (commands,
+ hshift
+ )
+ else
+ character.commands={
+ hshift,
+ charcommand[unicode]
+ }
+ end
+ end
+ end
+ if oldheight and oldheight>0 then
+ character.height=oldheight+hdelta
+ end
+ if olddepth and olddepth>0 then
+ character.depth=olddepth+ddelta
+ end
+ end
+ if mathparameters then
+ setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze)
+ setmathcharacters(tfmdata,characters,mathparameters,dx,dy,squeeze,wdelta,hdelta,ddelta)
+ end
+ parameters.factor=factor
+ parameters.hfactor=hfactor
+ parameters.vfactor=vfactor
+ if trace then
+ report_effect("applying")
+ report_effect(" effect : %s",effect.effect)
+ report_effect(" width : %s => %s",effect.width,multiplier)
+ report_effect(" factor : %s => %s",effect.factor,factor )
+ report_effect(" hfactor : %s => %s",effect.hfactor,hfactor)
+ report_effect(" vfactor : %s => %s",effect.vfactor,vfactor)
+ report_effect(" wdelta : %s => %s",effect.wdelta,wdelta)
+ report_effect(" hdelta : %s => %s",effect.hdelta,hdelta)
+ report_effect(" ddelta : %s => %s",effect.ddelta,ddelta)
+ end
+ end
+end
+local specification={
+ name="effect",
+ description="apply effects to glyphs",
+ initializers={
+ base=initializeeffect,
+ node=initializeeffect,
+ },
+ manipulators={
+ base=manipulateeffect,
+ node=manipulateeffect,
+ },
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initializeoutline(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ else
+ value=tonumber(value) or 0
+ end
+ local parameters=tfmdata.parameters
+ local properties=tfmdata.properties
+ parameters.mode=effects.outline
+ parameters.width=value*1000
+ properties.effect={
+ effect=effect,
+ width=width,
+ }
+end
+local specification={
+ name="outline",
+ description="outline glyphs",
+ initializers={
+ base=initializeoutline,
+ node=initializeoutline,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “font-imp-effects”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-lig” b9dbe77ce747d4c35bb2a20ffbe5aa51] ---
+
+
+fonts.handlers.otf.addfeature {
+ ["dataset"]={
+ {
+ ["data"]={
+ ["À"]={ "A","̀" },
+ ["Á"]={ "A","́" },
+ ["Â"]={ "A","̂" },
+ ["Ã"]={ "A","̃" },
+ ["Ä"]={ "A","̈" },
+ ["Å"]={ "A","̊" },
+ ["Ç"]={ "C","̧" },
+ ["È"]={ "E","̀" },
+ ["É"]={ "E","́" },
+ ["Ê"]={ "E","̂" },
+ ["Ë"]={ "E","̈" },
+ ["Ì"]={ "I","̀" },
+ ["Í"]={ "I","́" },
+ ["Î"]={ "I","̂" },
+ ["Ï"]={ "I","̈" },
+ ["Ñ"]={ "N","̃" },
+ ["Ò"]={ "O","̀" },
+ ["Ó"]={ "O","́" },
+ ["Ô"]={ "O","̂" },
+ ["Õ"]={ "O","̃" },
+ ["Ö"]={ "O","̈" },
+ ["Ù"]={ "U","̀" },
+ ["Ú"]={ "U","́" },
+ ["Û"]={ "U","̂" },
+ ["Ü"]={ "U","̈" },
+ ["Ý"]={ "Y","́" },
+ ["à"]={ "a","̀" },
+ ["á"]={ "a","́" },
+ ["â"]={ "a","̂" },
+ ["ã"]={ "a","̃" },
+ ["ä"]={ "a","̈" },
+ ["å"]={ "a","̊" },
+ ["ç"]={ "c","̧" },
+ ["è"]={ "e","̀" },
+ ["é"]={ "e","́" },
+ ["ê"]={ "e","̂" },
+ ["ë"]={ "e","̈" },
+ ["ì"]={ "i","̀" },
+ ["í"]={ "i","́" },
+ ["î"]={ "i","̂" },
+ ["ï"]={ "i","̈" },
+ ["ñ"]={ "n","̃" },
+ ["ò"]={ "o","̀" },
+ ["ó"]={ "o","́" },
+ ["ô"]={ "o","̂" },
+ ["õ"]={ "o","̃" },
+ ["ö"]={ "o","̈" },
+ ["ù"]={ "u","̀" },
+ ["ú"]={ "u","́" },
+ ["û"]={ "u","̂" },
+ ["ü"]={ "u","̈" },
+ ["ý"]={ "y","́" },
+ ["ÿ"]={ "y","̈" },
+ ["Ā"]={ "A","̄" },
+ ["ā"]={ "a","̄" },
+ ["Ă"]={ "A","̆" },
+ ["ă"]={ "a","̆" },
+ ["Ą"]={ "A","̨" },
+ ["ą"]={ "a","̨" },
+ ["Ć"]={ "C","́" },
+ ["ć"]={ "c","́" },
+ ["Ĉ"]={ "C","̂" },
+ ["ĉ"]={ "c","̂" },
+ ["Ċ"]={ "C","̇" },
+ ["ċ"]={ "c","̇" },
+ ["Č"]={ "C","̌" },
+ ["č"]={ "c","̌" },
+ ["Ď"]={ "D","̌" },
+ ["ď"]={ "d","̌" },
+ ["Ē"]={ "E","̄" },
+ ["ē"]={ "e","̄" },
+ ["Ĕ"]={ "E","̆" },
+ ["ĕ"]={ "e","̆" },
+ ["Ė"]={ "E","̇" },
+ ["ė"]={ "e","̇" },
+ ["Ę"]={ "E","̨" },
+ ["ę"]={ "e","̨" },
+ ["Ě"]={ "E","̌" },
+ ["ě"]={ "e","̌" },
+ ["Ĝ"]={ "G","̂" },
+ ["ĝ"]={ "g","̂" },
+ ["Ğ"]={ "G","̆" },
+ ["ğ"]={ "g","̆" },
+ ["Ġ"]={ "G","̇" },
+ ["ġ"]={ "g","̇" },
+ ["Ģ"]={ "G","̧" },
+ ["ģ"]={ "g","̧" },
+ ["Ĥ"]={ "H","̂" },
+ ["ĥ"]={ "h","̂" },
+ ["Ĩ"]={ "I","̃" },
+ ["ĩ"]={ "i","̃" },
+ ["Ī"]={ "I","̄" },
+ ["ī"]={ "i","̄" },
+ ["Ĭ"]={ "I","̆" },
+ ["ĭ"]={ "i","̆" },
+ ["Į"]={ "I","̨" },
+ ["į"]={ "i","̨" },
+ ["İ"]={ "I","̇" },
+ ["Ĵ"]={ "J","̂" },
+ ["ĵ"]={ "j","̂" },
+ ["Ķ"]={ "K","̧" },
+ ["ķ"]={ "k","̧" },
+ ["Ĺ"]={ "L","́" },
+ ["ĺ"]={ "l","́" },
+ ["Ļ"]={ "L","̧" },
+ ["ļ"]={ "l","̧" },
+ ["Ľ"]={ "L","̌" },
+ ["ľ"]={ "l","̌" },
+ ["Ń"]={ "N","́" },
+ ["ń"]={ "n","́" },
+ ["Ņ"]={ "N","̧" },
+ ["ņ"]={ "n","̧" },
+ ["Ň"]={ "N","̌" },
+ ["ň"]={ "n","̌" },
+ ["Ō"]={ "O","̄" },
+ ["ō"]={ "o","̄" },
+ ["Ŏ"]={ "O","̆" },
+ ["ŏ"]={ "o","̆" },
+ ["Ő"]={ "O","̋" },
+ ["ő"]={ "o","̋" },
+ ["Ŕ"]={ "R","́" },
+ ["ŕ"]={ "r","́" },
+ ["Ŗ"]={ "R","̧" },
+ ["ŗ"]={ "r","̧" },
+ ["Ř"]={ "R","̌" },
+ ["ř"]={ "r","̌" },
+ ["Ś"]={ "S","́" },
+ ["ś"]={ "s","́" },
+ ["Ŝ"]={ "S","̂" },
+ ["ŝ"]={ "s","̂" },
+ ["Ş"]={ "S","̧" },
+ ["ş"]={ "s","̧" },
+ ["Š"]={ "S","̌" },
+ ["š"]={ "s","̌" },
+ ["Ţ"]={ "T","̧" },
+ ["ţ"]={ "t","̧" },
+ ["Ť"]={ "T","̌" },
+ ["ť"]={ "t","̌" },
+ ["Ũ"]={ "U","̃" },
+ ["ũ"]={ "u","̃" },
+ ["Ū"]={ "U","̄" },
+ ["ū"]={ "u","̄" },
+ ["Ŭ"]={ "U","̆" },
+ ["ŭ"]={ "u","̆" },
+ ["Ů"]={ "U","̊" },
+ ["ů"]={ "u","̊" },
+ ["Ű"]={ "U","̋" },
+ ["ű"]={ "u","̋" },
+ ["Ų"]={ "U","̨" },
+ ["ų"]={ "u","̨" },
+ ["Ŵ"]={ "W","̂" },
+ ["ŵ"]={ "w","̂" },
+ ["Ŷ"]={ "Y","̂" },
+ ["ŷ"]={ "y","̂" },
+ ["Ÿ"]={ "Y","̈" },
+ ["Ź"]={ "Z","́" },
+ ["ź"]={ "z","́" },
+ ["Ż"]={ "Z","̇" },
+ ["ż"]={ "z","̇" },
+ ["Ž"]={ "Z","̌" },
+ ["ž"]={ "z","̌" },
+ ["Ơ"]={ "O","̛" },
+ ["ơ"]={ "o","̛" },
+ ["Ư"]={ "U","̛" },
+ ["ư"]={ "u","̛" },
+ ["Ǎ"]={ "A","̌" },
+ ["ǎ"]={ "a","̌" },
+ ["Ǐ"]={ "I","̌" },
+ ["ǐ"]={ "i","̌" },
+ ["Ǒ"]={ "O","̌" },
+ ["ǒ"]={ "o","̌" },
+ ["Ǔ"]={ "U","̌" },
+ ["ǔ"]={ "u","̌" },
+ ["Ǖ"]={ "Ü","̄" },
+ ["ǖ"]={ "ü","̄" },
+ ["Ǘ"]={ "Ü","́" },
+ ["ǘ"]={ "ü","́" },
+ ["Ǚ"]={ "Ü","̌" },
+ ["ǚ"]={ "ü","̌" },
+ ["Ǜ"]={ "Ü","̀" },
+ ["ǜ"]={ "ü","̀" },
+ ["Ǟ"]={ "Ä","̄" },
+ ["ǟ"]={ "ä","̄" },
+ ["Ǡ"]={ "Ȧ","̄" },
+ ["ǡ"]={ "ȧ","̄" },
+ ["Ǣ"]={ "Æ","̄" },
+ ["ǣ"]={ "æ","̄" },
+ ["Ǧ"]={ "G","̌" },
+ ["ǧ"]={ "g","̌" },
+ ["Ǩ"]={ "K","̌" },
+ ["ǩ"]={ "k","̌" },
+ ["Ǫ"]={ "O","̨" },
+ ["ǫ"]={ "o","̨" },
+ ["Ǭ"]={ "Ǫ","̄" },
+ ["ǭ"]={ "ǫ","̄" },
+ ["Ǯ"]={ "Ʒ","̌" },
+ ["ǯ"]={ "ʒ","̌" },
+ ["ǰ"]={ "j","̌" },
+ ["Ǵ"]={ "G","́" },
+ ["ǵ"]={ "g","́" },
+ ["Ǹ"]={ "N","̀" },
+ ["ǹ"]={ "n","̀" },
+ ["Ǻ"]={ "Å","́" },
+ ["ǻ"]={ "å","́" },
+ ["Ǽ"]={ "Æ","́" },
+ ["ǽ"]={ "æ","́" },
+ ["Ǿ"]={ "Ø","́" },
+ ["ǿ"]={ "ø","́" },
+ ["Ȁ"]={ "A","̏" },
+ ["ȁ"]={ "a","̏" },
+ ["Ȃ"]={ "A","̑" },
+ ["ȃ"]={ "a","̑" },
+ ["Ȅ"]={ "E","̏" },
+ ["ȅ"]={ "e","̏" },
+ ["Ȇ"]={ "E","̑" },
+ ["ȇ"]={ "e","̑" },
+ ["Ȉ"]={ "I","̏" },
+ ["ȉ"]={ "i","̏" },
+ ["Ȋ"]={ "I","̑" },
+ ["ȋ"]={ "i","̑" },
+ ["Ȍ"]={ "O","̏" },
+ ["ȍ"]={ "o","̏" },
+ ["Ȏ"]={ "O","̑" },
+ ["ȏ"]={ "o","̑" },
+ ["Ȑ"]={ "R","̏" },
+ ["ȑ"]={ "r","̏" },
+ ["Ȓ"]={ "R","̑" },
+ ["ȓ"]={ "r","̑" },
+ ["Ȕ"]={ "U","̏" },
+ ["ȕ"]={ "u","̏" },
+ ["Ȗ"]={ "U","̑" },
+ ["ȗ"]={ "u","̑" },
+ ["Ș"]={ "S","̦" },
+ ["ș"]={ "s","̦" },
+ ["Ț"]={ "T","̦" },
+ ["ț"]={ "t","̦" },
+ ["Ȟ"]={ "H","̌" },
+ ["ȟ"]={ "h","̌" },
+ ["Ȧ"]={ "A","̇" },
+ ["ȧ"]={ "a","̇" },
+ ["Ȩ"]={ "E","̧" },
+ ["ȩ"]={ "e","̧" },
+ ["Ȫ"]={ "Ö","̄" },
+ ["ȫ"]={ "ö","̄" },
+ ["Ȭ"]={ "Õ","̄" },
+ ["ȭ"]={ "õ","̄" },
+ ["Ȯ"]={ "O","̇" },
+ ["ȯ"]={ "o","̇" },
+ ["Ȱ"]={ "Ȯ","̄" },
+ ["ȱ"]={ "ȯ","̄" },
+ ["Ȳ"]={ "Y","̄" },
+ ["ȳ"]={ "y","̄" },
+ ["̈́"]={ "̈","́" },
+ ["΅"]={ "¨","́" },
+ ["Ά"]={ "Α","́" },
+ ["Έ"]={ "Ε","́" },
+ ["Ή"]={ "Η","́" },
+ ["Ί"]={ "Ι","́" },
+ ["Ό"]={ "Ο","́" },
+ ["Ύ"]={ "Υ","́" },
+ ["Ώ"]={ "Ω","́" },
+ ["ΐ"]={ "ϊ","́" },
+ ["Ϊ"]={ "Ι","̈" },
+ ["Ϋ"]={ "Υ","̈" },
+ ["ά"]={ "α","́" },
+ ["έ"]={ "ε","́" },
+ ["ή"]={ "η","́" },
+ ["ί"]={ "ι","́" },
+ ["ΰ"]={ "ϋ","́" },
+ ["ϊ"]={ "ι","̈" },
+ ["ϋ"]={ "υ","̈" },
+ ["ό"]={ "ο","́" },
+ ["ύ"]={ "υ","́" },
+ ["ώ"]={ "ω","́" },
+ ["ϓ"]={ "ϒ","́" },
+ ["ϔ"]={ "ϒ","̈" },
+ ["Ѐ"]={ "Е","̀" },
+ ["Ё"]={ "Е","̈" },
+ ["Ѓ"]={ "Г","́" },
+ ["Ї"]={ "І","̈" },
+ ["Ќ"]={ "К","́" },
+ ["Ѝ"]={ "И","̀" },
+ ["Ў"]={ "У","̆" },
+ ["Й"]={ "И","̆" },
+ ["й"]={ "и","̆" },
+ ["ѐ"]={ "е","̀" },
+ ["ё"]={ "е","̈" },
+ ["ѓ"]={ "г","́" },
+ ["ї"]={ "і","̈" },
+ ["ќ"]={ "к","́" },
+ ["ѝ"]={ "и","̀" },
+ ["ў"]={ "у","̆" },
+ ["Ѷ"]={ "Ѵ","̏" },
+ ["ѷ"]={ "ѵ","̏" },
+ ["Ӂ"]={ "Ж","̆" },
+ ["ӂ"]={ "ж","̆" },
+ ["Ӑ"]={ "А","̆" },
+ ["ӑ"]={ "а","̆" },
+ ["Ӓ"]={ "А","̈" },
+ ["ӓ"]={ "а","̈" },
+ ["Ӗ"]={ "Е","̆" },
+ ["ӗ"]={ "е","̆" },
+ ["Ӛ"]={ "Ә","̈" },
+ ["ӛ"]={ "ә","̈" },
+ ["Ӝ"]={ "Ж","̈" },
+ ["ӝ"]={ "ж","̈" },
+ ["Ӟ"]={ "З","̈" },
+ ["ӟ"]={ "з","̈" },
+ ["Ӣ"]={ "И","̄" },
+ ["ӣ"]={ "и","̄" },
+ ["Ӥ"]={ "И","̈" },
+ ["ӥ"]={ "и","̈" },
+ ["Ӧ"]={ "О","̈" },
+ ["ӧ"]={ "о","̈" },
+ ["Ӫ"]={ "Ө","̈" },
+ ["ӫ"]={ "ө","̈" },
+ ["Ӭ"]={ "Э","̈" },
+ ["ӭ"]={ "э","̈" },
+ ["Ӯ"]={ "У","̄" },
+ ["ӯ"]={ "у","̄" },
+ ["Ӱ"]={ "У","̈" },
+ ["ӱ"]={ "у","̈" },
+ ["Ӳ"]={ "У","̋" },
+ ["ӳ"]={ "у","̋" },
+ ["Ӵ"]={ "Ч","̈" },
+ ["ӵ"]={ "ч","̈" },
+ ["Ӹ"]={ "Ы","̈" },
+ ["ӹ"]={ "ы","̈" },
+ ["آ"]={ "ا","ٓ" },
+ ["أ"]={ "ا","ٔ" },
+ ["ؤ"]={ "و","ٔ" },
+ ["إ"]={ "ا","ٕ" },
+ ["ئ"]={ "ي","ٔ" },
+ ["ۀ"]={ "ە","ٔ" },
+ ["ۂ"]={ "ہ","ٔ" },
+ ["ۓ"]={ "ے","ٔ" },
+ ["ऩ"]={ "न","़" },
+ ["ऱ"]={ "र","़" },
+ ["ऴ"]={ "ळ","़" },
+ ["क़"]={ "क","़" },
+ ["ख़"]={ "ख","़" },
+ ["ग़"]={ "ग","़" },
+ ["ज़"]={ "ज","़" },
+ ["ड़"]={ "ड","़" },
+ ["ढ़"]={ "ढ","़" },
+ ["फ़"]={ "फ","़" },
+ ["य़"]={ "य","़" },
+ ["ো"]={ "ে","া" },
+ ["ৌ"]={ "ে","ৗ" },
+ ["ড়"]={ "ড","়" },
+ ["ঢ়"]={ "ঢ","়" },
+ ["য়"]={ "য","়" },
+ ["ਲ਼"]={ "ਲ","਼" },
+ ["ਸ਼"]={ "ਸ","਼" },
+ ["ਖ਼"]={ "ਖ","਼" },
+ ["ਗ਼"]={ "ਗ","਼" },
+ ["ਜ਼"]={ "ਜ","਼" },
+ ["ਫ਼"]={ "ਫ","਼" },
+ ["ୈ"]={ "େ","ୖ" },
+ ["ୋ"]={ "େ","ା" },
+ ["ୌ"]={ "େ","ୗ" },
+ ["ଡ଼"]={ "ଡ","଼" },
+ ["ଢ଼"]={ "ଢ","଼" },
+ ["ஔ"]={ "ஒ","ௗ" },
+ ["ொ"]={ "ெ","ா" },
+ ["ோ"]={ "ே","ா" },
+ ["ௌ"]={ "ெ","ௗ" },
+ ["ై"]={ "ె","ౖ" },
+ ["ೀ"]={ "ಿ","ೕ" },
+ ["ೇ"]={ "ೆ","ೕ" },
+ ["ೈ"]={ "ೆ","ೖ" },
+ ["ೊ"]={ "ೆ","ೂ" },
+ ["ೋ"]={ "ೊ","ೕ" },
+ ["ൊ"]={ "െ","ാ" },
+ ["ോ"]={ "േ","ാ" },
+ ["ൌ"]={ "െ","ൗ" },
+ ["ේ"]={ "ෙ","්" },
+ ["ො"]={ "ෙ","ා" },
+ ["ෝ"]={ "ො","්" },
+ ["ෞ"]={ "ෙ","ෟ" },
+ ["གྷ"]={ "ག","ྷ" },
+ ["ཌྷ"]={ "ཌ","ྷ" },
+ ["དྷ"]={ "ད","ྷ" },
+ ["བྷ"]={ "བ","ྷ" },
+ ["ཛྷ"]={ "ཛ","ྷ" },
+ ["ཀྵ"]={ "ཀ","ྵ" },
+ ["ཱི"]={ "ཱ","ི" },
+ ["ཱུ"]={ "ཱ","ུ" },
+ ["ྲྀ"]={ "ྲ","ྀ" },
+ ["ླྀ"]={ "ླ","ྀ" },
+ ["ཱྀ"]={ "ཱ","ྀ" },
+ ["ྒྷ"]={ "ྒ","ྷ" },
+ ["ྜྷ"]={ "ྜ","ྷ" },
+ ["ྡྷ"]={ "ྡ","ྷ" },
+ ["ྦྷ"]={ "ྦ","ྷ" },
+ ["ྫྷ"]={ "ྫ","ྷ" },
+ ["ྐྵ"]={ "ྐ","ྵ" },
+ ["ဦ"]={ "ဥ","ီ" },
+ ["ᬆ"]={ "ᬅ","ᬵ" },
+ ["ᬈ"]={ "ᬇ","ᬵ" },
+ ["ᬊ"]={ "ᬉ","ᬵ" },
+ ["ᬌ"]={ "ᬋ","ᬵ" },
+ ["ᬎ"]={ "ᬍ","ᬵ" },
+ ["ᬒ"]={ "ᬑ","ᬵ" },
+ ["ᬻ"]={ "ᬺ","ᬵ" },
+ ["ᬽ"]={ "ᬼ","ᬵ" },
+ ["ᭀ"]={ "ᬾ","ᬵ" },
+ ["ᭁ"]={ "ᬿ","ᬵ" },
+ ["ᭃ"]={ "ᭂ","ᬵ" },
+ ["Ḁ"]={ "A","̥" },
+ ["ḁ"]={ "a","̥" },
+ ["Ḃ"]={ "B","̇" },
+ ["ḃ"]={ "b","̇" },
+ ["Ḅ"]={ "B","̣" },
+ ["ḅ"]={ "b","̣" },
+ ["Ḇ"]={ "B","̱" },
+ ["ḇ"]={ "b","̱" },
+ ["Ḉ"]={ "Ç","́" },
+ ["ḉ"]={ "ç","́" },
+ ["Ḋ"]={ "D","̇" },
+ ["ḋ"]={ "d","̇" },
+ ["Ḍ"]={ "D","̣" },
+ ["ḍ"]={ "d","̣" },
+ ["Ḏ"]={ "D","̱" },
+ ["ḏ"]={ "d","̱" },
+ ["Ḑ"]={ "D","̧" },
+ ["ḑ"]={ "d","̧" },
+ ["Ḓ"]={ "D","̭" },
+ ["ḓ"]={ "d","̭" },
+ ["Ḕ"]={ "Ē","̀" },
+ ["ḕ"]={ "ē","̀" },
+ ["Ḗ"]={ "Ē","́" },
+ ["ḗ"]={ "ē","́" },
+ ["Ḙ"]={ "E","̭" },
+ ["ḙ"]={ "e","̭" },
+ ["Ḛ"]={ "E","̰" },
+ ["ḛ"]={ "e","̰" },
+ ["Ḝ"]={ "Ȩ","̆" },
+ ["ḝ"]={ "ȩ","̆" },
+ ["Ḟ"]={ "F","̇" },
+ ["ḟ"]={ "f","̇" },
+ ["Ḡ"]={ "G","̄" },
+ ["ḡ"]={ "g","̄" },
+ ["Ḣ"]={ "H","̇" },
+ ["ḣ"]={ "h","̇" },
+ ["Ḥ"]={ "H","̣" },
+ ["ḥ"]={ "h","̣" },
+ ["Ḧ"]={ "H","̈" },
+ ["ḧ"]={ "h","̈" },
+ ["Ḩ"]={ "H","̧" },
+ ["ḩ"]={ "h","̧" },
+ ["Ḫ"]={ "H","̮" },
+ ["ḫ"]={ "h","̮" },
+ ["Ḭ"]={ "I","̰" },
+ ["ḭ"]={ "i","̰" },
+ ["Ḯ"]={ "Ï","́" },
+ ["ḯ"]={ "ï","́" },
+ ["Ḱ"]={ "K","́" },
+ ["ḱ"]={ "k","́" },
+ ["Ḳ"]={ "K","̣" },
+ ["ḳ"]={ "k","̣" },
+ ["Ḵ"]={ "K","̱" },
+ ["ḵ"]={ "k","̱" },
+ ["Ḷ"]={ "L","̣" },
+ ["ḷ"]={ "l","̣" },
+ ["Ḹ"]={ "Ḷ","̄" },
+ ["ḹ"]={ "ḷ","̄" },
+ ["Ḻ"]={ "L","̱" },
+ ["ḻ"]={ "l","̱" },
+ ["Ḽ"]={ "L","̭" },
+ ["ḽ"]={ "l","̭" },
+ ["Ḿ"]={ "M","́" },
+ ["ḿ"]={ "m","́" },
+ ["Ṁ"]={ "M","̇" },
+ ["ṁ"]={ "m","̇" },
+ ["Ṃ"]={ "M","̣" },
+ ["ṃ"]={ "m","̣" },
+ ["Ṅ"]={ "N","̇" },
+ ["ṅ"]={ "n","̇" },
+ ["Ṇ"]={ "N","̣" },
+ ["ṇ"]={ "n","̣" },
+ ["Ṉ"]={ "N","̱" },
+ ["ṉ"]={ "n","̱" },
+ ["Ṋ"]={ "N","̭" },
+ ["ṋ"]={ "n","̭" },
+ ["Ṍ"]={ "Õ","́" },
+ ["ṍ"]={ "õ","́" },
+ ["Ṏ"]={ "Õ","̈" },
+ ["ṏ"]={ "õ","̈" },
+ ["Ṑ"]={ "Ō","̀" },
+ ["ṑ"]={ "ō","̀" },
+ ["Ṓ"]={ "Ō","́" },
+ ["ṓ"]={ "ō","́" },
+ ["Ṕ"]={ "P","́" },
+ ["ṕ"]={ "p","́" },
+ ["Ṗ"]={ "P","̇" },
+ ["ṗ"]={ "p","̇" },
+ ["Ṙ"]={ "R","̇" },
+ ["ṙ"]={ "r","̇" },
+ ["Ṛ"]={ "R","̣" },
+ ["ṛ"]={ "r","̣" },
+ ["Ṝ"]={ "Ṛ","̄" },
+ ["ṝ"]={ "ṛ","̄" },
+ ["Ṟ"]={ "R","̱" },
+ ["ṟ"]={ "r","̱" },
+ ["Ṡ"]={ "S","̇" },
+ ["ṡ"]={ "s","̇" },
+ ["Ṣ"]={ "S","̣" },
+ ["ṣ"]={ "s","̣" },
+ ["Ṥ"]={ "Ś","̇" },
+ ["ṥ"]={ "ś","̇" },
+ ["Ṧ"]={ "Š","̇" },
+ ["ṧ"]={ "š","̇" },
+ ["Ṩ"]={ "Ṣ","̇" },
+ ["ṩ"]={ "ṣ","̇" },
+ ["Ṫ"]={ "T","̇" },
+ ["ṫ"]={ "t","̇" },
+ ["Ṭ"]={ "T","̣" },
+ ["ṭ"]={ "t","̣" },
+ ["Ṯ"]={ "T","̱" },
+ ["ṯ"]={ "t","̱" },
+ ["Ṱ"]={ "T","̭" },
+ ["ṱ"]={ "t","̭" },
+ ["Ṳ"]={ "U","̤" },
+ ["ṳ"]={ "u","̤" },
+ ["Ṵ"]={ "U","̰" },
+ ["ṵ"]={ "u","̰" },
+ ["Ṷ"]={ "U","̭" },
+ ["ṷ"]={ "u","̭" },
+ ["Ṹ"]={ "Ũ","́" },
+ ["ṹ"]={ "ũ","́" },
+ ["Ṻ"]={ "Ū","̈" },
+ ["ṻ"]={ "ū","̈" },
+ ["Ṽ"]={ "V","̃" },
+ ["ṽ"]={ "v","̃" },
+ ["Ṿ"]={ "V","̣" },
+ ["ṿ"]={ "v","̣" },
+ ["Ẁ"]={ "W","̀" },
+ ["ẁ"]={ "w","̀" },
+ ["Ẃ"]={ "W","́" },
+ ["ẃ"]={ "w","́" },
+ ["Ẅ"]={ "W","̈" },
+ ["ẅ"]={ "w","̈" },
+ ["Ẇ"]={ "W","̇" },
+ ["ẇ"]={ "w","̇" },
+ ["Ẉ"]={ "W","̣" },
+ ["ẉ"]={ "w","̣" },
+ ["Ẋ"]={ "X","̇" },
+ ["ẋ"]={ "x","̇" },
+ ["Ẍ"]={ "X","̈" },
+ ["ẍ"]={ "x","̈" },
+ ["Ẏ"]={ "Y","̇" },
+ ["ẏ"]={ "y","̇" },
+ ["Ẑ"]={ "Z","̂" },
+ ["ẑ"]={ "z","̂" },
+ ["Ẓ"]={ "Z","̣" },
+ ["ẓ"]={ "z","̣" },
+ ["Ẕ"]={ "Z","̱" },
+ ["ẕ"]={ "z","̱" },
+ ["ẖ"]={ "h","̱" },
+ ["ẗ"]={ "t","̈" },
+ ["ẘ"]={ "w","̊" },
+ ["ẙ"]={ "y","̊" },
+ ["ẛ"]={ "ſ","̇" },
+ ["Ạ"]={ "A","̣" },
+ ["ạ"]={ "a","̣" },
+ ["Ả"]={ "A","̉" },
+ ["ả"]={ "a","̉" },
+ ["Ấ"]={ "Â","́" },
+ ["ấ"]={ "â","́" },
+ ["Ầ"]={ "Â","̀" },
+ ["ầ"]={ "â","̀" },
+ ["Ẩ"]={ "Â","̉" },
+ ["ẩ"]={ "â","̉" },
+ ["Ẫ"]={ "Â","̃" },
+ ["ẫ"]={ "â","̃" },
+ ["Ậ"]={ "Ạ","̂" },
+ ["ậ"]={ "ạ","̂" },
+ ["Ắ"]={ "Ă","́" },
+ ["ắ"]={ "ă","́" },
+ ["Ằ"]={ "Ă","̀" },
+ ["ằ"]={ "ă","̀" },
+ ["Ẳ"]={ "Ă","̉" },
+ ["ẳ"]={ "ă","̉" },
+ ["Ẵ"]={ "Ă","̃" },
+ ["ẵ"]={ "ă","̃" },
+ ["Ặ"]={ "Ạ","̆" },
+ ["ặ"]={ "ạ","̆" },
+ ["Ẹ"]={ "E","̣" },
+ ["ẹ"]={ "e","̣" },
+ ["Ẻ"]={ "E","̉" },
+ ["ẻ"]={ "e","̉" },
+ ["Ẽ"]={ "E","̃" },
+ ["ẽ"]={ "e","̃" },
+ ["Ế"]={ "Ê","́" },
+ ["ế"]={ "ê","́" },
+ ["Ề"]={ "Ê","̀" },
+ ["ề"]={ "ê","̀" },
+ ["Ể"]={ "Ê","̉" },
+ ["ể"]={ "ê","̉" },
+ ["Ễ"]={ "Ê","̃" },
+ ["ễ"]={ "ê","̃" },
+ ["Ệ"]={ "Ẹ","̂" },
+ ["ệ"]={ "ẹ","̂" },
+ ["Ỉ"]={ "I","̉" },
+ ["ỉ"]={ "i","̉" },
+ ["Ị"]={ "I","̣" },
+ ["ị"]={ "i","̣" },
+ ["Ọ"]={ "O","̣" },
+ ["ọ"]={ "o","̣" },
+ ["Ỏ"]={ "O","̉" },
+ ["ỏ"]={ "o","̉" },
+ ["Ố"]={ "Ô","́" },
+ ["ố"]={ "ô","́" },
+ ["Ồ"]={ "Ô","̀" },
+ ["ồ"]={ "ô","̀" },
+ ["Ổ"]={ "Ô","̉" },
+ ["ổ"]={ "ô","̉" },
+ ["Ỗ"]={ "Ô","̃" },
+ ["ỗ"]={ "ô","̃" },
+ ["Ộ"]={ "Ọ","̂" },
+ ["ộ"]={ "ọ","̂" },
+ ["Ớ"]={ "Ơ","́" },
+ ["ớ"]={ "ơ","́" },
+ ["Ờ"]={ "Ơ","̀" },
+ ["ờ"]={ "ơ","̀" },
+ ["Ở"]={ "Ơ","̉" },
+ ["ở"]={ "ơ","̉" },
+ ["Ỡ"]={ "Ơ","̃" },
+ ["ỡ"]={ "ơ","̃" },
+ ["Ợ"]={ "Ơ","̣" },
+ ["ợ"]={ "ơ","̣" },
+ ["Ụ"]={ "U","̣" },
+ ["ụ"]={ "u","̣" },
+ ["Ủ"]={ "U","̉" },
+ ["ủ"]={ "u","̉" },
+ ["Ứ"]={ "Ư","́" },
+ ["ứ"]={ "ư","́" },
+ ["Ừ"]={ "Ư","̀" },
+ ["ừ"]={ "ư","̀" },
+ ["Ử"]={ "Ư","̉" },
+ ["ử"]={ "ư","̉" },
+ ["Ữ"]={ "Ư","̃" },
+ ["ữ"]={ "ư","̃" },
+ ["Ự"]={ "Ư","̣" },
+ ["ự"]={ "ư","̣" },
+ ["Ỳ"]={ "Y","̀" },
+ ["ỳ"]={ "y","̀" },
+ ["Ỵ"]={ "Y","̣" },
+ ["ỵ"]={ "y","̣" },
+ ["Ỷ"]={ "Y","̉" },
+ ["ỷ"]={ "y","̉" },
+ ["Ỹ"]={ "Y","̃" },
+ ["ỹ"]={ "y","̃" },
+ ["ἀ"]={ "α","̓" },
+ ["ἁ"]={ "α","̔" },
+ ["ἂ"]={ "ἀ","̀" },
+ ["ἃ"]={ "ἁ","̀" },
+ ["ἄ"]={ "ἀ","́" },
+ ["ἅ"]={ "ἁ","́" },
+ ["ἆ"]={ "ἀ","͂" },
+ ["ἇ"]={ "ἁ","͂" },
+ ["Ἀ"]={ "Α","̓" },
+ ["Ἁ"]={ "Α","̔" },
+ ["Ἂ"]={ "Ἀ","̀" },
+ ["Ἃ"]={ "Ἁ","̀" },
+ ["Ἄ"]={ "Ἀ","́" },
+ ["Ἅ"]={ "Ἁ","́" },
+ ["Ἆ"]={ "Ἀ","͂" },
+ ["Ἇ"]={ "Ἁ","͂" },
+ ["ἐ"]={ "ε","̓" },
+ ["ἑ"]={ "ε","̔" },
+ ["ἒ"]={ "ἐ","̀" },
+ ["ἓ"]={ "ἑ","̀" },
+ ["ἔ"]={ "ἐ","́" },
+ ["ἕ"]={ "ἑ","́" },
+ ["Ἐ"]={ "Ε","̓" },
+ ["Ἑ"]={ "Ε","̔" },
+ ["Ἒ"]={ "Ἐ","̀" },
+ ["Ἓ"]={ "Ἑ","̀" },
+ ["Ἔ"]={ "Ἐ","́" },
+ ["Ἕ"]={ "Ἑ","́" },
+ ["ἠ"]={ "η","̓" },
+ ["ἡ"]={ "η","̔" },
+ ["ἢ"]={ "ἠ","̀" },
+ ["ἣ"]={ "ἡ","̀" },
+ ["ἤ"]={ "ἠ","́" },
+ ["ἥ"]={ "ἡ","́" },
+ ["ἦ"]={ "ἠ","͂" },
+ ["ἧ"]={ "ἡ","͂" },
+ ["Ἠ"]={ "Η","̓" },
+ ["Ἡ"]={ "Η","̔" },
+ ["Ἢ"]={ "Ἠ","̀" },
+ ["Ἣ"]={ "Ἡ","̀" },
+ ["Ἤ"]={ "Ἠ","́" },
+ ["Ἥ"]={ "Ἡ","́" },
+ ["Ἦ"]={ "Ἠ","͂" },
+ ["Ἧ"]={ "Ἡ","͂" },
+ ["ἰ"]={ "ι","̓" },
+ ["ἱ"]={ "ι","̔" },
+ ["ἲ"]={ "ἰ","̀" },
+ ["ἳ"]={ "ἱ","̀" },
+ ["ἴ"]={ "ἰ","́" },
+ ["ἵ"]={ "ἱ","́" },
+ ["ἶ"]={ "ἰ","͂" },
+ ["ἷ"]={ "ἱ","͂" },
+ ["Ἰ"]={ "Ι","̓" },
+ ["Ἱ"]={ "Ι","̔" },
+ ["Ἲ"]={ "Ἰ","̀" },
+ ["Ἳ"]={ "Ἱ","̀" },
+ ["Ἴ"]={ "Ἰ","́" },
+ ["Ἵ"]={ "Ἱ","́" },
+ ["Ἶ"]={ "Ἰ","͂" },
+ ["Ἷ"]={ "Ἱ","͂" },
+ ["ὀ"]={ "ο","̓" },
+ ["ὁ"]={ "ο","̔" },
+ ["ὂ"]={ "ὀ","̀" },
+ ["ὃ"]={ "ὁ","̀" },
+ ["ὄ"]={ "ὀ","́" },
+ ["ὅ"]={ "ὁ","́" },
+ ["Ὀ"]={ "Ο","̓" },
+ ["Ὁ"]={ "Ο","̔" },
+ ["Ὂ"]={ "Ὀ","̀" },
+ ["Ὃ"]={ "Ὁ","̀" },
+ ["Ὄ"]={ "Ὀ","́" },
+ ["Ὅ"]={ "Ὁ","́" },
+ ["ὐ"]={ "υ","̓" },
+ ["ὑ"]={ "υ","̔" },
+ ["ὒ"]={ "ὐ","̀" },
+ ["ὓ"]={ "ὑ","̀" },
+ ["ὔ"]={ "ὐ","́" },
+ ["ὕ"]={ "ὑ","́" },
+ ["ὖ"]={ "ὐ","͂" },
+ ["ὗ"]={ "ὑ","͂" },
+ ["Ὑ"]={ "Υ","̔" },
+ ["Ὓ"]={ "Ὑ","̀" },
+ ["Ὕ"]={ "Ὑ","́" },
+ ["Ὗ"]={ "Ὑ","͂" },
+ ["ὠ"]={ "ω","̓" },
+ ["ὡ"]={ "ω","̔" },
+ ["ὢ"]={ "ὠ","̀" },
+ ["ὣ"]={ "ὡ","̀" },
+ ["ὤ"]={ "ὠ","́" },
+ ["ὥ"]={ "ὡ","́" },
+ ["ὦ"]={ "ὠ","͂" },
+ ["ὧ"]={ "ὡ","͂" },
+ ["Ὠ"]={ "Ω","̓" },
+ ["Ὡ"]={ "Ω","̔" },
+ ["Ὢ"]={ "Ὠ","̀" },
+ ["Ὣ"]={ "Ὡ","̀" },
+ ["Ὤ"]={ "Ὠ","́" },
+ ["Ὥ"]={ "Ὡ","́" },
+ ["Ὦ"]={ "Ὠ","͂" },
+ ["Ὧ"]={ "Ὡ","͂" },
+ ["ὰ"]={ "α","̀" },
+ ["ὲ"]={ "ε","̀" },
+ ["ὴ"]={ "η","̀" },
+ ["ὶ"]={ "ι","̀" },
+ ["ὸ"]={ "ο","̀" },
+ ["ὺ"]={ "υ","̀" },
+ ["ὼ"]={ "ω","̀" },
+ ["ᾀ"]={ "ἀ","ͅ" },
+ ["ᾁ"]={ "ἁ","ͅ" },
+ ["ᾂ"]={ "ἂ","ͅ" },
+ ["ᾃ"]={ "ἃ","ͅ" },
+ ["ᾄ"]={ "ἄ","ͅ" },
+ ["ᾅ"]={ "ἅ","ͅ" },
+ ["ᾆ"]={ "ἆ","ͅ" },
+ ["ᾇ"]={ "ἇ","ͅ" },
+ ["ᾈ"]={ "Ἀ","ͅ" },
+ ["ᾉ"]={ "Ἁ","ͅ" },
+ ["ᾊ"]={ "Ἂ","ͅ" },
+ ["ᾋ"]={ "Ἃ","ͅ" },
+ ["ᾌ"]={ "Ἄ","ͅ" },
+ ["ᾍ"]={ "Ἅ","ͅ" },
+ ["ᾎ"]={ "Ἆ","ͅ" },
+ ["ᾏ"]={ "Ἇ","ͅ" },
+ ["ᾐ"]={ "ἠ","ͅ" },
+ ["ᾑ"]={ "ἡ","ͅ" },
+ ["ᾒ"]={ "ἢ","ͅ" },
+ ["ᾓ"]={ "ἣ","ͅ" },
+ ["ᾔ"]={ "ἤ","ͅ" },
+ ["ᾕ"]={ "ἥ","ͅ" },
+ ["ᾖ"]={ "ἦ","ͅ" },
+ ["ᾗ"]={ "ἧ","ͅ" },
+ ["ᾘ"]={ "Ἠ","ͅ" },
+ ["ᾙ"]={ "Ἡ","ͅ" },
+ ["ᾚ"]={ "Ἢ","ͅ" },
+ ["ᾛ"]={ "Ἣ","ͅ" },
+ ["ᾜ"]={ "Ἤ","ͅ" },
+ ["ᾝ"]={ "Ἥ","ͅ" },
+ ["ᾞ"]={ "Ἦ","ͅ" },
+ ["ᾟ"]={ "Ἧ","ͅ" },
+ ["ᾠ"]={ "ὠ","ͅ" },
+ ["ᾡ"]={ "ὡ","ͅ" },
+ ["ᾢ"]={ "ὢ","ͅ" },
+ ["ᾣ"]={ "ὣ","ͅ" },
+ ["ᾤ"]={ "ὤ","ͅ" },
+ ["ᾥ"]={ "ὥ","ͅ" },
+ ["ᾦ"]={ "ὦ","ͅ" },
+ ["ᾧ"]={ "ὧ","ͅ" },
+ ["ᾨ"]={ "Ὠ","ͅ" },
+ ["ᾩ"]={ "Ὡ","ͅ" },
+ ["ᾪ"]={ "Ὢ","ͅ" },
+ ["ᾫ"]={ "Ὣ","ͅ" },
+ ["ᾬ"]={ "Ὤ","ͅ" },
+ ["ᾭ"]={ "Ὥ","ͅ" },
+ ["ᾮ"]={ "Ὦ","ͅ" },
+ ["ᾯ"]={ "Ὧ","ͅ" },
+ ["ᾰ"]={ "α","̆" },
+ ["ᾱ"]={ "α","̄" },
+ ["ᾲ"]={ "ὰ","ͅ" },
+ ["ᾳ"]={ "α","ͅ" },
+ ["ᾴ"]={ "ά","ͅ" },
+ ["ᾶ"]={ "α","͂" },
+ ["ᾷ"]={ "ᾶ","ͅ" },
+ ["Ᾰ"]={ "Α","̆" },
+ ["Ᾱ"]={ "Α","̄" },
+ ["Ὰ"]={ "Α","̀" },
+ ["ᾼ"]={ "Α","ͅ" },
+ ["῁"]={ "¨","͂" },
+ ["ῂ"]={ "ὴ","ͅ" },
+ ["ῃ"]={ "η","ͅ" },
+ ["ῄ"]={ "ή","ͅ" },
+ ["ῆ"]={ "η","͂" },
+ ["ῇ"]={ "ῆ","ͅ" },
+ ["Ὲ"]={ "Ε","̀" },
+ ["Ὴ"]={ "Η","̀" },
+ ["ῌ"]={ "Η","ͅ" },
+ ["῍"]={ "᾿","̀" },
+ ["῎"]={ "᾿","́" },
+ ["῏"]={ "᾿","͂" },
+ ["ῐ"]={ "ι","̆" },
+ ["ῑ"]={ "ι","̄" },
+ ["ῒ"]={ "ϊ","̀" },
+ ["ῖ"]={ "ι","͂" },
+ ["ῗ"]={ "ϊ","͂" },
+ ["Ῐ"]={ "Ι","̆" },
+ ["Ῑ"]={ "Ι","̄" },
+ ["Ὶ"]={ "Ι","̀" },
+ ["῝"]={ "῾","̀" },
+ ["῞"]={ "῾","́" },
+ ["῟"]={ "῾","͂" },
+ ["ῠ"]={ "υ","̆" },
+ ["ῡ"]={ "υ","̄" },
+ ["ῢ"]={ "ϋ","̀" },
+ ["ῤ"]={ "ρ","̓" },
+ ["ῥ"]={ "ρ","̔" },
+ ["ῦ"]={ "υ","͂" },
+ ["ῧ"]={ "ϋ","͂" },
+ ["Ῠ"]={ "Υ","̆" },
+ ["Ῡ"]={ "Υ","̄" },
+ ["Ὺ"]={ "Υ","̀" },
+ ["Ῥ"]={ "Ρ","̔" },
+ ["῭"]={ "¨","̀" },
+ ["ῲ"]={ "ὼ","ͅ" },
+ ["ῳ"]={ "ω","ͅ" },
+ ["ῴ"]={ "ώ","ͅ" },
+ ["ῶ"]={ "ω","͂" },
+ ["ῷ"]={ "ῶ","ͅ" },
+ ["Ὸ"]={ "Ο","̀" },
+ ["Ὼ"]={ "Ω","̀" },
+ ["ῼ"]={ "Ω","ͅ" },
+ ["↚"]={ "←","̸" },
+ ["↛"]={ "→","̸" },
+ ["↮"]={ "↔","̸" },
+ ["⇍"]={ "⇐","̸" },
+ ["⇎"]={ "⇔","̸" },
+ ["⇏"]={ "⇒","̸" },
+ ["∄"]={ "∃","̸" },
+ ["∉"]={ "∈","̸" },
+ ["∌"]={ "∋","̸" },
+ ["∤"]={ "∣","̸" },
+ ["∦"]={ "∥","̸" },
+ ["≁"]={ "∼","̸" },
+ ["≄"]={ "≃","̸" },
+ ["≇"]={ "≅","̸" },
+ ["≉"]={ "≈","̸" },
+ ["≠"]={ "=","̸" },
+ ["≢"]={ "≡","̸" },
+ ["≭"]={ "≍","̸" },
+ ["≮"]={ "<","̸" },
+ ["≯"]={ ">","̸" },
+ ["≰"]={ "≤","̸" },
+ ["≱"]={ "≥","̸" },
+ ["≴"]={ "≲","̸" },
+ ["≵"]={ "≳","̸" },
+ ["≸"]={ "≶","̸" },
+ ["≹"]={ "≷","̸" },
+ ["⊀"]={ "≺","̸" },
+ ["⊁"]={ "≻","̸" },
+ ["⊄"]={ "⊂","̸" },
+ ["⊅"]={ "⊃","̸" },
+ ["⊈"]={ "⊆","̸" },
+ ["⊉"]={ "⊇","̸" },
+ ["⊬"]={ "⊢","̸" },
+ ["⊭"]={ "⊨","̸" },
+ ["⊮"]={ "⊩","̸" },
+ ["⊯"]={ "⊫","̸" },
+ ["⋠"]={ "≼","̸" },
+ ["⋡"]={ "≽","̸" },
+ ["⋢"]={ "⊑","̸" },
+ ["⋣"]={ "⊒","̸" },
+ ["⋪"]={ "⊲","̸" },
+ ["⋫"]={ "⊳","̸" },
+ ["⋬"]={ "⊴","̸" },
+ ["⋭"]={ "⊵","̸" },
+ ["⫝̸"]={ "⫝","̸" },
+ ["が"]={ "か","゙" },
+ ["ぎ"]={ "き","゙" },
+ ["ぐ"]={ "く","゙" },
+ ["げ"]={ "け","゙" },
+ ["ご"]={ "こ","゙" },
+ ["ざ"]={ "さ","゙" },
+ ["じ"]={ "し","゙" },
+ ["ず"]={ "す","゙" },
+ ["ぜ"]={ "せ","゙" },
+ ["ぞ"]={ "そ","゙" },
+ ["だ"]={ "た","゙" },
+ ["ぢ"]={ "ち","゙" },
+ ["づ"]={ "つ","゙" },
+ ["で"]={ "て","゙" },
+ ["ど"]={ "と","゙" },
+ ["ば"]={ "は","゙" },
+ ["ぱ"]={ "は","゚" },
+ ["び"]={ "ひ","゙" },
+ ["ぴ"]={ "ひ","゚" },
+ ["ぶ"]={ "ふ","゙" },
+ ["ぷ"]={ "ふ","゚" },
+ ["べ"]={ "へ","゙" },
+ ["ぺ"]={ "へ","゚" },
+ ["ぼ"]={ "ほ","゙" },
+ ["ぽ"]={ "ほ","゚" },
+ ["ゔ"]={ "う","゙" },
+ ["ゞ"]={ "ゝ","゙" },
+ ["ガ"]={ "カ","゙" },
+ ["ギ"]={ "キ","゙" },
+ ["グ"]={ "ク","゙" },
+ ["ゲ"]={ "ケ","゙" },
+ ["ゴ"]={ "コ","゙" },
+ ["ザ"]={ "サ","゙" },
+ ["ジ"]={ "シ","゙" },
+ ["ズ"]={ "ス","゙" },
+ ["ゼ"]={ "セ","゙" },
+ ["ゾ"]={ "ソ","゙" },
+ ["ダ"]={ "タ","゙" },
+ ["ヂ"]={ "チ","゙" },
+ ["ヅ"]={ "ツ","゙" },
+ ["デ"]={ "テ","゙" },
+ ["ド"]={ "ト","゙" },
+ ["バ"]={ "ハ","゙" },
+ ["パ"]={ "ハ","゚" },
+ ["ビ"]={ "ヒ","゙" },
+ ["ピ"]={ "ヒ","゚" },
+ ["ブ"]={ "フ","゙" },
+ ["プ"]={ "フ","゚" },
+ ["ベ"]={ "ヘ","゙" },
+ ["ペ"]={ "ヘ","゚" },
+ ["ボ"]={ "ホ","゙" },
+ ["ポ"]={ "ホ","゚" },
+ ["ヴ"]={ "ウ","゙" },
+ ["ヷ"]={ "ワ","゙" },
+ ["ヸ"]={ "ヰ","゙" },
+ ["ヹ"]={ "ヱ","゙" },
+ ["ヺ"]={ "ヲ","゙" },
+ ["ヾ"]={ "ヽ","゙" },
+ ["יִ"]={ "י","ִ" },
+ ["ײַ"]={ "ײ","ַ" },
+ ["שׁ"]={ "ש","ׁ" },
+ ["שׂ"]={ "ש","ׂ" },
+ ["שּׁ"]={ "שּ","ׁ" },
+ ["שּׂ"]={ "שּ","ׂ" },
+ ["אַ"]={ "א","ַ" },
+ ["אָ"]={ "א","ָ" },
+ ["אּ"]={ "א","ּ" },
+ ["בּ"]={ "ב","ּ" },
+ ["גּ"]={ "ג","ּ" },
+ ["דּ"]={ "ד","ּ" },
+ ["הּ"]={ "ה","ּ" },
+ ["וּ"]={ "ו","ּ" },
+ ["זּ"]={ "ז","ּ" },
+ ["טּ"]={ "ט","ּ" },
+ ["יּ"]={ "י","ּ" },
+ ["ךּ"]={ "ך","ּ" },
+ ["כּ"]={ "כ","ּ" },
+ ["לּ"]={ "ל","ּ" },
+ ["מּ"]={ "מ","ּ" },
+ ["נּ"]={ "נ","ּ" },
+ ["סּ"]={ "ס","ּ" },
+ ["ףּ"]={ "ף","ּ" },
+ ["פּ"]={ "פ","ּ" },
+ ["צּ"]={ "צ","ּ" },
+ ["קּ"]={ "ק","ּ" },
+ ["רּ"]={ "ר","ּ" },
+ ["שּ"]={ "ש","ּ" },
+ ["תּ"]={ "ת","ּ" },
+ ["וֹ"]={ "ו","ֹ" },
+ ["בֿ"]={ "ב","ֿ" },
+ ["כֿ"]={ "כ","ֿ" },
+ ["פֿ"]={ "פ","ֿ" },
+ ["𑂚"]={ "𑂙","𑂺" },
+ ["𑂜"]={ "𑂛","𑂺" },
+ ["𑂫"]={ "𑂥","𑂺" },
+ ["𑄮"]={ "𑄱","𑄧" },
+ ["𑄯"]={ "𑄲","𑄧" },
+ ["𑍋"]={ "𑍇","𑌾" },
+ ["𑍌"]={ "𑍇","𑍗" },
+ ["𑒻"]={ "𑒹","𑒺" },
+ ["𑒼"]={ "𑒹","𑒰" },
+ ["𑒾"]={ "𑒹","𑒽" },
+ ["𑖺"]={ "𑖸","𑖯" },
+ ["𑖻"]={ "𑖹","𑖯" },
+ ["𝅗𝅥"]={ "𝅗","𝅥" },
+ ["𝅘𝅥"]={ "𝅘","𝅥" },
+ ["𝅘𝅥𝅮"]={ "𝅘𝅥","𝅮" },
+ ["𝅘𝅥𝅯"]={ "𝅘𝅥","𝅯" },
+ ["𝅘𝅥𝅰"]={ "𝅘𝅥","𝅰" },
+ ["𝅘𝅥𝅱"]={ "𝅘𝅥","𝅱" },
+ ["𝅘𝅥𝅲"]={ "𝅘𝅥","𝅲" },
+ ["𝆹𝅥"]={ "𝆹","𝅥" },
+ ["𝆺𝅥"]={ "𝆺","𝅥" },
+ ["𝆹𝅥𝅮"]={ "𝆹𝅥","𝅮" },
+ ["𝆺𝅥𝅮"]={ "𝆺𝅥","𝅮" },
+ ["𝆹𝅥𝅯"]={ "𝆹𝅥","𝅯" },
+ ["𝆺𝅥𝅯"]={ "𝆺𝅥","𝅯" },
+ },
+ },
+ {
+ ["data"]={
+ ["À"]={ "A","̀" },
+ ["Á"]={ "A","́" },
+ ["Â"]={ "A","̂" },
+ ["Ã"]={ "A","̃" },
+ ["Ä"]={ "A","̈" },
+ ["Å"]={ "A","̊" },
+ ["Ç"]={ "C","̧" },
+ ["È"]={ "E","̀" },
+ ["É"]={ "E","́" },
+ ["Ê"]={ "E","̂" },
+ ["Ë"]={ "E","̈" },
+ ["Ì"]={ "I","̀" },
+ ["Í"]={ "I","́" },
+ ["Î"]={ "I","̂" },
+ ["Ï"]={ "I","̈" },
+ ["Ñ"]={ "N","̃" },
+ ["Ò"]={ "O","̀" },
+ ["Ó"]={ "O","́" },
+ ["Ô"]={ "O","̂" },
+ ["Õ"]={ "O","̃" },
+ ["Ö"]={ "O","̈" },
+ ["Ù"]={ "U","̀" },
+ ["Ú"]={ "U","́" },
+ ["Û"]={ "U","̂" },
+ ["Ü"]={ "U","̈" },
+ ["Ý"]={ "Y","́" },
+ ["à"]={ "a","̀" },
+ ["á"]={ "a","́" },
+ ["â"]={ "a","̂" },
+ ["ã"]={ "a","̃" },
+ ["ä"]={ "a","̈" },
+ ["å"]={ "a","̊" },
+ ["ç"]={ "c","̧" },
+ ["è"]={ "e","̀" },
+ ["é"]={ "e","́" },
+ ["ê"]={ "e","̂" },
+ ["ë"]={ "e","̈" },
+ ["ì"]={ "i","̀" },
+ ["í"]={ "i","́" },
+ ["î"]={ "i","̂" },
+ ["ï"]={ "i","̈" },
+ ["ñ"]={ "n","̃" },
+ ["ò"]={ "o","̀" },
+ ["ó"]={ "o","́" },
+ ["ô"]={ "o","̂" },
+ ["õ"]={ "o","̃" },
+ ["ö"]={ "o","̈" },
+ ["ù"]={ "u","̀" },
+ ["ú"]={ "u","́" },
+ ["û"]={ "u","̂" },
+ ["ü"]={ "u","̈" },
+ ["ý"]={ "y","́" },
+ ["ÿ"]={ "y","̈" },
+ ["Ā"]={ "A","̄" },
+ ["ā"]={ "a","̄" },
+ ["Ă"]={ "A","̆" },
+ ["ă"]={ "a","̆" },
+ ["Ą"]={ "A","̨" },
+ ["ą"]={ "a","̨" },
+ ["Ć"]={ "C","́" },
+ ["ć"]={ "c","́" },
+ ["Ĉ"]={ "C","̂" },
+ ["ĉ"]={ "c","̂" },
+ ["Ċ"]={ "C","̇" },
+ ["ċ"]={ "c","̇" },
+ ["Č"]={ "C","̌" },
+ ["č"]={ "c","̌" },
+ ["Ď"]={ "D","̌" },
+ ["ď"]={ "d","̌" },
+ ["Ē"]={ "E","̄" },
+ ["ē"]={ "e","̄" },
+ ["Ĕ"]={ "E","̆" },
+ ["ĕ"]={ "e","̆" },
+ ["Ė"]={ "E","̇" },
+ ["ė"]={ "e","̇" },
+ ["Ę"]={ "E","̨" },
+ ["ę"]={ "e","̨" },
+ ["Ě"]={ "E","̌" },
+ ["ě"]={ "e","̌" },
+ ["Ĝ"]={ "G","̂" },
+ ["ĝ"]={ "g","̂" },
+ ["Ğ"]={ "G","̆" },
+ ["ğ"]={ "g","̆" },
+ ["Ġ"]={ "G","̇" },
+ ["ġ"]={ "g","̇" },
+ ["Ģ"]={ "G","̧" },
+ ["ģ"]={ "g","̧" },
+ ["Ĥ"]={ "H","̂" },
+ ["ĥ"]={ "h","̂" },
+ ["Ĩ"]={ "I","̃" },
+ ["ĩ"]={ "i","̃" },
+ ["Ī"]={ "I","̄" },
+ ["ī"]={ "i","̄" },
+ ["Ĭ"]={ "I","̆" },
+ ["ĭ"]={ "i","̆" },
+ ["Į"]={ "I","̨" },
+ ["į"]={ "i","̨" },
+ ["İ"]={ "I","̇" },
+ ["Ĵ"]={ "J","̂" },
+ ["ĵ"]={ "j","̂" },
+ ["Ķ"]={ "K","̧" },
+ ["ķ"]={ "k","̧" },
+ ["Ĺ"]={ "L","́" },
+ ["ĺ"]={ "l","́" },
+ ["Ļ"]={ "L","̧" },
+ ["ļ"]={ "l","̧" },
+ ["Ľ"]={ "L","̌" },
+ ["ľ"]={ "l","̌" },
+ ["Ń"]={ "N","́" },
+ ["ń"]={ "n","́" },
+ ["Ņ"]={ "N","̧" },
+ ["ņ"]={ "n","̧" },
+ ["Ň"]={ "N","̌" },
+ ["ň"]={ "n","̌" },
+ ["Ō"]={ "O","̄" },
+ ["ō"]={ "o","̄" },
+ ["Ŏ"]={ "O","̆" },
+ ["ŏ"]={ "o","̆" },
+ ["Ő"]={ "O","̋" },
+ ["ő"]={ "o","̋" },
+ ["Ŕ"]={ "R","́" },
+ ["ŕ"]={ "r","́" },
+ ["Ŗ"]={ "R","̧" },
+ ["ŗ"]={ "r","̧" },
+ ["Ř"]={ "R","̌" },
+ ["ř"]={ "r","̌" },
+ ["Ś"]={ "S","́" },
+ ["ś"]={ "s","́" },
+ ["Ŝ"]={ "S","̂" },
+ ["ŝ"]={ "s","̂" },
+ ["Ş"]={ "S","̧" },
+ ["ş"]={ "s","̧" },
+ ["Š"]={ "S","̌" },
+ ["š"]={ "s","̌" },
+ ["Ţ"]={ "T","̧" },
+ ["ţ"]={ "t","̧" },
+ ["Ť"]={ "T","̌" },
+ ["ť"]={ "t","̌" },
+ ["Ũ"]={ "U","̃" },
+ ["ũ"]={ "u","̃" },
+ ["Ū"]={ "U","̄" },
+ ["ū"]={ "u","̄" },
+ ["Ŭ"]={ "U","̆" },
+ ["ŭ"]={ "u","̆" },
+ ["Ů"]={ "U","̊" },
+ ["ů"]={ "u","̊" },
+ ["Ű"]={ "U","̋" },
+ ["ű"]={ "u","̋" },
+ ["Ų"]={ "U","̨" },
+ ["ų"]={ "u","̨" },
+ ["Ŵ"]={ "W","̂" },
+ ["ŵ"]={ "w","̂" },
+ ["Ŷ"]={ "Y","̂" },
+ ["ŷ"]={ "y","̂" },
+ ["Ÿ"]={ "Y","̈" },
+ ["Ź"]={ "Z","́" },
+ ["ź"]={ "z","́" },
+ ["Ż"]={ "Z","̇" },
+ ["ż"]={ "z","̇" },
+ ["Ž"]={ "Z","̌" },
+ ["ž"]={ "z","̌" },
+ ["Ơ"]={ "O","̛" },
+ ["ơ"]={ "o","̛" },
+ ["Ư"]={ "U","̛" },
+ ["ư"]={ "u","̛" },
+ ["Ǎ"]={ "A","̌" },
+ ["ǎ"]={ "a","̌" },
+ ["Ǐ"]={ "I","̌" },
+ ["ǐ"]={ "i","̌" },
+ ["Ǒ"]={ "O","̌" },
+ ["ǒ"]={ "o","̌" },
+ ["Ǔ"]={ "U","̌" },
+ ["ǔ"]={ "u","̌" },
+ ["Ǖ"]={ "Ü","̄" },
+ ["ǖ"]={ "ü","̄" },
+ ["Ǘ"]={ "Ü","́" },
+ ["ǘ"]={ "ü","́" },
+ ["Ǚ"]={ "Ü","̌" },
+ ["ǚ"]={ "ü","̌" },
+ ["Ǜ"]={ "Ü","̀" },
+ ["ǜ"]={ "ü","̀" },
+ ["Ǟ"]={ "Ä","̄" },
+ ["ǟ"]={ "ä","̄" },
+ ["Ǡ"]={ "Ȧ","̄" },
+ ["ǡ"]={ "ȧ","̄" },
+ ["Ǣ"]={ "Æ","̄" },
+ ["ǣ"]={ "æ","̄" },
+ ["Ǧ"]={ "G","̌" },
+ ["ǧ"]={ "g","̌" },
+ ["Ǩ"]={ "K","̌" },
+ ["ǩ"]={ "k","̌" },
+ ["Ǫ"]={ "O","̨" },
+ ["ǫ"]={ "o","̨" },
+ ["Ǭ"]={ "Ǫ","̄" },
+ ["ǭ"]={ "ǫ","̄" },
+ ["Ǯ"]={ "Ʒ","̌" },
+ ["ǯ"]={ "ʒ","̌" },
+ ["ǰ"]={ "j","̌" },
+ ["Ǵ"]={ "G","́" },
+ ["ǵ"]={ "g","́" },
+ ["Ǹ"]={ "N","̀" },
+ ["ǹ"]={ "n","̀" },
+ ["Ǻ"]={ "Å","́" },
+ ["ǻ"]={ "å","́" },
+ ["Ǽ"]={ "Æ","́" },
+ ["ǽ"]={ "æ","́" },
+ ["Ǿ"]={ "Ø","́" },
+ ["ǿ"]={ "ø","́" },
+ ["Ȁ"]={ "A","̏" },
+ ["ȁ"]={ "a","̏" },
+ ["Ȃ"]={ "A","̑" },
+ ["ȃ"]={ "a","̑" },
+ ["Ȅ"]={ "E","̏" },
+ ["ȅ"]={ "e","̏" },
+ ["Ȇ"]={ "E","̑" },
+ ["ȇ"]={ "e","̑" },
+ ["Ȉ"]={ "I","̏" },
+ ["ȉ"]={ "i","̏" },
+ ["Ȋ"]={ "I","̑" },
+ ["ȋ"]={ "i","̑" },
+ ["Ȍ"]={ "O","̏" },
+ ["ȍ"]={ "o","̏" },
+ ["Ȏ"]={ "O","̑" },
+ ["ȏ"]={ "o","̑" },
+ ["Ȑ"]={ "R","̏" },
+ ["ȑ"]={ "r","̏" },
+ ["Ȓ"]={ "R","̑" },
+ ["ȓ"]={ "r","̑" },
+ ["Ȕ"]={ "U","̏" },
+ ["ȕ"]={ "u","̏" },
+ ["Ȗ"]={ "U","̑" },
+ ["ȗ"]={ "u","̑" },
+ ["Ș"]={ "S","̦" },
+ ["ș"]={ "s","̦" },
+ ["Ț"]={ "T","̦" },
+ ["ț"]={ "t","̦" },
+ ["Ȟ"]={ "H","̌" },
+ ["ȟ"]={ "h","̌" },
+ ["Ȧ"]={ "A","̇" },
+ ["ȧ"]={ "a","̇" },
+ ["Ȩ"]={ "E","̧" },
+ ["ȩ"]={ "e","̧" },
+ ["Ȫ"]={ "Ö","̄" },
+ ["ȫ"]={ "ö","̄" },
+ ["Ȭ"]={ "Õ","̄" },
+ ["ȭ"]={ "õ","̄" },
+ ["Ȯ"]={ "O","̇" },
+ ["ȯ"]={ "o","̇" },
+ ["Ȱ"]={ "Ȯ","̄" },
+ ["ȱ"]={ "ȯ","̄" },
+ ["Ȳ"]={ "Y","̄" },
+ ["ȳ"]={ "y","̄" },
+ ["̈́"]={ "̈","́" },
+ ["΅"]={ "¨","́" },
+ ["Ά"]={ "Α","́" },
+ ["Έ"]={ "Ε","́" },
+ ["Ή"]={ "Η","́" },
+ ["Ί"]={ "Ι","́" },
+ ["Ό"]={ "Ο","́" },
+ ["Ύ"]={ "Υ","́" },
+ ["Ώ"]={ "Ω","́" },
+ ["ΐ"]={ "ϊ","́" },
+ ["Ϊ"]={ "Ι","̈" },
+ ["Ϋ"]={ "Υ","̈" },
+ ["ά"]={ "α","́" },
+ ["έ"]={ "ε","́" },
+ ["ή"]={ "η","́" },
+ ["ί"]={ "ι","́" },
+ ["ΰ"]={ "ϋ","́" },
+ ["ϊ"]={ "ι","̈" },
+ ["ϋ"]={ "υ","̈" },
+ ["ό"]={ "ο","́" },
+ ["ύ"]={ "υ","́" },
+ ["ώ"]={ "ω","́" },
+ ["ϓ"]={ "ϒ","́" },
+ ["ϔ"]={ "ϒ","̈" },
+ ["Ѐ"]={ "Е","̀" },
+ ["Ё"]={ "Е","̈" },
+ ["Ѓ"]={ "Г","́" },
+ ["Ї"]={ "І","̈" },
+ ["Ќ"]={ "К","́" },
+ ["Ѝ"]={ "И","̀" },
+ ["Ў"]={ "У","̆" },
+ ["Й"]={ "И","̆" },
+ ["й"]={ "и","̆" },
+ ["ѐ"]={ "е","̀" },
+ ["ё"]={ "е","̈" },
+ ["ѓ"]={ "г","́" },
+ ["ї"]={ "і","̈" },
+ ["ќ"]={ "к","́" },
+ ["ѝ"]={ "и","̀" },
+ ["ў"]={ "у","̆" },
+ ["Ѷ"]={ "Ѵ","̏" },
+ ["ѷ"]={ "ѵ","̏" },
+ ["Ӂ"]={ "Ж","̆" },
+ ["ӂ"]={ "ж","̆" },
+ ["Ӑ"]={ "А","̆" },
+ ["ӑ"]={ "а","̆" },
+ ["Ӓ"]={ "А","̈" },
+ ["ӓ"]={ "а","̈" },
+ ["Ӗ"]={ "Е","̆" },
+ ["ӗ"]={ "е","̆" },
+ ["Ӛ"]={ "Ә","̈" },
+ ["ӛ"]={ "ә","̈" },
+ ["Ӝ"]={ "Ж","̈" },
+ ["ӝ"]={ "ж","̈" },
+ ["Ӟ"]={ "З","̈" },
+ ["ӟ"]={ "з","̈" },
+ ["Ӣ"]={ "И","̄" },
+ ["ӣ"]={ "и","̄" },
+ ["Ӥ"]={ "И","̈" },
+ ["ӥ"]={ "и","̈" },
+ ["Ӧ"]={ "О","̈" },
+ ["ӧ"]={ "о","̈" },
+ ["Ӫ"]={ "Ө","̈" },
+ ["ӫ"]={ "ө","̈" },
+ ["Ӭ"]={ "Э","̈" },
+ ["ӭ"]={ "э","̈" },
+ ["Ӯ"]={ "У","̄" },
+ ["ӯ"]={ "у","̄" },
+ ["Ӱ"]={ "У","̈" },
+ ["ӱ"]={ "у","̈" },
+ ["Ӳ"]={ "У","̋" },
+ ["ӳ"]={ "у","̋" },
+ ["Ӵ"]={ "Ч","̈" },
+ ["ӵ"]={ "ч","̈" },
+ ["Ӹ"]={ "Ы","̈" },
+ ["ӹ"]={ "ы","̈" },
+ ["آ"]={ "ا","ٓ" },
+ ["أ"]={ "ا","ٔ" },
+ ["ؤ"]={ "و","ٔ" },
+ ["إ"]={ "ا","ٕ" },
+ ["ئ"]={ "ي","ٔ" },
+ ["ۀ"]={ "ە","ٔ" },
+ ["ۂ"]={ "ہ","ٔ" },
+ ["ۓ"]={ "ے","ٔ" },
+ ["ऩ"]={ "न","़" },
+ ["ऱ"]={ "र","़" },
+ ["ऴ"]={ "ळ","़" },
+ ["क़"]={ "क","़" },
+ ["ख़"]={ "ख","़" },
+ ["ग़"]={ "ग","़" },
+ ["ज़"]={ "ज","़" },
+ ["ड़"]={ "ड","़" },
+ ["ढ़"]={ "ढ","़" },
+ ["फ़"]={ "फ","़" },
+ ["य़"]={ "य","़" },
+ ["ো"]={ "ে","া" },
+ ["ৌ"]={ "ে","ৗ" },
+ ["ড়"]={ "ড","়" },
+ ["ঢ়"]={ "ঢ","়" },
+ ["য়"]={ "য","়" },
+ ["ਲ਼"]={ "ਲ","਼" },
+ ["ਸ਼"]={ "ਸ","਼" },
+ ["ਖ਼"]={ "ਖ","਼" },
+ ["ਗ਼"]={ "ਗ","਼" },
+ ["ਜ਼"]={ "ਜ","਼" },
+ ["ਫ਼"]={ "ਫ","਼" },
+ ["ୈ"]={ "େ","ୖ" },
+ ["ୋ"]={ "େ","ା" },
+ ["ୌ"]={ "େ","ୗ" },
+ ["ଡ଼"]={ "ଡ","଼" },
+ ["ଢ଼"]={ "ଢ","଼" },
+ ["ஔ"]={ "ஒ","ௗ" },
+ ["ொ"]={ "ெ","ா" },
+ ["ோ"]={ "ே","ா" },
+ ["ௌ"]={ "ெ","ௗ" },
+ ["ై"]={ "ె","ౖ" },
+ ["ೀ"]={ "ಿ","ೕ" },
+ ["ೇ"]={ "ೆ","ೕ" },
+ ["ೈ"]={ "ೆ","ೖ" },
+ ["ೊ"]={ "ೆ","ೂ" },
+ ["ೋ"]={ "ೊ","ೕ" },
+ ["ൊ"]={ "െ","ാ" },
+ ["ോ"]={ "േ","ാ" },
+ ["ൌ"]={ "െ","ൗ" },
+ ["ේ"]={ "ෙ","්" },
+ ["ො"]={ "ෙ","ා" },
+ ["ෝ"]={ "ො","්" },
+ ["ෞ"]={ "ෙ","ෟ" },
+ ["གྷ"]={ "ག","ྷ" },
+ ["ཌྷ"]={ "ཌ","ྷ" },
+ ["དྷ"]={ "ད","ྷ" },
+ ["བྷ"]={ "བ","ྷ" },
+ ["ཛྷ"]={ "ཛ","ྷ" },
+ ["ཀྵ"]={ "ཀ","ྵ" },
+ ["ཱི"]={ "ཱ","ི" },
+ ["ཱུ"]={ "ཱ","ུ" },
+ ["ྲྀ"]={ "ྲ","ྀ" },
+ ["ླྀ"]={ "ླ","ྀ" },
+ ["ཱྀ"]={ "ཱ","ྀ" },
+ ["ྒྷ"]={ "ྒ","ྷ" },
+ ["ྜྷ"]={ "ྜ","ྷ" },
+ ["ྡྷ"]={ "ྡ","ྷ" },
+ ["ྦྷ"]={ "ྦ","ྷ" },
+ ["ྫྷ"]={ "ྫ","ྷ" },
+ ["ྐྵ"]={ "ྐ","ྵ" },
+ ["ဦ"]={ "ဥ","ီ" },
+ ["ᬆ"]={ "ᬅ","ᬵ" },
+ ["ᬈ"]={ "ᬇ","ᬵ" },
+ ["ᬊ"]={ "ᬉ","ᬵ" },
+ ["ᬌ"]={ "ᬋ","ᬵ" },
+ ["ᬎ"]={ "ᬍ","ᬵ" },
+ ["ᬒ"]={ "ᬑ","ᬵ" },
+ ["ᬻ"]={ "ᬺ","ᬵ" },
+ ["ᬽ"]={ "ᬼ","ᬵ" },
+ ["ᭀ"]={ "ᬾ","ᬵ" },
+ ["ᭁ"]={ "ᬿ","ᬵ" },
+ ["ᭃ"]={ "ᭂ","ᬵ" },
+ ["Ḁ"]={ "A","̥" },
+ ["ḁ"]={ "a","̥" },
+ ["Ḃ"]={ "B","̇" },
+ ["ḃ"]={ "b","̇" },
+ ["Ḅ"]={ "B","̣" },
+ ["ḅ"]={ "b","̣" },
+ ["Ḇ"]={ "B","̱" },
+ ["ḇ"]={ "b","̱" },
+ ["Ḉ"]={ "Ç","́" },
+ ["ḉ"]={ "ç","́" },
+ ["Ḋ"]={ "D","̇" },
+ ["ḋ"]={ "d","̇" },
+ ["Ḍ"]={ "D","̣" },
+ ["ḍ"]={ "d","̣" },
+ ["Ḏ"]={ "D","̱" },
+ ["ḏ"]={ "d","̱" },
+ ["Ḑ"]={ "D","̧" },
+ ["ḑ"]={ "d","̧" },
+ ["Ḓ"]={ "D","̭" },
+ ["ḓ"]={ "d","̭" },
+ ["Ḕ"]={ "Ē","̀" },
+ ["ḕ"]={ "ē","̀" },
+ ["Ḗ"]={ "Ē","́" },
+ ["ḗ"]={ "ē","́" },
+ ["Ḙ"]={ "E","̭" },
+ ["ḙ"]={ "e","̭" },
+ ["Ḛ"]={ "E","̰" },
+ ["ḛ"]={ "e","̰" },
+ ["Ḝ"]={ "Ȩ","̆" },
+ ["ḝ"]={ "ȩ","̆" },
+ ["Ḟ"]={ "F","̇" },
+ ["ḟ"]={ "f","̇" },
+ ["Ḡ"]={ "G","̄" },
+ ["ḡ"]={ "g","̄" },
+ ["Ḣ"]={ "H","̇" },
+ ["ḣ"]={ "h","̇" },
+ ["Ḥ"]={ "H","̣" },
+ ["ḥ"]={ "h","̣" },
+ ["Ḧ"]={ "H","̈" },
+ ["ḧ"]={ "h","̈" },
+ ["Ḩ"]={ "H","̧" },
+ ["ḩ"]={ "h","̧" },
+ ["Ḫ"]={ "H","̮" },
+ ["ḫ"]={ "h","̮" },
+ ["Ḭ"]={ "I","̰" },
+ ["ḭ"]={ "i","̰" },
+ ["Ḯ"]={ "Ï","́" },
+ ["ḯ"]={ "ï","́" },
+ ["Ḱ"]={ "K","́" },
+ ["ḱ"]={ "k","́" },
+ ["Ḳ"]={ "K","̣" },
+ ["ḳ"]={ "k","̣" },
+ ["Ḵ"]={ "K","̱" },
+ ["ḵ"]={ "k","̱" },
+ ["Ḷ"]={ "L","̣" },
+ ["ḷ"]={ "l","̣" },
+ ["Ḹ"]={ "Ḷ","̄" },
+ ["ḹ"]={ "ḷ","̄" },
+ ["Ḻ"]={ "L","̱" },
+ ["ḻ"]={ "l","̱" },
+ ["Ḽ"]={ "L","̭" },
+ ["ḽ"]={ "l","̭" },
+ ["Ḿ"]={ "M","́" },
+ ["ḿ"]={ "m","́" },
+ ["Ṁ"]={ "M","̇" },
+ ["ṁ"]={ "m","̇" },
+ ["Ṃ"]={ "M","̣" },
+ ["ṃ"]={ "m","̣" },
+ ["Ṅ"]={ "N","̇" },
+ ["ṅ"]={ "n","̇" },
+ ["Ṇ"]={ "N","̣" },
+ ["ṇ"]={ "n","̣" },
+ ["Ṉ"]={ "N","̱" },
+ ["ṉ"]={ "n","̱" },
+ ["Ṋ"]={ "N","̭" },
+ ["ṋ"]={ "n","̭" },
+ ["Ṍ"]={ "Õ","́" },
+ ["ṍ"]={ "õ","́" },
+ ["Ṏ"]={ "Õ","̈" },
+ ["ṏ"]={ "õ","̈" },
+ ["Ṑ"]={ "Ō","̀" },
+ ["ṑ"]={ "ō","̀" },
+ ["Ṓ"]={ "Ō","́" },
+ ["ṓ"]={ "ō","́" },
+ ["Ṕ"]={ "P","́" },
+ ["ṕ"]={ "p","́" },
+ ["Ṗ"]={ "P","̇" },
+ ["ṗ"]={ "p","̇" },
+ ["Ṙ"]={ "R","̇" },
+ ["ṙ"]={ "r","̇" },
+ ["Ṛ"]={ "R","̣" },
+ ["ṛ"]={ "r","̣" },
+ ["Ṝ"]={ "Ṛ","̄" },
+ ["ṝ"]={ "ṛ","̄" },
+ ["Ṟ"]={ "R","̱" },
+ ["ṟ"]={ "r","̱" },
+ ["Ṡ"]={ "S","̇" },
+ ["ṡ"]={ "s","̇" },
+ ["Ṣ"]={ "S","̣" },
+ ["ṣ"]={ "s","̣" },
+ ["Ṥ"]={ "Ś","̇" },
+ ["ṥ"]={ "ś","̇" },
+ ["Ṧ"]={ "Š","̇" },
+ ["ṧ"]={ "š","̇" },
+ ["Ṩ"]={ "Ṣ","̇" },
+ ["ṩ"]={ "ṣ","̇" },
+ ["Ṫ"]={ "T","̇" },
+ ["ṫ"]={ "t","̇" },
+ ["Ṭ"]={ "T","̣" },
+ ["ṭ"]={ "t","̣" },
+ ["Ṯ"]={ "T","̱" },
+ ["ṯ"]={ "t","̱" },
+ ["Ṱ"]={ "T","̭" },
+ ["ṱ"]={ "t","̭" },
+ ["Ṳ"]={ "U","̤" },
+ ["ṳ"]={ "u","̤" },
+ ["Ṵ"]={ "U","̰" },
+ ["ṵ"]={ "u","̰" },
+ ["Ṷ"]={ "U","̭" },
+ ["ṷ"]={ "u","̭" },
+ ["Ṹ"]={ "Ũ","́" },
+ ["ṹ"]={ "ũ","́" },
+ ["Ṻ"]={ "Ū","̈" },
+ ["ṻ"]={ "ū","̈" },
+ ["Ṽ"]={ "V","̃" },
+ ["ṽ"]={ "v","̃" },
+ ["Ṿ"]={ "V","̣" },
+ ["ṿ"]={ "v","̣" },
+ ["Ẁ"]={ "W","̀" },
+ ["ẁ"]={ "w","̀" },
+ ["Ẃ"]={ "W","́" },
+ ["ẃ"]={ "w","́" },
+ ["Ẅ"]={ "W","̈" },
+ ["ẅ"]={ "w","̈" },
+ ["Ẇ"]={ "W","̇" },
+ ["ẇ"]={ "w","̇" },
+ ["Ẉ"]={ "W","̣" },
+ ["ẉ"]={ "w","̣" },
+ ["Ẋ"]={ "X","̇" },
+ ["ẋ"]={ "x","̇" },
+ ["Ẍ"]={ "X","̈" },
+ ["ẍ"]={ "x","̈" },
+ ["Ẏ"]={ "Y","̇" },
+ ["ẏ"]={ "y","̇" },
+ ["Ẑ"]={ "Z","̂" },
+ ["ẑ"]={ "z","̂" },
+ ["Ẓ"]={ "Z","̣" },
+ ["ẓ"]={ "z","̣" },
+ ["Ẕ"]={ "Z","̱" },
+ ["ẕ"]={ "z","̱" },
+ ["ẖ"]={ "h","̱" },
+ ["ẗ"]={ "t","̈" },
+ ["ẘ"]={ "w","̊" },
+ ["ẙ"]={ "y","̊" },
+ ["ẛ"]={ "ſ","̇" },
+ ["Ạ"]={ "A","̣" },
+ ["ạ"]={ "a","̣" },
+ ["Ả"]={ "A","̉" },
+ ["ả"]={ "a","̉" },
+ ["Ấ"]={ "Â","́" },
+ ["ấ"]={ "â","́" },
+ ["Ầ"]={ "Â","̀" },
+ ["ầ"]={ "â","̀" },
+ ["Ẩ"]={ "Â","̉" },
+ ["ẩ"]={ "â","̉" },
+ ["Ẫ"]={ "Â","̃" },
+ ["ẫ"]={ "â","̃" },
+ ["Ậ"]={ "Ạ","̂" },
+ ["ậ"]={ "ạ","̂" },
+ ["Ắ"]={ "Ă","́" },
+ ["ắ"]={ "ă","́" },
+ ["Ằ"]={ "Ă","̀" },
+ ["ằ"]={ "ă","̀" },
+ ["Ẳ"]={ "Ă","̉" },
+ ["ẳ"]={ "ă","̉" },
+ ["Ẵ"]={ "Ă","̃" },
+ ["ẵ"]={ "ă","̃" },
+ ["Ặ"]={ "Ạ","̆" },
+ ["ặ"]={ "ạ","̆" },
+ ["Ẹ"]={ "E","̣" },
+ ["ẹ"]={ "e","̣" },
+ ["Ẻ"]={ "E","̉" },
+ ["ẻ"]={ "e","̉" },
+ ["Ẽ"]={ "E","̃" },
+ ["ẽ"]={ "e","̃" },
+ ["Ế"]={ "Ê","́" },
+ ["ế"]={ "ê","́" },
+ ["Ề"]={ "Ê","̀" },
+ ["ề"]={ "ê","̀" },
+ ["Ể"]={ "Ê","̉" },
+ ["ể"]={ "ê","̉" },
+ ["Ễ"]={ "Ê","̃" },
+ ["ễ"]={ "ê","̃" },
+ ["Ệ"]={ "Ẹ","̂" },
+ ["ệ"]={ "ẹ","̂" },
+ ["Ỉ"]={ "I","̉" },
+ ["ỉ"]={ "i","̉" },
+ ["Ị"]={ "I","̣" },
+ ["ị"]={ "i","̣" },
+ ["Ọ"]={ "O","̣" },
+ ["ọ"]={ "o","̣" },
+ ["Ỏ"]={ "O","̉" },
+ ["ỏ"]={ "o","̉" },
+ ["Ố"]={ "Ô","́" },
+ ["ố"]={ "ô","́" },
+ ["Ồ"]={ "Ô","̀" },
+ ["ồ"]={ "ô","̀" },
+ ["Ổ"]={ "Ô","̉" },
+ ["ổ"]={ "ô","̉" },
+ ["Ỗ"]={ "Ô","̃" },
+ ["ỗ"]={ "ô","̃" },
+ ["Ộ"]={ "Ọ","̂" },
+ ["ộ"]={ "ọ","̂" },
+ ["Ớ"]={ "Ơ","́" },
+ ["ớ"]={ "ơ","́" },
+ ["Ờ"]={ "Ơ","̀" },
+ ["ờ"]={ "ơ","̀" },
+ ["Ở"]={ "Ơ","̉" },
+ ["ở"]={ "ơ","̉" },
+ ["Ỡ"]={ "Ơ","̃" },
+ ["ỡ"]={ "ơ","̃" },
+ ["Ợ"]={ "Ơ","̣" },
+ ["ợ"]={ "ơ","̣" },
+ ["Ụ"]={ "U","̣" },
+ ["ụ"]={ "u","̣" },
+ ["Ủ"]={ "U","̉" },
+ ["ủ"]={ "u","̉" },
+ ["Ứ"]={ "Ư","́" },
+ ["ứ"]={ "ư","́" },
+ ["Ừ"]={ "Ư","̀" },
+ ["ừ"]={ "ư","̀" },
+ ["Ử"]={ "Ư","̉" },
+ ["ử"]={ "ư","̉" },
+ ["Ữ"]={ "Ư","̃" },
+ ["ữ"]={ "ư","̃" },
+ ["Ự"]={ "Ư","̣" },
+ ["ự"]={ "ư","̣" },
+ ["Ỳ"]={ "Y","̀" },
+ ["ỳ"]={ "y","̀" },
+ ["Ỵ"]={ "Y","̣" },
+ ["ỵ"]={ "y","̣" },
+ ["Ỷ"]={ "Y","̉" },
+ ["ỷ"]={ "y","̉" },
+ ["Ỹ"]={ "Y","̃" },
+ ["ỹ"]={ "y","̃" },
+ ["ἀ"]={ "α","̓" },
+ ["ἁ"]={ "α","̔" },
+ ["ἂ"]={ "ἀ","̀" },
+ ["ἃ"]={ "ἁ","̀" },
+ ["ἄ"]={ "ἀ","́" },
+ ["ἅ"]={ "ἁ","́" },
+ ["ἆ"]={ "ἀ","͂" },
+ ["ἇ"]={ "ἁ","͂" },
+ ["Ἀ"]={ "Α","̓" },
+ ["Ἁ"]={ "Α","̔" },
+ ["Ἂ"]={ "Ἀ","̀" },
+ ["Ἃ"]={ "Ἁ","̀" },
+ ["Ἄ"]={ "Ἀ","́" },
+ ["Ἅ"]={ "Ἁ","́" },
+ ["Ἆ"]={ "Ἀ","͂" },
+ ["Ἇ"]={ "Ἁ","͂" },
+ ["ἐ"]={ "ε","̓" },
+ ["ἑ"]={ "ε","̔" },
+ ["ἒ"]={ "ἐ","̀" },
+ ["ἓ"]={ "ἑ","̀" },
+ ["ἔ"]={ "ἐ","́" },
+ ["ἕ"]={ "ἑ","́" },
+ ["Ἐ"]={ "Ε","̓" },
+ ["Ἑ"]={ "Ε","̔" },
+ ["Ἒ"]={ "Ἐ","̀" },
+ ["Ἓ"]={ "Ἑ","̀" },
+ ["Ἔ"]={ "Ἐ","́" },
+ ["Ἕ"]={ "Ἑ","́" },
+ ["ἠ"]={ "η","̓" },
+ ["ἡ"]={ "η","̔" },
+ ["ἢ"]={ "ἠ","̀" },
+ ["ἣ"]={ "ἡ","̀" },
+ ["ἤ"]={ "ἠ","́" },
+ ["ἥ"]={ "ἡ","́" },
+ ["ἦ"]={ "ἠ","͂" },
+ ["ἧ"]={ "ἡ","͂" },
+ ["Ἠ"]={ "Η","̓" },
+ ["Ἡ"]={ "Η","̔" },
+ ["Ἢ"]={ "Ἠ","̀" },
+ ["Ἣ"]={ "Ἡ","̀" },
+ ["Ἤ"]={ "Ἠ","́" },
+ ["Ἥ"]={ "Ἡ","́" },
+ ["Ἦ"]={ "Ἠ","͂" },
+ ["Ἧ"]={ "Ἡ","͂" },
+ ["ἰ"]={ "ι","̓" },
+ ["ἱ"]={ "ι","̔" },
+ ["ἲ"]={ "ἰ","̀" },
+ ["ἳ"]={ "ἱ","̀" },
+ ["ἴ"]={ "ἰ","́" },
+ ["ἵ"]={ "ἱ","́" },
+ ["ἶ"]={ "ἰ","͂" },
+ ["ἷ"]={ "ἱ","͂" },
+ ["Ἰ"]={ "Ι","̓" },
+ ["Ἱ"]={ "Ι","̔" },
+ ["Ἲ"]={ "Ἰ","̀" },
+ ["Ἳ"]={ "Ἱ","̀" },
+ ["Ἴ"]={ "Ἰ","́" },
+ ["Ἵ"]={ "Ἱ","́" },
+ ["Ἶ"]={ "Ἰ","͂" },
+ ["Ἷ"]={ "Ἱ","͂" },
+ ["ὀ"]={ "ο","̓" },
+ ["ὁ"]={ "ο","̔" },
+ ["ὂ"]={ "ὀ","̀" },
+ ["ὃ"]={ "ὁ","̀" },
+ ["ὄ"]={ "ὀ","́" },
+ ["ὅ"]={ "ὁ","́" },
+ ["Ὀ"]={ "Ο","̓" },
+ ["Ὁ"]={ "Ο","̔" },
+ ["Ὂ"]={ "Ὀ","̀" },
+ ["Ὃ"]={ "Ὁ","̀" },
+ ["Ὄ"]={ "Ὀ","́" },
+ ["Ὅ"]={ "Ὁ","́" },
+ ["ὐ"]={ "υ","̓" },
+ ["ὑ"]={ "υ","̔" },
+ ["ὒ"]={ "ὐ","̀" },
+ ["ὓ"]={ "ὑ","̀" },
+ ["ὔ"]={ "ὐ","́" },
+ ["ὕ"]={ "ὑ","́" },
+ ["ὖ"]={ "ὐ","͂" },
+ ["ὗ"]={ "ὑ","͂" },
+ ["Ὑ"]={ "Υ","̔" },
+ ["Ὓ"]={ "Ὑ","̀" },
+ ["Ὕ"]={ "Ὑ","́" },
+ ["Ὗ"]={ "Ὑ","͂" },
+ ["ὠ"]={ "ω","̓" },
+ ["ὡ"]={ "ω","̔" },
+ ["ὢ"]={ "ὠ","̀" },
+ ["ὣ"]={ "ὡ","̀" },
+ ["ὤ"]={ "ὠ","́" },
+ ["ὥ"]={ "ὡ","́" },
+ ["ὦ"]={ "ὠ","͂" },
+ ["ὧ"]={ "ὡ","͂" },
+ ["Ὠ"]={ "Ω","̓" },
+ ["Ὡ"]={ "Ω","̔" },
+ ["Ὢ"]={ "Ὠ","̀" },
+ ["Ὣ"]={ "Ὡ","̀" },
+ ["Ὤ"]={ "Ὠ","́" },
+ ["Ὥ"]={ "Ὡ","́" },
+ ["Ὦ"]={ "Ὠ","͂" },
+ ["Ὧ"]={ "Ὡ","͂" },
+ ["ὰ"]={ "α","̀" },
+ ["ὲ"]={ "ε","̀" },
+ ["ὴ"]={ "η","̀" },
+ ["ὶ"]={ "ι","̀" },
+ ["ὸ"]={ "ο","̀" },
+ ["ὺ"]={ "υ","̀" },
+ ["ὼ"]={ "ω","̀" },
+ ["ᾀ"]={ "ἀ","ͅ" },
+ ["ᾁ"]={ "ἁ","ͅ" },
+ ["ᾂ"]={ "ἂ","ͅ" },
+ ["ᾃ"]={ "ἃ","ͅ" },
+ ["ᾄ"]={ "ἄ","ͅ" },
+ ["ᾅ"]={ "ἅ","ͅ" },
+ ["ᾆ"]={ "ἆ","ͅ" },
+ ["ᾇ"]={ "ἇ","ͅ" },
+ ["ᾈ"]={ "Ἀ","ͅ" },
+ ["ᾉ"]={ "Ἁ","ͅ" },
+ ["ᾊ"]={ "Ἂ","ͅ" },
+ ["ᾋ"]={ "Ἃ","ͅ" },
+ ["ᾌ"]={ "Ἄ","ͅ" },
+ ["ᾍ"]={ "Ἅ","ͅ" },
+ ["ᾎ"]={ "Ἆ","ͅ" },
+ ["ᾏ"]={ "Ἇ","ͅ" },
+ ["ᾐ"]={ "ἠ","ͅ" },
+ ["ᾑ"]={ "ἡ","ͅ" },
+ ["ᾒ"]={ "ἢ","ͅ" },
+ ["ᾓ"]={ "ἣ","ͅ" },
+ ["ᾔ"]={ "ἤ","ͅ" },
+ ["ᾕ"]={ "ἥ","ͅ" },
+ ["ᾖ"]={ "ἦ","ͅ" },
+ ["ᾗ"]={ "ἧ","ͅ" },
+ ["ᾘ"]={ "Ἠ","ͅ" },
+ ["ᾙ"]={ "Ἡ","ͅ" },
+ ["ᾚ"]={ "Ἢ","ͅ" },
+ ["ᾛ"]={ "Ἣ","ͅ" },
+ ["ᾜ"]={ "Ἤ","ͅ" },
+ ["ᾝ"]={ "Ἥ","ͅ" },
+ ["ᾞ"]={ "Ἦ","ͅ" },
+ ["ᾟ"]={ "Ἧ","ͅ" },
+ ["ᾠ"]={ "ὠ","ͅ" },
+ ["ᾡ"]={ "ὡ","ͅ" },
+ ["ᾢ"]={ "ὢ","ͅ" },
+ ["ᾣ"]={ "ὣ","ͅ" },
+ ["ᾤ"]={ "ὤ","ͅ" },
+ ["ᾥ"]={ "ὥ","ͅ" },
+ ["ᾦ"]={ "ὦ","ͅ" },
+ ["ᾧ"]={ "ὧ","ͅ" },
+ ["ᾨ"]={ "Ὠ","ͅ" },
+ ["ᾩ"]={ "Ὡ","ͅ" },
+ ["ᾪ"]={ "Ὢ","ͅ" },
+ ["ᾫ"]={ "Ὣ","ͅ" },
+ ["ᾬ"]={ "Ὤ","ͅ" },
+ ["ᾭ"]={ "Ὥ","ͅ" },
+ ["ᾮ"]={ "Ὦ","ͅ" },
+ ["ᾯ"]={ "Ὧ","ͅ" },
+ ["ᾰ"]={ "α","̆" },
+ ["ᾱ"]={ "α","̄" },
+ ["ᾲ"]={ "ὰ","ͅ" },
+ ["ᾳ"]={ "α","ͅ" },
+ ["ᾴ"]={ "ά","ͅ" },
+ ["ᾶ"]={ "α","͂" },
+ ["ᾷ"]={ "ᾶ","ͅ" },
+ ["Ᾰ"]={ "Α","̆" },
+ ["Ᾱ"]={ "Α","̄" },
+ ["Ὰ"]={ "Α","̀" },
+ ["ᾼ"]={ "Α","ͅ" },
+ ["῁"]={ "¨","͂" },
+ ["ῂ"]={ "ὴ","ͅ" },
+ ["ῃ"]={ "η","ͅ" },
+ ["ῄ"]={ "ή","ͅ" },
+ ["ῆ"]={ "η","͂" },
+ ["ῇ"]={ "ῆ","ͅ" },
+ ["Ὲ"]={ "Ε","̀" },
+ ["Ὴ"]={ "Η","̀" },
+ ["ῌ"]={ "Η","ͅ" },
+ ["῍"]={ "᾿","̀" },
+ ["῎"]={ "᾿","́" },
+ ["῏"]={ "᾿","͂" },
+ ["ῐ"]={ "ι","̆" },
+ ["ῑ"]={ "ι","̄" },
+ ["ῒ"]={ "ϊ","̀" },
+ ["ῖ"]={ "ι","͂" },
+ ["ῗ"]={ "ϊ","͂" },
+ ["Ῐ"]={ "Ι","̆" },
+ ["Ῑ"]={ "Ι","̄" },
+ ["Ὶ"]={ "Ι","̀" },
+ ["῝"]={ "῾","̀" },
+ ["῞"]={ "῾","́" },
+ ["῟"]={ "῾","͂" },
+ ["ῠ"]={ "υ","̆" },
+ ["ῡ"]={ "υ","̄" },
+ ["ῢ"]={ "ϋ","̀" },
+ ["ῤ"]={ "ρ","̓" },
+ ["ῥ"]={ "ρ","̔" },
+ ["ῦ"]={ "υ","͂" },
+ ["ῧ"]={ "ϋ","͂" },
+ ["Ῠ"]={ "Υ","̆" },
+ ["Ῡ"]={ "Υ","̄" },
+ ["Ὺ"]={ "Υ","̀" },
+ ["Ῥ"]={ "Ρ","̔" },
+ ["῭"]={ "¨","̀" },
+ ["ῲ"]={ "ὼ","ͅ" },
+ ["ῳ"]={ "ω","ͅ" },
+ ["ῴ"]={ "ώ","ͅ" },
+ ["ῶ"]={ "ω","͂" },
+ ["ῷ"]={ "ῶ","ͅ" },
+ ["Ὸ"]={ "Ο","̀" },
+ ["Ὼ"]={ "Ω","̀" },
+ ["ῼ"]={ "Ω","ͅ" },
+ ["↚"]={ "←","̸" },
+ ["↛"]={ "→","̸" },
+ ["↮"]={ "↔","̸" },
+ ["⇍"]={ "⇐","̸" },
+ ["⇎"]={ "⇔","̸" },
+ ["⇏"]={ "⇒","̸" },
+ ["∄"]={ "∃","̸" },
+ ["∉"]={ "∈","̸" },
+ ["∌"]={ "∋","̸" },
+ ["∤"]={ "∣","̸" },
+ ["∦"]={ "∥","̸" },
+ ["≁"]={ "∼","̸" },
+ ["≄"]={ "≃","̸" },
+ ["≇"]={ "≅","̸" },
+ ["≉"]={ "≈","̸" },
+ ["≠"]={ "=","̸" },
+ ["≢"]={ "≡","̸" },
+ ["≭"]={ "≍","̸" },
+ ["≮"]={ "<","̸" },
+ ["≯"]={ ">","̸" },
+ ["≰"]={ "≤","̸" },
+ ["≱"]={ "≥","̸" },
+ ["≴"]={ "≲","̸" },
+ ["≵"]={ "≳","̸" },
+ ["≸"]={ "≶","̸" },
+ ["≹"]={ "≷","̸" },
+ ["⊀"]={ "≺","̸" },
+ ["⊁"]={ "≻","̸" },
+ ["⊄"]={ "⊂","̸" },
+ ["⊅"]={ "⊃","̸" },
+ ["⊈"]={ "⊆","̸" },
+ ["⊉"]={ "⊇","̸" },
+ ["⊬"]={ "⊢","̸" },
+ ["⊭"]={ "⊨","̸" },
+ ["⊮"]={ "⊩","̸" },
+ ["⊯"]={ "⊫","̸" },
+ ["⋠"]={ "≼","̸" },
+ ["⋡"]={ "≽","̸" },
+ ["⋢"]={ "⊑","̸" },
+ ["⋣"]={ "⊒","̸" },
+ ["⋪"]={ "⊲","̸" },
+ ["⋫"]={ "⊳","̸" },
+ ["⋬"]={ "⊴","̸" },
+ ["⋭"]={ "⊵","̸" },
+ ["⫝̸"]={ "⫝","̸" },
+ ["が"]={ "か","゙" },
+ ["ぎ"]={ "き","゙" },
+ ["ぐ"]={ "く","゙" },
+ ["げ"]={ "け","゙" },
+ ["ご"]={ "こ","゙" },
+ ["ざ"]={ "さ","゙" },
+ ["じ"]={ "し","゙" },
+ ["ず"]={ "す","゙" },
+ ["ぜ"]={ "せ","゙" },
+ ["ぞ"]={ "そ","゙" },
+ ["だ"]={ "た","゙" },
+ ["ぢ"]={ "ち","゙" },
+ ["づ"]={ "つ","゙" },
+ ["で"]={ "て","゙" },
+ ["ど"]={ "と","゙" },
+ ["ば"]={ "は","゙" },
+ ["ぱ"]={ "は","゚" },
+ ["び"]={ "ひ","゙" },
+ ["ぴ"]={ "ひ","゚" },
+ ["ぶ"]={ "ふ","゙" },
+ ["ぷ"]={ "ふ","゚" },
+ ["べ"]={ "へ","゙" },
+ ["ぺ"]={ "へ","゚" },
+ ["ぼ"]={ "ほ","゙" },
+ ["ぽ"]={ "ほ","゚" },
+ ["ゔ"]={ "う","゙" },
+ ["ゞ"]={ "ゝ","゙" },
+ ["ガ"]={ "カ","゙" },
+ ["ギ"]={ "キ","゙" },
+ ["グ"]={ "ク","゙" },
+ ["ゲ"]={ "ケ","゙" },
+ ["ゴ"]={ "コ","゙" },
+ ["ザ"]={ "サ","゙" },
+ ["ジ"]={ "シ","゙" },
+ ["ズ"]={ "ス","゙" },
+ ["ゼ"]={ "セ","゙" },
+ ["ゾ"]={ "ソ","゙" },
+ ["ダ"]={ "タ","゙" },
+ ["ヂ"]={ "チ","゙" },
+ ["ヅ"]={ "ツ","゙" },
+ ["デ"]={ "テ","゙" },
+ ["ド"]={ "ト","゙" },
+ ["バ"]={ "ハ","゙" },
+ ["パ"]={ "ハ","゚" },
+ ["ビ"]={ "ヒ","゙" },
+ ["ピ"]={ "ヒ","゚" },
+ ["ブ"]={ "フ","゙" },
+ ["プ"]={ "フ","゚" },
+ ["ベ"]={ "ヘ","゙" },
+ ["ペ"]={ "ヘ","゚" },
+ ["ボ"]={ "ホ","゙" },
+ ["ポ"]={ "ホ","゚" },
+ ["ヴ"]={ "ウ","゙" },
+ ["ヷ"]={ "ワ","゙" },
+ ["ヸ"]={ "ヰ","゙" },
+ ["ヹ"]={ "ヱ","゙" },
+ ["ヺ"]={ "ヲ","゙" },
+ ["ヾ"]={ "ヽ","゙" },
+ ["יִ"]={ "י","ִ" },
+ ["ײַ"]={ "ײ","ַ" },
+ ["שׁ"]={ "ש","ׁ" },
+ ["שׂ"]={ "ש","ׂ" },
+ ["שּׁ"]={ "שּ","ׁ" },
+ ["שּׂ"]={ "שּ","ׂ" },
+ ["אַ"]={ "א","ַ" },
+ ["אָ"]={ "א","ָ" },
+ ["אּ"]={ "א","ּ" },
+ ["בּ"]={ "ב","ּ" },
+ ["גּ"]={ "ג","ּ" },
+ ["דּ"]={ "ד","ּ" },
+ ["הּ"]={ "ה","ּ" },
+ ["וּ"]={ "ו","ּ" },
+ ["זּ"]={ "ז","ּ" },
+ ["טּ"]={ "ט","ּ" },
+ ["יּ"]={ "י","ּ" },
+ ["ךּ"]={ "ך","ּ" },
+ ["כּ"]={ "כ","ּ" },
+ ["לּ"]={ "ל","ּ" },
+ ["מּ"]={ "מ","ּ" },
+ ["נּ"]={ "נ","ּ" },
+ ["סּ"]={ "ס","ּ" },
+ ["ףּ"]={ "ף","ּ" },
+ ["פּ"]={ "פ","ּ" },
+ ["צּ"]={ "צ","ּ" },
+ ["קּ"]={ "ק","ּ" },
+ ["רּ"]={ "ר","ּ" },
+ ["שּ"]={ "ש","ּ" },
+ ["תּ"]={ "ת","ּ" },
+ ["וֹ"]={ "ו","ֹ" },
+ ["בֿ"]={ "ב","ֿ" },
+ ["כֿ"]={ "כ","ֿ" },
+ ["פֿ"]={ "פ","ֿ" },
+ ["𑂚"]={ "𑂙","𑂺" },
+ ["𑂜"]={ "𑂛","𑂺" },
+ ["𑂫"]={ "𑂥","𑂺" },
+ ["𑄮"]={ "𑄱","𑄧" },
+ ["𑄯"]={ "𑄲","𑄧" },
+ ["𑍋"]={ "𑍇","𑌾" },
+ ["𑍌"]={ "𑍇","𑍗" },
+ ["𑒻"]={ "𑒹","𑒺" },
+ ["𑒼"]={ "𑒹","𑒰" },
+ ["𑒾"]={ "𑒹","𑒽" },
+ ["𑖺"]={ "𑖸","𑖯" },
+ ["𑖻"]={ "𑖹","𑖯" },
+ ["𝅗𝅥"]={ "𝅗","𝅥" },
+ ["𝅘𝅥"]={ "𝅘","𝅥" },
+ ["𝅘𝅥𝅮"]={ "𝅘𝅥","𝅮" },
+ ["𝅘𝅥𝅯"]={ "𝅘𝅥","𝅯" },
+ ["𝅘𝅥𝅰"]={ "𝅘𝅥","𝅰" },
+ ["𝅘𝅥𝅱"]={ "𝅘𝅥","𝅱" },
+ ["𝅘𝅥𝅲"]={ "𝅘𝅥","𝅲" },
+ ["𝆹𝅥"]={ "𝆹","𝅥" },
+ ["𝆺𝅥"]={ "𝆺","𝅥" },
+ ["𝆹𝅥𝅮"]={ "𝆹𝅥","𝅮" },
+ ["𝆺𝅥𝅮"]={ "𝆺𝅥","𝅮" },
+ ["𝆹𝅥𝅯"]={ "𝆹𝅥","𝅯" },
+ ["𝆺𝅥𝅯"]={ "𝆺𝅥","𝅯" },
+ },
+ },
+ },
+ ["name"]="collapse",
+ ["prepend"]=true,
+ ["type"]="ligature",
+}
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-lig”] ---
+
+
+do --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-gbn” d25472d54c4841db43a745764a63533e] ---
+
+if not modules then modules={} end modules ['luatex-fonts-gbn']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+ os.exit()
+end
+local next=next
+local fonts=fonts
+local nodes=nodes
+local nuts=nodes.nuts
+local traverse_id=nuts.traverse_id
+local flush_node=nuts.flush_node
+local glyph_code=nodes.nodecodes.glyph
+local disc_code=nodes.nodecodes.disc
+local tonode=nuts.tonode
+local tonut=nuts.tonut
+local getfont=nuts.getfont
+local getchar=nuts.getchar
+local getid=nuts.getid
+local getboth=nuts.getboth
+local getprev=nuts.getprev
+local getnext=nuts.getnext
+local getdisc=nuts.getdisc
+local setchar=nuts.setchar
+local setlink=nuts.setlink
+local setprev=nuts.setprev
+local n_ligaturing=node.ligaturing
+local n_kerning=node.kerning
+local d_ligaturing=nuts.ligaturing
+local d_kerning=nuts.kerning
+local basemodepass=true
+local function l_warning() logs.report("fonts","don't call 'node.ligaturing' directly") l_warning=nil end
+local function k_warning() logs.report("fonts","don't call 'node.kerning' directly") k_warning=nil end
+function node.ligaturing(...)
+ if basemodepass and l_warning then
+ l_warning()
+ end
+ return n_ligaturing(...)
+end
+function node.kerning(...)
+ if basemodepass and k_warning then
+ k_warning()
+ end
+ return n_kerning(...)
+end
+function nuts.ligaturing(...)
+ if basemodepass and l_warning then
+ l_warning()
+ end
+ return d_ligaturing(...)
+end
+function nuts.kerning(...)
+ if basemodepass and k_warning then
+ k_warning()
+ end
+ return d_kerning(...)
+end
+function nodes.handlers.setbasemodepass(v)
+ basemodepass=v
+end
+local function nodepass(head,groupcode,size,packtype,direction)
+ local fontdata=fonts.hashes.identifiers
+ if fontdata then
+ local usedfonts={}
+ local basefonts={}
+ local prevfont=nil
+ local basefont=nil
+ local variants=nil
+ local redundant=nil
+ local nofused=0
+ for n in traverse_id(glyph_code,head) do
+ local font=getfont(n)
+ if font~=prevfont then
+ if basefont then
+ basefont[2]=getprev(n)
+ end
+ prevfont=font
+ local used=usedfonts[font]
+ if not used then
+ local tfmdata=fontdata[font]
+ if tfmdata then
+ local shared=tfmdata.shared
+ if shared then
+ local processors=shared.processes
+ if processors and #processors>0 then
+ usedfonts[font]=processors
+ nofused=nofused+1
+ elseif basemodepass then
+ basefont={ n,nil }
+ basefonts[#basefonts+1]=basefont
+ end
+ end
+ local resources=tfmdata.resources
+ variants=resources and resources.variants
+ variants=variants and next(variants) and variants or false
+ end
+ else
+ local tfmdata=fontdata[prevfont]
+ if tfmdata then
+ local resources=tfmdata.resources
+ variants=resources and resources.variants
+ variants=variants and next(variants) and variants or false
+ end
+ end
+ end
+ if variants then
+ local char=getchar(n)
+ if (char>=0xFE00 and char<=0xFE0F) or (char>=0xE0100 and char<=0xE01EF) then
+ local hash=variants[char]
+ if hash then
+ local p=getprev(n)
+ if p and getid(p)==glyph_code then
+ local variant=hash[getchar(p)]
+ if variant then
+ setchar(p,variant)
+ end
+ end
+ end
+ if not redundant then
+ redundant={ n }
+ else
+ redundant[#redundant+1]=n
+ end
+ end
+ end
+ end
+ local nofbasefonts=#basefonts
+ if redundant then
+ for i=1,#redundant do
+ local r=redundant[i]
+ local p,n=getboth(r)
+ if r==head then
+ head=n
+ setprev(n)
+ else
+ setlink(p,n)
+ end
+ if nofbasefonts>0 then
+ for i=1,nofbasefonts do
+ local bi=basefonts[i]
+ if r==bi[1] then
+ bi[1]=n
+ end
+ if r==bi[2] then
+ bi[2]=n
+ end
+ end
+ end
+ flush_node(r)
+ end
+ end
+ for d in traverse_id(disc_code,head) do
+ local _,_,r=getdisc(d)
+ if r then
+ for n in traverse_id(glyph_code,r) do
+ local font=getfont(n)
+ if font~=prevfont then
+ prevfont=font
+ local used=usedfonts[font]
+ if not used then
+ local tfmdata=fontdata[font]
+ if tfmdata then
+ local shared=tfmdata.shared
+ if shared then
+ local processors=shared.processes
+ if processors and #processors>0 then
+ usedfonts[font]=processors
+ nofused=nofused+1
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if next(usedfonts) then
+ for font,processors in next,usedfonts do
+ for i=1,#processors do
+ head=processors[i](head,font,0,direction,nofused) or head
+ end
+ end
+ end
+ if basemodepass and nofbasefonts>0 then
+ for i=1,nofbasefonts do
+ local range=basefonts[i]
+ local start=range[1]
+ local stop=range[2]
+ if start then
+ local front=head==start
+ local prev,next
+ if stop then
+ next=getnext(stop)
+ start,stop=d_ligaturing(start,stop)
+ start,stop=d_kerning(start,stop)
+ else
+ prev=getprev(start)
+ start=d_ligaturing(start)
+ start=d_kerning(start)
+ end
+ if prev then
+ setlink(prev,start)
+ end
+ if next then
+ setlink(stop,next)
+ end
+ if front and head~=start then
+ head=start
+ end
+ end
+ end
+ end
+ end
+ return head
+end
+local function basepass(head)
+ if basemodepass then
+ head=d_ligaturing(head)
+ head=d_kerning(head)
+ end
+ return head
+end
+local protectpass=node.direct.protect_glyphs
+local injectpass=nodes.injections.handler
+function nodes.handlers.nodepass(head,...)
+ if head then
+ return tonode(nodepass(tonut(head),...))
+ end
+end
+function nodes.handlers.basepass(head)
+ if head then
+ return tonode(basepass(tonut(head)))
+ end
+end
+function nodes.handlers.injectpass(head)
+ if head then
+ return tonode(injectpass(tonut(head)))
+ end
+end
+function nodes.handlers.protectpass(head)
+ if head then
+ protectpass(tonut(head))
+ return head
+ end
+end
+function nodes.simple_font_handler(head,groupcode,size,packtype,direction)
+ if head then
+ head=tonut(head)
+ head=nodepass(head,groupcode,size,packtype,direction)
+ head=injectpass(head)
+ if not basemodepass then
+ head=basepass(head)
+ end
+ protectpass(head)
+ head=tonode(head)
+ end
+ return head
+end
+
+end --- [luaotfload, fontloader-2019-08-13.lua scope for “fonts-gbn”] ---
+
+
+--- vim:ft=lua:sw=2:ts=8:et:tw=79
diff --git a/macros/luatex/generic/luaotfload/fontloader-basics-chr.lua b/macros/luatex/generic/luaotfload/fontloader-basics-chr.lua
new file mode 100644
index 0000000000..0ac0eab14e
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-basics-chr.lua
@@ -0,0 +1,3619 @@
+-- automatically generated from context data (luatex-basics-prepare.tex)
+
+characters = characters or { }
+
+-- dummies
+
+characters.blockrange = { }
+
+-- classifiers needed for analysis
+
+characters.classifiers={
+ [768]=5,
+ [769]=5,
+ [770]=5,
+ [771]=5,
+ [772]=5,
+ [773]=5,
+ [774]=5,
+ [775]=5,
+ [776]=5,
+ [777]=5,
+ [778]=5,
+ [779]=5,
+ [780]=5,
+ [781]=5,
+ [782]=5,
+ [783]=5,
+ [784]=5,
+ [785]=5,
+ [786]=5,
+ [787]=5,
+ [788]=5,
+ [789]=5,
+ [790]=5,
+ [791]=5,
+ [792]=5,
+ [793]=5,
+ [794]=5,
+ [795]=5,
+ [796]=5,
+ [797]=5,
+ [798]=5,
+ [799]=5,
+ [800]=5,
+ [801]=5,
+ [802]=5,
+ [803]=5,
+ [804]=5,
+ [805]=5,
+ [806]=5,
+ [807]=5,
+ [808]=5,
+ [809]=5,
+ [810]=5,
+ [811]=5,
+ [812]=5,
+ [813]=5,
+ [814]=5,
+ [815]=5,
+ [816]=5,
+ [817]=5,
+ [818]=5,
+ [819]=5,
+ [820]=5,
+ [821]=5,
+ [822]=5,
+ [823]=5,
+ [824]=5,
+ [825]=5,
+ [826]=5,
+ [827]=5,
+ [828]=5,
+ [829]=5,
+ [830]=5,
+ [831]=5,
+ [832]=5,
+ [833]=5,
+ [834]=5,
+ [835]=5,
+ [836]=5,
+ [837]=5,
+ [838]=5,
+ [839]=5,
+ [840]=5,
+ [841]=5,
+ [842]=5,
+ [843]=5,
+ [844]=5,
+ [845]=5,
+ [846]=5,
+ [847]=5,
+ [848]=5,
+ [849]=5,
+ [850]=5,
+ [851]=5,
+ [852]=5,
+ [853]=5,
+ [854]=5,
+ [855]=5,
+ [856]=5,
+ [857]=5,
+ [858]=5,
+ [859]=5,
+ [860]=5,
+ [861]=5,
+ [862]=5,
+ [863]=5,
+ [864]=5,
+ [865]=5,
+ [866]=5,
+ [867]=5,
+ [868]=5,
+ [869]=5,
+ [870]=5,
+ [871]=5,
+ [872]=5,
+ [873]=5,
+ [874]=5,
+ [875]=5,
+ [876]=5,
+ [877]=5,
+ [878]=5,
+ [879]=5,
+ [1155]=5,
+ [1156]=5,
+ [1157]=5,
+ [1158]=5,
+ [1159]=5,
+ [1425]=5,
+ [1426]=5,
+ [1427]=5,
+ [1428]=5,
+ [1429]=5,
+ [1430]=5,
+ [1431]=5,
+ [1432]=5,
+ [1433]=5,
+ [1434]=5,
+ [1435]=5,
+ [1436]=5,
+ [1437]=5,
+ [1438]=5,
+ [1439]=5,
+ [1440]=5,
+ [1441]=5,
+ [1442]=5,
+ [1443]=5,
+ [1444]=5,
+ [1445]=5,
+ [1446]=5,
+ [1447]=5,
+ [1448]=5,
+ [1449]=5,
+ [1450]=5,
+ [1451]=5,
+ [1452]=5,
+ [1453]=5,
+ [1454]=5,
+ [1455]=5,
+ [1456]=5,
+ [1457]=5,
+ [1458]=5,
+ [1459]=5,
+ [1460]=5,
+ [1461]=5,
+ [1462]=5,
+ [1463]=5,
+ [1464]=5,
+ [1465]=5,
+ [1466]=5,
+ [1467]=5,
+ [1468]=5,
+ [1469]=5,
+ [1471]=5,
+ [1473]=5,
+ [1474]=5,
+ [1476]=5,
+ [1477]=5,
+ [1479]=5,
+ [1536]=4,
+ [1537]=4,
+ [1538]=4,
+ [1539]=4,
+ [1540]=4,
+ [1541]=4,
+ [1542]=6,
+ [1543]=6,
+ [1544]=4,
+ [1545]=6,
+ [1546]=6,
+ [1547]=4,
+ [1548]=6,
+ [1549]=6,
+ [1550]=6,
+ [1551]=6,
+ [1552]=5,
+ [1553]=5,
+ [1554]=5,
+ [1555]=5,
+ [1556]=5,
+ [1557]=5,
+ [1558]=5,
+ [1559]=5,
+ [1560]=5,
+ [1561]=5,
+ [1562]=5,
+ [1563]=6,
+ [1564]=6,
+ [1566]=6,
+ [1567]=6,
+ [1568]=2,
+ [1569]=4,
+ [1570]=3,
+ [1571]=3,
+ [1572]=3,
+ [1573]=3,
+ [1574]=2,
+ [1575]=3,
+ [1576]=2,
+ [1577]=3,
+ [1578]=2,
+ [1579]=2,
+ [1580]=2,
+ [1581]=2,
+ [1582]=2,
+ [1583]=3,
+ [1584]=3,
+ [1585]=3,
+ [1586]=3,
+ [1587]=2,
+ [1588]=2,
+ [1589]=2,
+ [1590]=2,
+ [1591]=2,
+ [1592]=2,
+ [1593]=2,
+ [1594]=2,
+ [1595]=2,
+ [1596]=2,
+ [1597]=2,
+ [1598]=2,
+ [1599]=2,
+ [1600]=2,
+ [1601]=2,
+ [1602]=2,
+ [1603]=2,
+ [1604]=2,
+ [1605]=2,
+ [1606]=2,
+ [1607]=2,
+ [1608]=3,
+ [1609]=2,
+ [1610]=2,
+ [1611]=5,
+ [1612]=5,
+ [1613]=5,
+ [1614]=5,
+ [1615]=5,
+ [1616]=5,
+ [1617]=5,
+ [1618]=5,
+ [1619]=5,
+ [1620]=5,
+ [1621]=5,
+ [1622]=5,
+ [1623]=5,
+ [1624]=5,
+ [1625]=5,
+ [1626]=5,
+ [1627]=5,
+ [1628]=5,
+ [1629]=5,
+ [1630]=5,
+ [1631]=5,
+ [1632]=6,
+ [1633]=6,
+ [1634]=6,
+ [1635]=6,
+ [1636]=6,
+ [1637]=6,
+ [1638]=6,
+ [1639]=6,
+ [1640]=6,
+ [1641]=6,
+ [1642]=6,
+ [1643]=6,
+ [1644]=6,
+ [1645]=6,
+ [1646]=2,
+ [1647]=2,
+ [1648]=5,
+ [1649]=3,
+ [1650]=3,
+ [1651]=3,
+ [1652]=4,
+ [1653]=3,
+ [1654]=3,
+ [1655]=3,
+ [1656]=2,
+ [1657]=2,
+ [1658]=2,
+ [1659]=2,
+ [1660]=2,
+ [1661]=2,
+ [1662]=2,
+ [1663]=2,
+ [1664]=2,
+ [1665]=2,
+ [1666]=2,
+ [1667]=2,
+ [1668]=2,
+ [1669]=2,
+ [1670]=2,
+ [1671]=2,
+ [1672]=3,
+ [1673]=3,
+ [1674]=3,
+ [1675]=3,
+ [1676]=3,
+ [1677]=3,
+ [1678]=3,
+ [1679]=3,
+ [1680]=3,
+ [1681]=3,
+ [1682]=3,
+ [1683]=3,
+ [1684]=3,
+ [1685]=3,
+ [1686]=3,
+ [1687]=3,
+ [1688]=3,
+ [1689]=3,
+ [1690]=2,
+ [1691]=2,
+ [1692]=2,
+ [1693]=2,
+ [1694]=2,
+ [1695]=2,
+ [1696]=2,
+ [1697]=2,
+ [1698]=2,
+ [1699]=2,
+ [1700]=2,
+ [1701]=2,
+ [1702]=2,
+ [1703]=2,
+ [1704]=2,
+ [1705]=2,
+ [1706]=2,
+ [1707]=2,
+ [1708]=2,
+ [1709]=2,
+ [1710]=2,
+ [1711]=2,
+ [1712]=2,
+ [1713]=2,
+ [1714]=2,
+ [1715]=2,
+ [1716]=2,
+ [1717]=2,
+ [1718]=2,
+ [1719]=2,
+ [1720]=2,
+ [1721]=2,
+ [1722]=2,
+ [1723]=2,
+ [1724]=2,
+ [1725]=2,
+ [1726]=2,
+ [1727]=2,
+ [1728]=3,
+ [1729]=2,
+ [1730]=2,
+ [1731]=3,
+ [1732]=3,
+ [1733]=3,
+ [1734]=3,
+ [1735]=3,
+ [1736]=3,
+ [1737]=3,
+ [1738]=3,
+ [1739]=3,
+ [1740]=2,
+ [1741]=3,
+ [1742]=2,
+ [1743]=3,
+ [1744]=2,
+ [1745]=2,
+ [1746]=3,
+ [1747]=3,
+ [1748]=6,
+ [1749]=3,
+ [1750]=5,
+ [1751]=5,
+ [1752]=5,
+ [1753]=5,
+ [1754]=5,
+ [1755]=5,
+ [1756]=5,
+ [1757]=4,
+ [1758]=6,
+ [1759]=5,
+ [1760]=5,
+ [1761]=5,
+ [1762]=5,
+ [1763]=5,
+ [1764]=5,
+ [1765]=6,
+ [1766]=6,
+ [1767]=5,
+ [1768]=5,
+ [1769]=6,
+ [1770]=5,
+ [1771]=5,
+ [1772]=5,
+ [1773]=5,
+ [1774]=3,
+ [1775]=3,
+ [1776]=6,
+ [1777]=6,
+ [1778]=6,
+ [1779]=6,
+ [1780]=6,
+ [1781]=6,
+ [1782]=6,
+ [1783]=6,
+ [1784]=6,
+ [1785]=6,
+ [1786]=2,
+ [1787]=2,
+ [1788]=2,
+ [1789]=6,
+ [1790]=6,
+ [1791]=2,
+ [1792]=6,
+ [1793]=6,
+ [1794]=6,
+ [1795]=6,
+ [1796]=6,
+ [1797]=6,
+ [1798]=6,
+ [1799]=6,
+ [1800]=6,
+ [1801]=6,
+ [1802]=6,
+ [1803]=6,
+ [1804]=6,
+ [1805]=6,
+ [1808]=3,
+ [1809]=5,
+ [1810]=2,
+ [1811]=2,
+ [1812]=2,
+ [1813]=3,
+ [1814]=3,
+ [1815]=3,
+ [1816]=3,
+ [1817]=3,
+ [1818]=2,
+ [1819]=2,
+ [1820]=2,
+ [1821]=2,
+ [1822]=3,
+ [1823]=2,
+ [1824]=2,
+ [1825]=2,
+ [1826]=2,
+ [1827]=2,
+ [1828]=2,
+ [1829]=2,
+ [1830]=2,
+ [1831]=2,
+ [1832]=3,
+ [1833]=2,
+ [1834]=3,
+ [1835]=2,
+ [1836]=3,
+ [1837]=2,
+ [1838]=2,
+ [1839]=3,
+ [1840]=5,
+ [1841]=5,
+ [1842]=5,
+ [1843]=5,
+ [1844]=5,
+ [1845]=5,
+ [1846]=5,
+ [1847]=5,
+ [1848]=5,
+ [1849]=5,
+ [1850]=5,
+ [1851]=5,
+ [1852]=5,
+ [1853]=5,
+ [1854]=5,
+ [1855]=5,
+ [1856]=5,
+ [1857]=5,
+ [1858]=5,
+ [1859]=5,
+ [1860]=5,
+ [1861]=5,
+ [1862]=5,
+ [1863]=5,
+ [1864]=5,
+ [1865]=5,
+ [1866]=5,
+ [1869]=3,
+ [1870]=2,
+ [1871]=2,
+ [1872]=2,
+ [1873]=2,
+ [1874]=2,
+ [1875]=2,
+ [1876]=2,
+ [1877]=2,
+ [1878]=2,
+ [1879]=2,
+ [1880]=2,
+ [1881]=3,
+ [1882]=3,
+ [1883]=3,
+ [1884]=2,
+ [1885]=2,
+ [1886]=2,
+ [1887]=2,
+ [1888]=2,
+ [1889]=2,
+ [1890]=2,
+ [1891]=2,
+ [1892]=2,
+ [1893]=2,
+ [1894]=2,
+ [1895]=2,
+ [1896]=2,
+ [1897]=2,
+ [1898]=2,
+ [1899]=3,
+ [1900]=3,
+ [1901]=2,
+ [1902]=2,
+ [1903]=2,
+ [1904]=2,
+ [1905]=3,
+ [1906]=2,
+ [1907]=3,
+ [1908]=3,
+ [1909]=2,
+ [1910]=2,
+ [1911]=2,
+ [1912]=3,
+ [1913]=3,
+ [1914]=2,
+ [1915]=2,
+ [1916]=2,
+ [1917]=2,
+ [1918]=2,
+ [1919]=2,
+ [1958]=5,
+ [1959]=5,
+ [1960]=5,
+ [1961]=5,
+ [1962]=5,
+ [1963]=5,
+ [1964]=5,
+ [1965]=5,
+ [1966]=5,
+ [1967]=5,
+ [1968]=5,
+ [1984]=6,
+ [1985]=6,
+ [1986]=6,
+ [1987]=6,
+ [1988]=6,
+ [1989]=6,
+ [1990]=6,
+ [1991]=6,
+ [1992]=6,
+ [1993]=6,
+ [1994]=2,
+ [1995]=2,
+ [1996]=2,
+ [1997]=2,
+ [1998]=2,
+ [1999]=2,
+ [2000]=2,
+ [2001]=2,
+ [2002]=2,
+ [2003]=2,
+ [2004]=2,
+ [2005]=2,
+ [2006]=2,
+ [2007]=2,
+ [2008]=2,
+ [2009]=2,
+ [2010]=2,
+ [2011]=2,
+ [2012]=2,
+ [2013]=2,
+ [2014]=2,
+ [2015]=2,
+ [2016]=2,
+ [2017]=2,
+ [2018]=2,
+ [2019]=2,
+ [2020]=2,
+ [2021]=2,
+ [2022]=2,
+ [2023]=2,
+ [2024]=2,
+ [2025]=2,
+ [2026]=2,
+ [2027]=5,
+ [2028]=5,
+ [2029]=5,
+ [2030]=5,
+ [2031]=5,
+ [2032]=5,
+ [2033]=5,
+ [2034]=5,
+ [2035]=5,
+ [2036]=6,
+ [2037]=6,
+ [2038]=6,
+ [2039]=6,
+ [2040]=6,
+ [2041]=6,
+ [2042]=2,
+ [2045]=5,
+ [2046]=6,
+ [2047]=6,
+ [2070]=5,
+ [2071]=5,
+ [2072]=5,
+ [2073]=5,
+ [2075]=5,
+ [2076]=5,
+ [2077]=5,
+ [2078]=5,
+ [2079]=5,
+ [2080]=5,
+ [2081]=5,
+ [2082]=5,
+ [2083]=5,
+ [2085]=5,
+ [2086]=5,
+ [2087]=5,
+ [2089]=5,
+ [2090]=5,
+ [2091]=5,
+ [2092]=5,
+ [2093]=5,
+ [2112]=3,
+ [2113]=2,
+ [2114]=2,
+ [2115]=2,
+ [2116]=2,
+ [2117]=2,
+ [2118]=3,
+ [2119]=3,
+ [2120]=2,
+ [2121]=3,
+ [2122]=2,
+ [2123]=2,
+ [2124]=2,
+ [2125]=2,
+ [2126]=2,
+ [2127]=2,
+ [2128]=2,
+ [2129]=2,
+ [2130]=2,
+ [2131]=2,
+ [2132]=3,
+ [2133]=2,
+ [2134]=4,
+ [2135]=4,
+ [2136]=4,
+ [2137]=5,
+ [2138]=5,
+ [2139]=5,
+ [2144]=2,
+ [2145]=4,
+ [2146]=2,
+ [2147]=2,
+ [2148]=2,
+ [2149]=2,
+ [2150]=4,
+ [2151]=3,
+ [2152]=2,
+ [2153]=3,
+ [2154]=3,
+ [2208]=2,
+ [2209]=2,
+ [2210]=2,
+ [2211]=2,
+ [2212]=2,
+ [2213]=2,
+ [2214]=2,
+ [2215]=2,
+ [2216]=2,
+ [2217]=2,
+ [2218]=3,
+ [2219]=3,
+ [2220]=3,
+ [2221]=4,
+ [2222]=3,
+ [2223]=2,
+ [2224]=2,
+ [2225]=3,
+ [2226]=3,
+ [2227]=2,
+ [2228]=2,
+ [2230]=2,
+ [2231]=2,
+ [2232]=2,
+ [2233]=3,
+ [2234]=2,
+ [2235]=2,
+ [2236]=2,
+ [2237]=2,
+ [2259]=5,
+ [2260]=5,
+ [2261]=5,
+ [2262]=5,
+ [2263]=5,
+ [2264]=5,
+ [2265]=5,
+ [2266]=5,
+ [2267]=5,
+ [2268]=5,
+ [2269]=5,
+ [2270]=5,
+ [2271]=5,
+ [2272]=5,
+ [2273]=5,
+ [2274]=4,
+ [2275]=5,
+ [2276]=5,
+ [2277]=5,
+ [2278]=5,
+ [2279]=5,
+ [2280]=5,
+ [2281]=5,
+ [2282]=5,
+ [2283]=5,
+ [2284]=5,
+ [2285]=5,
+ [2286]=5,
+ [2287]=5,
+ [2288]=5,
+ [2289]=5,
+ [2290]=5,
+ [2291]=5,
+ [2292]=5,
+ [2293]=5,
+ [2294]=5,
+ [2295]=5,
+ [2296]=5,
+ [2297]=5,
+ [2298]=5,
+ [2299]=5,
+ [2300]=5,
+ [2301]=5,
+ [2302]=5,
+ [2303]=5,
+ [2304]=5,
+ [2305]=5,
+ [2306]=5,
+ [2362]=5,
+ [2364]=5,
+ [2369]=5,
+ [2370]=5,
+ [2371]=5,
+ [2372]=5,
+ [2373]=5,
+ [2374]=5,
+ [2375]=5,
+ [2376]=5,
+ [2381]=5,
+ [2385]=5,
+ [2386]=5,
+ [2387]=5,
+ [2388]=5,
+ [2389]=5,
+ [2390]=5,
+ [2391]=5,
+ [2402]=5,
+ [2403]=5,
+ [2433]=5,
+ [2492]=5,
+ [2497]=5,
+ [2498]=5,
+ [2499]=5,
+ [2500]=5,
+ [2509]=5,
+ [2530]=5,
+ [2531]=5,
+ [2558]=5,
+ [2561]=5,
+ [2562]=5,
+ [2620]=5,
+ [2625]=5,
+ [2626]=5,
+ [2631]=5,
+ [2632]=5,
+ [2635]=5,
+ [2636]=5,
+ [2637]=5,
+ [2641]=5,
+ [2672]=5,
+ [2673]=5,
+ [2677]=5,
+ [2689]=5,
+ [2690]=5,
+ [2748]=5,
+ [2753]=5,
+ [2754]=5,
+ [2755]=5,
+ [2756]=5,
+ [2757]=5,
+ [2759]=5,
+ [2760]=5,
+ [2765]=5,
+ [2786]=5,
+ [2787]=5,
+ [2810]=5,
+ [2811]=5,
+ [2812]=5,
+ [2813]=5,
+ [2814]=5,
+ [2815]=5,
+ [2817]=5,
+ [2876]=5,
+ [2879]=5,
+ [2881]=5,
+ [2882]=5,
+ [2883]=5,
+ [2884]=5,
+ [2893]=5,
+ [2902]=5,
+ [2914]=5,
+ [2915]=5,
+ [2946]=5,
+ [3008]=5,
+ [3021]=5,
+ [3072]=5,
+ [3076]=5,
+ [3134]=5,
+ [3135]=5,
+ [3136]=5,
+ [3142]=5,
+ [3143]=5,
+ [3144]=5,
+ [3146]=5,
+ [3147]=5,
+ [3148]=5,
+ [3149]=5,
+ [3157]=5,
+ [3158]=5,
+ [3170]=5,
+ [3171]=5,
+ [3201]=5,
+ [3260]=5,
+ [3263]=5,
+ [3270]=5,
+ [3276]=5,
+ [3277]=5,
+ [3298]=5,
+ [3299]=5,
+ [3328]=5,
+ [3329]=5,
+ [3387]=5,
+ [3388]=5,
+ [3393]=5,
+ [3394]=5,
+ [3395]=5,
+ [3396]=5,
+ [3405]=5,
+ [3426]=5,
+ [3427]=5,
+ [3530]=5,
+ [3538]=5,
+ [3539]=5,
+ [3540]=5,
+ [3542]=5,
+ [3633]=5,
+ [3636]=5,
+ [3637]=5,
+ [3638]=5,
+ [3639]=5,
+ [3640]=5,
+ [3641]=5,
+ [3642]=5,
+ [3655]=5,
+ [3656]=5,
+ [3657]=5,
+ [3658]=5,
+ [3659]=5,
+ [3660]=5,
+ [3661]=5,
+ [3662]=5,
+ [3761]=5,
+ [3764]=5,
+ [3765]=5,
+ [3766]=5,
+ [3767]=5,
+ [3768]=5,
+ [3769]=5,
+ [3770]=5,
+ [3771]=5,
+ [3772]=5,
+ [3784]=5,
+ [3785]=5,
+ [3786]=5,
+ [3787]=5,
+ [3788]=5,
+ [3789]=5,
+ [3864]=5,
+ [3865]=5,
+ [3893]=5,
+ [3895]=5,
+ [3897]=5,
+ [3953]=5,
+ [3954]=5,
+ [3955]=5,
+ [3956]=5,
+ [3957]=5,
+ [3958]=5,
+ [3959]=5,
+ [3960]=5,
+ [3961]=5,
+ [3962]=5,
+ [3963]=5,
+ [3964]=5,
+ [3965]=5,
+ [3966]=5,
+ [3968]=5,
+ [3969]=5,
+ [3970]=5,
+ [3971]=5,
+ [3972]=5,
+ [3974]=5,
+ [3975]=5,
+ [3981]=5,
+ [3982]=5,
+ [3983]=5,
+ [3984]=5,
+ [3985]=5,
+ [3986]=5,
+ [3987]=5,
+ [3988]=5,
+ [3989]=5,
+ [3990]=5,
+ [3991]=5,
+ [3993]=5,
+ [3994]=5,
+ [3995]=5,
+ [3996]=5,
+ [3997]=5,
+ [3998]=5,
+ [3999]=5,
+ [4000]=5,
+ [4001]=5,
+ [4002]=5,
+ [4003]=5,
+ [4004]=5,
+ [4005]=5,
+ [4006]=5,
+ [4007]=5,
+ [4008]=5,
+ [4009]=5,
+ [4010]=5,
+ [4011]=5,
+ [4012]=5,
+ [4013]=5,
+ [4014]=5,
+ [4015]=5,
+ [4016]=5,
+ [4017]=5,
+ [4018]=5,
+ [4019]=5,
+ [4020]=5,
+ [4021]=5,
+ [4022]=5,
+ [4023]=5,
+ [4024]=5,
+ [4025]=5,
+ [4026]=5,
+ [4027]=5,
+ [4028]=5,
+ [4038]=5,
+ [4141]=5,
+ [4142]=5,
+ [4143]=5,
+ [4144]=5,
+ [4146]=5,
+ [4147]=5,
+ [4148]=5,
+ [4149]=5,
+ [4150]=5,
+ [4151]=5,
+ [4153]=5,
+ [4154]=5,
+ [4157]=5,
+ [4158]=5,
+ [4184]=5,
+ [4185]=5,
+ [4190]=5,
+ [4191]=5,
+ [4192]=5,
+ [4209]=5,
+ [4210]=5,
+ [4211]=5,
+ [4212]=5,
+ [4226]=5,
+ [4229]=5,
+ [4230]=5,
+ [4237]=5,
+ [4253]=5,
+ [4957]=5,
+ [4958]=5,
+ [4959]=5,
+ [5906]=5,
+ [5907]=5,
+ [5908]=5,
+ [5938]=5,
+ [5939]=5,
+ [5940]=5,
+ [5970]=5,
+ [5971]=5,
+ [6002]=5,
+ [6003]=5,
+ [6071]=5,
+ [6072]=5,
+ [6073]=5,
+ [6074]=5,
+ [6075]=5,
+ [6076]=5,
+ [6077]=5,
+ [6086]=5,
+ [6089]=5,
+ [6090]=5,
+ [6091]=5,
+ [6092]=5,
+ [6093]=5,
+ [6094]=5,
+ [6095]=5,
+ [6096]=5,
+ [6097]=5,
+ [6098]=5,
+ [6099]=5,
+ [6109]=5,
+ [6150]=4,
+ [6151]=2,
+ [6154]=2,
+ [6155]=5,
+ [6156]=5,
+ [6157]=5,
+ [6158]=4,
+ [6176]=2,
+ [6177]=2,
+ [6178]=2,
+ [6179]=2,
+ [6180]=2,
+ [6181]=2,
+ [6182]=2,
+ [6183]=2,
+ [6184]=2,
+ [6185]=2,
+ [6186]=2,
+ [6187]=2,
+ [6188]=2,
+ [6189]=2,
+ [6190]=2,
+ [6191]=2,
+ [6192]=2,
+ [6193]=2,
+ [6194]=2,
+ [6195]=2,
+ [6196]=2,
+ [6197]=2,
+ [6198]=2,
+ [6199]=2,
+ [6200]=2,
+ [6201]=2,
+ [6202]=2,
+ [6203]=2,
+ [6204]=2,
+ [6205]=2,
+ [6206]=2,
+ [6207]=2,
+ [6208]=2,
+ [6209]=2,
+ [6210]=2,
+ [6211]=2,
+ [6212]=2,
+ [6213]=2,
+ [6214]=2,
+ [6215]=2,
+ [6216]=2,
+ [6217]=2,
+ [6218]=2,
+ [6219]=2,
+ [6220]=2,
+ [6221]=2,
+ [6222]=2,
+ [6223]=2,
+ [6224]=2,
+ [6225]=2,
+ [6226]=2,
+ [6227]=2,
+ [6228]=2,
+ [6229]=2,
+ [6230]=2,
+ [6231]=2,
+ [6232]=2,
+ [6233]=2,
+ [6234]=2,
+ [6235]=2,
+ [6236]=2,
+ [6237]=2,
+ [6238]=2,
+ [6239]=2,
+ [6240]=2,
+ [6241]=2,
+ [6242]=2,
+ [6243]=2,
+ [6244]=2,
+ [6245]=2,
+ [6246]=2,
+ [6247]=2,
+ [6248]=2,
+ [6249]=2,
+ [6250]=2,
+ [6251]=2,
+ [6252]=2,
+ [6253]=2,
+ [6254]=2,
+ [6255]=2,
+ [6256]=2,
+ [6257]=2,
+ [6258]=2,
+ [6259]=2,
+ [6260]=2,
+ [6261]=2,
+ [6262]=2,
+ [6263]=2,
+ [6264]=2,
+ [6272]=4,
+ [6273]=4,
+ [6274]=4,
+ [6275]=4,
+ [6276]=4,
+ [6279]=2,
+ [6280]=2,
+ [6281]=2,
+ [6282]=2,
+ [6283]=2,
+ [6284]=2,
+ [6285]=2,
+ [6286]=2,
+ [6287]=2,
+ [6288]=2,
+ [6289]=2,
+ [6290]=2,
+ [6291]=2,
+ [6292]=2,
+ [6293]=2,
+ [6294]=2,
+ [6295]=2,
+ [6296]=2,
+ [6297]=2,
+ [6298]=2,
+ [6299]=2,
+ [6300]=2,
+ [6301]=2,
+ [6302]=2,
+ [6303]=2,
+ [6304]=2,
+ [6305]=2,
+ [6306]=2,
+ [6307]=2,
+ [6308]=2,
+ [6309]=2,
+ [6310]=2,
+ [6311]=2,
+ [6312]=2,
+ [6313]=5,
+ [6314]=2,
+ [6432]=5,
+ [6433]=5,
+ [6434]=5,
+ [6439]=5,
+ [6440]=5,
+ [6450]=5,
+ [6457]=5,
+ [6458]=5,
+ [6459]=5,
+ [6679]=5,
+ [6680]=5,
+ [6742]=5,
+ [6744]=5,
+ [6745]=5,
+ [6746]=5,
+ [6747]=5,
+ [6748]=5,
+ [6749]=5,
+ [6750]=5,
+ [6752]=5,
+ [6754]=5,
+ [6757]=5,
+ [6758]=5,
+ [6759]=5,
+ [6760]=5,
+ [6761]=5,
+ [6762]=5,
+ [6763]=5,
+ [6764]=5,
+ [6771]=5,
+ [6772]=5,
+ [6773]=5,
+ [6774]=5,
+ [6775]=5,
+ [6776]=5,
+ [6777]=5,
+ [6778]=5,
+ [6779]=5,
+ [6780]=5,
+ [6783]=5,
+ [6832]=5,
+ [6833]=5,
+ [6834]=5,
+ [6835]=5,
+ [6836]=5,
+ [6837]=5,
+ [6838]=5,
+ [6839]=5,
+ [6840]=5,
+ [6841]=5,
+ [6842]=5,
+ [6843]=5,
+ [6844]=5,
+ [6845]=5,
+ [6912]=5,
+ [6913]=5,
+ [6914]=5,
+ [6915]=5,
+ [6964]=5,
+ [6966]=5,
+ [6967]=5,
+ [6968]=5,
+ [6969]=5,
+ [6970]=5,
+ [6972]=5,
+ [6978]=5,
+ [7019]=5,
+ [7020]=5,
+ [7021]=5,
+ [7022]=5,
+ [7023]=5,
+ [7024]=5,
+ [7025]=5,
+ [7026]=5,
+ [7027]=5,
+ [7040]=5,
+ [7041]=5,
+ [7074]=5,
+ [7075]=5,
+ [7076]=5,
+ [7077]=5,
+ [7080]=5,
+ [7081]=5,
+ [7083]=5,
+ [7142]=5,
+ [7144]=5,
+ [7145]=5,
+ [7149]=5,
+ [7151]=5,
+ [7152]=5,
+ [7153]=5,
+ [7212]=5,
+ [7213]=5,
+ [7214]=5,
+ [7215]=5,
+ [7216]=5,
+ [7217]=5,
+ [7218]=5,
+ [7219]=5,
+ [7222]=5,
+ [7223]=5,
+ [7376]=5,
+ [7377]=5,
+ [7378]=5,
+ [7380]=5,
+ [7381]=5,
+ [7382]=5,
+ [7383]=5,
+ [7384]=5,
+ [7385]=5,
+ [7386]=5,
+ [7387]=5,
+ [7388]=5,
+ [7389]=5,
+ [7390]=5,
+ [7391]=5,
+ [7392]=5,
+ [7394]=5,
+ [7395]=5,
+ [7396]=5,
+ [7397]=5,
+ [7398]=5,
+ [7399]=5,
+ [7400]=5,
+ [7405]=5,
+ [7412]=5,
+ [7416]=5,
+ [7417]=5,
+ [7616]=5,
+ [7617]=5,
+ [7618]=5,
+ [7619]=5,
+ [7620]=5,
+ [7621]=5,
+ [7622]=5,
+ [7623]=5,
+ [7624]=5,
+ [7625]=5,
+ [7626]=5,
+ [7627]=5,
+ [7628]=5,
+ [7629]=5,
+ [7630]=5,
+ [7631]=5,
+ [7632]=5,
+ [7633]=5,
+ [7634]=5,
+ [7635]=5,
+ [7636]=5,
+ [7637]=5,
+ [7638]=5,
+ [7639]=5,
+ [7640]=5,
+ [7641]=5,
+ [7642]=5,
+ [7643]=5,
+ [7644]=5,
+ [7645]=5,
+ [7646]=5,
+ [7647]=5,
+ [7648]=5,
+ [7649]=5,
+ [7650]=5,
+ [7651]=5,
+ [7652]=5,
+ [7653]=5,
+ [7654]=5,
+ [7655]=5,
+ [7656]=5,
+ [7657]=5,
+ [7658]=5,
+ [7659]=5,
+ [7660]=5,
+ [7661]=5,
+ [7662]=5,
+ [7663]=5,
+ [7664]=5,
+ [7665]=5,
+ [7666]=5,
+ [7667]=5,
+ [7668]=5,
+ [7669]=5,
+ [7670]=5,
+ [7671]=5,
+ [7672]=5,
+ [7673]=5,
+ [7675]=5,
+ [7676]=5,
+ [7677]=5,
+ [7678]=5,
+ [7679]=5,
+ [8204]=4,
+ [8205]=2,
+ [8239]=4,
+ [8294]=4,
+ [8295]=4,
+ [8296]=4,
+ [8297]=4,
+ [8400]=5,
+ [8401]=5,
+ [8402]=5,
+ [8403]=5,
+ [8404]=5,
+ [8405]=5,
+ [8406]=5,
+ [8407]=5,
+ [8408]=5,
+ [8409]=5,
+ [8410]=5,
+ [8411]=5,
+ [8412]=5,
+ [8417]=5,
+ [8421]=5,
+ [8422]=5,
+ [8423]=5,
+ [8424]=5,
+ [8425]=5,
+ [8426]=5,
+ [8427]=5,
+ [8428]=5,
+ [8429]=5,
+ [8430]=5,
+ [8431]=5,
+ [8432]=5,
+ [11503]=5,
+ [11504]=5,
+ [11505]=5,
+ [11647]=5,
+ [11744]=5,
+ [11745]=5,
+ [11746]=5,
+ [11747]=5,
+ [11748]=5,
+ [11749]=5,
+ [11750]=5,
+ [11751]=5,
+ [11752]=5,
+ [11753]=5,
+ [11754]=5,
+ [11755]=5,
+ [11756]=5,
+ [11757]=5,
+ [11758]=5,
+ [11759]=5,
+ [11760]=5,
+ [11761]=5,
+ [11762]=5,
+ [11763]=5,
+ [11764]=5,
+ [11765]=5,
+ [11766]=5,
+ [11767]=5,
+ [11768]=5,
+ [11769]=5,
+ [11770]=5,
+ [11771]=5,
+ [11772]=5,
+ [11773]=5,
+ [11774]=5,
+ [11775]=5,
+ [12330]=5,
+ [12331]=5,
+ [12332]=5,
+ [12333]=5,
+ [12334]=5,
+ [12335]=5,
+ [12441]=5,
+ [12442]=5,
+ [42607]=5,
+ [42612]=5,
+ [42613]=5,
+ [42614]=5,
+ [42615]=5,
+ [42616]=5,
+ [42617]=5,
+ [42618]=5,
+ [42619]=5,
+ [42620]=5,
+ [42621]=5,
+ [42654]=5,
+ [42655]=5,
+ [42736]=5,
+ [42737]=5,
+ [43014]=5,
+ [43019]=5,
+ [43045]=5,
+ [43046]=5,
+ [43072]=2,
+ [43073]=2,
+ [43074]=2,
+ [43075]=2,
+ [43076]=2,
+ [43077]=2,
+ [43078]=2,
+ [43079]=2,
+ [43080]=2,
+ [43081]=2,
+ [43082]=2,
+ [43083]=2,
+ [43084]=2,
+ [43085]=2,
+ [43086]=2,
+ [43087]=2,
+ [43088]=2,
+ [43089]=2,
+ [43090]=2,
+ [43091]=2,
+ [43092]=2,
+ [43093]=2,
+ [43094]=2,
+ [43095]=2,
+ [43096]=2,
+ [43097]=2,
+ [43098]=2,
+ [43099]=2,
+ [43100]=2,
+ [43101]=2,
+ [43102]=2,
+ [43103]=2,
+ [43104]=2,
+ [43105]=2,
+ [43106]=2,
+ [43107]=2,
+ [43108]=2,
+ [43109]=2,
+ [43110]=2,
+ [43111]=2,
+ [43112]=2,
+ [43113]=2,
+ [43114]=2,
+ [43115]=2,
+ [43116]=2,
+ [43117]=2,
+ [43118]=2,
+ [43119]=2,
+ [43120]=2,
+ [43121]=2,
+ [43122]=1,
+ [43123]=4,
+ [43204]=5,
+ [43205]=5,
+ [43232]=5,
+ [43233]=5,
+ [43234]=5,
+ [43235]=5,
+ [43236]=5,
+ [43237]=5,
+ [43238]=5,
+ [43239]=5,
+ [43240]=5,
+ [43241]=5,
+ [43242]=5,
+ [43243]=5,
+ [43244]=5,
+ [43245]=5,
+ [43246]=5,
+ [43247]=5,
+ [43248]=5,
+ [43249]=5,
+ [43263]=5,
+ [43302]=5,
+ [43303]=5,
+ [43304]=5,
+ [43305]=5,
+ [43306]=5,
+ [43307]=5,
+ [43308]=5,
+ [43309]=5,
+ [43335]=5,
+ [43336]=5,
+ [43337]=5,
+ [43338]=5,
+ [43339]=5,
+ [43340]=5,
+ [43341]=5,
+ [43342]=5,
+ [43343]=5,
+ [43344]=5,
+ [43345]=5,
+ [43392]=5,
+ [43393]=5,
+ [43394]=5,
+ [43443]=5,
+ [43446]=5,
+ [43447]=5,
+ [43448]=5,
+ [43449]=5,
+ [43452]=5,
+ [43493]=5,
+ [43561]=5,
+ [43562]=5,
+ [43563]=5,
+ [43564]=5,
+ [43565]=5,
+ [43566]=5,
+ [43569]=5,
+ [43570]=5,
+ [43573]=5,
+ [43574]=5,
+ [43587]=5,
+ [43596]=5,
+ [43644]=5,
+ [43696]=5,
+ [43698]=5,
+ [43699]=5,
+ [43700]=5,
+ [43703]=5,
+ [43704]=5,
+ [43710]=5,
+ [43711]=5,
+ [43713]=5,
+ [43756]=5,
+ [43757]=5,
+ [43766]=5,
+ [44005]=5,
+ [44008]=5,
+ [44013]=5,
+ [64286]=5,
+ [65056]=5,
+ [65057]=5,
+ [65058]=5,
+ [65059]=5,
+ [65060]=5,
+ [65061]=5,
+ [65062]=5,
+ [65063]=5,
+ [65064]=5,
+ [65065]=5,
+ [65066]=5,
+ [65067]=5,
+ [65068]=5,
+ [65069]=5,
+ [65070]=5,
+ [65071]=5,
+ [66045]=5,
+ [66272]=5,
+ [66422]=5,
+ [66423]=5,
+ [66424]=5,
+ [66425]=5,
+ [66426]=5,
+ [68097]=5,
+ [68098]=5,
+ [68099]=5,
+ [68101]=5,
+ [68102]=5,
+ [68108]=5,
+ [68109]=5,
+ [68110]=5,
+ [68111]=5,
+ [68152]=5,
+ [68153]=5,
+ [68154]=5,
+ [68159]=5,
+ [68288]=2,
+ [68289]=2,
+ [68290]=2,
+ [68291]=2,
+ [68292]=2,
+ [68293]=3,
+ [68294]=4,
+ [68295]=3,
+ [68296]=4,
+ [68297]=3,
+ [68298]=3,
+ [68299]=4,
+ [68300]=4,
+ [68301]=1,
+ [68302]=3,
+ [68303]=3,
+ [68304]=3,
+ [68305]=3,
+ [68306]=3,
+ [68307]=2,
+ [68308]=2,
+ [68309]=2,
+ [68310]=2,
+ [68311]=1,
+ [68312]=2,
+ [68313]=2,
+ [68314]=2,
+ [68315]=2,
+ [68316]=2,
+ [68317]=3,
+ [68318]=2,
+ [68319]=2,
+ [68320]=2,
+ [68321]=3,
+ [68322]=4,
+ [68323]=4,
+ [68324]=3,
+ [68325]=5,
+ [68326]=5,
+ [68331]=2,
+ [68332]=2,
+ [68333]=2,
+ [68334]=2,
+ [68335]=3,
+ [68480]=2,
+ [68481]=3,
+ [68482]=2,
+ [68483]=3,
+ [68484]=3,
+ [68485]=3,
+ [68486]=2,
+ [68487]=2,
+ [68488]=2,
+ [68489]=3,
+ [68490]=2,
+ [68491]=2,
+ [68492]=3,
+ [68493]=2,
+ [68494]=3,
+ [68495]=3,
+ [68496]=2,
+ [68497]=3,
+ [68521]=3,
+ [68522]=3,
+ [68523]=3,
+ [68524]=3,
+ [68525]=2,
+ [68526]=2,
+ [68527]=4,
+ [68864]=1,
+ [68865]=2,
+ [68866]=2,
+ [68867]=2,
+ [68868]=2,
+ [68869]=2,
+ [68870]=2,
+ [68871]=2,
+ [68872]=2,
+ [68873]=2,
+ [68874]=2,
+ [68875]=2,
+ [68876]=2,
+ [68877]=2,
+ [68878]=2,
+ [68879]=2,
+ [68880]=2,
+ [68881]=2,
+ [68882]=2,
+ [68883]=2,
+ [68884]=2,
+ [68885]=2,
+ [68886]=2,
+ [68887]=2,
+ [68888]=2,
+ [68889]=2,
+ [68890]=2,
+ [68891]=2,
+ [68892]=2,
+ [68893]=2,
+ [68894]=2,
+ [68895]=2,
+ [68896]=2,
+ [68897]=2,
+ [68898]=3,
+ [68899]=2,
+ [68900]=5,
+ [68901]=5,
+ [68902]=5,
+ [68903]=5,
+ [69424]=2,
+ [69425]=2,
+ [69426]=2,
+ [69427]=3,
+ [69428]=2,
+ [69429]=2,
+ [69430]=2,
+ [69431]=2,
+ [69432]=2,
+ [69433]=2,
+ [69434]=2,
+ [69435]=2,
+ [69436]=2,
+ [69437]=2,
+ [69438]=2,
+ [69439]=2,
+ [69440]=2,
+ [69441]=2,
+ [69442]=2,
+ [69443]=2,
+ [69444]=2,
+ [69445]=4,
+ [69446]=5,
+ [69447]=5,
+ [69448]=5,
+ [69449]=5,
+ [69450]=5,
+ [69451]=5,
+ [69452]=5,
+ [69453]=5,
+ [69454]=5,
+ [69455]=5,
+ [69456]=5,
+ [69457]=2,
+ [69458]=2,
+ [69459]=2,
+ [69460]=3,
+ [69633]=5,
+ [69688]=5,
+ [69689]=5,
+ [69690]=5,
+ [69691]=5,
+ [69692]=5,
+ [69693]=5,
+ [69694]=5,
+ [69695]=5,
+ [69696]=5,
+ [69697]=5,
+ [69698]=5,
+ [69699]=5,
+ [69700]=5,
+ [69701]=5,
+ [69702]=5,
+ [69759]=5,
+ [69760]=5,
+ [69761]=5,
+ [69811]=5,
+ [69812]=5,
+ [69813]=5,
+ [69814]=5,
+ [69817]=5,
+ [69818]=5,
+ [69821]=4,
+ [69837]=4,
+ [69888]=5,
+ [69889]=5,
+ [69890]=5,
+ [69927]=5,
+ [69928]=5,
+ [69929]=5,
+ [69930]=5,
+ [69931]=5,
+ [69933]=5,
+ [69934]=5,
+ [69935]=5,
+ [69936]=5,
+ [69937]=5,
+ [69938]=5,
+ [69939]=5,
+ [69940]=5,
+ [70003]=5,
+ [70016]=5,
+ [70017]=5,
+ [70070]=5,
+ [70071]=5,
+ [70072]=5,
+ [70073]=5,
+ [70074]=5,
+ [70075]=5,
+ [70076]=5,
+ [70077]=5,
+ [70078]=5,
+ [70090]=5,
+ [70091]=5,
+ [70092]=5,
+ [70191]=5,
+ [70192]=5,
+ [70193]=5,
+ [70196]=5,
+ [70198]=5,
+ [70199]=5,
+ [70206]=5,
+ [70367]=5,
+ [70371]=5,
+ [70372]=5,
+ [70373]=5,
+ [70374]=5,
+ [70375]=5,
+ [70376]=5,
+ [70377]=5,
+ [70378]=5,
+ [70400]=5,
+ [70401]=5,
+ [70459]=5,
+ [70460]=5,
+ [70464]=5,
+ [70502]=5,
+ [70503]=5,
+ [70504]=5,
+ [70505]=5,
+ [70506]=5,
+ [70507]=5,
+ [70508]=5,
+ [70512]=5,
+ [70513]=5,
+ [70514]=5,
+ [70515]=5,
+ [70516]=5,
+ [70712]=5,
+ [70713]=5,
+ [70714]=5,
+ [70715]=5,
+ [70716]=5,
+ [70717]=5,
+ [70718]=5,
+ [70719]=5,
+ [70722]=5,
+ [70723]=5,
+ [70724]=5,
+ [70726]=5,
+ [70750]=5,
+ [70835]=5,
+ [70836]=5,
+ [70837]=5,
+ [70838]=5,
+ [70839]=5,
+ [70840]=5,
+ [70842]=5,
+ [70847]=5,
+ [70848]=5,
+ [70850]=5,
+ [70851]=5,
+ [71090]=5,
+ [71091]=5,
+ [71092]=5,
+ [71093]=5,
+ [71100]=5,
+ [71101]=5,
+ [71103]=5,
+ [71104]=5,
+ [71132]=5,
+ [71133]=5,
+ [71219]=5,
+ [71220]=5,
+ [71221]=5,
+ [71222]=5,
+ [71223]=5,
+ [71224]=5,
+ [71225]=5,
+ [71226]=5,
+ [71229]=5,
+ [71231]=5,
+ [71232]=5,
+ [71339]=5,
+ [71341]=5,
+ [71344]=5,
+ [71345]=5,
+ [71346]=5,
+ [71347]=5,
+ [71348]=5,
+ [71349]=5,
+ [71351]=5,
+ [71453]=5,
+ [71454]=5,
+ [71455]=5,
+ [71458]=5,
+ [71459]=5,
+ [71460]=5,
+ [71461]=5,
+ [71463]=5,
+ [71464]=5,
+ [71465]=5,
+ [71466]=5,
+ [71467]=5,
+ [71727]=5,
+ [71728]=5,
+ [71729]=5,
+ [71730]=5,
+ [71731]=5,
+ [71732]=5,
+ [71733]=5,
+ [71734]=5,
+ [71735]=5,
+ [71737]=5,
+ [71738]=5,
+ [72148]=5,
+ [72149]=5,
+ [72150]=5,
+ [72151]=5,
+ [72154]=5,
+ [72155]=5,
+ [72160]=5,
+ [72193]=5,
+ [72194]=5,
+ [72195]=5,
+ [72196]=5,
+ [72197]=5,
+ [72198]=5,
+ [72201]=5,
+ [72202]=5,
+ [72243]=5,
+ [72244]=5,
+ [72245]=5,
+ [72246]=5,
+ [72247]=5,
+ [72248]=5,
+ [72251]=5,
+ [72252]=5,
+ [72253]=5,
+ [72254]=5,
+ [72263]=5,
+ [72273]=5,
+ [72274]=5,
+ [72275]=5,
+ [72276]=5,
+ [72277]=5,
+ [72278]=5,
+ [72281]=5,
+ [72282]=5,
+ [72283]=5,
+ [72330]=5,
+ [72331]=5,
+ [72332]=5,
+ [72333]=5,
+ [72334]=5,
+ [72335]=5,
+ [72336]=5,
+ [72337]=5,
+ [72338]=5,
+ [72339]=5,
+ [72340]=5,
+ [72341]=5,
+ [72342]=5,
+ [72344]=5,
+ [72345]=5,
+ [72752]=5,
+ [72753]=5,
+ [72754]=5,
+ [72755]=5,
+ [72756]=5,
+ [72757]=5,
+ [72758]=5,
+ [72760]=5,
+ [72761]=5,
+ [72762]=5,
+ [72763]=5,
+ [72764]=5,
+ [72765]=5,
+ [72767]=5,
+ [72850]=5,
+ [72851]=5,
+ [72852]=5,
+ [72853]=5,
+ [72854]=5,
+ [72855]=5,
+ [72856]=5,
+ [72857]=5,
+ [72858]=5,
+ [72859]=5,
+ [72860]=5,
+ [72861]=5,
+ [72862]=5,
+ [72863]=5,
+ [72864]=5,
+ [72865]=5,
+ [72866]=5,
+ [72867]=5,
+ [72868]=5,
+ [72869]=5,
+ [72870]=5,
+ [72871]=5,
+ [72874]=5,
+ [72875]=5,
+ [72876]=5,
+ [72877]=5,
+ [72878]=5,
+ [72879]=5,
+ [72880]=5,
+ [72882]=5,
+ [72883]=5,
+ [72885]=5,
+ [72886]=5,
+ [73009]=5,
+ [73010]=5,
+ [73011]=5,
+ [73012]=5,
+ [73013]=5,
+ [73014]=5,
+ [73018]=5,
+ [73020]=5,
+ [73021]=5,
+ [73023]=5,
+ [73024]=5,
+ [73025]=5,
+ [73026]=5,
+ [73027]=5,
+ [73028]=5,
+ [73029]=5,
+ [73031]=5,
+ [73104]=5,
+ [73105]=5,
+ [73109]=5,
+ [73111]=5,
+ [73459]=5,
+ [73460]=5,
+ [92912]=5,
+ [92913]=5,
+ [92914]=5,
+ [92915]=5,
+ [92916]=5,
+ [92976]=5,
+ [92977]=5,
+ [92978]=5,
+ [92979]=5,
+ [92980]=5,
+ [92981]=5,
+ [92982]=5,
+ [94031]=5,
+ [94095]=5,
+ [94096]=5,
+ [94097]=5,
+ [94098]=5,
+ [113821]=5,
+ [113822]=5,
+ [119143]=5,
+ [119144]=5,
+ [119145]=5,
+ [119163]=5,
+ [119164]=5,
+ [119165]=5,
+ [119166]=5,
+ [119167]=5,
+ [119168]=5,
+ [119169]=5,
+ [119170]=5,
+ [119173]=5,
+ [119174]=5,
+ [119175]=5,
+ [119176]=5,
+ [119177]=5,
+ [119178]=5,
+ [119179]=5,
+ [119210]=5,
+ [119211]=5,
+ [119212]=5,
+ [119213]=5,
+ [119362]=5,
+ [119363]=5,
+ [119364]=5,
+ [121344]=5,
+ [121345]=5,
+ [121346]=5,
+ [121347]=5,
+ [121348]=5,
+ [121349]=5,
+ [121350]=5,
+ [121351]=5,
+ [121352]=5,
+ [121353]=5,
+ [121354]=5,
+ [121355]=5,
+ [121356]=5,
+ [121357]=5,
+ [121358]=5,
+ [121359]=5,
+ [121360]=5,
+ [121361]=5,
+ [121362]=5,
+ [121363]=5,
+ [121364]=5,
+ [121365]=5,
+ [121366]=5,
+ [121367]=5,
+ [121368]=5,
+ [121369]=5,
+ [121370]=5,
+ [121371]=5,
+ [121372]=5,
+ [121373]=5,
+ [121374]=5,
+ [121375]=5,
+ [121376]=5,
+ [121377]=5,
+ [121378]=5,
+ [121379]=5,
+ [121380]=5,
+ [121381]=5,
+ [121382]=5,
+ [121383]=5,
+ [121384]=5,
+ [121385]=5,
+ [121386]=5,
+ [121387]=5,
+ [121388]=5,
+ [121389]=5,
+ [121390]=5,
+ [121391]=5,
+ [121392]=5,
+ [121393]=5,
+ [121394]=5,
+ [121395]=5,
+ [121396]=5,
+ [121397]=5,
+ [121398]=5,
+ [121403]=5,
+ [121404]=5,
+ [121405]=5,
+ [121406]=5,
+ [121407]=5,
+ [121408]=5,
+ [121409]=5,
+ [121410]=5,
+ [121411]=5,
+ [121412]=5,
+ [121413]=5,
+ [121414]=5,
+ [121415]=5,
+ [121416]=5,
+ [121417]=5,
+ [121418]=5,
+ [121419]=5,
+ [121420]=5,
+ [121421]=5,
+ [121422]=5,
+ [121423]=5,
+ [121424]=5,
+ [121425]=5,
+ [121426]=5,
+ [121427]=5,
+ [121428]=5,
+ [121429]=5,
+ [121430]=5,
+ [121431]=5,
+ [121432]=5,
+ [121433]=5,
+ [121434]=5,
+ [121435]=5,
+ [121436]=5,
+ [121437]=5,
+ [121438]=5,
+ [121439]=5,
+ [121440]=5,
+ [121441]=5,
+ [121442]=5,
+ [121443]=5,
+ [121444]=5,
+ [121445]=5,
+ [121446]=5,
+ [121447]=5,
+ [121448]=5,
+ [121449]=5,
+ [121450]=5,
+ [121451]=5,
+ [121452]=5,
+ [121461]=5,
+ [121476]=5,
+ [121499]=5,
+ [121500]=5,
+ [121501]=5,
+ [121502]=5,
+ [121503]=5,
+ [121505]=5,
+ [121506]=5,
+ [121507]=5,
+ [121508]=5,
+ [121509]=5,
+ [121510]=5,
+ [121511]=5,
+ [121512]=5,
+ [121513]=5,
+ [121514]=5,
+ [121515]=5,
+ [121516]=5,
+ [121517]=5,
+ [121518]=5,
+ [121519]=5,
+ [122880]=5,
+ [122881]=5,
+ [122882]=5,
+ [122883]=5,
+ [122884]=5,
+ [122885]=5,
+ [122886]=5,
+ [122888]=5,
+ [122889]=5,
+ [122890]=5,
+ [122891]=5,
+ [122892]=5,
+ [122893]=5,
+ [122894]=5,
+ [122895]=5,
+ [122896]=5,
+ [122897]=5,
+ [122898]=5,
+ [122899]=5,
+ [122900]=5,
+ [122901]=5,
+ [122902]=5,
+ [122903]=5,
+ [122904]=5,
+ [122907]=5,
+ [122908]=5,
+ [122909]=5,
+ [122910]=5,
+ [122911]=5,
+ [122912]=5,
+ [122913]=5,
+ [122915]=5,
+ [122916]=5,
+ [122918]=5,
+ [122919]=5,
+ [122920]=5,
+ [122921]=5,
+ [122922]=5,
+ [123184]=5,
+ [123185]=5,
+ [123186]=5,
+ [123187]=5,
+ [123188]=5,
+ [123189]=5,
+ [123190]=5,
+ [123628]=5,
+ [123629]=5,
+ [123630]=5,
+ [123631]=5,
+ [125136]=5,
+ [125137]=5,
+ [125138]=5,
+ [125139]=5,
+ [125140]=5,
+ [125141]=5,
+ [125142]=5,
+ [125184]=2,
+ [125185]=2,
+ [125186]=2,
+ [125187]=2,
+ [125188]=2,
+ [125189]=2,
+ [125190]=2,
+ [125191]=2,
+ [125192]=2,
+ [125193]=2,
+ [125194]=2,
+ [125195]=2,
+ [125196]=2,
+ [125197]=2,
+ [125198]=2,
+ [125199]=2,
+ [125200]=2,
+ [125201]=2,
+ [125202]=2,
+ [125203]=2,
+ [125204]=2,
+ [125205]=2,
+ [125206]=2,
+ [125207]=2,
+ [125208]=2,
+ [125209]=2,
+ [125210]=2,
+ [125211]=2,
+ [125212]=2,
+ [125213]=2,
+ [125214]=2,
+ [125215]=2,
+ [125216]=2,
+ [125217]=2,
+ [125218]=2,
+ [125219]=2,
+ [125220]=2,
+ [125221]=2,
+ [125222]=2,
+ [125223]=2,
+ [125224]=2,
+ [125225]=2,
+ [125226]=2,
+ [125227]=2,
+ [125228]=2,
+ [125229]=2,
+ [125230]=2,
+ [125231]=2,
+ [125232]=2,
+ [125233]=2,
+ [125234]=2,
+ [125235]=2,
+ [125236]=2,
+ [125237]=2,
+ [125238]=2,
+ [125239]=2,
+ [125240]=2,
+ [125241]=2,
+ [125242]=2,
+ [125243]=2,
+ [125244]=2,
+ [125245]=2,
+ [125246]=2,
+ [125247]=2,
+ [125248]=2,
+ [125249]=2,
+ [125250]=2,
+ [125251]=2,
+ [125252]=5,
+ [125253]=5,
+ [125254]=5,
+ [125255]=5,
+ [125256]=5,
+ [125257]=5,
+ [125258]=5,
+ [1042752]=5,
+}
+
+characters.indicgroups={
+ ["above_mark"]={
+ [2304]=true,
+ [2305]=true,
+ [2306]=true,
+ [2362]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2385]=true,
+ [2387]=true,
+ [2388]=true,
+ [2389]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2690]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2879]=true,
+ [3008]=true,
+ [3021]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3142]=true,
+ [3143]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3149]=true,
+ [3263]=true,
+ [3270]=true,
+ [3406]=true,
+ [4141]=true,
+ [4142]=true,
+ [4146]=true,
+ [4147]=true,
+ [4148]=true,
+ [4149]=true,
+ [4150]=true,
+ [4154]=true,
+ [4209]=true,
+ [4210]=true,
+ [4211]=true,
+ [4212]=true,
+ [4229]=true,
+ [4230]=true,
+ [4253]=true,
+ [43232]=true,
+ [43233]=true,
+ [43234]=true,
+ [43235]=true,
+ [43236]=true,
+ [43237]=true,
+ [43238]=true,
+ [43239]=true,
+ [43240]=true,
+ [43241]=true,
+ [43242]=true,
+ [43243]=true,
+ [43244]=true,
+ [43245]=true,
+ [43246]=true,
+ [43247]=true,
+ [43248]=true,
+ [43249]=true,
+ [43493]=true,
+ [43644]=true,
+ },
+ ["after_half"]={},
+ ["after_main"]={
+ [2864]=true,
+ [2879]=true,
+ [2902]=true,
+ [3376]=true,
+ },
+ ["after_postscript"]={
+ [2433]=true,
+ [2494]=true,
+ [2496]=true,
+ [2519]=true,
+ [2561]=true,
+ [2562]=true,
+ [2622]=true,
+ [2624]=true,
+ [2625]=true,
+ [2626]=true,
+ [2672]=true,
+ [2673]=true,
+ [2735]=true,
+ [2750]=true,
+ [2752]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2786]=true,
+ [2787]=true,
+ [2878]=true,
+ [2880]=true,
+ [2903]=true,
+ [2992]=true,
+ [3006]=true,
+ [3007]=true,
+ [3009]=true,
+ [3010]=true,
+ [3031]=true,
+ [3120]=true,
+ [3248]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3415]=true,
+ },
+ ["after_subscript"]={
+ [2366]=true,
+ [2368]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2402]=true,
+ [2403]=true,
+ [2480]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2530]=true,
+ [2531]=true,
+ [2544]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [3008]=true,
+ [3139]=true,
+ [3140]=true,
+ [3267]=true,
+ [3268]=true,
+ [3285]=true,
+ [3286]=true,
+ },
+ ["anudatta"]={
+ [2386]=true,
+ },
+ ["before_half"]={
+ [2367]=true,
+ [2382]=true,
+ [2495]=true,
+ [2503]=true,
+ [2504]=true,
+ [2623]=true,
+ [2751]=true,
+ [2887]=true,
+ },
+ ["before_main"]={
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ },
+ ["before_postscript"]={
+ [2352]=true,
+ [2736]=true,
+ },
+ ["before_subscript"]={
+ [2608]=true,
+ [2817]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3137]=true,
+ [3138]=true,
+ [3142]=true,
+ [3143]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3157]=true,
+ [3158]=true,
+ [3262]=true,
+ [3263]=true,
+ [3265]=true,
+ [3266]=true,
+ [3270]=true,
+ [3276]=true,
+ [3298]=true,
+ [3299]=true,
+ },
+ ["below_mark"]={
+ [2364]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2381]=true,
+ [2386]=true,
+ [2390]=true,
+ [2391]=true,
+ [2402]=true,
+ [2403]=true,
+ [2492]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2509]=true,
+ [2620]=true,
+ [2625]=true,
+ [2626]=true,
+ [2637]=true,
+ [2748]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2765]=true,
+ [2876]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [2884]=true,
+ [2893]=true,
+ [2914]=true,
+ [2915]=true,
+ [3009]=true,
+ [3010]=true,
+ [3170]=true,
+ [3171]=true,
+ [3260]=true,
+ [3286]=true,
+ [3298]=true,
+ [3299]=true,
+ [3426]=true,
+ [3427]=true,
+ [4143]=true,
+ [4144]=true,
+ [4151]=true,
+ [4153]=true,
+ [4157]=true,
+ [4158]=true,
+ [4184]=true,
+ [4185]=true,
+ [4190]=true,
+ [4191]=true,
+ [4192]=true,
+ [4226]=true,
+ [4237]=true,
+ },
+ ["consonant"]={
+ [2325]=true,
+ [2326]=true,
+ [2327]=true,
+ [2328]=true,
+ [2329]=true,
+ [2330]=true,
+ [2331]=true,
+ [2332]=true,
+ [2333]=true,
+ [2334]=true,
+ [2335]=true,
+ [2336]=true,
+ [2337]=true,
+ [2338]=true,
+ [2339]=true,
+ [2340]=true,
+ [2341]=true,
+ [2342]=true,
+ [2343]=true,
+ [2344]=true,
+ [2345]=true,
+ [2346]=true,
+ [2347]=true,
+ [2348]=true,
+ [2349]=true,
+ [2350]=true,
+ [2351]=true,
+ [2352]=true,
+ [2353]=true,
+ [2354]=true,
+ [2355]=true,
+ [2356]=true,
+ [2357]=true,
+ [2358]=true,
+ [2359]=true,
+ [2360]=true,
+ [2361]=true,
+ [2392]=true,
+ [2393]=true,
+ [2394]=true,
+ [2395]=true,
+ [2396]=true,
+ [2397]=true,
+ [2398]=true,
+ [2399]=true,
+ [2424]=true,
+ [2425]=true,
+ [2426]=true,
+ [2453]=true,
+ [2454]=true,
+ [2455]=true,
+ [2456]=true,
+ [2457]=true,
+ [2458]=true,
+ [2459]=true,
+ [2460]=true,
+ [2461]=true,
+ [2462]=true,
+ [2463]=true,
+ [2464]=true,
+ [2465]=true,
+ [2466]=true,
+ [2467]=true,
+ [2468]=true,
+ [2469]=true,
+ [2470]=true,
+ [2471]=true,
+ [2472]=true,
+ [2474]=true,
+ [2475]=true,
+ [2476]=true,
+ [2477]=true,
+ [2478]=true,
+ [2479]=true,
+ [2480]=true,
+ [2482]=true,
+ [2486]=true,
+ [2487]=true,
+ [2488]=true,
+ [2489]=true,
+ [2510]=true,
+ [2524]=true,
+ [2525]=true,
+ [2527]=true,
+ [2581]=true,
+ [2582]=true,
+ [2583]=true,
+ [2584]=true,
+ [2585]=true,
+ [2586]=true,
+ [2587]=true,
+ [2588]=true,
+ [2589]=true,
+ [2590]=true,
+ [2591]=true,
+ [2592]=true,
+ [2593]=true,
+ [2594]=true,
+ [2595]=true,
+ [2596]=true,
+ [2597]=true,
+ [2598]=true,
+ [2599]=true,
+ [2600]=true,
+ [2602]=true,
+ [2603]=true,
+ [2604]=true,
+ [2605]=true,
+ [2606]=true,
+ [2607]=true,
+ [2608]=true,
+ [2610]=true,
+ [2611]=true,
+ [2613]=true,
+ [2614]=true,
+ [2616]=true,
+ [2617]=true,
+ [2649]=true,
+ [2650]=true,
+ [2651]=true,
+ [2652]=true,
+ [2654]=true,
+ [2709]=true,
+ [2710]=true,
+ [2711]=true,
+ [2712]=true,
+ [2713]=true,
+ [2714]=true,
+ [2715]=true,
+ [2716]=true,
+ [2717]=true,
+ [2718]=true,
+ [2719]=true,
+ [2720]=true,
+ [2721]=true,
+ [2722]=true,
+ [2723]=true,
+ [2724]=true,
+ [2725]=true,
+ [2726]=true,
+ [2727]=true,
+ [2728]=true,
+ [2730]=true,
+ [2731]=true,
+ [2732]=true,
+ [2733]=true,
+ [2734]=true,
+ [2735]=true,
+ [2736]=true,
+ [2738]=true,
+ [2739]=true,
+ [2741]=true,
+ [2742]=true,
+ [2743]=true,
+ [2744]=true,
+ [2745]=true,
+ [2837]=true,
+ [2838]=true,
+ [2839]=true,
+ [2840]=true,
+ [2841]=true,
+ [2842]=true,
+ [2843]=true,
+ [2844]=true,
+ [2845]=true,
+ [2846]=true,
+ [2847]=true,
+ [2848]=true,
+ [2849]=true,
+ [2850]=true,
+ [2851]=true,
+ [2852]=true,
+ [2853]=true,
+ [2854]=true,
+ [2855]=true,
+ [2856]=true,
+ [2858]=true,
+ [2859]=true,
+ [2860]=true,
+ [2861]=true,
+ [2862]=true,
+ [2863]=true,
+ [2864]=true,
+ [2866]=true,
+ [2867]=true,
+ [2869]=true,
+ [2870]=true,
+ [2871]=true,
+ [2872]=true,
+ [2873]=true,
+ [2908]=true,
+ [2909]=true,
+ [2929]=true,
+ [2965]=true,
+ [2969]=true,
+ [2970]=true,
+ [2972]=true,
+ [2974]=true,
+ [2975]=true,
+ [2979]=true,
+ [2980]=true,
+ [2984]=true,
+ [2985]=true,
+ [2986]=true,
+ [2990]=true,
+ [2991]=true,
+ [2992]=true,
+ [2993]=true,
+ [2994]=true,
+ [2995]=true,
+ [2996]=true,
+ [2997]=true,
+ [2998]=true,
+ [2999]=true,
+ [3000]=true,
+ [3001]=true,
+ [3093]=true,
+ [3094]=true,
+ [3095]=true,
+ [3096]=true,
+ [3097]=true,
+ [3098]=true,
+ [3099]=true,
+ [3100]=true,
+ [3101]=true,
+ [3102]=true,
+ [3103]=true,
+ [3104]=true,
+ [3105]=true,
+ [3106]=true,
+ [3107]=true,
+ [3108]=true,
+ [3109]=true,
+ [3110]=true,
+ [3111]=true,
+ [3112]=true,
+ [3114]=true,
+ [3115]=true,
+ [3116]=true,
+ [3117]=true,
+ [3118]=true,
+ [3119]=true,
+ [3120]=true,
+ [3121]=true,
+ [3122]=true,
+ [3123]=true,
+ [3124]=true,
+ [3125]=true,
+ [3126]=true,
+ [3127]=true,
+ [3128]=true,
+ [3129]=true,
+ [3133]=true,
+ [3221]=true,
+ [3222]=true,
+ [3223]=true,
+ [3224]=true,
+ [3225]=true,
+ [3226]=true,
+ [3227]=true,
+ [3228]=true,
+ [3229]=true,
+ [3230]=true,
+ [3231]=true,
+ [3232]=true,
+ [3233]=true,
+ [3234]=true,
+ [3235]=true,
+ [3236]=true,
+ [3237]=true,
+ [3238]=true,
+ [3239]=true,
+ [3240]=true,
+ [3242]=true,
+ [3243]=true,
+ [3244]=true,
+ [3245]=true,
+ [3246]=true,
+ [3247]=true,
+ [3248]=true,
+ [3249]=true,
+ [3250]=true,
+ [3251]=true,
+ [3253]=true,
+ [3254]=true,
+ [3255]=true,
+ [3256]=true,
+ [3257]=true,
+ [3294]=true,
+ [3349]=true,
+ [3350]=true,
+ [3351]=true,
+ [3352]=true,
+ [3353]=true,
+ [3354]=true,
+ [3355]=true,
+ [3356]=true,
+ [3357]=true,
+ [3358]=true,
+ [3359]=true,
+ [3360]=true,
+ [3361]=true,
+ [3362]=true,
+ [3363]=true,
+ [3364]=true,
+ [3365]=true,
+ [3366]=true,
+ [3367]=true,
+ [3368]=true,
+ [3369]=true,
+ [3370]=true,
+ [3371]=true,
+ [3372]=true,
+ [3373]=true,
+ [3374]=true,
+ [3375]=true,
+ [3376]=true,
+ [3377]=true,
+ [3378]=true,
+ [3379]=true,
+ [3380]=true,
+ [3381]=true,
+ [3382]=true,
+ [3383]=true,
+ [3384]=true,
+ [3385]=true,
+ [3386]=true,
+ [4096]=true,
+ [4097]=true,
+ [4098]=true,
+ [4099]=true,
+ [4100]=true,
+ [4101]=true,
+ [4102]=true,
+ [4103]=true,
+ [4104]=true,
+ [4105]=true,
+ [4106]=true,
+ [4107]=true,
+ [4108]=true,
+ [4109]=true,
+ [4110]=true,
+ [4111]=true,
+ [4112]=true,
+ [4113]=true,
+ [4114]=true,
+ [4115]=true,
+ [4116]=true,
+ [4117]=true,
+ [4118]=true,
+ [4119]=true,
+ [4120]=true,
+ [4121]=true,
+ [4122]=true,
+ [4123]=true,
+ [4124]=true,
+ [4125]=true,
+ [4126]=true,
+ [4127]=true,
+ [4128]=true,
+ [4155]=true,
+ [4156]=true,
+ [4157]=true,
+ [4158]=true,
+ [4159]=true,
+ [4176]=true,
+ [4177]=true,
+ [4186]=true,
+ [4187]=true,
+ [4188]=true,
+ [4189]=true,
+ [4190]=true,
+ [4191]=true,
+ [4192]=true,
+ [4193]=true,
+ [4197]=true,
+ [4198]=true,
+ [4206]=true,
+ [4207]=true,
+ [4208]=true,
+ [4213]=true,
+ [4214]=true,
+ [4215]=true,
+ [4216]=true,
+ [4217]=true,
+ [4218]=true,
+ [4219]=true,
+ [4220]=true,
+ [4221]=true,
+ [4222]=true,
+ [4223]=true,
+ [4224]=true,
+ [4225]=true,
+ [4226]=true,
+ [4238]=true,
+ [43488]=true,
+ [43489]=true,
+ [43490]=true,
+ [43491]=true,
+ [43492]=true,
+ [43495]=true,
+ [43496]=true,
+ [43497]=true,
+ [43498]=true,
+ [43499]=true,
+ [43500]=true,
+ [43501]=true,
+ [43502]=true,
+ [43503]=true,
+ [43514]=true,
+ [43515]=true,
+ [43516]=true,
+ [43517]=true,
+ [43518]=true,
+ [43616]=true,
+ [43617]=true,
+ [43618]=true,
+ [43619]=true,
+ [43620]=true,
+ [43621]=true,
+ [43622]=true,
+ [43623]=true,
+ [43624]=true,
+ [43625]=true,
+ [43626]=true,
+ [43628]=true,
+ [43629]=true,
+ [43630]=true,
+ [43631]=true,
+ [43633]=true,
+ [43634]=true,
+ [43635]=true,
+ [43636]=true,
+ [43637]=true,
+ [43638]=true,
+ [43642]=true,
+ [43646]=true,
+ [43647]=true,
+ },
+ ["dependent_vowel"]={
+ [2362]=true,
+ [2363]=true,
+ [2366]=true,
+ [2367]=true,
+ [2368]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2382]=true,
+ [2383]=true,
+ [2389]=true,
+ [2390]=true,
+ [2391]=true,
+ [2402]=true,
+ [2403]=true,
+ [2494]=true,
+ [2495]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2503]=true,
+ [2504]=true,
+ [2507]=true,
+ [2508]=true,
+ [2622]=true,
+ [2623]=true,
+ [2624]=true,
+ [2625]=true,
+ [2626]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2750]=true,
+ [2751]=true,
+ [2752]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2878]=true,
+ [2879]=true,
+ [2880]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [2884]=true,
+ [2887]=true,
+ [2888]=true,
+ [2891]=true,
+ [2892]=true,
+ [2914]=true,
+ [2915]=true,
+ [3006]=true,
+ [3007]=true,
+ [3008]=true,
+ [3009]=true,
+ [3010]=true,
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3018]=true,
+ [3019]=true,
+ [3020]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3137]=true,
+ [3138]=true,
+ [3139]=true,
+ [3140]=true,
+ [3142]=true,
+ [3143]=true,
+ [3144]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3170]=true,
+ [3171]=true,
+ [3262]=true,
+ [3263]=true,
+ [3264]=true,
+ [3265]=true,
+ [3266]=true,
+ [3267]=true,
+ [3268]=true,
+ [3270]=true,
+ [3271]=true,
+ [3272]=true,
+ [3274]=true,
+ [3275]=true,
+ [3276]=true,
+ [3285]=true,
+ [3286]=true,
+ [3298]=true,
+ [3299]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3396]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ [3402]=true,
+ [3403]=true,
+ [3404]=true,
+ [3415]=true,
+ [3426]=true,
+ [3427]=true,
+ [4139]=true,
+ [4140]=true,
+ [4141]=true,
+ [4142]=true,
+ [4143]=true,
+ [4144]=true,
+ [4145]=true,
+ [4146]=true,
+ [4147]=true,
+ [4148]=true,
+ [4149]=true,
+ [4182]=true,
+ [4183]=true,
+ [4184]=true,
+ [4185]=true,
+ [4194]=true,
+ [4199]=true,
+ [4200]=true,
+ [4209]=true,
+ [4210]=true,
+ [4211]=true,
+ [4212]=true,
+ [4227]=true,
+ [4228]=true,
+ [4229]=true,
+ [4230]=true,
+ [4252]=true,
+ [4253]=true,
+ [43493]=true,
+ },
+ ["halant"]={
+ [2381]=true,
+ [2509]=true,
+ [2637]=true,
+ [2765]=true,
+ [2893]=true,
+ [3021]=true,
+ [3149]=true,
+ [3277]=true,
+ [3405]=true,
+ },
+ ["independent_vowel"]={
+ [2308]=true,
+ [2309]=true,
+ [2310]=true,
+ [2311]=true,
+ [2312]=true,
+ [2313]=true,
+ [2314]=true,
+ [2315]=true,
+ [2316]=true,
+ [2317]=true,
+ [2318]=true,
+ [2319]=true,
+ [2320]=true,
+ [2321]=true,
+ [2322]=true,
+ [2323]=true,
+ [2324]=true,
+ [2400]=true,
+ [2401]=true,
+ [2418]=true,
+ [2419]=true,
+ [2420]=true,
+ [2421]=true,
+ [2422]=true,
+ [2423]=true,
+ [2437]=true,
+ [2438]=true,
+ [2439]=true,
+ [2440]=true,
+ [2441]=true,
+ [2442]=true,
+ [2443]=true,
+ [2444]=true,
+ [2447]=true,
+ [2448]=true,
+ [2451]=true,
+ [2452]=true,
+ [2528]=true,
+ [2529]=true,
+ [2530]=true,
+ [2531]=true,
+ [2565]=true,
+ [2566]=true,
+ [2567]=true,
+ [2568]=true,
+ [2569]=true,
+ [2570]=true,
+ [2575]=true,
+ [2576]=true,
+ [2579]=true,
+ [2580]=true,
+ [2693]=true,
+ [2694]=true,
+ [2695]=true,
+ [2696]=true,
+ [2697]=true,
+ [2698]=true,
+ [2699]=true,
+ [2700]=true,
+ [2701]=true,
+ [2703]=true,
+ [2704]=true,
+ [2705]=true,
+ [2707]=true,
+ [2708]=true,
+ [2784]=true,
+ [2785]=true,
+ [2786]=true,
+ [2787]=true,
+ [2821]=true,
+ [2822]=true,
+ [2823]=true,
+ [2824]=true,
+ [2825]=true,
+ [2826]=true,
+ [2827]=true,
+ [2828]=true,
+ [2831]=true,
+ [2832]=true,
+ [2835]=true,
+ [2836]=true,
+ [2912]=true,
+ [2913]=true,
+ [2949]=true,
+ [2950]=true,
+ [2951]=true,
+ [2952]=true,
+ [2953]=true,
+ [2954]=true,
+ [2958]=true,
+ [2959]=true,
+ [2960]=true,
+ [2962]=true,
+ [2963]=true,
+ [2964]=true,
+ [3077]=true,
+ [3078]=true,
+ [3079]=true,
+ [3080]=true,
+ [3081]=true,
+ [3082]=true,
+ [3083]=true,
+ [3084]=true,
+ [3086]=true,
+ [3087]=true,
+ [3088]=true,
+ [3090]=true,
+ [3091]=true,
+ [3092]=true,
+ [3168]=true,
+ [3169]=true,
+ [3205]=true,
+ [3206]=true,
+ [3207]=true,
+ [3208]=true,
+ [3209]=true,
+ [3210]=true,
+ [3211]=true,
+ [3212]=true,
+ [3214]=true,
+ [3215]=true,
+ [3216]=true,
+ [3218]=true,
+ [3219]=true,
+ [3220]=true,
+ [3296]=true,
+ [3297]=true,
+ [3333]=true,
+ [3334]=true,
+ [3335]=true,
+ [3336]=true,
+ [3337]=true,
+ [3338]=true,
+ [3339]=true,
+ [3340]=true,
+ [3342]=true,
+ [3343]=true,
+ [3344]=true,
+ [3346]=true,
+ [3347]=true,
+ [3348]=true,
+ [3423]=true,
+ [3424]=true,
+ [3425]=true,
+ [4129]=true,
+ [4130]=true,
+ [4131]=true,
+ [4132]=true,
+ [4133]=true,
+ [4134]=true,
+ [4135]=true,
+ [4136]=true,
+ [4137]=true,
+ [4138]=true,
+ [4178]=true,
+ [4179]=true,
+ [4180]=true,
+ [4181]=true,
+ },
+ ["nukta"]={
+ [2364]=true,
+ [2492]=true,
+ [2620]=true,
+ [2748]=true,
+ [2876]=true,
+ [3260]=true,
+ },
+ ["post_mark"]={
+ [2307]=true,
+ [2363]=true,
+ [2366]=true,
+ [2368]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2383]=true,
+ [2494]=true,
+ [2496]=true,
+ [2622]=true,
+ [2624]=true,
+ [2750]=true,
+ [2752]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2878]=true,
+ [2880]=true,
+ [3006]=true,
+ [3007]=true,
+ [3137]=true,
+ [3138]=true,
+ [3139]=true,
+ [3140]=true,
+ [3262]=true,
+ [3265]=true,
+ [3266]=true,
+ [3267]=true,
+ [3268]=true,
+ [3276]=true,
+ [3285]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3396]=true,
+ [3415]=true,
+ [4139]=true,
+ [4140]=true,
+ [4152]=true,
+ [4155]=true,
+ [4182]=true,
+ [4183]=true,
+ [4194]=true,
+ [4195]=true,
+ [4196]=true,
+ [4199]=true,
+ [4200]=true,
+ [4201]=true,
+ [4202]=true,
+ [4203]=true,
+ [4204]=true,
+ [4205]=true,
+ [4227]=true,
+ [4231]=true,
+ [4232]=true,
+ [4233]=true,
+ [4234]=true,
+ [4235]=true,
+ [4236]=true,
+ [4239]=true,
+ [4250]=true,
+ [4251]=true,
+ [4252]=true,
+ [43643]=true,
+ [43645]=true,
+ },
+ ["pre_mark"]={
+ [2367]=true,
+ [2382]=true,
+ [2495]=true,
+ [2503]=true,
+ [2504]=true,
+ [2623]=true,
+ [2751]=true,
+ [2887]=true,
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ [4145]=true,
+ [4228]=true,
+ },
+ ["ra"]={
+ [2352]=true,
+ [2480]=true,
+ [2544]=true,
+ [2608]=true,
+ [2736]=true,
+ [2864]=true,
+ [2992]=true,
+ [3120]=true,
+ [3248]=true,
+ [3376]=true,
+ },
+ ["stress_tone_mark"]={
+ [2385]=true,
+ [2386]=true,
+ [2387]=true,
+ [2388]=true,
+ [4151]=true,
+ [4195]=true,
+ [4196]=true,
+ [4201]=true,
+ [4202]=true,
+ [4203]=true,
+ [4204]=true,
+ [4205]=true,
+ [4231]=true,
+ [4232]=true,
+ [4233]=true,
+ [4234]=true,
+ [4235]=true,
+ [4236]=true,
+ [4237]=true,
+ [4239]=true,
+ [4250]=true,
+ [4251]=true,
+ [43643]=true,
+ [43644]=true,
+ [43645]=true,
+ },
+ ["twopart_mark"]={
+ [2507]={ 2503, 2494 },
+ [2508]={ 2503, 2519 },
+ [2888]={ 2887, 2902 },
+ [2891]={ 2887, 2878 },
+ [2892]={ 2887, 2903 },
+ [3018]={ 3014, 3006 },
+ [3019]={ 3015, 3006 },
+ [3020]={ 3014, 3031 },
+ [3144]={ 3142, 3158 },
+ [3264]={ 3263, 3285 },
+ [3271]={ 3270, 3285 },
+ [3272]={ 3270, 3286 },
+ [3274]={ 3270, 3266 },
+ [3275]={ 3274, 3285 },
+ [3402]={ 3398, 3390 },
+ [3403]={ 3399, 3390 },
+ [3404]={ 3398, 3415 },
+ },
+ ["vowel_modifier"]={
+ [2304]=true,
+ [2305]=true,
+ [2306]=true,
+ [2307]=true,
+ [2433]=true,
+ [3330]=true,
+ [3331]=true,
+ [4150]=true,
+ [4152]=true,
+ [4153]=true,
+ [4154]=true,
+ [43232]=true,
+ [43233]=true,
+ [43234]=true,
+ [43235]=true,
+ [43236]=true,
+ [43237]=true,
+ [43238]=true,
+ [43239]=true,
+ [43240]=true,
+ [43241]=true,
+ [43242]=true,
+ [43243]=true,
+ [43244]=true,
+ [43245]=true,
+ [43246]=true,
+ [43247]=true,
+ [43249]=true,
+ },
+}
+
+-- done, uncomment for testing:
+
+-- return characters.indicgroups
diff --git a/macros/luatex/generic/luaotfload/fontloader-basics-gen.lua b/macros/luatex/generic/luaotfload/fontloader-basics-gen.lua
new file mode 100644
index 0000000000..3959ca0222
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-basics-gen.lua
@@ -0,0 +1,479 @@
+if not modules then modules = { } end modules ['luat-basics-gen'] = {
+ version = 1.100,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+-- We could load a few more of the general context libraries but it would
+-- not make plain / latex users more happy I guess. So, we stick to some
+-- placeholders.
+
+local match, gmatch, gsub, lower = string.match, string.gmatch, string.gsub, string.lower
+local formatters, split, format, dump = string.formatters, string.split, string.format, string.dump
+local loadfile, type = loadfile, type
+local setmetatable, getmetatable, collectgarbage = setmetatable, getmetatable, collectgarbage
+local floor = math.floor
+
+local dummyfunction = function()
+end
+
+local dummyreporter = function(c)
+ return function(f,...)
+ local r = texio.reporter or texio.write_nl
+ if f then
+ r(c .. " : " .. (formatters or format)(f,...))
+ else
+ r("")
+ end
+ end
+end
+
+local dummyreport = function(c,f,...)
+ local r = texio.reporter or texio.write_nl
+ if f then
+ r(c .. " : " .. (formatters or format)(f,...))
+ else
+ r("")
+ end
+end
+
+statistics = {
+ register = dummyfunction,
+ starttiming = dummyfunction,
+ stoptiming = dummyfunction,
+ elapsedtime = nil,
+}
+
+directives = {
+ register = dummyfunction,
+ enable = dummyfunction,
+ disable = dummyfunction,
+}
+
+trackers = {
+ register = dummyfunction,
+ enable = dummyfunction,
+ disable = dummyfunction,
+}
+
+experiments = {
+ register = dummyfunction,
+ enable = dummyfunction,
+ disable = dummyfunction,
+}
+
+storage = { -- probably no longer needed
+ register = dummyfunction,
+ shared = { },
+}
+
+logs = {
+ new = dummyreporter,
+ reporter = dummyreporter,
+ messenger = dummyreporter,
+ report = dummyreport,
+}
+
+callbacks = {
+ register = function(n,f)
+ return callback.register(n,f)
+ end,
+}
+
+utilities = utilities or { }
+
+utilities.storage = utilities.storage or {
+ allocate = function(t)
+ return t or { }
+ end,
+ mark = function(t)
+ return t or { }
+ end,
+}
+
+utilities.parsers = utilities.parsers or {
+ -- these are less flexible than in context but ok
+ -- for generic purpose
+ settings_to_array = function(s)
+ return split(s,",")
+ end,
+ settings_to_hash = function(s)
+ local t = { }
+ for k, v in gmatch(s,"([^%s,=]+)=([^%s,]+)") do
+ t[k] = v
+ end
+ return t
+ end,
+ settings_to_hash_colon_too = function(s)
+ local t = { }
+ for k, v in gmatch(s,"([^%s,=:]+)[=:]([^%s,]+)") do
+ t[k] = v
+ end
+ return t
+ end,
+}
+
+characters = characters or {
+ data = { }
+}
+
+-- we need to cheat a bit here
+
+texconfig.kpse_init = true
+
+resolvers = resolvers or { } -- no fancy file helpers used
+
+local remapper = {
+ otf = "opentype fonts",
+ ttf = "truetype fonts",
+ ttc = "truetype fonts",
+ cid = "cid maps",
+ cidmap = "cid maps",
+ -- fea = "font feature files", -- no longer supported
+ pfb = "type1 fonts", -- needed for vector loading
+ afm = "afm",
+ enc = "enc files",
+ lua = "tex",
+}
+
+function resolvers.findfile(name,fileformat)
+ name = gsub(name,"\\","/")
+ if not fileformat or fileformat == "" then
+ fileformat = file.suffix(name)
+ if fileformat == "" then
+ fileformat = "tex"
+ end
+ end
+ fileformat = lower(fileformat)
+ fileformat = remapper[fileformat] or fileformat
+ local found = kpse.find_file(name,fileformat)
+ if not found or found == "" then
+ found = kpse.find_file(name,"other text files")
+ end
+ return found
+end
+
+resolvers.findbinfile = resolvers.findfile
+
+function resolvers.loadbinfile(filename,filetype)
+ local data = io.loaddata(filename)
+ return true, data, #data
+end
+
+function resolvers.resolve(s)
+ return s
+end
+
+function resolvers.unresolve(s)
+ return s
+end
+
+-- Caches ... I will make a real stupid version some day when I'm in the
+-- mood. After all, the generic code does not need the more advanced
+-- ConTeXt features. Cached data is not shared between ConTeXt and other
+-- usage as I don't want any dependency at all. Also, ConTeXt might have
+-- different needs and tricks added.
+
+--~ containers.usecache = true
+
+caches = { }
+
+local writable = nil
+local readables = { }
+local usingjit = jit
+
+if not caches.namespace or caches.namespace == "" or caches.namespace == "context" then
+ caches.namespace = 'generic'
+end
+
+do
+
+ -- standard context tree setup
+
+ local cachepaths = kpse.expand_var('$TEXMFCACHE') or ""
+
+ -- quite like tex live or so (the weird $TEXMFCACHE test seems to be needed on miktex)
+
+ if cachepaths == "" or cachepaths == "$TEXMFCACHE" then
+ cachepaths = kpse.expand_var('$TEXMFVAR') or ""
+ end
+
+ -- this also happened to be used (the weird $TEXMFVAR test seems to be needed on miktex)
+
+ if cachepaths == "" or cachepaths == "$TEXMFVAR" then
+ cachepaths = kpse.expand_var('$VARTEXMF') or ""
+ end
+
+ -- and this is a last resort (hm, we could use TEMP or TEMPDIR)
+
+ if cachepaths == "" then
+ local fallbacks = { "TMPDIR", "TEMPDIR", "TMP", "TEMP", "HOME", "HOMEPATH" }
+ for i=1,#fallbacks do
+ cachepaths = os.getenv(fallbacks[i]) or ""
+ if cachepath ~= "" and lfs.isdir(cachepath) then
+ break
+ end
+ end
+ end
+
+ if cachepaths == "" then
+ cachepaths = "."
+ end
+
+ cachepaths = split(cachepaths,os.type == "windows" and ";" or ":")
+
+ for i=1,#cachepaths do
+ local cachepath = cachepaths[i]
+ if not lfs.isdir(cachepath) then
+ lfs.mkdirs(cachepath) -- needed for texlive and latex
+ if lfs.isdir(cachepath) then
+ logs.report("system","creating cache path '%s'",cachepath)
+ end
+ end
+ if file.is_writable(cachepath) then
+ writable = file.join(cachepath,"luatex-cache")
+ lfs.mkdir(writable)
+ writable = file.join(writable,caches.namespace)
+ lfs.mkdir(writable)
+ break
+ end
+ end
+
+ for i=1,#cachepaths do
+ if file.is_readable(cachepaths[i]) then
+ readables[#readables+1] = file.join(cachepaths[i],"luatex-cache",caches.namespace)
+ end
+ end
+
+ if not writable then
+ logs.report("system","no writeable cache path, quiting")
+ os.exit()
+ elseif #readables == 0 then
+ logs.report("system","no readable cache path, quiting")
+ os.exit()
+ elseif #readables == 1 and readables[1] == writable then
+ logs.report("system","using cache '%s'",writable)
+ else
+ logs.report("system","using write cache '%s'",writable)
+ logs.report("system","using read cache '%s'",table.concat(readables," "))
+ end
+
+end
+
+function caches.getwritablepath(category,subcategory)
+ local path = file.join(writable,category)
+ lfs.mkdir(path)
+ path = file.join(path,subcategory)
+ lfs.mkdir(path)
+ return path
+end
+
+function caches.getreadablepaths(category,subcategory)
+ local t = { }
+ for i=1,#readables do
+ t[i] = file.join(readables[i],category,subcategory)
+ end
+ return t
+end
+
+local function makefullname(path,name)
+ if path and path ~= "" then
+ return file.addsuffix(file.join(path,name),"lua"), file.addsuffix(file.join(path,name),usingjit and "lub" or "luc")
+ end
+end
+
+function caches.is_writable(path,name)
+ local fullname = makefullname(path,name)
+ return fullname and file.is_writable(fullname)
+end
+
+function caches.loaddata(readables,name,writable)
+ for i=1,#readables do
+ local path = readables[i]
+ local loader = false
+ local luaname, lucname = makefullname(path,name)
+ if lfs.isfile(lucname) then
+ logs.report("system","loading luc file '%s'",lucname)
+ loader = loadfile(lucname)
+ end
+ if not loader and lfs.isfile(luaname) then
+ -- can be different paths when we read a file database from disk
+ local luacrap, lucname = makefullname(writable,name)
+ logs.report("system","compiling luc file '%s'",lucname)
+ if lfs.isfile(lucname) then
+ loader = loadfile(lucname)
+ end
+ caches.compile(data,luaname,lucname)
+ if lfs.isfile(lucname) then
+ logs.report("system","loading luc file '%s'",lucname)
+ loader = loadfile(lucname)
+ else
+ logs.report("system","error in loading luc file '%s'",lucname)
+ end
+ if not loader then
+ logs.report("system","loading lua file '%s'",luaname)
+ loader = loadfile(luaname)
+ else
+ logs.report("system","error in loading lua file '%s'",luaname)
+ end
+ end
+ if loader then
+ loader = loader()
+ collectgarbage("step")
+ return loader
+ end
+ end
+ return false
+end
+
+function caches.savedata(path,name,data)
+ local luaname, lucname = makefullname(path,name)
+ if luaname then
+ logs.report("system","saving lua file '%s'",luaname)
+ table.tofile(luaname,data,true)
+ if lucname and type(caches.compile) == "function" then
+ os.remove(lucname) -- better be safe
+ logs.report("system","saving luc file '%s'",lucname)
+ caches.compile(data,luaname,lucname)
+ end
+ end
+end
+
+-- The method here is slightly different from the one we have in context. We
+-- also use different suffixes as we don't want any clashes (sharing cache
+-- files is not that handy as context moves on faster.)
+
+function caches.compile(data,luaname,lucname)
+ local d = io.loaddata(luaname)
+ if not d or d == "" then
+ d = table.serialize(data,true) -- slow
+ end
+ if d and d ~= "" then
+ local f = io.open(lucname,'wb')
+ if f then
+ local s = loadstring(d)
+ if s then
+ f:write(dump(s,true))
+ end
+ f:close()
+ end
+ end
+end
+
+-- simplfied version:
+
+function table.setmetatableindex(t,f)
+ if type(t) ~= "table" then
+ f, t = t, { }
+ end
+ local m = getmetatable(t)
+ if f == "table" then
+ f = function(t,k) local v = { } t[k] = v return v end
+ end
+ if m then
+ m.__index = f
+ else
+ setmetatable(t,{ __index = f })
+ end
+ return t
+end
+
+function table.makeweak(t)
+ local m = getmetatable(t)
+ if m then
+ m.__mode = "v"
+ else
+ setmetatable(t,{ __mode = "v" })
+ end
+ return t
+end
+
+-- helper for plain:
+
+arguments = { }
+
+if arg then
+ for i=1,#arg do
+ local k, v = match(arg[i],"^%-%-([^=]+)=?(.-)$")
+ if k and v then
+ arguments[k] = v
+ end
+ end
+end
+
+-- another one
+
+if not number.idiv then
+ function number.idiv(i,d)
+ return floor(i/d) -- i//d in 5.3
+ end
+end
+
+-- hook into unicode
+
+local u = unicode and unicode.utf8
+
+if u then
+
+ utf.lower = u.lower
+ utf.upper = u.upper
+ utf.char = u.char
+ utf.byte = u.byte
+ utf.len = u.len
+
+ -- needed on font-*
+
+ if lpeg.setutfcasers then
+ lpeg.setutfcasers(u.lower,u.upper)
+ end
+
+ -- needed on font-otr
+
+ local bytepairs = string.bytepairs
+ local utfchar = utf.char
+ local concat = table.concat
+
+ function utf.utf16_to_utf8_be(s)
+ if not s then
+ return nil
+ elseif s == "" then
+ return ""
+ end
+ local result, r, more = { }, 0, 0
+ for left, right in bytepairs(s) do
+ if right then
+ local now = 256*left + right
+ if more > 0 then
+ now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000
+ more = 0
+ r = r + 1
+ result[r] = utfchar(now)
+ elseif now >= 0xD800 and now <= 0xDBFF then
+ more = now
+ else
+ r = r + 1
+ result[r] = utfchar(now)
+ end
+ end
+ end
+ return concat(result)
+ end
+
+ local characters = string.utfcharacters
+
+ function utf.split(str)
+ local t, n = { }, 0
+ for s in characters(str) do
+ n = n + 1
+ t[n] = s
+ end
+ return t
+ end
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-basics-nod.lua b/macros/luatex/generic/luaotfload/fontloader-basics-nod.lua
new file mode 100644
index 0000000000..418b9d69d4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-basics-nod.lua
@@ -0,0 +1,263 @@
+if not modules then modules = { } end modules ['luatex-fonts-nod'] = {
+ version = 1.001,
+ comment = "companion to luatex-fonts.lua",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+-- Don't depend on code here as it is only needed to complement the font handler
+-- code. I will move some to another namespace as I don't see other macro packages
+-- use the context logic. It's a subset anyway. More will be stripped.
+
+-- Attributes:
+
+if tex.attribute[0] ~= 0 then
+
+ texio.write_nl("log","!")
+ texio.write_nl("log","! Attribute 0 is reserved for ConTeXt's font feature management and has to be")
+ texio.write_nl("log","! set to zero. Also, some attributes in the range 1-255 are used for special")
+ texio.write_nl("log","! purposes so setting them at the TeX end might break the font handler.")
+ texio.write_nl("log","!")
+
+ tex.attribute[0] = 0 -- else no features
+
+end
+
+attributes = attributes or { }
+attributes.unsetvalue = -0x7FFFFFFF
+
+local numbers, last = { }, 127
+
+attributes.private = attributes.private or function(name)
+ local number = numbers[name]
+ if not number then
+ if last < 255 then
+ last = last + 1
+ end
+ number = last
+ numbers[name] = number
+ end
+ return number
+end
+
+-- Nodes (a subset of context so that we don't get too much unused code):
+
+nodes = { }
+nodes.handlers = { }
+
+local nodecodes = { }
+local glyphcodes = node.subtypes("glyph")
+local disccodes = node.subtypes("disc")
+
+for k, v in next, node.types() do
+ v = string.gsub(v,"_","")
+ nodecodes[k] = v
+ nodecodes[v] = k
+end
+for k, v in next, glyphcodes do
+ glyphcodes[v] = k
+end
+for k, v in next, disccodes do
+ disccodes[v] = k
+end
+
+nodes.nodecodes = nodecodes
+nodes.glyphcodes = glyphcodes
+nodes.disccodes = disccodes
+
+nodes.handlers.protectglyphs = node.protect_glyphs -- beware: nodes!
+nodes.handlers.unprotectglyphs = node.unprotect_glyphs -- beware: nodes!
+
+-- in generic code, at least for some time, we stay nodes, while in context
+-- we can go nuts (e.g. experimental); this split permits us us keep code
+-- used elsewhere stable but at the same time play around in context
+
+-- much of this will go away .. it's part of the context interface and not
+-- officially in luatex-*.lua
+
+local direct = node.direct
+local nuts = { }
+nodes.nuts = nuts
+
+local tonode = direct.tonode
+local tonut = direct.todirect
+
+nodes.tonode = tonode
+nodes.tonut = tonut
+
+nuts.tonode = tonode
+nuts.tonut = tonut
+
+nuts.getattr = direct.get_attribute
+nuts.getboth = direct.getboth
+nuts.getchar = direct.getchar
+nuts.getcomponents = direct.getcomponents
+nuts.getdirection = direct.getdirection
+nuts.getdisc = direct.getdisc
+nuts.getfield = direct.getfield
+nuts.getfont = direct.getfont
+nuts.getid = direct.getid
+nuts.getkern = direct.getkern
+nuts.getlist = direct.getlist
+nuts.getnext = direct.getnext
+nuts.getoffsets = direct.getoffsets
+nuts.getprev = direct.getprev
+nuts.getsubtype = direct.getsubtype
+nuts.getwidth = direct.getwidth
+nuts.setattr = direct.setfield
+nuts.setboth = direct.setboth
+nuts.setchar = direct.setchar
+nuts.setcomponents = direct.setcomponents
+nuts.setdirection = direct.setdirection
+nuts.setdisc = direct.setdisc
+nuts.setfield = setfield
+nuts.setkern = direct.setkern
+nuts.setlink = direct.setlink
+nuts.setlist = direct.setlist
+nuts.setnext = direct.setnext
+nuts.setoffsets = direct.setoffsets
+nuts.setprev = direct.setprev
+nuts.setsplit = direct.setsplit
+nuts.setsubtype = direct.setsubtype
+nuts.setwidth = direct.setwidth
+
+nuts.getglyphdata = nuts.getattr
+nuts.setglyphdata = nuts.setattr
+
+nuts.ischar = direct.is_char
+nuts.isglyph = direct.is_glyph
+
+nuts.copy = direct.copy
+nuts.copy_list = direct.copy_list
+nuts.copy_node = direct.copy
+nuts.delete = direct.delete
+nuts.end_of_math = direct.end_of_math
+nuts.flush = direct.flush
+nuts.flush_list = direct.flush_list
+nuts.flush_node = direct.flush_node
+nuts.free = direct.free
+nuts.insert_after = direct.insert_after
+nuts.insert_before = direct.insert_before
+nuts.is_node = direct.is_node
+nuts.kerning = direct.kerning
+nuts.ligaturing = direct.ligaturing
+nuts.new = direct.new
+nuts.remove = direct.remove
+nuts.tail = direct.tail
+nuts.traverse = direct.traverse
+nuts.traverse_char = direct.traverse_char
+nuts.traverse_glyph = direct.traverse_glyph
+nuts.traverse_id = direct.traverse_id
+
+-- properties as used in the (new) injector:
+
+local propertydata = direct.get_properties_table()
+nodes.properties = { data = propertydata }
+
+if direct.set_properties_mode then
+ direct.set_properties_mode(true,true)
+ function direct.set_properties_mode() end
+end
+
+nuts.getprop = function(n,k)
+ local p = propertydata[n]
+ if p then
+ return p[k]
+ end
+end
+
+nuts.setprop = function(n,k,v)
+ if v then
+ local p = propertydata[n]
+ if p then
+ p[k] = v
+ else
+ propertydata[n] = { [k] = v }
+ end
+ end
+end
+
+nodes.setprop = nodes.setproperty
+nodes.getprop = nodes.getproperty
+
+-- a few helpers (we need to keep 'm in sync with context) .. some day components
+-- might go so here we isolate them
+
+local setprev = nuts.setprev
+local setnext = nuts.setnext
+local getnext = nuts.getnext
+local setlink = nuts.setlink
+local getfield = nuts.getfield
+local setfield = nuts.setfield
+local getcomponents = nuts.getcomponents
+local setcomponents = nuts.setcomponents
+
+local find_tail = nuts.tail
+local flush_list = nuts.flush_list
+local flush_node = nuts.flush_node
+local traverse_id = nuts.traverse_id
+local copy_node = nuts.copy_node
+
+local glyph_code = nodes.nodecodes.glyph
+
+function nuts.copy_no_components(g,copyinjection)
+ local components = getcomponents(g)
+ if components then
+ setcomponents(g)
+ local n = copy_node(g)
+ if copyinjection then
+ copyinjection(n,g)
+ end
+ setcomponents(g,components)
+ -- maybe also upgrade the subtype but we don't use it anyway
+ return n
+ else
+ local n = copy_node(g)
+ if copyinjection then
+ copyinjection(n,g)
+ end
+ return n
+ end
+end
+
+function nuts.copy_only_glyphs(current)
+ local head = nil
+ local previous = nil
+ for n in traverse_id(glyph_code,current) do
+ n = copy_node(n)
+ if head then
+ setlink(previous,n)
+ else
+ head = n
+ end
+ previous = n
+ end
+ return head
+end
+
+nuts.uses_font = direct.uses_font
+
+do
+
+ -- another poor mans substitute ... i will move these to a more protected
+ -- namespace .. experimental hack
+
+ local dummy = tonut(node.new("glyph"))
+
+ nuts.traversers = {
+ glyph = nuts.traverse_id(nodecodes.glyph,dummy),
+ glue = nuts.traverse_id(nodecodes.glue,dummy),
+ disc = nuts.traverse_id(nodecodes.disc,dummy),
+ boundary = nuts.traverse_id(nodecodes.boundary,dummy),
+
+ char = nuts.traverse_char(dummy),
+
+ node = nuts.traverse(dummy),
+ }
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-data-con.lua b/macros/luatex/generic/luaotfload/fontloader-data-con.lua
new file mode 100644
index 0000000000..c79fca7c5c
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-data-con.lua
@@ -0,0 +1,138 @@
+if not modules then modules = { } end modules ['data-con'] = {
+ version = 1.100,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local format, lower, gsub = string.format, string.lower, string.gsub
+
+local trace_cache = false trackers.register("resolvers.cache", function(v) trace_cache = v end)
+local trace_containers = false trackers.register("resolvers.containers", function(v) trace_containers = v end)
+local trace_storage = false trackers.register("resolvers.storage", function(v) trace_storage = v end)
+
+--[[ldx--
+<p>Once we found ourselves defining similar cache constructs
+several times, containers were introduced. Containers are used
+to collect tables in memory and reuse them when possible based
+on (unique) hashes (to be provided by the calling function).</p>
+
+<p>Caching to disk is disabled by default. Version numbers are
+stored in the saved table which makes it possible to change the
+table structures without bothering about the disk cache.</p>
+
+<p>Examples of usage can be found in the font related code.</p>
+--ldx]]--
+
+containers = containers or { }
+local containers = containers
+containers.usecache = true
+
+local report_containers = logs.reporter("resolvers","containers")
+
+local allocated = { }
+
+local mt = {
+ __index = function(t,k)
+ if k == "writable" then
+ local writable = caches.getwritablepath(t.category,t.subcategory) or { "." }
+ t.writable = writable
+ return writable
+ elseif k == "readables" then
+ local readables = caches.getreadablepaths(t.category,t.subcategory) or { "." }
+ t.readables = readables
+ return readables
+ end
+ end,
+ __storage__ = true
+}
+
+function containers.define(category, subcategory, version, enabled)
+ if category and subcategory then
+ local c = allocated[category]
+ if not c then
+ c = { }
+ allocated[category] = c
+ end
+ local s = c[subcategory]
+ if not s then
+ s = {
+ category = category,
+ subcategory = subcategory,
+ storage = { },
+ enabled = enabled,
+ version = version or math.pi, -- after all, this is TeX
+ trace = false,
+ -- writable = caches.getwritablepath and caches.getwritablepath (category,subcategory) or { "." },
+ -- readables = caches.getreadablepaths and caches.getreadablepaths(category,subcategory) or { "." },
+ }
+ setmetatable(s,mt)
+ c[subcategory] = s
+ end
+ return s
+ end
+end
+
+function containers.is_usable(container,name)
+ return container.enabled and caches and caches.is_writable(container.writable, name)
+end
+
+function containers.is_valid(container,name)
+ if name and name ~= "" then
+ local storage = container.storage[name]
+ return storage and storage.cache_version == container.version
+ else
+ return false
+ end
+end
+
+function containers.read(container,name)
+ local storage = container.storage
+ local stored = storage[name]
+ if not stored and container.enabled and caches and containers.usecache then
+ stored = caches.loaddata(container.readables,name,container.writable)
+ if stored and stored.cache_version == container.version then
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","load",container.subcategory,name)
+ end
+ else
+ stored = nil
+ end
+ storage[name] = stored
+ elseif stored then
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","reuse",container.subcategory,name)
+ end
+ end
+ return stored
+end
+
+function containers.write(container, name, data)
+ if data then
+ data.cache_version = container.version
+ if container.enabled and caches then
+ local unique, shared = data.unique, data.shared
+ data.unique, data.shared = nil, nil
+ caches.savedata(container.writable, name, data)
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","save",container.subcategory,name)
+ end
+ data.unique, data.shared = unique, shared
+ end
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","store",container.subcategory,name)
+ end
+ container.storage[name] = data
+ end
+ return data
+end
+
+function containers.content(container,name)
+ return container.storage[name]
+end
+
+function containers.cleanname(name)
+ -- return (gsub(lower(name),"[^%w]+","-"))
+ return (gsub(lower(name),"[^%w\128-\255]+","-")) -- more utf friendly
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-afk.lua b/macros/luatex/generic/luaotfload/fontloader-font-afk.lua
new file mode 100644
index 0000000000..761016d348
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-afk.lua
@@ -0,0 +1,200 @@
+if not modules then modules = { } end modules ['font-afk'] = {
+ version = 1.001,
+ comment = "companion to font-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files",
+ dataonly = true,
+}
+
+--[[ldx--
+<p>For ligatures, only characters with a code smaller than 128 make sense,
+anything larger is encoding dependent. An interesting complication is that a
+character can be in an encoding twice but is hashed once.</p>
+--ldx]]--
+
+local allocate = utilities.storage.allocate
+
+fonts.handlers.afm.helpdata = {
+ ligatures = allocate { -- okay, nowadays we could parse the name but type 1 fonts
+ ['f'] = { -- don't have that many ligatures anyway
+ { 'f', 'ff' },
+ { 'i', 'fi' },
+ { 'l', 'fl' },
+ },
+ ['ff'] = {
+ { 'i', 'ffi' }
+ },
+ ['fi'] = {
+ { 'i', 'fii' }
+ },
+ ['fl'] = {
+ { 'i', 'fli' }
+ },
+ ['s'] = {
+ { 't', 'st' }
+ },
+ ['i'] = {
+ { 'j', 'ij' }
+ },
+ },
+ texligatures = allocate {
+ -- ['space'] = {
+ -- { 'L', 'Lslash' },
+ -- { 'l', 'lslash' }
+ -- },
+ -- ['question'] = {
+ -- { 'quoteleft', 'questiondown' }
+ -- },
+ -- ['exclam'] = {
+ -- { 'quoteleft', 'exclamdown' }
+ -- },
+ ['quoteleft'] = {
+ { 'quoteleft', 'quotedblleft' }
+ },
+ ['quoteright'] = {
+ { 'quoteright', 'quotedblright' }
+ },
+ ['hyphen'] = {
+ { 'hyphen', 'endash' }
+ },
+ ['endash'] = {
+ { 'hyphen', 'emdash' }
+ }
+ },
+ leftkerned = allocate {
+ AEligature = "A", aeligature = "a",
+ OEligature = "O", oeligature = "o",
+ IJligature = "I", ijligature = "i",
+ AE = "A", ae = "a",
+ OE = "O", oe = "o",
+ IJ = "I", ij = "i",
+ Ssharp = "S", ssharp = "s",
+ },
+ rightkerned = allocate {
+ AEligature = "E", aeligature = "e",
+ OEligature = "E", oeligature = "e",
+ IJligature = "J", ijligature = "j",
+ AE = "E", ae = "e",
+ OE = "E", oe = "e",
+ IJ = "J", ij = "j",
+ Ssharp = "S", ssharp = "s",
+ },
+ bothkerned = allocate {
+ Acircumflex = "A", acircumflex = "a",
+ Ccircumflex = "C", ccircumflex = "c",
+ Ecircumflex = "E", ecircumflex = "e",
+ Gcircumflex = "G", gcircumflex = "g",
+ Hcircumflex = "H", hcircumflex = "h",
+ Icircumflex = "I", icircumflex = "i",
+ Jcircumflex = "J", jcircumflex = "j",
+ Ocircumflex = "O", ocircumflex = "o",
+ Scircumflex = "S", scircumflex = "s",
+ Ucircumflex = "U", ucircumflex = "u",
+ Wcircumflex = "W", wcircumflex = "w",
+ Ycircumflex = "Y", ycircumflex = "y",
+
+ Agrave = "A", agrave = "a",
+ Egrave = "E", egrave = "e",
+ Igrave = "I", igrave = "i",
+ Ograve = "O", ograve = "o",
+ Ugrave = "U", ugrave = "u",
+ Ygrave = "Y", ygrave = "y",
+
+ Atilde = "A", atilde = "a",
+ Itilde = "I", itilde = "i",
+ Otilde = "O", otilde = "o",
+ Utilde = "U", utilde = "u",
+ Ntilde = "N", ntilde = "n",
+
+ Adiaeresis = "A", adiaeresis = "a", Adieresis = "A", adieresis = "a",
+ Ediaeresis = "E", ediaeresis = "e", Edieresis = "E", edieresis = "e",
+ Idiaeresis = "I", idiaeresis = "i", Idieresis = "I", idieresis = "i",
+ Odiaeresis = "O", odiaeresis = "o", Odieresis = "O", odieresis = "o",
+ Udiaeresis = "U", udiaeresis = "u", Udieresis = "U", udieresis = "u",
+ Ydiaeresis = "Y", ydiaeresis = "y", Ydieresis = "Y", ydieresis = "y",
+
+ Aacute = "A", aacute = "a",
+ Cacute = "C", cacute = "c",
+ Eacute = "E", eacute = "e",
+ Iacute = "I", iacute = "i",
+ Lacute = "L", lacute = "l",
+ Nacute = "N", nacute = "n",
+ Oacute = "O", oacute = "o",
+ Racute = "R", racute = "r",
+ Sacute = "S", sacute = "s",
+ Uacute = "U", uacute = "u",
+ Yacute = "Y", yacute = "y",
+ Zacute = "Z", zacute = "z",
+
+ Dstroke = "D", dstroke = "d",
+ Hstroke = "H", hstroke = "h",
+ Tstroke = "T", tstroke = "t",
+
+ Cdotaccent = "C", cdotaccent = "c",
+ Edotaccent = "E", edotaccent = "e",
+ Gdotaccent = "G", gdotaccent = "g",
+ Idotaccent = "I", idotaccent = "i",
+ Zdotaccent = "Z", zdotaccent = "z",
+
+ Amacron = "A", amacron = "a",
+ Emacron = "E", emacron = "e",
+ Imacron = "I", imacron = "i",
+ Omacron = "O", omacron = "o",
+ Umacron = "U", umacron = "u",
+
+ Ccedilla = "C", ccedilla = "c",
+ Kcedilla = "K", kcedilla = "k",
+ Lcedilla = "L", lcedilla = "l",
+ Ncedilla = "N", ncedilla = "n",
+ Rcedilla = "R", rcedilla = "r",
+ Scedilla = "S", scedilla = "s",
+ Tcedilla = "T", tcedilla = "t",
+
+ Ohungarumlaut = "O", ohungarumlaut = "o",
+ Uhungarumlaut = "U", uhungarumlaut = "u",
+
+ Aogonek = "A", aogonek = "a",
+ Eogonek = "E", eogonek = "e",
+ Iogonek = "I", iogonek = "i",
+ Uogonek = "U", uogonek = "u",
+
+ Aring = "A", aring = "a",
+ Uring = "U", uring = "u",
+
+ Abreve = "A", abreve = "a",
+ Ebreve = "E", ebreve = "e",
+ Gbreve = "G", gbreve = "g",
+ Ibreve = "I", ibreve = "i",
+ Obreve = "O", obreve = "o",
+ Ubreve = "U", ubreve = "u",
+
+ Ccaron = "C", ccaron = "c",
+ Dcaron = "D", dcaron = "d",
+ Ecaron = "E", ecaron = "e",
+ Lcaron = "L", lcaron = "l",
+ Ncaron = "N", ncaron = "n",
+ Rcaron = "R", rcaron = "r",
+ Scaron = "S", scaron = "s",
+ Tcaron = "T", tcaron = "t",
+ Zcaron = "Z", zcaron = "z",
+
+ dotlessI = "I", dotlessi = "i",
+ dotlessJ = "J", dotlessj = "j",
+
+ AEligature = "AE", aeligature = "ae", AE = "AE", ae = "ae",
+ OEligature = "OE", oeligature = "oe", OE = "OE", oe = "oe",
+ IJligature = "IJ", ijligature = "ij", IJ = "IJ", ij = "ij",
+
+ Lstroke = "L", lstroke = "l", Lslash = "L", lslash = "l",
+ Ostroke = "O", ostroke = "o", Oslash = "O", oslash = "o",
+
+ Ssharp = "SS", ssharp = "ss",
+
+ Aumlaut = "A", aumlaut = "a",
+ Eumlaut = "E", eumlaut = "e",
+ Iumlaut = "I", iumlaut = "i",
+ Oumlaut = "O", oumlaut = "o",
+ Uumlaut = "U", uumlaut = "u",
+ }
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-cff.lua b/macros/luatex/generic/luaotfload/fontloader-font-cff.lua
new file mode 100644
index 0000000000..a19acc1a1d
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-cff.lua
@@ -0,0 +1,2483 @@
+if not modules then modules = { } end modules ['font-cff'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- todo: option.outlines
+-- todo: option.boundingbox
+-- per charstring (less memory)
+
+-- This is a heavy one as it is a rather packed format. We don't need al the information
+-- now but we might need it later (who know what magic we can do with metapost). So at
+-- some point this might become a module. We just follow Adobe Technical Notes #5176 and
+-- #5177. In case of doubt I looked in the fontforge code that comes with LuaTeX but
+-- it's not the easiest source to read (and doesn't cover cff2).
+
+-- For now we save the segments in a list of segments with the operator last in an entry
+-- because that reflects the original. But it might make more sense to use a single array
+-- per segment. For pdf a simple concat works ok, but for other purposes a operator first
+-- flush is nicer.
+--
+-- In retrospect I could have looked into the backend code of LuaTeX but it never
+-- occurred to me that parsing charstrings was needed there (which has to to
+-- with merging subroutines and flattening, not so much with calculations.) On
+-- the other hand, we can now feed back cff2 stuff.
+
+local next, type, tonumber, rawget = next, type, tonumber, rawget
+local byte, char, gmatch = string.byte, string.char, string.gmatch
+local concat, remove, unpack = table.concat, table.remove, table.unpack
+local floor, abs, round, ceil, min, max = math.floor, math.abs, math.round, math.ceil, math.min, math.max
+local P, C, R, S, C, Cs, Ct = lpeg.P, lpeg.C, lpeg.R, lpeg.S, lpeg.C, lpeg.Cs, lpeg.Ct
+local lpegmatch = lpeg.match
+local formatters = string.formatters
+local bytetable = string.bytetable
+local idiv = number.idiv
+local rshift, band, extract = bit32.rshift, bit32.band, bit32.extract
+
+local readers = fonts.handlers.otf.readers
+local streamreader = readers.streamreader
+
+local readstring = streamreader.readstring
+local readbyte = streamreader.readcardinal1 -- 8-bit unsigned integer
+local readushort = streamreader.readcardinal2 -- 16-bit unsigned integer
+local readuint = streamreader.readcardinal3 -- 24-bit unsigned integer
+local readulong = streamreader.readcardinal4 -- 32-bit unsigned integer
+local setposition = streamreader.setposition
+local getposition = streamreader.getposition
+local readbytetable = streamreader.readbytetable
+
+directives.register("fonts.streamreader",function()
+
+ streamreader = utilities.streams
+
+ readstring = streamreader.readstring
+ readbyte = streamreader.readcardinal1
+ readushort = streamreader.readcardinal2
+ readuint = streamreader.readcardinal3
+ readulong = streamreader.readcardinal4
+ setposition = streamreader.setposition
+ getposition = streamreader.getposition
+ readbytetable = streamreader.readbytetable
+
+end)
+
+local setmetatableindex = table.setmetatableindex
+
+local trace_charstrings = false trackers.register("fonts.cff.charstrings",function(v) trace_charstrings = v end)
+local report = logs.reporter("otf reader","cff")
+
+local parsedictionaries
+local parsecharstring
+local parsecharstrings
+local resetcharstrings
+local parseprivates
+local startparsing
+local stopparsing
+
+local defaultstrings = { [0] = -- taken from ff
+ ".notdef", "space", "exclam", "quotedbl", "numbersign", "dollar", "percent",
+ "ampersand", "quoteright", "parenleft", "parenright", "asterisk", "plus",
+ "comma", "hyphen", "period", "slash", "zero", "one", "two", "three", "four",
+ "five", "six", "seven", "eight", "nine", "colon", "semicolon", "less",
+ "equal", "greater", "question", "at", "A", "B", "C", "D", "E", "F", "G", "H",
+ "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W",
+ "X", "Y", "Z", "bracketleft", "backslash", "bracketright", "asciicircum",
+ "underscore", "quoteleft", "a", "b", "c", "d", "e", "f", "g", "h", "i", "j",
+ "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y",
+ "z", "braceleft", "bar", "braceright", "asciitilde", "exclamdown", "cent",
+ "sterling", "fraction", "yen", "florin", "section", "currency",
+ "quotesingle", "quotedblleft", "guillemotleft", "guilsinglleft",
+ "guilsinglright", "fi", "fl", "endash", "dagger", "daggerdbl",
+ "periodcentered", "paragraph", "bullet", "quotesinglbase", "quotedblbase",
+ "quotedblright", "guillemotright", "ellipsis", "perthousand", "questiondown",
+ "grave", "acute", "circumflex", "tilde", "macron", "breve", "dotaccent",
+ "dieresis", "ring", "cedilla", "hungarumlaut", "ogonek", "caron", "emdash",
+ "AE", "ordfeminine", "Lslash", "Oslash", "OE", "ordmasculine", "ae",
+ "dotlessi", "lslash", "oslash", "oe", "germandbls", "onesuperior",
+ "logicalnot", "mu", "trademark", "Eth", "onehalf", "plusminus", "Thorn",
+ "onequarter", "divide", "brokenbar", "degree", "thorn", "threequarters",
+ "twosuperior", "registered", "minus", "eth", "multiply", "threesuperior",
+ "copyright", "Aacute", "Acircumflex", "Adieresis", "Agrave", "Aring",
+ "Atilde", "Ccedilla", "Eacute", "Ecircumflex", "Edieresis", "Egrave",
+ "Iacute", "Icircumflex", "Idieresis", "Igrave", "Ntilde", "Oacute",
+ "Ocircumflex", "Odieresis", "Ograve", "Otilde", "Scaron", "Uacute",
+ "Ucircumflex", "Udieresis", "Ugrave", "Yacute", "Ydieresis", "Zcaron",
+ "aacute", "acircumflex", "adieresis", "agrave", "aring", "atilde",
+ "ccedilla", "eacute", "ecircumflex", "edieresis", "egrave", "iacute",
+ "icircumflex", "idieresis", "igrave", "ntilde", "oacute", "ocircumflex",
+ "odieresis", "ograve", "otilde", "scaron", "uacute", "ucircumflex",
+ "udieresis", "ugrave", "yacute", "ydieresis", "zcaron", "exclamsmall",
+ "Hungarumlautsmall", "dollaroldstyle", "dollarsuperior", "ampersandsmall",
+ "Acutesmall", "parenleftsuperior", "parenrightsuperior", "twodotenleader",
+ "onedotenleader", "zerooldstyle", "oneoldstyle", "twooldstyle",
+ "threeoldstyle", "fouroldstyle", "fiveoldstyle", "sixoldstyle",
+ "sevenoldstyle", "eightoldstyle", "nineoldstyle", "commasuperior",
+ "threequartersemdash", "periodsuperior", "questionsmall", "asuperior",
+ "bsuperior", "centsuperior", "dsuperior", "esuperior", "isuperior",
+ "lsuperior", "msuperior", "nsuperior", "osuperior", "rsuperior", "ssuperior",
+ "tsuperior", "ff", "ffi", "ffl", "parenleftinferior", "parenrightinferior",
+ "Circumflexsmall", "hyphensuperior", "Gravesmall", "Asmall", "Bsmall",
+ "Csmall", "Dsmall", "Esmall", "Fsmall", "Gsmall", "Hsmall", "Ismall",
+ "Jsmall", "Ksmall", "Lsmall", "Msmall", "Nsmall", "Osmall", "Psmall",
+ "Qsmall", "Rsmall", "Ssmall", "Tsmall", "Usmall", "Vsmall", "Wsmall",
+ "Xsmall", "Ysmall", "Zsmall", "colonmonetary", "onefitted", "rupiah",
+ "Tildesmall", "exclamdownsmall", "centoldstyle", "Lslashsmall",
+ "Scaronsmall", "Zcaronsmall", "Dieresissmall", "Brevesmall", "Caronsmall",
+ "Dotaccentsmall", "Macronsmall", "figuredash", "hypheninferior",
+ "Ogoneksmall", "Ringsmall", "Cedillasmall", "questiondownsmall", "oneeighth",
+ "threeeighths", "fiveeighths", "seveneighths", "onethird", "twothirds",
+ "zerosuperior", "foursuperior", "fivesuperior", "sixsuperior",
+ "sevensuperior", "eightsuperior", "ninesuperior", "zeroinferior",
+ "oneinferior", "twoinferior", "threeinferior", "fourinferior",
+ "fiveinferior", "sixinferior", "seveninferior", "eightinferior",
+ "nineinferior", "centinferior", "dollarinferior", "periodinferior",
+ "commainferior", "Agravesmall", "Aacutesmall", "Acircumflexsmall",
+ "Atildesmall", "Adieresissmall", "Aringsmall", "AEsmall", "Ccedillasmall",
+ "Egravesmall", "Eacutesmall", "Ecircumflexsmall", "Edieresissmall",
+ "Igravesmall", "Iacutesmall", "Icircumflexsmall", "Idieresissmall",
+ "Ethsmall", "Ntildesmall", "Ogravesmall", "Oacutesmall", "Ocircumflexsmall",
+ "Otildesmall", "Odieresissmall", "OEsmall", "Oslashsmall", "Ugravesmall",
+ "Uacutesmall", "Ucircumflexsmall", "Udieresissmall", "Yacutesmall",
+ "Thornsmall", "Ydieresissmall", "001.000", "001.001", "001.002", "001.003",
+ "Black", "Bold", "Book", "Light", "Medium", "Regular", "Roman", "Semibold",
+}
+
+local cffreaders = {
+ readbyte,
+ readushort,
+ readuint,
+ readulong,
+}
+
+-- The header contains information about its own size.
+
+local function readheader(f)
+ local offset = getposition(f)
+ local major = readbyte(f)
+ local header = {
+ offset = offset,
+ major = major,
+ minor = readbyte(f),
+ size = readbyte(f), -- headersize
+ }
+ if major == 1 then
+ header.dsize = readbyte(f) -- list of dict offsets
+ elseif major == 2 then
+ header.dsize = readushort(f) -- topdict size
+ else
+ -- I'm probably no longer around by then and we use AI's to
+ -- handle this kind of stuff, if we typeset documents at all.
+ end
+ setposition(f,offset+header.size)
+ return header
+end
+
+-- The indexes all look the same, so we share a loader. We could pass a handler
+-- and run over the array but why bother, we only have a few uses.
+
+local function readlengths(f,longcount)
+ local count = longcount and readulong(f) or readushort(f)
+ if count == 0 then
+ return { }
+ end
+ local osize = readbyte(f)
+ local read = cffreaders[osize]
+ if not read then
+ report("bad offset size: %i",osize)
+ return { }
+ end
+ local lengths = { }
+ local previous = read(f)
+ for i=1,count do
+ local offset = read(f)
+ local length = offset - previous
+ if length < 0 then
+ report("bad offset: %i",length)
+ length = 0
+ end
+ lengths[i] = length
+ previous = offset
+ end
+ return lengths
+end
+
+-- There can be subfonts so names is an array. However, in our case it's always
+-- one font. The same is true for the top dictionaries. Watch how we only load
+-- the dictionary string as for interpretation we need to have the strings loaded
+-- as well.
+
+local function readfontnames(f)
+ local names = readlengths(f)
+ for i=1,#names do
+ names[i] = readstring(f,names[i])
+ end
+ return names
+end
+
+local function readtopdictionaries(f)
+ local dictionaries = readlengths(f)
+ for i=1,#dictionaries do
+ dictionaries[i] = readstring(f,dictionaries[i])
+ end
+ return dictionaries
+end
+
+-- Strings are added to a list of standard strings so we start the font specific
+-- one with an offset. Strings are shared so we have one table.
+
+local function readstrings(f)
+ local lengths = readlengths(f)
+ local strings = setmetatableindex({ }, defaultstrings)
+ local index = #defaultstrings
+ for i=1,#lengths do
+ index = index + 1
+ strings[index] = readstring(f,lengths[i])
+ end
+ return strings
+end
+
+-- Parsing the dictionaries is delayed till we have the strings loaded. The parser
+-- is stack based so the operands come before the operator (like in postscript).
+
+-- local function delta(t)
+-- local n = #t
+-- if n > 1 then
+-- local p = t[1]
+-- for i=2,n do
+-- local c = t[i]
+-- t[i] = c + p
+-- p = c
+-- end
+-- end
+-- end
+
+do
+
+ -- We use a closure so that we don't need to pass too much around. For cff2 we can
+ -- at some point use a simple version as there is less.
+
+ local stack = { }
+ local top = 0
+ local result = { }
+ local strings = { }
+
+ local p_single =
+ P("\00") / function()
+ result.version = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\01") / function()
+ result.notice = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\02") / function()
+ result.fullname = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\03") / function()
+ result.familyname = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\04") / function()
+ result.weight = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\05") / function()
+ result.fontbbox = { unpack(stack,1,4) }
+ top = 0
+ end
+ + P("\06") / function()
+ result.bluevalues = { unpack(stack,1,top) }
+ top = 0
+ end
+ + P("\07") / function()
+ result.otherblues = { unpack(stack,1,top) }
+ top = 0
+ end
+ + P("\08") / function()
+ result.familyblues = { unpack(stack,1,top) }
+ top = 0
+ end
+ + P("\09") / function()
+ result.familyotherblues = { unpack(stack,1,top) }
+ top = 0
+ end
+ + P("\10") / function()
+ result.strhw = stack[top]
+ top = 0
+ end
+ + P("\11") / function()
+ result.strvw = stack[top]
+ top = 0
+ end
+ + P("\13") / function()
+ result.uniqueid = stack[top]
+ top = 0
+ end
+ + P("\14") / function()
+ result.xuid = concat(stack,"",1,top)
+ top = 0
+ end
+ + P("\15") / function()
+ result.charset = stack[top]
+ top = 0
+ end
+ + P("\16") / function()
+ result.encoding = stack[top]
+ top = 0
+ end
+ + P("\17") / function() -- valid cff2
+ result.charstrings = stack[top]
+ top = 0
+ end
+ + P("\18") / function()
+ result.private = {
+ size = stack[top-1],
+ offset = stack[top],
+ }
+ top = 0
+ end
+ + P("\19") / function()
+ result.subroutines = stack[top]
+ top = 0 -- new, forgotten ?
+ end
+ + P("\20") / function()
+ result.defaultwidthx = stack[top]
+ top = 0 -- new, forgotten ?
+ end
+ + P("\21") / function()
+ result.nominalwidthx = stack[top]
+ top = 0 -- new, forgotten ?
+ end
+ -- + P("\22") / function() -- reserved
+ -- end
+ -- + P("\23") / function() -- reserved
+ -- end
+ + P("\24") / function() -- new in cff2
+ result.vstore = stack[top]
+ top = 0
+ end
+ + P("\25") / function() -- new in cff2
+ result.maxstack = stack[top]
+ top = 0
+ end
+ -- + P("\26") / function() -- reserved
+ -- end
+ -- + P("\27") / function() -- reserved
+ -- end
+
+ local p_double = P("\12") * (
+ P("\00") / function()
+ result.copyright = stack[top]
+ top = 0
+ end
+ + P("\01") / function()
+ result.monospaced = stack[top] == 1 and true or false -- isfixedpitch
+ top = 0
+ end
+ + P("\02") / function()
+ result.italicangle = stack[top]
+ top = 0
+ end
+ + P("\03") / function()
+ result.underlineposition = stack[top]
+ top = 0
+ end
+ + P("\04") / function()
+ result.underlinethickness = stack[top]
+ top = 0
+ end
+ + P("\05") / function()
+ result.painttype = stack[top]
+ top = 0
+ end
+ + P("\06") / function()
+ result.charstringtype = stack[top]
+ top = 0
+ end
+ + P("\07") / function() -- valid cff2
+ result.fontmatrix = { unpack(stack,1,6) }
+ top = 0
+ end
+ + P("\08") / function()
+ result.strokewidth = stack[top]
+ top = 0
+ end
+ + P("\09") / function()
+ result.bluescale = stack[top]
+ top = 0
+ end
+ + P("\10") / function()
+ result.bluesnap = stack[top]
+ top = 0
+ end
+ + P("\11") / function()
+ result.bluefuzz = stack[top]
+ top = 0
+ end
+ + P("\12") / function()
+ result.stemsnaph = { unpack(stack,1,top) }
+ top = 0
+ end
+ + P("\13") / function()
+ result.stemsnapv = { unpack(stack,1,top) }
+ top = 0
+ end
+ + P("\20") / function()
+ result.syntheticbase = stack[top]
+ top = 0
+ end
+ + P("\21") / function()
+ result.postscript = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\22") / function()
+ result.basefontname = strings[stack[top]] or "unset"
+ top = 0
+ end
+ + P("\21") / function()
+ result.basefontblend = stack[top]
+ top = 0
+ end
+ + P("\30") / function()
+ result.cid.registry = strings[stack[top-2]] or "unset"
+ result.cid.ordering = strings[stack[top-1]] or "unset"
+ result.cid.supplement = stack[top]
+ top = 0
+ end
+ + P("\31") / function()
+ result.cid.fontversion = stack[top]
+ top = 0
+ end
+ + P("\32") / function()
+ result.cid.fontrevision= stack[top]
+ top = 0
+ end
+ + P("\33") / function()
+ result.cid.fonttype = stack[top]
+ top = 0
+ end
+ + P("\34") / function()
+ result.cid.count = stack[top]
+ top = 0
+ end
+ + P("\35") / function()
+ result.cid.uidbase = stack[top]
+ top = 0
+ end
+ + P("\36") / function() -- valid cff2
+ result.cid.fdarray = stack[top]
+ top = 0
+ end
+ + P("\37") / function() -- valid cff2
+ result.cid.fdselect = stack[top]
+ top = 0
+ end
+ + P("\38") / function()
+ result.cid.fontname = strings[stack[top]] or "unset"
+ top = 0
+ end
+ )
+
+ -- Some lpeg fun ... a first variant split the byte and made a new string but
+ -- the second variant is much faster. Not that it matters much as we don't see
+ -- such numbers often.
+
+ local remap = {
+ ["\x00"] = "00", ["\x01"] = "01", ["\x02"] = "02", ["\x03"] = "03", ["\x04"] = "04", ["\x05"] = "05", ["\x06"] = "06", ["\x07"] = "07", ["\x08"] = "08", ["\x09"] = "09", ["\x0A"] = "0.", ["\x0B"] = "0E", ["\x0C"] = "0E-", ["\x0D"] = "0", ["\x0E"] = "0-", ["\x0F"] = "0",
+ ["\x10"] = "10", ["\x11"] = "11", ["\x12"] = "12", ["\x13"] = "13", ["\x14"] = "14", ["\x15"] = "15", ["\x16"] = "16", ["\x17"] = "17", ["\x18"] = "18", ["\x19"] = "19", ["\x1A"] = "1.", ["\x1B"] = "1E", ["\x1C"] = "1E-", ["\x1D"] = "1", ["\x1E"] = "1-", ["\x1F"] = "1",
+ ["\x20"] = "20", ["\x21"] = "21", ["\x22"] = "22", ["\x23"] = "23", ["\x24"] = "24", ["\x25"] = "25", ["\x26"] = "26", ["\x27"] = "27", ["\x28"] = "28", ["\x29"] = "29", ["\x2A"] = "2.", ["\x2B"] = "2E", ["\x2C"] = "2E-", ["\x2D"] = "2", ["\x2E"] = "2-", ["\x2F"] = "2",
+ ["\x30"] = "30", ["\x31"] = "31", ["\x32"] = "32", ["\x33"] = "33", ["\x34"] = "34", ["\x35"] = "35", ["\x36"] = "36", ["\x37"] = "37", ["\x38"] = "38", ["\x39"] = "39", ["\x3A"] = "3.", ["\x3B"] = "3E", ["\x3C"] = "3E-", ["\x3D"] = "3", ["\x3E"] = "3-", ["\x3F"] = "3",
+ ["\x40"] = "40", ["\x41"] = "41", ["\x42"] = "42", ["\x43"] = "43", ["\x44"] = "44", ["\x45"] = "45", ["\x46"] = "46", ["\x47"] = "47", ["\x48"] = "48", ["\x49"] = "49", ["\x4A"] = "4.", ["\x4B"] = "4E", ["\x4C"] = "4E-", ["\x4D"] = "4", ["\x4E"] = "4-", ["\x4F"] = "4",
+ ["\x50"] = "50", ["\x51"] = "51", ["\x52"] = "52", ["\x53"] = "53", ["\x54"] = "54", ["\x55"] = "55", ["\x56"] = "56", ["\x57"] = "57", ["\x58"] = "58", ["\x59"] = "59", ["\x5A"] = "5.", ["\x5B"] = "5E", ["\x5C"] = "5E-", ["\x5D"] = "5", ["\x5E"] = "5-", ["\x5F"] = "5",
+ ["\x60"] = "60", ["\x61"] = "61", ["\x62"] = "62", ["\x63"] = "63", ["\x64"] = "64", ["\x65"] = "65", ["\x66"] = "66", ["\x67"] = "67", ["\x68"] = "68", ["\x69"] = "69", ["\x6A"] = "6.", ["\x6B"] = "6E", ["\x6C"] = "6E-", ["\x6D"] = "6", ["\x6E"] = "6-", ["\x6F"] = "6",
+ ["\x70"] = "70", ["\x71"] = "71", ["\x72"] = "72", ["\x73"] = "73", ["\x74"] = "74", ["\x75"] = "75", ["\x76"] = "76", ["\x77"] = "77", ["\x78"] = "78", ["\x79"] = "79", ["\x7A"] = "7.", ["\x7B"] = "7E", ["\x7C"] = "7E-", ["\x7D"] = "7", ["\x7E"] = "7-", ["\x7F"] = "7",
+ ["\x80"] = "80", ["\x81"] = "81", ["\x82"] = "82", ["\x83"] = "83", ["\x84"] = "84", ["\x85"] = "85", ["\x86"] = "86", ["\x87"] = "87", ["\x88"] = "88", ["\x89"] = "89", ["\x8A"] = "8.", ["\x8B"] = "8E", ["\x8C"] = "8E-", ["\x8D"] = "8", ["\x8E"] = "8-", ["\x8F"] = "8",
+ ["\x90"] = "90", ["\x91"] = "91", ["\x92"] = "92", ["\x93"] = "93", ["\x94"] = "94", ["\x95"] = "95", ["\x96"] = "96", ["\x97"] = "97", ["\x98"] = "98", ["\x99"] = "99", ["\x9A"] = "9.", ["\x9B"] = "9E", ["\x9C"] = "9E-", ["\x9D"] = "9", ["\x9E"] = "9-", ["\x9F"] = "9",
+ ["\xA0"] = ".0", ["\xA1"] = ".1", ["\xA2"] = ".2", ["\xA3"] = ".3", ["\xA4"] = ".4", ["\xA5"] = ".5", ["\xA6"] = ".6", ["\xA7"] = ".7", ["\xA8"] = ".8", ["\xA9"] = ".9", ["\xAA"] = "..", ["\xAB"] = ".E", ["\xAC"] = ".E-", ["\xAD"] = ".", ["\xAE"] = ".-", ["\xAF"] = ".",
+ ["\xB0"] = "E0", ["\xB1"] = "E1", ["\xB2"] = "E2", ["\xB3"] = "E3", ["\xB4"] = "E4", ["\xB5"] = "E5", ["\xB6"] = "E6", ["\xB7"] = "E7", ["\xB8"] = "E8", ["\xB9"] = "E9", ["\xBA"] = "E.", ["\xBB"] = "EE", ["\xBC"] = "EE-", ["\xBD"] = "E", ["\xBE"] = "E-", ["\xBF"] = "E",
+ ["\xC0"] = "E-0", ["\xC1"] = "E-1", ["\xC2"] = "E-2", ["\xC3"] = "E-3", ["\xC4"] = "E-4", ["\xC5"] = "E-5", ["\xC6"] = "E-6", ["\xC7"] = "E-7", ["\xC8"] = "E-8", ["\xC9"] = "E-9", ["\xCA"] = "E-.", ["\xCB"] = "E-E", ["\xCC"] = "E-E-", ["\xCD"] = "E-", ["\xCE"] = "E--", ["\xCF"] = "E-",
+ ["\xD0"] = "-0", ["\xD1"] = "-1", ["\xD2"] = "-2", ["\xD3"] = "-3", ["\xD4"] = "-4", ["\xD5"] = "-5", ["\xD6"] = "-6", ["\xD7"] = "-7", ["\xD8"] = "-8", ["\xD9"] = "-9", ["\xDA"] = "-.", ["\xDB"] = "-E", ["\xDC"] = "-E-", ["\xDD"] = "-", ["\xDE"] = "--", ["\xDF"] = "-",
+ }
+
+ local p_last = S("\x0F\x1F\x2F\x3F\x4F\x5F\x6F\x7F\x8F\x9F\xAF\xBF")
+ + R("\xF0\xFF")
+
+ local p_nibbles = P("\30") * Cs(((1-p_last)/remap)^0 * (P(1)/remap)) / function(n)
+ -- 0-9=digit a=. b=E c=E- d=reserved e=- f=finish
+ top = top + 1
+ stack[top] = tonumber(n) or 0
+ end
+
+ local p_byte = C(R("\32\246")) / function(b0)
+ -- -107 .. +107
+ top = top + 1
+ stack[top] = byte(b0) - 139
+ end
+
+ local p_positive = C(R("\247\250")) * C(1) / function(b0,b1)
+ -- +108 .. +1131
+ top = top + 1
+ stack[top] = (byte(b0)-247)*256 + byte(b1) + 108
+ end
+
+ local p_negative = C(R("\251\254")) * C(1) / function(b0,b1)
+ -- -1131 .. -108
+ top = top + 1
+ stack[top] = -(byte(b0)-251)*256 - byte(b1) - 108
+ end
+
+ local p_short = P("\28") * C(1) * C(1) / function(b1,b2)
+ -- -32768 .. +32767 : b1<<8 | b2
+ top = top + 1
+ local n = 0x100 * byte(b1) + byte(b2)
+ if n >= 0x8000 then
+ stack[top] = n - 0xFFFF - 1
+ else
+ stack[top] = n
+ end
+ end
+
+ local p_long = P("\29") * C(1) * C(1) * C(1) * C(1) / function(b1,b2,b3,b4)
+ -- -2^31 .. +2^31-1 : b1<<24 | b2<<16 | b3<<8 | b4
+ top = top + 1
+ local n = 0x1000000 * byte(b1) + 0x10000 * byte(b2) + 0x100 * byte(b3) + byte(b4)
+ if n >= 0x8000000 then
+ stack[top] = n - 0xFFFFFFFF - 1
+ else
+ stack[top] = n
+ end
+ end
+
+ local p_unsupported = P(1) / function(detail)
+ top = 0
+ end
+
+ local p_dictionary = (
+ p_byte
+ + p_positive
+ + p_negative
+ + p_short
+ + p_long
+ + p_nibbles
+ + p_single
+ + p_double
+ + p_unsupported
+ )^1
+
+ parsedictionaries = function(data,dictionaries,what)
+ stack = { }
+ strings = data.strings
+ for i=1,#dictionaries do
+ top = 0
+ result = what == "cff" and {
+ monospaced = false,
+ italicangle = 0,
+ underlineposition = -100,
+ underlinethickness = 50,
+ painttype = 0,
+ charstringtype = 2,
+ fontmatrix = { 0.001, 0, 0, 0.001, 0, 0 },
+ fontbbox = { 0, 0, 0, 0 },
+ strokewidth = 0,
+ charset = 0,
+ encoding = 0,
+ cid = {
+ fontversion = 0,
+ fontrevision = 0,
+ fonttype = 0,
+ count = 8720,
+ }
+ } or {
+ charstringtype = 2,
+ charset = 0,
+ vstore = 0,
+ cid = {
+ -- nothing yet
+ },
+ }
+ lpegmatch(p_dictionary,dictionaries[i])
+ dictionaries[i] = result
+ end
+ --
+ result = { }
+ top = 0
+ stack = { }
+ end
+
+ parseprivates = function(data,dictionaries)
+ stack = { }
+ strings = data.strings
+ for i=1,#dictionaries do
+ local private = dictionaries[i].private
+ if private and private.data then
+ top = 0
+ result = {
+ forcebold = false,
+ languagegroup = 0,
+ expansionfactor = 0.06,
+ initialrandomseed = 0,
+ subroutines = 0,
+ defaultwidthx = 0,
+ nominalwidthx = 0,
+ cid = {
+ -- actually an error
+ },
+ }
+ lpegmatch(p_dictionary,private.data)
+ private.data = result
+ end
+ end
+ result = { }
+ top = 0
+ stack = { }
+ end
+
+ -- All bezier curves have 6 points with successive pairs relative to
+ -- the previous pair. Some can be left out and are then copied or zero
+ -- (optimization).
+ --
+ -- We are not really interested in all the details of a glyph because we
+ -- only need to calculate the boundingbox. So, todo: a quick no result but
+ -- calculate only variant.
+ --
+ -- The conversion is straightforward and the specification os clear once
+ -- you understand that the x and y needs to be updates each step. It's also
+ -- quite easy to test because in mp a shape will look bad when a few variables
+ -- are swapped. But still there might be bugs down here because not all
+ -- variants are seen in a font so far. We are less compact that the ff code
+ -- because there quite some variants are done in one helper with a lot of
+ -- testing for states.
+
+ local x = 0
+ local y = 0
+ local width = false
+ local r = 0
+ local stems = 0
+ local globalbias = 0
+ local localbias = 0
+ local nominalwidth = 0
+ local defaultwidth = 0
+ local charset = false
+ local globals = false
+ local locals = false
+ local depth = 1
+ local xmin = 0
+ local xmax = 0
+ local ymin = 0
+ local ymax = 0
+ local checked = false
+ local keepcurve = false
+ local version = 2
+ local regions = false
+ local nofregions = 0
+ local region = false
+ local factors = false
+ local axis = false
+ local vsindex = 0
+
+ local function showstate(where)
+ report("%w%-10s : [%s] n=%i",depth*2,where,concat(stack," ",1,top),top)
+ end
+
+ local function showvalue(where,value,showstack)
+ if showstack then
+ report("%w%-10s : %s : [%s] n=%i",depth*2,where,tostring(value),concat(stack," ",1,top),top)
+ else
+ report("%w%-10s : %s",depth*2,where,tostring(value))
+ end
+ end
+
+ -- All these indirect calls make this run slower but it's cleaner this way
+ -- and we cache the result. As we moved the boundingbox code inline we gain
+ -- some back. I inlined some of then and a bit speed can be gained by more
+ -- inlining but not that much.
+
+ local function xymoveto()
+ if keepcurve then
+ r = r + 1
+ result[r] = { x, y, "m" }
+ end
+ if checked then
+ if x > xmax then xmax = x elseif x < xmin then xmin = x end
+ if y > ymax then ymax = y elseif y < ymin then ymin = y end
+ else
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ checked = true
+ end
+ end
+
+ local function xmoveto() -- slight speedup
+ if keepcurve then
+ r = r + 1
+ result[r] = { x, y, "m" }
+ end
+ if not checked then
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ checked = true
+ elseif x > xmax then
+ xmax = x
+ elseif x < xmin then
+ xmin = x
+ end
+ end
+
+ local function ymoveto() -- slight speedup
+ if keepcurve then
+ r = r + 1
+ result[r] = { x, y, "m" }
+ end
+ if not checked then
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ checked = true
+ elseif y > ymax then
+ ymax = y
+ elseif y < ymin then
+ ymin = y
+ end
+ end
+
+ local function moveto()
+ if trace_charstrings then
+ showstate("moveto")
+ end
+ top = 0 -- forgotten
+ xymoveto()
+ end
+
+ local function xylineto() -- we could inline, no blend
+ if keepcurve then
+ r = r + 1
+ result[r] = { x, y, "l" }
+ end
+ if checked then
+ if x > xmax then xmax = x elseif x < xmin then xmin = x end
+ if y > ymax then ymax = y elseif y < ymin then ymin = y end
+ else
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ checked = true
+ end
+ end
+
+ local function xlineto() -- slight speedup
+ if keepcurve then
+ r = r + 1
+ result[r] = { x, y, "l" }
+ end
+ if not checked then
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ checked = true
+ elseif x > xmax then
+ xmax = x
+ elseif x < xmin then
+ xmin = x
+ end
+ end
+
+ local function ylineto() -- slight speedup
+ if keepcurve then
+ r = r + 1
+ result[r] = { x, y, "l" }
+ end
+ if not checked then
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ checked = true
+ elseif y > ymax then
+ ymax = y
+ elseif y < ymin then
+ ymin = y
+ end
+ end
+
+ local function xycurveto(x1,y1,x2,y2,x3,y3) -- called local so no blend here
+ if trace_charstrings then
+ showstate("curveto")
+ end
+ if keepcurve then
+ r = r + 1
+ result[r] = { x1, y1, x2, y2, x3, y3, "c" }
+ end
+ if checked then
+ if x1 > xmax then xmax = x1 elseif x1 < xmin then xmin = x1 end
+ if y1 > ymax then ymax = y1 elseif y1 < ymin then ymin = y1 end
+ else
+ xmin = x1
+ ymin = y1
+ xmax = x1
+ ymax = y1
+ checked = true
+ end
+ if x2 > xmax then xmax = x2 elseif x2 < xmin then xmin = x2 end
+ if y2 > ymax then ymax = y2 elseif y2 < ymin then ymin = y2 end
+ if x3 > xmax then xmax = x3 elseif x3 < xmin then xmin = x3 end
+ if y3 > ymax then ymax = y3 elseif y3 < ymin then ymin = y3 end
+ end
+
+ local function rmoveto()
+ if not width then
+ if top > 2 then
+ width = stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width = true
+ end
+ end
+ if trace_charstrings then
+ showstate("rmoveto")
+ end
+ x = x + stack[top-1] -- dx1
+ y = y + stack[top] -- dy1
+ top = 0
+ xymoveto()
+ end
+
+ local function hmoveto()
+ if not width then
+ if top > 1 then
+ width = stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width = true
+ end
+ end
+ if trace_charstrings then
+ showstate("hmoveto")
+ end
+ x = x + stack[top] -- dx1
+ top = 0
+ xmoveto()
+ end
+
+ local function vmoveto()
+ if not width then
+ if top > 1 then
+ width = stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width = true
+ end
+ end
+ if trace_charstrings then
+ showstate("vmoveto")
+ end
+ y = y + stack[top] -- dy1
+ top = 0
+ ymoveto()
+ end
+
+ local function rlineto()
+ if trace_charstrings then
+ showstate("rlineto")
+ end
+ for i=1,top,2 do
+ x = x + stack[i] -- dxa
+ y = y + stack[i+1] -- dya
+ xylineto()
+ end
+ top = 0
+ end
+
+ local function hlineto() -- x (y,x)+ | (x,y)+
+ if trace_charstrings then
+ showstate("hlineto")
+ end
+ if top == 1 then
+ x = x + stack[1]
+ xlineto()
+ else
+ local swap = true
+ for i=1,top do
+ if swap then
+ x = x + stack[i]
+ xlineto()
+ swap = false
+ else
+ y = y + stack[i]
+ ylineto()
+ swap = true
+ end
+ end
+ end
+ top = 0
+ end
+
+ local function vlineto() -- y (x,y)+ | (y,x)+
+ if trace_charstrings then
+ showstate("vlineto")
+ end
+ if top == 1 then
+ y = y + stack[1]
+ ylineto()
+ else
+ local swap = false
+ for i=1,top do
+ if swap then
+ x = x + stack[i]
+ xlineto()
+ swap = false
+ else
+ y = y + stack[i]
+ ylineto()
+ swap = true
+ end
+ end
+ end
+ top = 0
+ end
+
+ local function rrcurveto()
+ if trace_charstrings then
+ showstate("rrcurveto")
+ end
+ for i=1,top,6 do
+ local ax = x + stack[i] -- dxa
+ local ay = y + stack[i+1] -- dya
+ local bx = ax + stack[i+2] -- dxb
+ local by = ay + stack[i+3] -- dyb
+ x = bx + stack[i+4] -- dxc
+ y = by + stack[i+5] -- dyc
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top = 0
+ end
+
+ local function hhcurveto()
+ if trace_charstrings then
+ showstate("hhcurveto")
+ end
+ local s = 1
+ if top % 2 ~= 0 then
+ y = y + stack[1] -- dy1
+ s = 2
+ end
+ for i=s,top,4 do
+ local ax = x + stack[i] -- dxa
+ local ay = y
+ local bx = ax + stack[i+1] -- dxb
+ local by = ay + stack[i+2] -- dyb
+ x = bx + stack[i+3] -- dxc
+ y = by
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top = 0
+ end
+
+ local function vvcurveto()
+ if trace_charstrings then
+ showstate("vvcurveto")
+ end
+ local s = 1
+ local d = 0
+ if top % 2 ~= 0 then
+ d = stack[1] -- dx1
+ s = 2
+ end
+ for i=s,top,4 do
+ local ax = x + d
+ local ay = y + stack[i] -- dya
+ local bx = ax + stack[i+1] -- dxb
+ local by = ay + stack[i+2] -- dyb
+ x = bx
+ y = by + stack[i+3] -- dyc
+ xycurveto(ax,ay,bx,by,x,y)
+ d = 0
+ end
+ top = 0
+ end
+
+ local function xxcurveto(swap)
+ local last = top % 4 ~= 0 and stack[top]
+ if last then
+ top = top - 1
+ end
+ for i=1,top,4 do
+ local ax, ay, bx, by
+ if swap then
+ ax = x + stack[i]
+ ay = y
+ bx = ax + stack[i+1]
+ by = ay + stack[i+2]
+ y = by + stack[i+3]
+ if last and i+3 == top then
+ x = bx + last
+ else
+ x = bx
+ end
+ swap = false
+ else
+ ax = x
+ ay = y + stack[i]
+ bx = ax + stack[i+1]
+ by = ay + stack[i+2]
+ x = bx + stack[i+3]
+ if last and i+3 == top then
+ y = by + last
+ else
+ y = by
+ end
+ swap = true
+ end
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top = 0
+ end
+
+ local function hvcurveto()
+ if trace_charstrings then
+ showstate("hvcurveto")
+ end
+ xxcurveto(true)
+ end
+
+ local function vhcurveto()
+ if trace_charstrings then
+ showstate("vhcurveto")
+ end
+ xxcurveto(false)
+ end
+
+ local function rcurveline()
+ if trace_charstrings then
+ showstate("rcurveline")
+ end
+ for i=1,top-2,6 do
+ local ax = x + stack[i] -- dxa
+ local ay = y + stack[i+1] -- dya
+ local bx = ax + stack[i+2] -- dxb
+ local by = ay + stack[i+3] -- dyb
+ x = bx + stack[i+4] -- dxc
+ y = by + stack[i+5] -- dyc
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ x = x + stack[top-1] -- dxc
+ y = y + stack[top] -- dyc
+ xylineto()
+ top = 0
+ end
+
+ local function rlinecurve()
+ if trace_charstrings then
+ showstate("rlinecurve")
+ end
+ if top > 6 then
+ for i=1,top-6,2 do
+ x = x + stack[i]
+ y = y + stack[i+1]
+ xylineto()
+ end
+ end
+ local ax = x + stack[top-5]
+ local ay = y + stack[top-4]
+ local bx = ax + stack[top-3]
+ local by = ay + stack[top-2]
+ x = bx + stack[top-1]
+ y = by + stack[top]
+ xycurveto(ax,ay,bx,by,x,y)
+ top = 0
+ end
+
+ -- flex is not yet tested! no loop
+
+ local function flex() -- fd not used
+ if trace_charstrings then
+ showstate("flex")
+ end
+ local ax = x + stack[1] -- dx1
+ local ay = y + stack[2] -- dy1
+ local bx = ax + stack[3] -- dx2
+ local by = ay + stack[4] -- dy2
+ local cx = bx + stack[5] -- dx3
+ local cy = by + stack[6] -- dy3
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx = cx + stack[7] -- dx4
+ local dy = cy + stack[8] -- dy4
+ local ex = dx + stack[9] -- dx5
+ local ey = dy + stack[10] -- dy5
+ x = ex + stack[11] -- dx6
+ y = ey + stack[12] -- dy6
+ xycurveto(dx,dy,ex,ey,x,y)
+ top = 0
+ end
+
+ local function hflex()
+ if trace_charstrings then
+ showstate("hflex")
+ end
+ local ax = x + stack[1] -- dx1
+ local ay = y
+ local bx = ax + stack[2] -- dx2
+ local by = ay + stack[3] -- dy2
+ local cx = bx + stack[4] -- dx3
+ local cy = by
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx = cx + stack[5] -- dx4
+ local dy = by
+ local ex = dx + stack[6] -- dx5
+ local ey = y
+ x = ex + stack[7] -- dx6
+ xycurveto(dx,dy,ex,ey,x,y)
+ top = 0
+ end
+
+ local function hflex1()
+ if trace_charstrings then
+ showstate("hflex1")
+ end
+ local ax = x + stack[1] -- dx1
+ local ay = y + stack[2] -- dy1
+ local bx = ax + stack[3] -- dx2
+ local by = ay + stack[4] -- dy2
+ local cx = bx + stack[5] -- dx3
+ local cy = by
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx = cx + stack[6] -- dx4
+ local dy = by
+ local ex = dx + stack[7] -- dx5
+ local ey = dy + stack[8] -- dy5
+ x = ex + stack[9] -- dx6
+ xycurveto(dx,dy,ex,ey,x,y)
+ top = 0
+ end
+
+ local function flex1()
+ if trace_charstrings then
+ showstate("flex1")
+ end
+ local ax = x + stack[1] --dx1
+ local ay = y + stack[2] --dy1
+ local bx = ax + stack[3] --dx2
+ local by = ay + stack[4] --dy2
+ local cx = bx + stack[5] --dx3
+ local cy = by + stack[6] --dy3
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx = cx + stack[7] --dx4
+ local dy = cy + stack[8] --dy4
+ local ex = dx + stack[9] --dx5
+ local ey = dy + stack[10] --dy5
+ if abs(ex - x) > abs(ey - y) then -- spec: abs(dx) > abs(dy)
+ x = ex + stack[11]
+ else
+ y = ey + stack[11]
+ end
+ xycurveto(dx,dy,ex,ey,x,y)
+ top = 0
+ end
+
+ local function getstem()
+ if top == 0 then
+ -- bad
+ elseif top % 2 ~= 0 then
+ if width then
+ remove(stack,1)
+ else
+ width = remove(stack,1)
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ end
+ top = top - 1
+ end
+ if trace_charstrings then
+ showstate("stem")
+ end
+ stems = stems + idiv(top,2)
+ top = 0
+ end
+
+ local function getmask()
+ if top == 0 then
+ -- bad
+ elseif top % 2 ~= 0 then
+ if width then
+ remove(stack,1)
+ else
+ width = remove(stack,1)
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ end
+ top = top - 1
+ end
+ if trace_charstrings then
+ showstate(operator == 19 and "hintmark" or "cntrmask")
+ end
+ stems = stems + idiv(top,2)
+ top = 0
+ if stems == 0 then
+ -- forget about it
+ elseif stems <= 8 then
+ return 1
+ else
+ -- return floor((stems+7)/8)
+ return idiv(stems+7,8)
+ end
+ end
+
+ local function unsupported(t)
+ if trace_charstrings then
+ showstate("unsupported " .. t)
+ end
+ top = 0
+ end
+
+ local function unsupportedsub(t)
+ if trace_charstrings then
+ showstate("unsupported sub " .. t)
+ end
+ top = 0
+ end
+
+ -- type 1 (not used in type 2)
+
+ local function getstem3()
+ if trace_charstrings then
+ showstate("stem3")
+ end
+ top = 0
+ end
+
+ local function divide()
+ if version == 1 then
+ local d = stack[top]
+ top = top - 1
+ stack[top] = stack[top] / d
+ end
+ end
+
+ local function closepath()
+ if version == 1 then
+ if trace_charstrings then
+ showstate("closepath")
+ end
+ end
+ top = 0
+ end
+
+ local function hsbw()
+ if version == 1 then
+ if trace_charstrings then
+ showstate("hsbw")
+ end
+ -- lsb = stack[top-1]
+ width = stack[top]
+ end
+ top = 0
+ end
+
+ local function seac()
+ if version == 1 then
+ if trace_charstrings then
+ showstate("seac")
+ end
+ end
+ top = 0
+ end
+
+ local function sbw()
+ if version == 1 then
+ if trace_charstrings then
+ showstate("sbw")
+ end
+ width = stack[top-1]
+ end
+ top = 0
+ end
+
+ -- these are probably used for special cases i.e. call out to postscript
+
+ local function callothersubr()
+ if version == 1 then
+ -- we don't support this (ok, we could mimick these othersubs)
+ if trace_charstrings then
+ showstate("callothersubr (unsupported)")
+ end
+ end
+ top = 0
+ end
+
+ local function pop()
+ if version == 1 then
+ -- we don't support this
+ if trace_charstrings then
+ showstate("pop (unsupported)")
+ end
+ top = top + 1
+ stack[top] = 0 -- a dummy
+ else
+ top = 0
+ end
+ end
+
+ local function setcurrentpoint()
+ if version == 1 then
+ -- we don't support this
+ if trace_charstrings then
+ showstate("pop (unsupported)")
+ end
+ x = x + stack[top-1]
+ y = y + stack[top]
+ end
+ top = 0
+ end
+
+ -- So far for unsupported postscript. Now some cff2 magic. As I still need
+ -- to wrap my head around the rather complex variable font specification
+ -- with regions and axis, the following approach kind of works but is more
+ -- some trial and error trick. It's still not clear how much of the complex
+ -- truetype description applies to cff.
+
+ local reginit = false
+
+ local function updateregions(n) -- n + 1
+ if regions then
+ local current = regions[n] or regions[1]
+ nofregions = #current
+ if axis and n ~= reginit then
+ factors = { }
+ for i=1,nofregions do
+ local region = current[i]
+ local s = 1
+ for j=1,#axis do
+ local f = axis[j]
+ local r = region[j]
+ local start = r.start
+ local peak = r.peak
+ local stop = r.stop
+ if start > peak or peak > stop then
+ -- * 1
+ elseif start < 0 and stop > 0 and peak ~= 0 then
+ -- * 1
+ elseif peak == 0 then
+ -- * 1
+ elseif f < start or f > stop then
+ -- * 0
+ s = 0
+ break
+ elseif f < peak then
+ s = s * (f - start) / (peak - start)
+ elseif f > peak then
+ s = s * (stop - f) / (stop - peak)
+ else
+ -- * 1
+ end
+ end
+ factors[i] = s
+ end
+ end
+ end
+ reginit = n
+ end
+
+ local function setvsindex()
+ local vsindex = stack[top]
+ if trace_charstrings then
+ showstate(formatters["vsindex %i"](vsindex))
+ end
+ updateregions(vsindex)
+ top = top - 1
+ end
+
+ local function blend()
+ local n = stack[top]
+ top = top - 1
+ if axis then
+ -- x (r1x,r2x,r3x)
+ -- (x,y) (r1x,r2x,r3x) (r1y,r2y,r3y)
+ if trace_charstrings then
+ local t = top - nofregions * n
+ local m = t - n
+ for i=1,n do
+ local k = m + i
+ local d = m + n + (i-1)*nofregions
+ local old = stack[k]
+ local new = old
+ for r=1,nofregions do
+ new = new + stack[d+r] * factors[r]
+ end
+ stack[k] = new
+ showstate(formatters["blend %i of %i: %s -> %s"](i,n,old,new))
+ end
+ top = t
+ elseif n == 1 then
+ top = top - nofregions
+ local v = stack[top]
+ for r=1,nofregions do
+ v = v + stack[top+r] * factors[r]
+ end
+ stack[top] = v
+ else
+ top = top - nofregions * n
+ local d = top
+ local k = top - n
+ for i=1,n do
+ k = k + 1
+ local v = stack[k]
+ for r=1,nofregions do
+ v = v + stack[d+r] * factors[r]
+ end
+ stack[k] = v
+ d = d + nofregions
+ end
+ end
+ else
+ -- error
+ end
+ end
+
+ -- Bah, we cannot use a fast lpeg because a hint has an unknown size and a
+ -- runtime capture cannot handle that well.
+
+ local actions = { [0] =
+ unsupported, -- 0
+ getstem, -- 1 -- hstem
+ unsupported, -- 2
+ getstem, -- 3 -- vstem
+ vmoveto, -- 4
+ rlineto, -- 5
+ hlineto, -- 6
+ vlineto, -- 7
+ rrcurveto, -- 8
+ unsupported, -- 9 -- closepath
+ unsupported, -- 10 -- calllocal,
+ unsupported, -- 11 -- callreturn,
+ unsupported, -- 12 -- elsewhere
+ hsbw, -- 13 -- hsbw (type 1 cff)
+ unsupported, -- 14 -- endchar,
+ setvsindex, -- 15 -- cff2
+ blend, -- 16 -- cff2
+ unsupported, -- 17
+ getstem, -- 18 -- hstemhm
+ getmask, -- 19 -- hintmask
+ getmask, -- 20 -- cntrmask
+ rmoveto, -- 21
+ hmoveto, -- 22
+ getstem, -- 23 -- vstemhm
+ rcurveline, -- 24
+ rlinecurve, -- 25
+ vvcurveto, -- 26
+ hhcurveto, -- 27
+ unsupported, -- 28 -- elsewhere
+ unsupported, -- 29 -- elsewhere
+ vhcurveto, -- 30
+ hvcurveto, -- 31
+ }
+
+ local subactions = {
+ -- cff 1
+ [000] = dotsection,
+ [001] = getstem3,
+ [002] = getstem3,
+ [006] = seac,
+ [007] = sbw,
+ [012] = divide,
+ [016] = callothersubr,
+ [017] = pop,
+ [033] = setcurrentpoint,
+ -- cff 2
+ [034] = hflex,
+ [035] = flex,
+ [036] = hflex1,
+ [037] = flex1,
+ }
+
+ local chars = setmetatableindex(function (t,k)
+ local v = char(k)
+ t[k] = v
+ return v
+ end)
+
+ local c_endchar = chars[14]
+
+ -- todo: round in blend
+
+ local encode = { }
+
+ -- this eventually can become a helper
+
+ setmetatableindex(encode,function(t,i)
+ for i=-2048,-1130 do
+ t[i] = char(28,band(rshift(i,8),0xFF),band(i,0xFF))
+ end
+ for i=-1131,-108 do
+ local v = 0xFB00 - i - 108
+ t[i] = char(band(rshift(v,8),0xFF),band(v,0xFF))
+ end
+ for i=-107,107 do
+ t[i] = chars[i + 139]
+ end
+ for i=108,1131 do
+ local v = 0xF700 + i - 108
+-- t[i] = char(band(rshift(v,8),0xFF),band(v,0xFF))
+ t[i] = char(extract(v,8,8),extract(v,0,8))
+ end
+ for i=1132,2048 do
+ t[i] = char(28,band(rshift(i,8),0xFF),band(i,0xFF))
+ end
+ setmetatableindex(encode,function(t,k)
+ -- 16.16-bit signed fixed value
+ local r = round(k)
+ local v = rawget(t,r)
+ if v then
+ return v
+ end
+ local v1 = floor(k)
+ local v2 = floor((k - v1) * 0x10000)
+ return char(255,extract(v1,8,8),extract(v1,0,8),extract(v2,8,8),extract(v2,0,8))
+ end)
+ return t[i]
+ end)
+
+ readers.cffencoder = encode
+
+ local function p_setvsindex()
+ local vsindex = stack[top]
+ updateregions(vsindex)
+ top = top - 1
+ end
+
+ local function p_blend()
+ -- leaves n values on stack
+ local n = stack[top]
+ top = top - 1
+ if not axis then
+ -- fatal error
+ elseif n == 1 then
+ top = top - nofregions
+ local v = stack[top]
+ for r=1,nofregions do
+ v = v + stack[top+r] * factors[r]
+ end
+ stack[top] = round(v)
+ else
+ top = top - nofregions * n
+ local d = top
+ local k = top - n
+ for i=1,n do
+ k = k + 1
+ local v = stack[k]
+ for r=1,nofregions do
+ v = v + stack[d+r] * factors[r]
+ end
+ stack[k] = round(v)
+ d = d + nofregions
+ end
+ end
+ end
+
+ local function p_getstem()
+ local n = 0
+ if top % 2 ~= 0 then
+ n = 1
+ end
+ if top > n then
+ stems = stems + idiv(top-n,2)
+ end
+ end
+
+ local function p_getmask()
+ local n = 0
+ if top % 2 ~= 0 then
+ n = 1
+ end
+ if top > n then
+ stems = stems + idiv(top-n,2)
+ end
+ if stems == 0 then
+ return 0
+ elseif stems <= 8 then
+ return 1
+ else
+ return idiv(stems+7,8)
+ end
+ end
+
+ -- end of experiment
+
+ local process
+
+ local function call(scope,list,bias) -- ,process)
+ depth = depth + 1
+ if top == 0 then
+ showstate(formatters["unknown %s call %s"](scope,"?"))
+ top = 0
+ else
+ local index = stack[top] + bias
+ top = top - 1
+ if trace_charstrings then
+ showvalue(scope,index,true)
+ end
+ local tab = list[index]
+ if tab then
+ process(tab)
+ else
+ showstate(formatters["unknown %s call %s"](scope,index))
+ top = 0
+ end
+ end
+ depth = depth - 1
+ end
+
+ -- precompiling and reuse is much slower than redoing the calls
+
+ local justpass = false
+
+ -- local function decode(str)
+ -- local a, b, c, d, e = byte(str,1,5)
+ -- if a == 28 then
+ -- if c then
+ -- local n = 0x100 * b + c
+ -- if n >= 0x8000 then
+ -- return n - 0x10000
+ -- else
+ -- return n
+ -- end
+ -- end
+ -- elseif a < 32 then
+ -- return false
+ -- elseif a <= 246 then
+ -- return a - 139
+ -- elseif a <= 250 then
+ -- if b then
+ -- return a*256 - 63124 + b
+ -- end
+ -- elseif a <= 254 then
+ -- if b then
+ -- return -a*256 + 64148 - b
+ -- end
+ -- else
+ -- if e then
+ -- local n = 0x100 * b + c
+ -- if n >= 0x8000 then
+ -- return n - 0x10000 + (0x100 * d + e)/0xFFFF
+ -- else
+ -- return n + (0x100 * d + e)/0xFFFF
+ -- end
+ -- end
+ -- end
+ -- return false
+ -- end
+
+ process = function(tab)
+ local i = 1
+ local n = #tab
+ while i <= n do
+ local t = tab[i]
+ if t >= 32 then
+ top = top + 1
+ if t <= 246 then
+ -- -107 .. +107
+ stack[top] = t - 139
+ i = i + 1
+ elseif t <= 250 then
+ -- +108 .. +1131
+ -- stack[top] = (t-247)*256 + tab[i+1] + 108
+ -- stack[top] = t*256 - 247*256 + tab[i+1] + 108
+ stack[top] = t*256 - 63124 + tab[i+1]
+ i = i + 2
+ elseif t <= 254 then
+ -- -1131 .. -108
+ -- stack[top] = -(t-251)*256 - tab[i+1] - 108
+ -- stack[top] = -t*256 + 251*256 - tab[i+1] - 108
+ stack[top] = -t*256 + 64148 - tab[i+1]
+ i = i + 2
+ else
+ -- a 16.16 float
+ local n = 0x100 * tab[i+1] + tab[i+2]
+ if n >= 0x8000 then
+ stack[top] = n - 0x10000 + (0x100 * tab[i+3] + tab[i+4])/0xFFFF
+ else
+ stack[top] = n + (0x100 * tab[i+3] + tab[i+4])/0xFFFF
+ end
+ i = i + 5
+ end
+ elseif t == 28 then
+ -- -32768 .. +32767 : b1<<8 | b2
+ top = top + 1
+ local n = 0x100 * tab[i+1] + tab[i+2]
+ if n >= 0x8000 then
+ -- stack[top] = n - 0xFFFF - 1
+ stack[top] = n - 0x10000
+ else
+ stack[top] = n
+ end
+ i = i + 3
+ elseif t == 11 then -- not in cff2
+ if trace_charstrings then
+ showstate("return")
+ end
+ return
+ elseif t == 10 then
+ call("local",locals,localbias) -- ,process)
+ i = i + 1
+ elseif t == 14 then -- not in cff2
+ if width then
+ -- okay
+ elseif top > 0 then
+ width = stack[1]
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ else
+ width = true
+ end
+ if trace_charstrings then
+ showstate("endchar")
+ end
+ return
+ elseif t == 29 then
+ call("global",globals,globalbias) -- ,process)
+ i = i + 1
+ elseif t == 12 then
+ i = i + 1
+ local t = tab[i]
+ if justpass then
+ if t >= 34 and t <= 37 then -- flexes
+ for i=1,top do
+ r = r + 1 ; result[r] = encode[stack[i]]
+ end
+ r = r + 1 ; result[r] = chars[12]
+ r = r + 1 ; result[r] = chars[t]
+ top = 0
+ else
+ local a = subactions[t]
+ if a then
+ a(t)
+ else
+ top = 0
+ end
+ end
+ else
+ local a = subactions[t]
+ if a then
+ a(t)
+ else
+ if trace_charstrings then
+ showvalue("<subaction>",t)
+ end
+ top = 0
+ end
+ end
+ i = i + 1
+ elseif justpass then
+ -- todo: local a = passactions
+ if t == 15 then
+ p_setvsindex()
+ i = i + 1
+ elseif t == 16 then
+ local s = p_blend() or 0
+ i = i + s + 1
+ -- cff 1: (when cff2 strip them)
+ elseif t == 1 or t == 3 or t == 18 or operation == 23 then
+ p_getstem() -- at the start
+if true then
+ if top > 0 then
+ for i=1,top do
+ r = r + 1 ; result[r] = encode[stack[i]]
+ end
+ top = 0
+ end
+ r = r + 1 ; result[r] = chars[t]
+else
+ top = 0
+end
+ i = i + 1
+ -- cff 1: (when cff2 strip them)
+ elseif t == 19 or t == 20 then
+ local s = p_getmask() or 0 -- after the stems
+if true then
+ if top > 0 then
+ for i=1,top do
+ r = r + 1 ; result[r] = encode[stack[i]]
+ end
+ top = 0
+ end
+ r = r + 1 ; result[r] = chars[t]
+ for j=1,s do
+ i = i + 1
+ r = r + 1 ; result[r] = chars[tab[i]]
+ end
+else
+ i = i + s
+ top = 0
+end
+ i = i + 1
+ -- cff 1: closepath
+ elseif t == 9 then
+ top = 0
+ i = i + 1
+ elseif t == 13 then
+ local s = hsbw() or 0
+ i = i + s + 1
+ else
+ if top > 0 then
+ for i=1,top do
+ r = r + 1 ; result[r] = encode[stack[i]]
+ end
+ top = 0
+ end
+ r = r + 1 ; result[r] = chars[t]
+ i = i + 1
+ end
+ else
+ local a = actions[t]
+ if a then
+ local s = a(t)
+ if s then
+ i = i + s + 1
+ else
+ i = i + 1
+ end
+ else
+ if trace_charstrings then
+ showvalue("<action>",t)
+ end
+ top = 0
+ i = i + 1
+ end
+ end
+ end
+ end
+
+ -- local function calculatebounds(segments,x,y)
+ -- local nofsegments = #segments
+ -- if nofsegments == 0 then
+ -- return { x, y, x, y }
+ -- else
+ -- local xmin = 10000
+ -- local xmax = -10000
+ -- local ymin = 10000
+ -- local ymax = -10000
+ -- if x < xmin then xmin = x end
+ -- if x > xmax then xmax = x end
+ -- if y < ymin then ymin = y end
+ -- if y > ymax then ymax = y end
+ -- -- we now have a reasonable start so we could
+ -- -- simplify the next checks
+ -- for i=1,nofsegments do
+ -- local s = segments[i]
+ -- local x = s[1]
+ -- local y = s[2]
+ -- if x < xmin then xmin = x end
+ -- if x > xmax then xmax = x end
+ -- if y < ymin then ymin = y end
+ -- if y > ymax then ymax = y end
+ -- if s[#s] == "c" then -- "curveto"
+ -- local x = s[3]
+ -- local y = s[4]
+ -- if x < xmin then xmin = x elseif x > xmax then xmax = x end
+ -- if y < ymin then ymin = y elseif y > ymax then ymax = y end
+ -- local x = s[5]
+ -- local y = s[6]
+ -- if x < xmin then xmin = x elseif x > xmax then xmax = x end
+ -- if y < ymin then ymin = y elseif y > ymax then ymax = y end
+ -- end
+ -- end
+ -- return { round(xmin), round(ymin), round(xmax), round(ymax) } -- doesn't make ceil more sense
+ -- end
+ -- end
+
+ local function setbias(globals,locals,nobias)
+ if nobias then
+ return 0, 0
+ else
+ local g = #globals
+ local l = #locals
+ return
+ ((g < 1240 and 107) or (g < 33900 and 1131) or 32768) + 1,
+ ((l < 1240 and 107) or (l < 33900 and 1131) or 32768) + 1
+ end
+ end
+
+ local function processshape(tab,index)
+
+ if not tab then
+ glyphs[index] = {
+ boundingbox = { 0, 0, 0, 0 },
+ width = 0,
+ name = charset and charset[index] or nil,
+ }
+ return
+ end
+
+ tab = bytetable(tab)
+
+ x = 0
+ y = 0
+ width = false
+ r = 0
+ top = 0
+ stems = 0
+ result = { } -- we could reuse it when only boundingbox calculations are needed
+
+ xmin = 0
+ xmax = 0
+ ymin = 0
+ ymax = 0
+ checked = false
+ if trace_charstrings then
+ report("glyph: %i",index)
+ report("data : % t",tab)
+ end
+
+ if regions then
+ updateregions(vsindex)
+ end
+
+ process(tab)
+
+ local boundingbox = {
+ round(xmin),
+ round(ymin),
+ round(xmax),
+ round(ymax),
+ }
+
+ if width == true or width == false then
+ width = defaultwidth
+ else
+ width = nominalwidth + width
+ end
+
+ local glyph = glyphs[index] -- can be autodefined in otr
+ if justpass then
+ r = r + 1
+ result[r] = c_endchar
+ local stream = concat(result)
+ -- if trace_charstrings then
+ -- report("vdata: %s",stream)
+ -- end
+ if glyph then
+ glyph.stream = stream
+ else
+ glyphs[index] = { stream = stream }
+ end
+ elseif glyph then
+ glyph.segments = keepcurve ~= false and result or nil
+ glyph.boundingbox = boundingbox
+ if not glyph.width then
+ glyph.width = width
+ end
+ if charset and not glyph.name then
+ glyph.name = charset[index]
+ end
+ -- glyph.sidebearing = 0 -- todo
+ elseif keepcurve then
+ glyphs[index] = {
+ segments = result,
+ boundingbox = boundingbox,
+ width = width,
+ name = charset and charset[index] or nil,
+ -- sidebearing = 0,
+ }
+ else
+ glyphs[index] = {
+ boundingbox = boundingbox,
+ width = width,
+ name = charset and charset[index] or nil,
+ }
+ end
+
+ if trace_charstrings then
+ report("width : %s",tostring(width))
+ report("boundingbox: % t",boundingbox)
+ end
+
+ end
+
+ startparsing = function(fontdata,data,streams)
+ reginit = false
+ axis = false
+ regions = data.regions
+ justpass = streams == true
+ if regions then
+ regions = { regions } -- needs checking
+ axis = data.factors or false
+ end
+ end
+
+ stopparsing = function(fontdata,data)
+ stack = { }
+ glyphs = false
+ result = { }
+ top = 0
+ locals = false
+ globals = false
+ strings = false
+ end
+
+ local function setwidths(private)
+ if not private then
+ return 0, 0
+ end
+ local privatedata = private.data
+ if not privatedata then
+ return 0, 0
+ end
+ return privatedata.nominalwidthx or 0, privatedata.defaultwidthx or 0
+ end
+
+ parsecharstrings = function(fontdata,data,glphs,doshapes,tversion,streams,nobias)
+
+ local dictionary = data.dictionaries[1]
+ local charstrings = dictionary.charstrings
+
+ keepcurve = doshapes
+ version = tversion
+ strings = data.strings
+ globals = data.routines or { }
+ locals = dictionary.subroutines or { }
+ charset = dictionary.charset
+ vsindex = dictionary.vsindex or 0
+ glyphs = glphs or { }
+
+ globalbias, localbias = setbias(globals,locals,nobias)
+ nominalwidth, defaultwidth = setwidths(dictionary.private)
+
+ if charstrings then
+ startparsing(fontdata,data,streams)
+ for index=1,#charstrings do
+ processshape(charstrings[index],index-1)
+-- charstrings[index] = nil -- free memory (what if used more often?)
+ end
+ stopparsing(fontdata,data)
+ else
+ report("no charstrings")
+ end
+ return glyphs
+ end
+
+ parsecharstring = function(fontdata,data,dictionary,tab,glphs,index,doshapes,tversion,streams)
+
+ keepcurve = doshapes
+ version = tversion
+ strings = data.strings
+ globals = data.routines or { }
+ locals = dictionary.subroutines or { }
+ charset = false
+ vsindex = dictionary.vsindex or 0
+ glyphs = glphs or { }
+
+ justpass = streams == true
+
+ globalbias, localbias = setbias(globals,locals,nobias)
+ nominalwidth, defaultwidth = setwidths(dictionary.private)
+
+ processshape(tab,index-1)
+
+ -- return glyphs[index]
+ end
+
+end
+
+local function readglobals(f,data)
+ local routines = readlengths(f)
+ for i=1,#routines do
+ routines[i] = readbytetable(f,routines[i])
+ end
+ data.routines = routines
+end
+
+local function readencodings(f,data)
+ data.encodings = { }
+end
+
+local function readcharsets(f,data,dictionary)
+ local header = data.header
+ local strings = data.strings
+ local nofglyphs = data.nofglyphs
+ local charsetoffset = dictionary.charset
+ if charsetoffset and charsetoffset ~= 0 then
+ setposition(f,header.offset+charsetoffset)
+ local format = readbyte(f)
+ local charset = { [0] = ".notdef" }
+ dictionary.charset = charset
+ if format == 0 then
+ for i=1,nofglyphs do
+ charset[i] = strings[readushort(f)]
+ end
+ elseif format == 1 or format == 2 then
+ local readcount = format == 1 and readbyte or readushort
+ local i = 1
+ while i <= nofglyphs do
+ local sid = readushort(f)
+ local n = readcount(f)
+ for s=sid,sid+n do
+ charset[i] = strings[s]
+ i = i + 1
+ if i > nofglyphs then
+ break
+ end
+ end
+ end
+ else
+ report("cff parser: unsupported charset format %a",format)
+ end
+ else
+ dictionary.nocharset = true
+ dictionary.charset = nil
+ end
+end
+
+local function readprivates(f,data)
+ local header = data.header
+ local dictionaries = data.dictionaries
+ local private = dictionaries[1].private
+ if private then
+ setposition(f,header.offset+private.offset)
+ private.data = readstring(f,private.size)
+ end
+end
+
+local function readlocals(f,data,dictionary)
+ local header = data.header
+ local private = dictionary.private
+ if private then
+ local subroutineoffset = private.data.subroutines
+ if subroutineoffset ~= 0 then
+ setposition(f,header.offset+private.offset+subroutineoffset)
+ local subroutines = readlengths(f)
+ for i=1,#subroutines do
+ subroutines[i] = readbytetable(f,subroutines[i])
+ end
+ dictionary.subroutines = subroutines
+ private.data.subroutines = nil
+ else
+ dictionary.subroutines = { }
+ end
+ else
+ dictionary.subroutines = { }
+ end
+end
+
+-- These charstrings are little programs and described in: Technical Note #5177. A truetype
+-- font has only one dictionary.
+
+local function readcharstrings(f,data,what)
+ local header = data.header
+ local dictionaries = data.dictionaries
+ local dictionary = dictionaries[1]
+ local stringtype = dictionary.charstringtype
+ local offset = dictionary.charstrings
+ if type(offset) ~= "number" then
+ -- weird
+ elseif stringtype == 2 then
+ setposition(f,header.offset+offset)
+ -- could be a metatable .. delayed loading
+ local charstrings = readlengths(f,what=="cff2")
+ local nofglyphs = #charstrings
+ for i=1,nofglyphs do
+ charstrings[i] = readstring(f,charstrings[i])
+ end
+ data.nofglyphs = nofglyphs
+ dictionary.charstrings = charstrings
+ else
+ report("unsupported charstr type %i",stringtype)
+ data.nofglyphs = 0
+ dictionary.charstrings = { }
+ end
+end
+
+-- cid (maybe do this stepwise so less mem) -- share with above
+
+local function readcidprivates(f,data)
+ local header = data.header
+ local dictionaries = data.dictionaries[1].cid.dictionaries
+ for i=1,#dictionaries do
+ local dictionary = dictionaries[i]
+ local private = dictionary.private
+ if private then
+ setposition(f,header.offset+private.offset)
+ private.data = readstring(f,private.size)
+ end
+ end
+ parseprivates(data,dictionaries)
+end
+
+readers.parsecharstrings = parsecharstrings -- used in font-onr.lua (type 1)
+
+local function readnoselect(f,fontdata,data,glyphs,doshapes,version,streams)
+ local dictionaries = data.dictionaries
+ local dictionary = dictionaries[1]
+ readglobals(f,data)
+ readcharstrings(f,data,version)
+ if version == "cff2" then
+ dictionary.charset = nil
+ else
+ readencodings(f,data)
+ readcharsets(f,data,dictionary)
+ end
+ readprivates(f,data)
+ parseprivates(data,data.dictionaries)
+ readlocals(f,data,dictionary)
+ startparsing(fontdata,data,streams)
+ parsecharstrings(fontdata,data,glyphs,doshapes,version,streams)
+ stopparsing(fontdata,data)
+end
+
+local function readfdselect(f,fontdata,data,glyphs,doshapes,version,streams)
+ local header = data.header
+ local dictionaries = data.dictionaries
+ local dictionary = dictionaries[1]
+ local cid = dictionary.cid
+ local cidselect = cid and cid.fdselect
+ readglobals(f,data)
+ readcharstrings(f,data,version)
+ if version ~= "cff2" then
+ readencodings(f,data)
+ end
+ local charstrings = dictionary.charstrings
+ local fdindex = { }
+ local nofglyphs = data.nofglyphs
+ local maxindex = -1
+ setposition(f,header.offset+cidselect)
+ local format = readbyte(f)
+ if format == 1 then
+ for i=0,nofglyphs do -- notdef included (needs checking)
+ local index = readbyte(f)
+ fdindex[i] = index
+ if index > maxindex then
+ maxindex = index
+ end
+ end
+ elseif format == 3 then
+ local nofranges = readushort(f)
+ local first = readushort(f)
+ local index = readbyte(f)
+ while true do
+ local last = readushort(f)
+ if index > maxindex then
+ maxindex = index
+ end
+ for i=first,last do
+ fdindex[i] = index
+ end
+ if last >= nofglyphs then
+ break
+ else
+ first = last + 1
+ index = readbyte(f)
+ end
+ end
+ else
+ -- unsupported format
+ end
+ -- hm, always
+ if maxindex >= 0 then
+ local cidarray = cid.fdarray
+ if cidarray then
+ setposition(f,header.offset+cidarray)
+ local dictionaries = readlengths(f)
+ for i=1,#dictionaries do
+ dictionaries[i] = readstring(f,dictionaries[i])
+ end
+ parsedictionaries(data,dictionaries)
+ cid.dictionaries = dictionaries
+ readcidprivates(f,data)
+ for i=1,#dictionaries do
+ readlocals(f,data,dictionaries[i])
+ end
+ startparsing(fontdata,data,streams)
+ for i=1,#charstrings do
+ parsecharstring(fontdata,data,dictionaries[fdindex[i]+1],charstrings[i],glyphs,i,doshapes,version,streams)
+-- charstrings[i] = nil
+ end
+ stopparsing(fontdata,data)
+ else
+ report("no cid array")
+ end
+ end
+end
+
+local gotodatatable = readers.helpers.gotodatatable
+
+local function cleanup(data,dictionaries)
+ -- for i=1,#dictionaries do
+ -- local d = dictionaries[i]
+ -- d.subroutines = nil
+ -- end
+ -- data.strings = nil
+ -- if data then
+ -- data.charstrings = nil
+ -- data.routines = nil
+ -- end
+end
+
+function readers.cff(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"cff",specification.details or specification.glyphs)
+ if tableoffset then
+ local header = readheader(f)
+ if header.major ~= 1 then
+ report("only version %s is supported for table %a",1,"cff")
+ return
+ end
+ local glyphs = fontdata.glyphs
+ local names = readfontnames(f)
+ local dictionaries = readtopdictionaries(f)
+ local strings = readstrings(f)
+ local data = {
+ header = header,
+ names = names,
+ dictionaries = dictionaries,
+ strings = strings,
+ nofglyphs = fontdata.nofglyphs,
+ }
+ --
+ parsedictionaries(data,dictionaries,"cff")
+ --
+ local dic = dictionaries[1]
+ local cid = dic.cid
+ --
+ local cffinfo = {
+ familyname = dic.familyname,
+ fullname = dic.fullname,
+ boundingbox = dic.boundingbox,
+ weight = dic.weight,
+ italicangle = dic.italicangle,
+ underlineposition = dic.underlineposition,
+ underlinethickness = dic.underlinethickness,
+ defaultwidth = dic.defaultwidthx,
+ nominalwidth = dic.nominalwidthx,
+ monospaced = dic.monospaced,
+ }
+ fontdata.cidinfo = cid and {
+ registry = cid.registry,
+ ordering = cid.ordering,
+ supplement = cid.supplement,
+ }
+ fontdata.cffinfo = cffinfo
+ --
+ local all = specification.shapes or specification.streams or false
+ if specification.glyphs or all then
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,all,"cff",specification.streams)
+ else
+ readnoselect(f,fontdata,data,glyphs,all,"cff",specification.streams)
+ end
+ end
+ local private = dic.private
+ if private then
+ local data = private.data
+ if type(data) == "table" then
+ cffinfo.defaultwidth = data.defaultwidthx or cffinfo.defaultwidth
+ cffinfo.nominalwidth = data.nominalwidthx or cffinfo.nominalwidth
+ cffinfo.bluevalues = data.bluevalues
+ cffinfo.otherblues = data.otherblues
+ cffinfo.familyblues = data.familyblues
+ cffinfo.familyotherblues = data.familyotherblues
+ cffinfo.bluescale = data.bluescale
+ cffinfo.blueshift = data.blueshift
+ cffinfo.bluefuzz = data.bluefuzz
+ cffinfo.stdhw = data.stdhw
+ cffinfo.stdvw = data.stdvw
+ end
+ end
+ cleanup(data,dictionaries)
+ end
+end
+
+function readers.cff2(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"cff2",specification.glyphs)
+ if tableoffset then
+ local header = readheader(f)
+ if header.major ~= 2 then
+ report("only version %s is supported for table %a",2,"cff2")
+ return
+ end
+ local glyphs = fontdata.glyphs
+ local dictionaries = { readstring(f,header.dsize) }
+ local data = {
+ header = header,
+ dictionaries = dictionaries,
+ nofglyphs = fontdata.nofglyphs,
+ }
+ --
+ parsedictionaries(data,dictionaries,"cff2")
+ --
+ local offset = dictionaries[1].vstore
+ if offset > 0 then
+ local storeoffset = dictionaries[1].vstore + data.header.offset + 2 -- cff has a preceding size field
+ local regions, deltas = readers.helpers.readvariationdata(f,storeoffset,factors)
+ --
+ data.regions = regions
+ data.deltas = deltas
+ else
+ data.regions = { }
+ data.deltas = { }
+ end
+ data.factors = specification.factors
+ --
+ local cid = data.dictionaries[1].cid
+ local all = specification.shapes or specification.streams or false
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,all,"cff2",specification.streams)
+ else
+ readnoselect(f,fontdata,data,glyphs,all,"cff2",specification.streams)
+ end
+ cleanup(data,dictionaries)
+ end
+end
+
+-- temporary helper needed for checking backend patches
+
+function readers.cffcheck(filename)
+ local f = io.open(filename,"rb")
+ if f then
+ local fontdata = {
+ glyphs = { },
+ }
+ local header = readheader(f)
+ if header.major ~= 1 then
+ report("only version %s is supported for table %a",1,"cff")
+ return
+ end
+ local names = readfontnames(f)
+ local dictionaries = readtopdictionaries(f)
+ local strings = readstrings(f)
+ local glyphs = { }
+ local data = {
+ header = header,
+ names = names,
+ dictionaries = dictionaries,
+ strings = strings,
+ glyphs = glyphs,
+ nofglyphs = 0,
+ }
+ --
+ parsedictionaries(data,dictionaries,"cff")
+ --
+ local cid = data.dictionaries[1].cid
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,false)
+ else
+ readnoselect(f,fontdata,data,glyphs,false)
+ end
+ return data
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-cid.lua b/macros/luatex/generic/luaotfload/fontloader-font-cid.lua
new file mode 100644
index 0000000000..781bc9fec9
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-cid.lua
@@ -0,0 +1,177 @@
+if not modules then modules = { } end modules ['font-cid'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local format, match, lower = string.format, string.match, string.lower
+local tonumber = tonumber
+local P, S, R, C, V, lpegmatch = lpeg.P, lpeg.S, lpeg.R, lpeg.C, lpeg.V, lpeg.match
+
+local fonts, logs, trackers = fonts, logs, trackers
+
+local trace_loading = false trackers.register("otf.loading", function(v) trace_loading = v end)
+
+local report_otf = logs.reporter("fonts","otf loading")
+
+local cid = { }
+fonts.cid = cid
+
+local cidmap = { }
+local cidmax = 10
+
+-- original string parser: 0.109, lpeg parser: 0.036 seconds for Adobe-CNS1-4.cidmap
+--
+-- 18964 18964 (leader)
+-- 0 /.notdef
+-- 1..95 0020
+-- 99 3000
+
+local number = C(R("09","af","AF")^1)
+local space = S(" \n\r\t")
+local spaces = space^0
+local period = P(".")
+local periods = period * period
+local name = P("/") * C((1-space)^1)
+
+local unicodes, names = { }, { } -- we could use Carg now
+
+local function do_one(a,b)
+ unicodes[tonumber(a)] = tonumber(b,16)
+end
+
+local function do_range(a,b,c)
+ c = tonumber(c,16)
+ for i=tonumber(a),tonumber(b) do
+ unicodes[i] = c
+ c = c + 1
+ end
+end
+
+local function do_name(a,b)
+ names[tonumber(a)] = b
+end
+
+local grammar = P { "start",
+ start = number * spaces * number * V("series"),
+ series = (spaces * (V("one") + V("range") + V("named")))^1,
+ one = (number * spaces * number) / do_one,
+ range = (number * periods * number * spaces * number) / do_range,
+ named = (number * spaces * name) / do_name
+}
+
+local function loadcidfile(filename)
+ local data = io.loaddata(filename)
+ if data then
+ unicodes, names = { }, { }
+ lpegmatch(grammar,data)
+ local supplement, registry, ordering = match(filename,"^(.-)%-(.-)%-()%.(.-)$")
+ return {
+ supplement = supplement,
+ registry = registry,
+ ordering = ordering,
+ filename = filename,
+ unicodes = unicodes,
+ names = names,
+ }
+ end
+end
+
+cid.loadfile = loadcidfile -- we use the frozen variant
+local template = "%s-%s-%s.cidmap"
+
+local function locate(registry,ordering,supplement)
+ local filename = format(template,registry,ordering,supplement)
+ local hashname = lower(filename)
+ local found = cidmap[hashname]
+ if not found then
+ if trace_loading then
+ report_otf("checking cidmap, registry %a, ordering %a, supplement %a, filename %a",registry,ordering,supplement,filename)
+ end
+ local fullname = resolvers.findfile(filename,'cid') or ""
+ if fullname ~= "" then
+ found = loadcidfile(fullname)
+ if found then
+ if trace_loading then
+ report_otf("using cidmap file %a",filename)
+ end
+ cidmap[hashname] = found
+ found.usedname = file.basename(filename)
+ end
+ end
+ end
+ return found
+end
+
+-- cf Arthur R. we can safely scan upwards since cids are downward compatible
+
+function cid.getmap(specification)
+ if not specification then
+ report_otf("invalid cidinfo specification, table expected")
+ return
+ end
+ local registry = specification.registry
+ local ordering = specification.ordering
+ local supplement = specification.supplement
+ local filename = format(registry,ordering,supplement)
+ local lowername = lower(filename)
+ local found = cidmap[lowername]
+ if found then
+ return found
+ end
+ if ordering == "Identity" then
+ local found = {
+ supplement = supplement,
+ registry = registry,
+ ordering = ordering,
+ filename = filename,
+ unicodes = { },
+ names = { },
+ }
+ cidmap[lowername] = found
+ return found
+ end
+ -- check for already loaded file
+ if trace_loading then
+ report_otf("cidmap needed, registry %a, ordering %a, supplement %a",registry,ordering,supplement)
+ end
+ found = locate(registry,ordering,supplement)
+ if not found then
+ local supnum = tonumber(supplement)
+ local cidnum = nil
+ -- next highest (alternatively we could start high)
+ if supnum < cidmax then
+ for s=supnum+1,cidmax do
+ local c = locate(registry,ordering,s)
+ if c then
+ found, cidnum = c, s
+ break
+ end
+ end
+ end
+ -- next lowest (least worse fit)
+ if not found and supnum > 0 then
+ for s=supnum-1,0,-1 do
+ local c = locate(registry,ordering,s)
+ if c then
+ found, cidnum = c, s
+ break
+ end
+ end
+ end
+ -- prevent further lookups -- somewhat tricky
+ registry = lower(registry)
+ ordering = lower(ordering)
+ if found and cidnum > 0 then
+ for s=0,cidnum-1 do
+ local filename = format(template,registry,ordering,s)
+ if not cidmap[filename] then
+ cidmap[filename] = found
+ end
+ end
+ end
+ end
+ return found
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-con.lua b/macros/luatex/generic/luaotfload/fontloader-font-con.lua
new file mode 100644
index 0000000000..9c1e825fa2
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-con.lua
@@ -0,0 +1,1711 @@
+if not modules then modules = { } end modules ['font-con'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- some names of table entries will be changed (no _)
+
+local next, tostring, tonumber, rawget = next, tostring, tonumber, rawget
+local format, match, lower, gsub, find = string.format, string.match, string.lower, string.gsub, string.find
+local sort, insert, concat = table.sort, table.insert, table.concat
+local sortedkeys, sortedhash, serialize, fastcopy = table.sortedkeys, table.sortedhash, table.serialize, table.fastcopy
+local derivetable = table.derive
+local ioflush = io.flush
+local round = math.round
+local setmetatable, getmetatable, rawget, rawset = setmetatable, getmetatable, rawget, rawset
+
+local trace_defining = false trackers.register("fonts.defining", function(v) trace_defining = v end)
+local trace_scaling = false trackers.register("fonts.scaling", function(v) trace_scaling = v end)
+
+local report_defining = logs.reporter("fonts","defining")
+
+-- watch out: no negative depths and negative eights permitted in regular fonts
+
+--[[ldx--
+<p>Here we only implement a few helper functions.</p>
+--ldx]]--
+
+local fonts = fonts
+local constructors = fonts.constructors or { }
+fonts.constructors = constructors
+local handlers = fonts.handlers or { } -- can have preloaded tables
+fonts.handlers = handlers
+
+local allocate = utilities.storage.allocate
+local setmetatableindex = table.setmetatableindex
+
+-- will be directives
+
+constructors.dontembed = allocate()
+constructors.autocleanup = true
+constructors.namemode = "fullpath" -- will be a function
+
+constructors.version = 1.01
+constructors.cache = containers.define("fonts", "constructors", constructors.version, false)
+
+constructors.privateoffset = fonts.privateoffsets.textbase or 0xF0000
+constructors.cacheintex = true -- so we see the original table in fonts.font
+
+constructors.addtounicode = true
+
+-- This might become an interface:
+
+local designsizes = allocate()
+constructors.designsizes = designsizes
+local loadedfonts = allocate()
+constructors.loadedfonts = loadedfonts
+
+--[[ldx--
+<p>We need to normalize the scale factor (in scaled points). This has to
+do with the fact that <l n='tex'/> uses a negative multiple of 1000 as
+a signal for a font scaled based on the design size.</p>
+--ldx]]--
+
+local factors = {
+ pt = 65536.0,
+ bp = 65781.8,
+}
+
+function constructors.setfactor(f)
+ constructors.factor = factors[f or 'pt'] or factors.pt
+end
+
+constructors.setfactor()
+
+function constructors.scaled(scaledpoints, designsize) -- handles designsize in sp as well
+ if scaledpoints < 0 then
+ local factor = constructors.factor
+ if designsize then
+ if designsize > factor then -- or just 1000 / when? mp?
+ return (- scaledpoints/1000) * designsize -- sp's
+ else
+ return (- scaledpoints/1000) * designsize * factor
+ end
+ else
+ return (- scaledpoints/1000) * 10 * factor
+ end
+ else
+ return scaledpoints
+ end
+end
+
+function constructors.getprivate(tfmdata)
+ local properties = tfmdata.properties
+ local private = properties.private
+ properties.private = private + 1
+ return private
+end
+
+function constructors.setmathparameter(tfmdata,name,value)
+ local m = tfmdata.mathparameters
+ local c = tfmdata.MathConstants
+ if m then
+ m[name] = value
+ end
+ if c and c ~= m then
+ c[name] = value
+ end
+end
+
+function constructors.getmathparameter(tfmdata,name)
+ local p = tfmdata.mathparameters or tfmdata.MathConstants
+ if p then
+ return p[name]
+ end
+end
+
+--[[ldx--
+<p>Beware, the boundingbox is passed as reference so we may not overwrite it
+in the process; numbers are of course copies. Here 65536 equals 1pt. (Due to
+excessive memory usage in CJK fonts, we no longer pass the boundingbox.)</p>
+--ldx]]--
+
+-- The scaler is only used for otf and afm and virtual fonts. If a virtual font has italic
+-- correction make sure to set the hasitalics flag. Some more flags will be added in the
+-- future.
+
+--[[ldx--
+<p>The reason why the scaler was originally split, is that for a while we experimented
+with a helper function. However, in practice the <l n='api'/> calls are too slow to
+make this profitable and the <l n='lua'/> based variant was just faster. A days
+wasted day but an experience richer.</p>
+--ldx]]--
+
+-- we can get rid of the tfm instance when we have fast access to the
+-- scaled character dimensions at the tex end, e.g. a fontobject.width
+-- actually we already have some of that now as virtual keys in glyphs
+--
+-- flushing the kern and ligature tables from memory saves a lot (only
+-- base mode) but it complicates vf building where the new characters
+-- demand this data .. solution: functions that access them
+
+function constructors.cleanuptable(tfmdata)
+ if constructors.autocleanup and tfmdata.properties.virtualized then
+ for k, v in next, tfmdata.characters do
+ if v.commands then v.commands = nil end
+ -- if v.kerns then v.kerns = nil end
+ end
+ end
+end
+
+-- experimental, sharing kerns (unscaled and scaled) saves memory
+-- local sharedkerns, basekerns = constructors.check_base_kerns(tfmdata)
+-- loop over descriptions (afm and otf have descriptions, tfm not)
+-- there is no need (yet) to assign a value to chr.tonunicode
+
+-- constructors.prepare_base_kerns(tfmdata) -- optimalization
+
+-- we have target.name=metricfile and target.fullname=RealName and target.filename=diskfilename
+-- when collapsing fonts, luatex looks as both target.name and target.fullname as ttc files
+-- can have multiple subfonts
+
+function constructors.calculatescale(tfmdata,scaledpoints)
+ local parameters = tfmdata.parameters
+ if scaledpoints < 0 then
+ scaledpoints = (- scaledpoints/1000) * (tfmdata.designsize or parameters.designsize) -- already in sp
+ end
+ return scaledpoints, scaledpoints / (parameters.units or 1000) -- delta
+end
+
+local unscaled = {
+ ScriptPercentScaleDown = true,
+ ScriptScriptPercentScaleDown = true,
+ RadicalDegreeBottomRaisePercent = true,
+ NoLimitSupFactor = true,
+ NoLimitSubFactor = true,
+}
+
+function constructors.assignmathparameters(target,original) -- simple variant, not used in context
+ -- when a tfm file is loaded, it has already been scaled
+ -- and it never enters the scaled so this is otf only and
+ -- even then we do some extra in the context math plugins
+ local mathparameters = original.mathparameters
+ if mathparameters and next(mathparameters) then
+ local targetparameters = target.parameters
+ local targetproperties = target.properties
+ local targetmathparameters = { }
+ local factor = targetproperties.math_is_scaled and 1 or targetparameters.factor
+ for name, value in next, mathparameters do
+ if unscaled[name] then
+ targetmathparameters[name] = value
+ else
+ targetmathparameters[name] = value * factor
+ end
+ end
+ if not targetmathparameters.FractionDelimiterSize then
+ targetmathparameters.FractionDelimiterSize = 1.01 * targetparameters.size
+ end
+ if not mathparameters.FractionDelimiterDisplayStyleSize then
+ targetmathparameters.FractionDelimiterDisplayStyleSize = 2.40 * targetparameters.size
+ end
+ target.mathparameters = targetmathparameters
+ end
+end
+
+function constructors.beforecopyingcharacters(target,original)
+ -- can be used for additional tweaking
+end
+
+function constructors.aftercopyingcharacters(target,original)
+ -- can be used for additional tweaking
+end
+
+-- It's probably ok to hash just the indices because there is not that much
+-- chance that one will shift slots and leave the others unset then. Anyway,
+-- there is of course some overhead here, but it might as well get compensated
+-- by less time spent on including the font resource twice. For the moment
+-- we default to false, so a macro package has to enable it explicitly. In
+-- LuaTeX the fullname is used to identify a font as being unique.
+
+constructors.sharefonts = false
+constructors.nofsharedfonts = 0
+local sharednames = { }
+
+function constructors.trytosharefont(target,tfmdata)
+ if constructors.sharefonts then -- not robust !
+ local characters = target.characters
+ local n = 1
+ local t = { target.psname }
+ local u = sortedkeys(characters)
+ for i=1,#u do
+ local k = u[i]
+ n = n + 1 ; t[n] = k
+ n = n + 1 ; t[n] = characters[k].index or k
+ end
+ local h = md5.HEX(concat(t," "))
+ local s = sharednames[h]
+ if s then
+ if trace_defining then
+ report_defining("font %a uses backend resources of font %a",target.fullname,s)
+ end
+ target.fullname = s
+ constructors.nofsharedfonts = constructors.nofsharedfonts + 1
+ target.properties.sharedwith = s
+ else
+ sharednames[h] = target.fullname
+ end
+ end
+end
+
+-- function constructors.enhanceparameters(parameters)
+-- local xheight = parameters.x_height
+-- local quad = parameters.quad
+-- local space = parameters.space
+-- local stretch = parameters.space_stretch
+-- local shrink = parameters.space_shrink
+-- local extra = parameters.extra_space
+-- local slant = parameters.slant
+-- -- synonyms
+-- parameters.xheight = xheight
+-- parameters.spacestretch = stretch
+-- parameters.spaceshrink = shrink
+-- parameters.extraspace = extra
+-- parameters.em = quad
+-- parameters.ex = xheight
+-- parameters.slantperpoint = slant
+-- parameters.spacing = {
+-- width = space,
+-- stretch = stretch,
+-- shrink = shrink,
+-- extra = extra,
+-- }
+-- end
+
+local synonyms = {
+ exheight = "x_height",
+ xheight = "x_height",
+ ex = "x_height",
+ emwidth = "quad",
+ em = "quad",
+ spacestretch = "space_stretch",
+ stretch = "space_stretch",
+ spaceshrink = "space_shrink",
+ shrink = "space_shrink",
+ extraspace = "extra_space",
+ xspace = "extra_space",
+ slantperpoint = "slant",
+}
+
+function constructors.enhanceparameters(parameters)
+ local mt = getmetatable(parameters)
+ local getter = function(t,k)
+ if not k then
+ return nil
+ end
+ local s = synonyms[k]
+ if s then
+ return rawget(t,s) or (mt and mt[s]) or nil
+ end
+ if k == "spacing" then
+ return {
+ width = t.space,
+ stretch = t.space_stretch,
+ shrink = t.space_shrink,
+ extra = t.extra_space,
+ }
+ end
+ return mt and mt[k] or nil
+ end
+ local setter = function(t,k,v)
+ if not k then
+ return 0
+ end
+ local s = synonyms[k]
+ if s then
+ rawset(t,s,v)
+ elseif k == "spacing" then
+ if type(v) == "table" then
+ rawset(t,"space",v.width or 0)
+ rawset(t,"space_stretch",v.stretch or 0)
+ rawset(t,"space_shrink",v.shrink or 0)
+ rawset(t,"extra_space",v.extra or 0)
+ end
+ else
+ rawset(t,k,v)
+ end
+ end
+ setmetatable(parameters, {
+ __index = getter,
+ __newindex = setter,
+ })
+end
+
+local function mathkerns(v,vdelta)
+ local k = { }
+ for i=1,#v do
+ local entry = v[i]
+ local height = entry.height
+ local kern = entry.kern
+ k[i] = {
+ height = height and vdelta*height or 0,
+ kern = kern and vdelta*kern or 0,
+ }
+ end
+ return k
+end
+
+local psfake = 0
+
+local function fixedpsname(psname,fallback)
+ local usedname = psname
+ if psname and psname ~= "" then
+ if find(psname," ",1,true) then
+ usedname = gsub(psname,"[%s]+","-")
+ else
+ -- we assume that the name is sane enough (we might sanitize completely some day)
+ end
+ elseif not fallback or fallback == "" then
+ psfake = psfake + 1
+ psname = "fakename-" .. psfake
+ else
+ -- filenames can be a mess so we do a drastic cleanup
+ psname = fallback
+ usedname = gsub(psname,"[^a-zA-Z0-9]+","-")
+ end
+ return usedname, psname ~= usedname
+end
+
+function constructors.scale(tfmdata,specification)
+ local target = { } -- the new table
+ --
+ if tonumber(specification) then
+ specification = { size = specification }
+ end
+ target.specification = specification
+ --
+ local scaledpoints = specification.size
+ local relativeid = specification.relativeid
+ --
+ local properties = tfmdata.properties or { }
+ local goodies = tfmdata.goodies or { }
+ local resources = tfmdata.resources or { }
+ local descriptions = tfmdata.descriptions or { } -- bad news if empty
+ local characters = tfmdata.characters or { } -- bad news if empty
+ local changed = tfmdata.changed or { } -- for base mode
+ local shared = tfmdata.shared or { }
+ local parameters = tfmdata.parameters or { }
+ local mathparameters = tfmdata.mathparameters or { }
+ --
+ local targetcharacters = { }
+ local targetdescriptions = derivetable(descriptions)
+ local targetparameters = derivetable(parameters)
+ local targetproperties = derivetable(properties)
+ local targetgoodies = goodies -- we need to loop so no metatable
+ target.characters = targetcharacters
+ target.descriptions = targetdescriptions
+ target.parameters = targetparameters
+ -- target.mathparameters = targetmathparameters -- happens elsewhere
+ target.properties = targetproperties
+ target.goodies = targetgoodies
+ target.shared = shared
+ target.resources = resources
+ target.unscaled = tfmdata -- the original unscaled one
+ --
+ -- specification.mathsize : 1=text 2=script 3=scriptscript
+ -- specification.textsize : natural (text)size
+ -- parameters.mathsize : 1=text 2=script 3=scriptscript >1000 enforced size (feature value other than yes)
+ --
+ local mathsize = tonumber(specification.mathsize) or 0
+ local textsize = tonumber(specification.textsize) or scaledpoints
+ local forcedsize = tonumber(parameters.mathsize ) or 0 -- can be set by the feature "mathsize"
+ local extrafactor = tonumber(specification.factor ) or 1
+ if (mathsize == 2 or forcedsize == 2) and parameters.scriptpercentage then
+ scaledpoints = parameters.scriptpercentage * textsize / 100
+ elseif (mathsize == 3 or forcedsize == 3) and parameters.scriptscriptpercentage then
+ scaledpoints = parameters.scriptscriptpercentage * textsize / 100
+ elseif forcedsize > 1000 then -- safeguard
+ scaledpoints = forcedsize
+ else
+ -- in context x and xx also use mathsize
+ end
+ targetparameters.mathsize = mathsize -- context specific
+ targetparameters.textsize = textsize -- context specific
+ targetparameters.forcedsize = forcedsize -- context specific
+ targetparameters.extrafactor = extrafactor -- context specific
+ --
+ local addtounicode = constructors.addtounicode
+ --
+ local tounicode = fonts.mappings.tounicode
+ local unknowncode = tounicode(0xFFFD)
+ --
+ local defaultwidth = resources.defaultwidth or 0
+ local defaultheight = resources.defaultheight or 0
+ local defaultdepth = resources.defaultdepth or 0
+ local units = parameters.units or 1000
+ --
+ -- boundary keys are no longer needed as we now have a string 'right_boundary'
+ -- that can be used in relevant tables (kerns and ligatures) ... not that I ever
+ -- used them
+ --
+ -- boundarychar_label = 0, -- not needed
+ -- boundarychar = 65536, -- there is now a string 'right_boundary'
+ -- false_boundarychar = 65536, -- produces invalid tfm in luatex
+ --
+ targetproperties.language = properties.language or "dflt" -- inherited
+ targetproperties.script = properties.script or "dflt" -- inherited
+ targetproperties.mode = properties.mode or "base" -- inherited
+ --
+ local askedscaledpoints = scaledpoints
+ local scaledpoints, delta = constructors.calculatescale(tfmdata,scaledpoints,nil,specification) -- no shortcut, dan be redefined
+ --
+ local hdelta = delta
+ local vdelta = delta
+ --
+ target.designsize = parameters.designsize -- not really needed so it might become obsolete
+ target.units = units
+ target.units_per_em = units -- just a trigger for the backend
+ --
+ local direction = properties.direction or tfmdata.direction or 0 -- pointless, as we don't use omf fonts at all
+ target.direction = direction
+ properties.direction = direction
+ --
+ target.size = scaledpoints
+ --
+ target.encodingbytes = properties.encodingbytes or 1
+ target.embedding = properties.embedding or "subset"
+ target.tounicode = 1
+ target.cidinfo = properties.cidinfo
+ target.format = properties.format
+ target.cache = constructors.cacheintex and "yes" or "renew"
+ --
+ local fontname = properties.fontname or tfmdata.fontname
+ local fullname = properties.fullname or tfmdata.fullname
+ local filename = properties.filename or tfmdata.filename
+ local psname = properties.psname or tfmdata.psname
+ local name = properties.name or tfmdata.name
+ --
+ -- The psname used in pdf file as well as for selecting subfont in ttc although
+ -- we don't need that subfont look up here (mapfile stuff).
+ --
+ local psname, psfixed = fixedpsname(psname,fontname or fullname or file.nameonly(filename))
+ --
+ target.fontname = fontname
+ target.fullname = fullname
+ target.filename = filename
+ target.psname = psname
+ target.name = name
+ --
+ properties.fontname = fontname
+ properties.fullname = fullname
+ properties.filename = filename
+ properties.psname = psname
+ properties.name = name
+ -- expansion (hz)
+ local expansion = parameters.expansion
+ if expansion then
+ target.stretch = expansion.stretch
+ target.shrink = expansion.shrink
+ target.step = expansion.step
+ end
+ -- slanting
+ local slantfactor = parameters.slantfactor or 0
+ if slantfactor ~= 0 then
+ target.slant = slantfactor * 1000
+ else
+ target.slant = 0
+ end
+ -- widening
+ local extendfactor = parameters.extendfactor or 0
+ if extendfactor ~= 0 and extendfactor ~= 1 then
+ hdelta = hdelta * extendfactor
+ target.extend = extendfactor * 1000
+ else
+ target.extend = 1000 -- extent ?
+ end
+ -- squeezing
+ local squeezefactor = parameters.squeezefactor or 0
+ if squeezefactor ~= 0 and squeezefactor ~= 1 then
+ vdelta = vdelta * squeezefactor
+ target.squeeze = squeezefactor * 1000
+ else
+ target.squeeze = 1000 -- extent ?
+ end
+ -- effects
+ local mode = parameters.mode or 0
+ if mode ~= 0 then
+ target.mode = mode
+ end
+ local width = parameters.width or 0
+ if width ~= 0 then
+ target.width = width * delta * 1000 / 655360
+ end
+ --
+ targetparameters.factor = delta
+ targetparameters.hfactor = hdelta
+ targetparameters.vfactor = vdelta
+ targetparameters.size = scaledpoints
+ targetparameters.units = units
+ targetparameters.scaledpoints = askedscaledpoints
+ targetparameters.mode = mode
+ targetparameters.width = width
+ --
+ local isvirtual = properties.virtualized or tfmdata.type == "virtual"
+ local hasquality = parameters.expansion or parameters.protrusion
+ local hasitalics = properties.hasitalics
+ local autoitalicamount = properties.autoitalicamount
+ local stackmath = not properties.nostackmath
+ local haskerns = properties.haskerns or properties.mode == "base" -- we can have afm in node mode
+ local hasligatures = properties.hasligatures or properties.mode == "base" -- we can have afm in node mode
+ local realdimensions = properties.realdimensions
+ local writingmode = properties.writingmode or "horizontal"
+ local identity = properties.identity or "horizontal"
+ --
+ local vfonts = target.fonts
+ if vfonts and #vfonts > 0 then
+ target.fonts = fastcopy(vfonts) -- maybe we virtualize more afterwards
+ elseif isvirtual then
+ target.fonts = { { id = 0 } } -- catch error
+ end
+ --
+ if changed and not next(changed) then
+ changed = false
+ end
+ --
+ target.type = isvirtual and "virtual" or "real"
+ target.writingmode = writingmode == "vertical" and "vertical" or "horizontal"
+ target.identity = identity == "vertical" and "vertical" or "horizontal"
+ --
+ target.postprocessors = tfmdata.postprocessors
+ --
+ local targetslant = (parameters.slant or parameters[1] or 0) * factors.pt -- per point
+ local targetspace = (parameters.space or parameters[2] or 0) * hdelta
+ local targetspace_stretch = (parameters.space_stretch or parameters[3] or 0) * hdelta
+ local targetspace_shrink = (parameters.space_shrink or parameters[4] or 0) * hdelta
+ local targetx_height = (parameters.x_height or parameters[5] or 0) * vdelta
+ local targetquad = (parameters.quad or parameters[6] or 0) * hdelta
+ local targetextra_space = (parameters.extra_space or parameters[7] or 0) * hdelta
+ --
+ targetparameters.slant = targetslant -- slantperpoint
+ targetparameters.space = targetspace
+ targetparameters.space_stretch = targetspace_stretch
+ targetparameters.space_shrink = targetspace_shrink
+ targetparameters.x_height = targetx_height
+ targetparameters.quad = targetquad
+ targetparameters.extra_space = targetextra_space
+ --
+ local ascender = parameters.ascender
+ if ascender then
+ targetparameters.ascender = delta * ascender
+ end
+ local descender = parameters.descender
+ if descender then
+ targetparameters.descender = delta * descender
+ end
+ --
+ constructors.enhanceparameters(targetparameters) -- official copies for us, now virtual
+ --
+ local protrusionfactor = (targetquad ~= 0 and 1000/targetquad) or 0
+ local scaledwidth = defaultwidth * hdelta
+ local scaledheight = defaultheight * vdelta
+ local scaleddepth = defaultdepth * vdelta
+ --
+ local hasmath = (properties.hasmath or next(mathparameters)) and true
+ --
+ if hasmath then
+ constructors.assignmathparameters(target,tfmdata) -- does scaling and whatever is needed
+ properties.hasmath = true
+ target.nomath = false
+ target.MathConstants = target.mathparameters
+ else
+ properties.hasmath = false
+ target.nomath = true
+ target.mathparameters = nil -- nop
+ end
+ --
+ -- Here we support some context specific trickery (this might move to a plugin). During the
+ -- transition to opentype the engine had troubles with italics so we had some additional code
+ -- for fixing that. In node mode (text) we don't care much if italics gets passed because
+ -- the engine does nothign with them then.
+ --
+ if hasmath then
+ local mathitalics = properties.mathitalics
+ if mathitalics == false then
+ if trace_defining then
+ report_defining("%s italics %s for font %a, fullname %a, filename %a","math",hasitalics and "ignored" or "disabled",name,fullname,filename)
+ end
+ hasitalics = false
+ autoitalicamount = false
+ end
+ else
+ local textitalics = properties.textitalics
+ if textitalics == false then
+ if trace_defining then
+ report_defining("%s italics %s for font %a, fullname %a, filename %a","text",hasitalics and "ignored" or "disabled",name,fullname,filename)
+ end
+ hasitalics = false
+ autoitalicamount = false
+ end
+ end
+ --
+ -- end of context specific trickery
+ --
+ if trace_defining then
+ report_defining("defining tfm, name %a, fullname %a, filename %a, %spsname %a, hscale %a, vscale %a, math %a, italics %a",
+ name,fullname,filename,psfixed and "(fixed) " or "",psname,hdelta,vdelta,
+ hasmath and "enabled" or "disabled",hasitalics and "enabled" or "disabled")
+ end
+ --
+ constructors.beforecopyingcharacters(target,tfmdata)
+ --
+ local sharedkerns = { }
+ --
+ -- we can have a dumb mode (basemode without math etc) that skips most
+ --
+ for unicode, character in next, characters do
+ local chr, description, index
+ if changed then
+ local c = changed[unicode]
+ if c and c ~= unicode then
+ if c then
+ description = descriptions[c] or descriptions[unicode] or character
+ character = characters[c] or character
+ index = description.index or c
+ else
+ description = descriptions[unicode] or character
+ index = description.index or unicode
+ end
+ else
+ description = descriptions[unicode] or character
+ index = description.index or unicode
+ end
+ else
+ description = descriptions[unicode] or character
+ index = description.index or unicode
+ end
+ local width = description.width
+ local height = description.height
+ local depth = description.depth
+ local isunicode = description.unicode
+ if realdimensions then
+ -- this is mostly for checking issues
+ if not height or height == 0 then
+ local bb = description.boundingbox
+ local ht = bb[4]
+ if ht ~= 0 then
+ height = ht
+ end
+ if not depth or depth == 0 then
+ local dp = -bb[2]
+ if dp ~= 0 then
+ depth = dp
+ end
+ end
+ elseif not depth or depth == 0 then
+ local dp = -description.boundingbox[2]
+ if dp ~= 0 then
+ depth = dp
+ end
+ end
+ end
+ if width then width = hdelta*width else width = scaledwidth end
+ if height then height = vdelta*height else height = scaledheight end
+ -- if depth then depth = vdelta*depth else depth = scaleddepth end
+ if depth and depth ~= 0 then
+ depth = delta*depth
+ if isunicode then
+ chr = {
+ index = index,
+ height = height,
+ depth = depth,
+ width = width,
+ unicode = isunicode,
+ }
+ else
+ chr = {
+ index = index,
+ height = height,
+ depth = depth,
+ width = width,
+ }
+ end
+ else
+ if isunicode then
+ chr = {
+ index = index,
+ height = height,
+ width = width,
+ unicode = isunicode,
+ }
+ else
+ chr = {
+ index = index,
+ height = height,
+ width = width,
+ }
+ end
+ end
+ if addtounicode then
+ chr.tounicode = isunicode and tounicode(isunicode) or unknowncode
+ end
+ if hasquality then
+ -- we could move these calculations elsewhere (saves calculations)
+ local ve = character.expansion_factor
+ if ve then
+ chr.expansion_factor = ve*1000 -- expansionfactor, hm, can happen elsewhere
+ end
+ local vl = character.left_protruding
+ if vl then
+ chr.left_protruding = protrusionfactor*width*vl
+ end
+ local vr = character.right_protruding
+ if vr then
+ chr.right_protruding = protrusionfactor*width*vr
+ end
+ end
+ --
+ if hasmath then
+ --
+ -- todo, just operate on descriptions.math
+ local vn = character.next
+ if vn then
+ chr.next = vn
+ else
+ local vv = character.vert_variants
+ if vv then
+ local t = { }
+ for i=1,#vv do
+ local vvi = vv[i]
+ local s = vvi["start"] or 0
+ local e = vvi["end"] or 0
+ local a = vvi["advance"] or 0
+ t[i] = { -- zero check nicer for 5.3
+ ["start"] = s == 0 and 0 or s * vdelta,
+ ["end"] = e == 0 and 0 or e * vdelta,
+ ["advance"] = a == 0 and 0 or a * vdelta,
+ ["extender"] = vvi["extender"],
+ ["glyph"] = vvi["glyph"],
+ }
+ end
+ chr.vert_variants = t
+ else
+ local hv = character.horiz_variants
+ if hv then
+ local t = { }
+ for i=1,#hv do
+ local hvi = hv[i]
+ local s = hvi["start"] or 0
+ local e = hvi["end"] or 0
+ local a = hvi["advance"] or 0
+ t[i] = { -- zero check nicer for 5.3
+ ["start"] = s == 0 and 0 or s * hdelta,
+ ["end"] = e == 0 and 0 or e * hdelta,
+ ["advance"] = a == 0 and 0 or a * hdelta,
+ ["extender"] = hvi["extender"],
+ ["glyph"] = hvi["glyph"],
+ }
+ end
+ chr.horiz_variants = t
+ end
+ end
+ -- todo also check mathitalics (or that one can go away)
+ end
+ local vi = character.vert_italic
+ if vi and vi ~= 0 then
+ chr.vert_italic = vi*hdelta
+ end
+ local va = character.accent
+ if va then
+ chr.top_accent = vdelta*va
+ end
+ if stackmath then
+ local mk = character.mathkerns
+ if mk then
+ local tr = mk.topright
+ local tl = mk.topleft
+ local br = mk.bottomright
+ local bl = mk.bottomleft
+ chr.mathkern = { -- singular -> should be patched in luatex !
+ top_right = tr and mathkerns(tr,vdelta) or nil,
+ top_left = tl and mathkerns(tl,vdelta) or nil,
+ bottom_right = br and mathkerns(br,vdelta) or nil,
+ bottom_left = bl and mathkerns(bl,vdelta) or nil,
+ }
+ end
+ end
+ if hasitalics then
+ local vi = character.italic
+ if vi and vi ~= 0 then
+ chr.italic = vi*hdelta
+ end
+ end
+ elseif autoitalicamount then -- itlc feature
+ local vi = description.italic
+ if not vi then
+ local bb = description.boundingbox
+ if bb then
+ local vi = bb[3] - description.width + autoitalicamount
+ if vi > 0 then -- < 0 indicates no overshoot or a very small auto italic
+ chr.italic = vi*hdelta
+ end
+ else
+ -- report_defining("no boundingbox for character %C in font %a, fullname %a, filename %a",unicode,name,fullname,filename)
+ end
+ elseif vi ~= 0 then
+ chr.italic = vi*hdelta
+ end
+ elseif hasitalics then -- unlikely
+ local vi = character.italic
+ if vi and vi ~= 0 then
+ chr.italic = vi*hdelta
+ end
+ end
+ if haskerns then
+ local vk = character.kerns
+ if vk then
+ local s = sharedkerns[vk]
+ if not s then
+ s = { }
+ for k,v in next, vk do s[k] = v*hdelta end
+ sharedkerns[vk] = s
+ end
+ chr.kerns = s
+ end
+ end
+ if hasligatures then
+ local vl = character.ligatures
+ if vl then
+ if true then
+ chr.ligatures = vl -- shared
+ else
+ local tt = { }
+ for i, l in next, vl do
+ tt[i] = l
+ end
+ chr.ligatures = tt
+ end
+ end
+ end
+ if isvirtual then
+ local vc = character.commands
+ if vc then
+ -- we assume non scaled commands here
+ -- tricky .. we need to scale pseudo math glyphs too
+ -- which is why we deal with rules too
+ local ok = false
+ for i=1,#vc do
+ local key = vc[i][1]
+ if key == "right" or key == "down" or key == "rule" then
+ ok = true
+ break
+ end
+ end
+ if ok then
+ local tt = { }
+ for i=1,#vc do
+ local ivc = vc[i]
+ local key = ivc[1]
+ if key == "right" then
+ tt[i] = { key, ivc[2]*hdelta }
+ elseif key == "down" then
+ tt[i] = { key, ivc[2]*vdelta }
+ elseif key == "rule" then
+ tt[i] = { key, ivc[2]*vdelta, ivc[3]*hdelta }
+ else -- not comment
+ tt[i] = ivc -- shared since in cache and untouched
+ end
+ end
+ chr.commands = tt
+ else
+ chr.commands = vc
+ end
+ -- chr.index = nil
+ end
+ end
+ targetcharacters[unicode] = chr
+ end
+ --
+ properties.setitalics = hasitalics -- for postprocessing
+ --
+ constructors.aftercopyingcharacters(target,tfmdata)
+ --
+ constructors.trytosharefont(target,tfmdata)
+ --
+ -- catch inconsistencies
+ --
+ local vfonts = target.fonts
+ if isvirtual or target.type == "virtual" or properties.virtualized then
+ properties.virtualized = true
+ target.type = "virtual"
+ if not vfonts or #vfonts == 0 then
+ target.fonts = { { id = 0 } }
+ end
+ elseif vfonts then
+ properties.virtualized = true
+ target.type = "virtual"
+ if #vfonts == 0 then
+ target.fonts = { { id = 0 } }
+ end
+ end
+ --
+ return target
+end
+
+function constructors.finalize(tfmdata)
+ if tfmdata.properties and tfmdata.properties.finalized then
+ return
+ end
+ --
+ if not tfmdata.characters then
+ return nil
+ end
+ --
+ if not tfmdata.goodies then
+ tfmdata.goodies = { } -- context specific
+ end
+ --
+ local parameters = tfmdata.parameters
+ if not parameters then
+ return nil
+ end
+ --
+ if not parameters.expansion then
+ parameters.expansion = {
+ stretch = tfmdata.stretch or 0,
+ shrink = tfmdata.shrink or 0,
+ step = tfmdata.step or 0,
+ }
+ end
+ --
+ if not parameters.size then
+ parameters.size = tfmdata.size
+ end
+ --
+ if not parameters.mode then
+ parameters.mode = 0
+ end
+ --
+ if not parameters.width then
+ parameters.width = 0
+ end
+ --
+ if not parameters.slantfactor then
+ parameters.slantfactor = (tfmdata.slant or 0)/1000
+ end
+ --
+ if not parameters.extendfactor then
+ parameters.extendfactor = (tfmdata.extend or 1000)/1000
+ end
+ --
+ if not parameters.squeezefactor then
+ parameters.squeezefactor = (tfmdata.squeeze or 1000)/1000
+ end
+ --
+ local designsize = parameters.designsize
+ if designsize then
+ parameters.minsize = tfmdata.minsize or designsize
+ parameters.maxsize = tfmdata.maxsize or designsize
+ else
+ designsize = factors.pt * 10
+ parameters.designsize = designsize
+ parameters.minsize = designsize
+ parameters.maxsize = designsize
+ end
+ parameters.minsize = tfmdata.minsize or parameters.designsize
+ parameters.maxsize = tfmdata.maxsize or parameters.designsize
+ --
+ if not parameters.units then
+ parameters.units = tfmdata.units or tfmdata.units_per_em or 1000
+ end
+ --
+ if not tfmdata.descriptions then
+ local descriptions = { } -- yes or no
+ setmetatableindex(descriptions, function(t,k) local v = { } t[k] = v return v end)
+ tfmdata.descriptions = descriptions
+ end
+ --
+ local properties = tfmdata.properties
+ if not properties then
+ properties = { }
+ tfmdata.properties = properties
+ end
+ --
+ if not properties.virtualized then
+ properties.virtualized = tfmdata.type == "virtual"
+ end
+ --
+ properties.fontname = properties.fontname or tfmdata.fontname
+ properties.filename = properties.filename or tfmdata.filename
+ properties.fullname = properties.fullname or tfmdata.fullname
+ properties.name = properties.name or tfmdata.name
+ properties.psname = properties.psname or tfmdata.psname
+ --
+ properties.encodingbytes = tfmdata.encodingbytes or 1
+ properties.embedding = tfmdata.embedding or "subset"
+ properties.tounicode = tfmdata.tounicode or 1
+ properties.cidinfo = tfmdata.cidinfo or nil
+ properties.format = tfmdata.format or "type1"
+ properties.direction = tfmdata.direction or 0
+ properties.writingmode = tfmdata.writingmode or "horizontal"
+ properties.identity = tfmdata.identity or "horizontal"
+ properties.usedbitmap = tfmdata.usedbitmap
+ --
+ if not tfmdata.resources then
+ tfmdata.resources = { }
+ end
+ if not tfmdata.shared then
+ tfmdata.shared = { }
+ end
+ --
+ -- tfmdata.fonts
+ -- tfmdata.unscaled
+ --
+ if not properties.hasmath then
+ properties.hasmath = not tfmdata.nomath
+ end
+ --
+ tfmdata.MathConstants = nil
+ tfmdata.postprocessors = nil
+ --
+ tfmdata.fontname = nil
+ tfmdata.filename = nil
+ tfmdata.fullname = nil
+ tfmdata.name = nil -- most tricky part
+ tfmdata.psname = nil
+ --
+ tfmdata.encodingbytes = nil
+ tfmdata.embedding = nil
+ tfmdata.tounicode = nil
+ tfmdata.cidinfo = nil
+ tfmdata.format = nil
+ tfmdata.direction = nil
+ tfmdata.type = nil
+ tfmdata.nomath = nil
+ tfmdata.designsize = nil
+ --
+ tfmdata.size = nil
+ tfmdata.stretch = nil
+ tfmdata.shrink = nil
+ tfmdata.step = nil
+ tfmdata.slant = nil
+ tfmdata.extend = nil
+ tfmdata.squeeze = nil
+ tfmdata.mode = nil
+ tfmdata.width = nil
+ tfmdata.units = nil
+ tfmdata.units_per_em = nil
+ --
+ tfmdata.cache = nil
+ --
+ properties.finalized = true
+ --
+ return tfmdata
+end
+
+--[[ldx--
+<p>A unique hash value is generated by:</p>
+--ldx]]--
+
+local hashmethods = { }
+constructors.hashmethods = hashmethods
+
+function constructors.hashfeatures(specification) -- will be overloaded
+ local features = specification.features
+ if features then
+ local t, n = { }, 0
+ for category, list in sortedhash(features) do
+ if next(list) then
+ local hasher = hashmethods[category]
+ if hasher then
+ local hash = hasher(list)
+ if hash then
+ n = n + 1
+ t[n] = category .. ":" .. hash
+ end
+ end
+ end
+ end
+ if n > 0 then
+ return concat(t," & ")
+ end
+ end
+ return "unknown"
+end
+
+hashmethods.normal = function(list)
+ local s = { }
+ local n = 0
+ for k, v in next, list do
+ if not k then
+ -- no need to add to hash
+ elseif k == "number" or k == "features" then
+ -- no need to add to hash (maybe we need a skip list)
+ else
+ n = n + 1
+ if type(v) == "table" then
+ -- table.sequenced
+ local t = { }
+ local m = 0
+ for k, v in next, v do
+ m = m + 1
+ t[m] = k .. '=' .. tostring(v)
+ end
+ s[n] = k .. '={' .. concat(t,",") .. "}"
+ else
+ s[n] = k .. '=' .. tostring(v)
+ end
+ end
+ end
+ if n > 0 then
+ sort(s)
+ return concat(s,"+")
+ end
+end
+
+--[[ldx--
+<p>In principle we can share tfm tables when we are in need for a font, but then
+we need to define a font switch as an id/attr switch which is no fun, so in that
+case users can best use dynamic features ... so, we will not use that speedup. Okay,
+when we get rid of base mode we can optimize even further by sharing, but then we
+loose our testcases for <l n='luatex'/>.</p>
+--ldx]]--
+
+function constructors.hashinstance(specification,force)
+ local hash = specification.hash
+ local size = specification.size
+ local fallbacks = specification.fallbacks
+ if force or not hash then
+ hash = constructors.hashfeatures(specification)
+ specification.hash = hash
+ end
+ if size < 1000 and designsizes[hash] then
+ size = round(constructors.scaled(size,designsizes[hash]))
+ else
+ size = round(size)
+ end
+ specification.size = size
+ if fallbacks then
+ return hash .. ' @ ' .. size .. ' @ ' .. fallbacks
+ else
+ return hash .. ' @ ' .. size
+ end
+end
+
+function constructors.setname(tfmdata,specification) -- todo: get specification from tfmdata
+ if constructors.namemode == "specification" then
+ -- not to be used in context !
+ local specname = specification.specification
+ if specname then
+ tfmdata.properties.name = specname
+ if trace_defining then
+ report_otf("overloaded fontname %a",specname)
+ end
+ end
+ end
+end
+
+function constructors.checkedfilename(data)
+ local foundfilename = data.foundfilename
+ if not foundfilename then
+ local askedfilename = data.filename or ""
+ if askedfilename ~= "" then
+ askedfilename = resolvers.resolve(askedfilename) -- no shortcut
+ foundfilename = resolvers.findbinfile(askedfilename,"") or ""
+ if foundfilename == "" then
+ report_defining("source file %a is not found",askedfilename)
+ foundfilename = resolvers.findbinfile(file.basename(askedfilename),"") or ""
+ if foundfilename ~= "" then
+ report_defining("using source file %a due to cache mismatch",foundfilename)
+ end
+ end
+ end
+ data.foundfilename = foundfilename
+ end
+ return foundfilename
+end
+
+local formats = allocate()
+fonts.formats = formats
+
+setmetatableindex(formats, function(t,k)
+ local l = lower(k)
+ if rawget(t,k) then
+ t[k] = l
+ return l
+ end
+ return rawget(t,file.suffix(l))
+end)
+
+do
+
+ local function setindeed(mode,source,target,group,name,position)
+ local action = source[mode]
+ if not action then
+ return
+ end
+ local t = target[mode]
+ if not t then
+ report_defining("fatal error in setting feature %a, group %a, mode %a",name,group,mode)
+ os.exit()
+ elseif position then
+ -- todo: remove existing
+ insert(t, position, { name = name, action = action })
+ else
+ for i=1,#t do
+ local ti = t[i]
+ if ti.name == name then
+ ti.action = action
+ return
+ end
+ end
+ insert(t, { name = name, action = action })
+ end
+ end
+
+ local function set(group,name,target,source)
+ target = target[group]
+ if not target then
+ report_defining("fatal target error in setting feature %a, group %a",name,group)
+ os.exit()
+ end
+ local source = source[group]
+ if not source then
+ report_defining("fatal source error in setting feature %a, group %a",name,group)
+ os.exit()
+ end
+ local position = source.position
+ setindeed("node",source,target,group,name,position)
+ setindeed("base",source,target,group,name,position)
+ setindeed("plug",source,target,group,name,position)
+ end
+
+ local function register(where,specification)
+ local name = specification.name
+ if name and name ~= "" then
+ local default = specification.default
+ local description = specification.description
+ local initializers = specification.initializers
+ local processors = specification.processors
+ local manipulators = specification.manipulators
+ local modechecker = specification.modechecker
+ if default then
+ where.defaults[name] = default
+ end
+ if description and description ~= "" then
+ where.descriptions[name] = description
+ end
+ if initializers then
+ set('initializers',name,where,specification)
+ end
+ if processors then
+ set('processors', name,where,specification)
+ end
+ if manipulators then
+ set('manipulators',name,where,specification)
+ end
+ if modechecker then
+ where.modechecker = modechecker
+ end
+ end
+ end
+
+ constructors.registerfeature = register
+
+ function constructors.getfeatureaction(what,where,mode,name)
+ what = handlers[what].features
+ if what then
+ where = what[where]
+ if where then
+ mode = where[mode]
+ if mode then
+ for i=1,#mode do
+ local m = mode[i]
+ if m.name == name then
+ return m.action
+ end
+ end
+ end
+ end
+ end
+ end
+
+ local newfeatures = { }
+ constructors.newfeatures = newfeatures -- downward compatible
+ constructors.features = newfeatures
+
+ local function setnewfeatures(what)
+ local handler = handlers[what]
+ local features = handler.features
+ if not features then
+ local tables = handler.tables -- can be preloaded
+ local statistics = handler.statistics -- can be preloaded
+ features = allocate {
+ defaults = { },
+ descriptions = tables and tables.features or { },
+ used = statistics and statistics.usedfeatures or { },
+ initializers = { base = { }, node = { }, plug = { } },
+ processors = { base = { }, node = { }, plug = { } },
+ manipulators = { base = { }, node = { }, plug = { } },
+ }
+ features.register = function(specification) return register(features,specification) end
+ handler.features = features -- will also become hidden
+ end
+ return features
+ end
+
+ setmetatable(newfeatures, {
+ __call = function(t,k) local v = t[k] return v end,
+ __index = function(t,k) local v = setnewfeatures(k) t[k] = v return v end,
+ })
+
+end
+
+do
+
+ local newhandler = { }
+ constructors.handlers = newhandler -- downward compatible
+ constructors.newhandler = newhandler
+
+ local function setnewhandler(what) -- could be a metatable newindex
+ local handler = handlers[what]
+ if not handler then
+ handler = { }
+ handlers[what] = handler
+ end
+ return handler
+ end
+
+ setmetatable(newhandler, {
+ __call = function(t,k) local v = t[k] return v end,
+ __index = function(t,k) local v = setnewhandler(k) t[k] = v return v end,
+ })
+
+end
+
+do
+ -- a pitty that we need to be generic as we have nicer mechanisms for this ...
+
+ local newenhancer = { }
+ constructors.enhancers = newenhancer
+ constructors.newenhancer = newenhancer
+
+ local function setnewenhancer(format)
+
+ local handler = handlers[format]
+ local enhancers = handler.enhancers
+
+ if not enhancers then
+
+ local actions = allocate() -- no need to allocate thee
+ local before = allocate()
+ local after = allocate()
+ local order = allocate()
+ local known = { }
+ local nofsteps = 0
+ local patches = { before = before, after = after }
+
+ local trace = false
+ local report = logs.reporter("fonts",format .. " enhancing")
+
+ trackers.register(format .. ".loading", function(v) trace = v end)
+
+ local function enhance(name,data,filename,raw)
+ local enhancer = actions[name]
+ if enhancer then
+ if trace then
+ report("apply enhancement %a to file %a",name,filename)
+ ioflush()
+ end
+ enhancer(data,filename,raw)
+ else
+ -- no message as we can have private ones
+ end
+ end
+
+ local function apply(data,filename,raw)
+ local basename = file.basename(lower(filename))
+ if trace then
+ report("%s enhancing file %a","start",filename)
+ end
+ ioflush() -- we want instant messages
+ for e=1,nofsteps do
+ local enhancer = order[e]
+ local b = before[enhancer]
+ if b then
+ for pattern, action in next, b do
+ if find(basename,pattern) then
+ action(data,filename,raw)
+ end
+ end
+ end
+ enhance(enhancer,data,filename,raw) -- we have one installed: check extra features
+ local a = after[enhancer]
+ if a then
+ for pattern, action in next, a do
+ if find(basename,pattern) then
+ action(data,filename,raw)
+ end
+ end
+ end
+ ioflush() -- we want instant messages
+ end
+ if trace then
+ report("%s enhancing file %a","stop",filename)
+ end
+ ioflush() -- we want instant messages
+ end
+
+ local function register(what,action)
+ if action then
+ if actions[what] then
+ -- overloading, e.g."check extra features"
+ else
+ nofsteps = nofsteps + 1
+ order[nofsteps] = what
+ known[what] = nofsteps
+ end
+ actions[what] = action
+ else
+ report("bad enhancer %a",what)
+ end
+ end
+
+ -- We used to have a lot of enhancers but no longer with the new font loader. The order of enhancers
+ -- is the order of definition. The before/after patches are there for old times sake and happen
+ -- before or after a (named) enhancer. An example of a set enhancer is "check extra features" so one
+ -- one set patches before or after that is applied. Unknown enhancers are auto-registered. It's a bit
+ -- messy but we keep it for compatibility reasons.
+ --
+ -- fonts.handlers.otf.enhancers.patches.register("before","some patches","somefont",function(data,filename)
+ -- print("!!!!!!!") -- before | after
+ -- end)
+ --
+ -- fonts.handlers.otf.enhancers.register("more patches",function(data,filename)
+ -- print("???????") -- enhance
+ -- end)
+
+ local function patch(what,where,pattern,action)
+ local pw = patches[what]
+ if pw then
+ local ww = pw[where]
+ if ww then
+ ww[pattern] = action
+ else
+ pw[where] = { [pattern] = action }
+ if not known[where] then
+ nofsteps = nofsteps + 1
+ order[nofsteps] = where
+ known[where] = nofsteps
+ end
+ end
+ end
+ end
+
+ enhancers = {
+ register = register,
+ apply = apply,
+ patch = patch,
+ report = report,
+ patches = {
+ register = patch,
+ report = report,
+ }, -- for old times sake
+ }
+
+ handler.enhancers = enhancers
+ end
+ return enhancers
+ end
+
+ setmetatable(newenhancer, {
+ __call = function(t,k) local v = t[k] return v end,
+ __index = function(t,k) local v = setnewenhancer(k) t[k] = v return v end,
+ })
+
+end
+
+--[[ldx--
+<p>We need to check for default features. For this we provide
+a helper function.</p>
+--ldx]]--
+
+function constructors.checkedfeatures(what,features)
+ local defaults = handlers[what].features.defaults
+ if features and next(features) then
+ features = fastcopy(features) -- can be inherited (mt) but then no loops possible
+ for key, value in next, defaults do
+ if features[key] == nil then
+ features[key] = value
+ end
+ end
+ return features
+ else
+ return fastcopy(defaults) -- we can change features in place
+ end
+end
+
+-- before scaling
+
+function constructors.initializefeatures(what,tfmdata,features,trace,report)
+ if features and next(features) then
+ local properties = tfmdata.properties or { } -- brrr
+ local whathandler = handlers[what]
+ local whatfeatures = whathandler.features
+ local whatmodechecker = whatfeatures.modechecker
+ -- properties.mode can be enforces (for instance in font-otd)
+ local mode = properties.mode or (whatmodechecker and whatmodechecker(tfmdata,features,features.mode)) or features.mode or "base"
+ properties.mode = mode -- also status
+ features.mode = mode -- both properties.mode or features.mode can be changed
+ --
+ local done = { }
+ while true do
+ local redo = false
+ local initializers = whatfeatures.initializers[mode]
+ if initializers then
+ for i=1,#initializers do
+ local step = initializers[i]
+ local feature = step.name
+-- we could intercept mode here .. needs a rewrite of this whole loop then but it's cleaner that way
+ local value = features[feature]
+ if not value then
+ -- disabled
+ elseif done[feature] then
+ -- already done
+ else
+ local action = step.action
+ if trace then
+ report("initializing feature %a to %a for mode %a for font %a",feature,
+ value,mode,tfmdata.properties.fullname)
+ end
+ action(tfmdata,value,features) -- can set mode (e.g. goodies) so it can trigger a restart
+ if mode ~= properties.mode or mode ~= features.mode then
+ if whatmodechecker then
+ properties.mode = whatmodechecker(tfmdata,features,properties.mode) -- force checking
+ features.mode = properties.mode
+ end
+ if mode ~= properties.mode then
+ mode = properties.mode
+ redo = true
+ end
+ end
+ done[feature] = true
+ end
+ if redo then
+ break
+ end
+ end
+ if not redo then
+ break
+ end
+ else
+ break
+ end
+ end
+ properties.mode = mode -- to be sure
+ return true
+ else
+ return false
+ end
+end
+
+-- while typesetting
+
+function constructors.collectprocessors(what,tfmdata,features,trace,report)
+ local processes = { }
+ local nofprocesses = 0
+ if features and next(features) then
+ local properties = tfmdata.properties
+ local whathandler = handlers[what]
+ local whatfeatures = whathandler.features
+ local whatprocessors = whatfeatures.processors
+ local mode = properties.mode
+ local processors = whatprocessors[mode]
+ if processors then
+ for i=1,#processors do
+ local step = processors[i]
+ local feature = step.name
+ if features[feature] then
+ local action = step.action
+ if trace then
+ report("installing feature processor %a for mode %a for font %a",feature,mode,tfmdata.properties.fullname)
+ end
+ if action then
+ nofprocesses = nofprocesses + 1
+ processes[nofprocesses] = action
+ end
+ end
+ end
+ elseif trace then
+ report("no feature processors for mode %a for font %a",mode,properties.fullname)
+ end
+ end
+ return processes
+end
+
+-- after scaling
+
+function constructors.applymanipulators(what,tfmdata,features,trace,report)
+ if features and next(features) then
+ local properties = tfmdata.properties
+ local whathandler = handlers[what]
+ local whatfeatures = whathandler.features
+ local whatmanipulators = whatfeatures.manipulators
+ local mode = properties.mode
+ local manipulators = whatmanipulators[mode]
+ if manipulators then
+ for i=1,#manipulators do
+ local step = manipulators[i]
+ local feature = step.name
+ local value = features[feature]
+ if value then
+ local action = step.action
+ if trace then
+ report("applying feature manipulator %a for mode %a for font %a",feature,mode,properties.fullname)
+ end
+ if action then
+ action(tfmdata,feature,value)
+ end
+ end
+ end
+ end
+ end
+end
+
+function constructors.addcoreunicodes(unicodes) -- maybe make this a metatable if used at all
+ if not unicodes then
+ unicodes = { }
+ end
+ unicodes.space = 0x0020
+ unicodes.hyphen = 0x002D
+ unicodes.zwj = 0x200D
+ unicodes.zwnj = 0x200C
+ return unicodes
+end
+
+-- -- keep for a while: old tounicode code
+--
+-- if changed then
+-- -- basemode hack (we try to catch missing tounicodes, e.g. needed for ssty in math cambria)
+-- local c = changed[unicode]
+-- if c then
+-- -- local ligatures = character.ligatures -- the original ligatures (as we cannot rely on remapping)
+-- description = descriptions[c] or descriptions[unicode] or character
+-- character = characters[c] or character
+-- index = description.index or c
+-- if tounicode then
+-- touni = tounicode[index] -- nb: index!
+-- if not touni then -- goodie
+-- local d = descriptions[unicode] or characters[unicode]
+-- local i = d.index or unicode
+-- touni = tounicode[i] -- nb: index!
+-- end
+-- end
+-- -- if ligatures and not character.ligatures then
+-- -- character.ligatures = ligatures -- the original targets (for now at least.. see libertine smallcaps)
+-- -- end
+-- else
+-- description = descriptions[unicode] or character
+-- index = description.index or unicode
+-- if tounicode then
+-- touni = tounicode[index] -- nb: index!
+-- end
+-- end
+-- else
+-- description = descriptions[unicode] or character
+-- index = description.index or unicode
+-- if tounicode then
+-- touni = tounicode[index] -- nb: index!
+-- end
+-- end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-def.lua b/macros/luatex/generic/luaotfload/fontloader-font-def.lua
new file mode 100644
index 0000000000..f3d0f81871
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-def.lua
@@ -0,0 +1,536 @@
+if not modules then modules = { } end modules ['font-def'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- We can overload some of the definers.functions so we don't local them.
+
+local lower, gsub = string.lower, string.gsub
+local tostring, next = tostring, next
+local lpegmatch = lpeg.match
+local suffixonly, removesuffix, basename = file.suffix, file.removesuffix, file.basename
+local formatters = string.formatters
+local sortedhash, sortedkeys = table.sortedhash, table.sortedkeys
+
+local allocate = utilities.storage.allocate
+
+local trace_defining = false trackers .register("fonts.defining", function(v) trace_defining = v end)
+local directive_embedall = false directives.register("fonts.embedall", function(v) directive_embedall = v end)
+
+trackers.register("fonts.loading", "fonts.defining", "otf.loading", "afm.loading", "tfm.loading")
+
+local report_defining = logs.reporter("fonts","defining")
+
+--[[ldx--
+<p>Here we deal with defining fonts. We do so by intercepting the
+default loader that only handles <l n='tfm'/>.</p>
+--ldx]]--
+
+local fonts = fonts
+local fontdata = fonts.hashes.identifiers
+local readers = fonts.readers
+local definers = fonts.definers
+local specifiers = fonts.specifiers
+local constructors = fonts.constructors
+local fontgoodies = fonts.goodies
+
+readers.sequence = allocate { 'otf', 'ttf', 'afm', 'tfm', 'lua' } -- dfont ttc
+
+local variants = allocate()
+specifiers.variants = variants
+
+definers.methods = definers.methods or { }
+
+local internalized = allocate() -- internal tex numbers (private)
+local lastdefined = nil -- we don't want this one to end up in s-tra-02
+
+local loadedfonts = constructors.loadedfonts
+local designsizes = constructors.designsizes
+
+-- not in generic (some day I'll make two defs, one for context, one for generic)
+
+local resolvefile = fontgoodies and fontgoodies.filenames and fontgoodies.filenames.resolve or function(s) return s end
+
+--[[ldx--
+<p>We hardly gain anything when we cache the final (pre scaled)
+<l n='tfm'/> table. But it can be handy for debugging, so we no
+longer carry this code along. Also, we now have quite some reference
+to other tables so we would end up with lots of catches.</p>
+--ldx]]--
+
+--[[ldx--
+<p>We can prefix a font specification by <type>name:</type> or
+<type>file:</type>. The first case will result in a lookup in the
+synonym table.</p>
+
+<typing>
+[ name: | file: ] identifier [ separator [ specification ] ]
+</typing>
+
+<p>The following function split the font specification into components
+and prepares a table that will move along as we proceed.</p>
+--ldx]]--
+
+-- beware, we discard additional specs
+--
+-- method:name method:name(sub) method:name(sub)*spec method:name*spec
+-- name name(sub) name(sub)*spec name*spec
+-- name@spec*oeps
+
+local function makespecification(specification,lookup,name,sub,method,detail,size)
+ size = size or 655360
+ if not lookup or lookup == "" then
+ lookup = definers.defaultlookup
+ end
+ if trace_defining then
+ report_defining("specification %a, lookup %a, name %a, sub %a, method %a, detail %a",
+ specification, lookup, name, sub, method, detail)
+ end
+ local t = {
+ lookup = lookup, -- forced type
+ specification = specification, -- full specification
+ size = size, -- size in scaled points or -1000*n
+ name = name, -- font or filename
+ sub = sub, -- subfont (eg in ttc)
+ method = method, -- specification method
+ detail = detail, -- specification
+ resolved = "", -- resolved font name
+ forced = "", -- forced loader
+ features = { }, -- preprocessed features
+ }
+ return t
+end
+
+definers.makespecification = makespecification
+
+if context then
+
+ local splitter, splitspecifiers = nil, "" -- not so nice
+
+ local P, C, S, Cc, Cs = lpeg.P, lpeg.C, lpeg.S, lpeg.Cc, lpeg.Cs
+
+ local left = P("(")
+ local right = P(")")
+ local colon = P(":")
+ local space = P(" ")
+ local lbrace = P("{")
+ local rbrace = P("}")
+
+ definers.defaultlookup = "file"
+
+ local prefixpattern = P(false)
+
+ local function addspecifier(symbol)
+ splitspecifiers = splitspecifiers .. symbol
+ local method = S(splitspecifiers)
+ local lookup = C(prefixpattern) * colon
+ local sub = left * C(P(1-left-right-method)^1) * right
+ local specification = C(method) * C(P(1)^1)
+ local name = Cs((lbrace/"") * (1-rbrace)^1 * (rbrace/"") + (1-sub-specification)^1)
+ splitter = P((lookup + Cc("")) * name * (sub + Cc("")) * (specification + Cc("")))
+ end
+
+ local function addlookup(str)
+ prefixpattern = prefixpattern + P(str)
+ end
+
+ definers.addlookup = addlookup
+
+ addlookup("file")
+ addlookup("name")
+ addlookup("spec")
+
+ local function getspecification(str)
+ return lpegmatch(splitter,str or "") -- weird catch
+ end
+
+ definers.getspecification = getspecification
+
+ function definers.registersplit(symbol,action,verbosename)
+ addspecifier(symbol)
+ variants[symbol] = action
+ if verbosename then
+ variants[verbosename] = action
+ end
+ end
+
+ function definers.analyze(specification, size)
+ -- can be optimized with locals
+ local lookup, name, sub, method, detail = getspecification(specification or "")
+ return makespecification(specification, lookup, name, sub, method, detail, size)
+ end
+
+end
+
+--[[ldx--
+<p>We can resolve the filename using the next function:</p>
+--ldx]]--
+
+definers.resolvers = definers.resolvers or { }
+local resolvers = definers.resolvers
+
+-- todo: reporter
+
+function resolvers.file(specification)
+ local name = resolvefile(specification.name) -- catch for renames
+ local suffix = lower(suffixonly(name))
+ if fonts.formats[suffix] then
+ specification.forced = suffix
+ specification.forcedname = name
+ specification.name = removesuffix(name)
+ else
+ specification.name = name -- can be resolved
+ end
+end
+
+function resolvers.name(specification)
+ local resolve = fonts.names.resolve
+ if resolve then
+ local resolved, sub, subindex, instance = resolve(specification.name,specification.sub,specification) -- we pass specification for overloaded versions
+ if resolved then
+ specification.resolved = resolved
+ specification.sub = sub
+ specification.subindex = subindex
+ -- new, needed for experiments
+ if instance then
+ specification.instance = instance
+ local features = specification.features
+ if not features then
+ features = { }
+ specification.features = features
+ end
+ local normal = features.normal
+ if not normal then
+ normal = { }
+ features.normal = normal
+ end
+ normal.instance = instance
+ -- if not callbacks.supported.glyph_stream_provider then
+ -- normal.variableshapes = true -- for the moment
+ -- end
+ end
+ --
+ local suffix = lower(suffixonly(resolved))
+ if fonts.formats[suffix] then
+ specification.forced = suffix
+ specification.forcedname = resolved
+ specification.name = removesuffix(resolved)
+ else
+ specification.name = resolved
+ end
+ end
+ else
+ resolvers.file(specification)
+ end
+end
+
+function resolvers.spec(specification)
+ local resolvespec = fonts.names.resolvespec
+ if resolvespec then
+ local resolved, sub, subindex = resolvespec(specification.name,specification.sub,specification) -- we pass specification for overloaded versions
+ if resolved then
+ specification.resolved = resolved
+ specification.sub = sub
+ specification.subindex = subindex
+ specification.forced = lower(suffixonly(resolved))
+ specification.forcedname = resolved
+ specification.name = removesuffix(resolved)
+ end
+ else
+ resolvers.name(specification)
+ end
+end
+
+function definers.resolve(specification)
+ if not specification.resolved or specification.resolved == "" then -- resolved itself not per se in mapping hash
+ local r = resolvers[specification.lookup]
+ if r then
+ r(specification)
+ end
+ end
+ if specification.forced == "" then
+ specification.forced = nil
+ specification.forcedname = nil
+ end
+ specification.hash = lower(specification.name .. ' @ ' .. constructors.hashfeatures(specification))
+ if specification.sub and specification.sub ~= "" then
+ specification.hash = specification.sub .. ' @ ' .. specification.hash
+ end
+ return specification
+end
+
+--[[ldx--
+<p>The main read function either uses a forced reader (as determined by
+a lookup) or tries to resolve the name using the list of readers.</p>
+
+<p>We need to cache when possible. We do cache raw tfm data (from <l
+n='tfm'/>, <l n='afm'/> or <l n='otf'/>). After that we can cache based
+on specificstion (name) and size, that is, <l n='tex'/> only needs a number
+for an already loaded fonts. However, it may make sense to cache fonts
+before they're scaled as well (store <l n='tfm'/>'s with applied methods
+and features). However, there may be a relation between the size and
+features (esp in virtual fonts) so let's not do that now.</p>
+
+<p>Watch out, here we do load a font, but we don't prepare the
+specification yet.</p>
+--ldx]]--
+
+-- very experimental:
+
+function definers.applypostprocessors(tfmdata)
+ local postprocessors = tfmdata.postprocessors
+ if postprocessors then
+ local properties = tfmdata.properties
+ for i=1,#postprocessors do
+ local extrahash = postprocessors[i](tfmdata) -- after scaling etc
+ if type(extrahash) == "string" and extrahash ~= "" then
+ -- e.g. a reencoding needs this
+ extrahash = gsub(lower(extrahash),"[^a-z]","-")
+ properties.fullname = formatters["%s-%s"](properties.fullname,extrahash)
+ end
+ end
+ end
+ return tfmdata
+end
+
+-- function definers.applypostprocessors(tfmdata)
+-- return tfmdata
+-- end
+
+local function checkembedding(tfmdata)
+ local properties = tfmdata.properties
+ local embedding
+ if directive_embedall then
+ embedding = "full"
+ elseif properties and properties.filename and constructors.dontembed[properties.filename] then
+ embedding = "no"
+ else
+ embedding = "subset"
+ end
+ if properties then
+ properties.embedding = embedding
+ else
+ tfmdata.properties = { embedding = embedding }
+ end
+ tfmdata.embedding = embedding
+end
+
+local function checkfeatures(tfmdata)
+ local resources = tfmdata.resources
+ local shared = tfmdata.shared
+ if resources and shared then
+ local features = resources.features
+ local usedfeatures = shared.features
+ if features and usedfeatures then
+ local usedlanguage = usedfeatures.language or "dflt"
+ local usedscript = usedfeatures.script or "dflt"
+ local function check(what)
+ if what then
+ local foundlanguages = { }
+ for feature, scripts in next, what do
+ if usedscript == "auto" or scripts["*"] then
+ -- ok
+ elseif not scripts[usedscript] then
+ -- report_defining("font %!font:name!, feature %a, no script %a",
+ -- tfmdata,feature,usedscript)
+ else
+ for script, languages in next, scripts do
+ if languages["*"] then
+ -- ok
+ elseif context and not languages[usedlanguage] then
+ report_defining("font %!font:name!, feature %a, script %a, no language %a",
+ tfmdata,feature,script,usedlanguage)
+ end
+ end
+ end
+ for script, languages in next, scripts do
+ for language in next, languages do
+ foundlanguages[language] = true
+ end
+ end
+ end
+ if false then
+ foundlanguages["*"] = nil
+ foundlanguages = sortedkeys(foundlanguages)
+ for feature, scripts in sortedhash(what) do
+ for script, languages in next, scripts do
+ if not languages["*"] then
+ for i=1,#foundlanguages do
+ local language = foundlanguages[i]
+ if context and not languages[language] then
+ report_defining("font %!font:name!, feature %a, script %a, no language %a",
+ tfmdata,feature,script,language)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ check(features.gsub)
+ check(features.gpos)
+ end
+ end
+end
+
+function definers.loadfont(specification)
+ local hash = constructors.hashinstance(specification)
+ -- todo: also hash by instance / factors
+ local tfmdata = loadedfonts[hash] -- hashes by size !
+ if not tfmdata then
+ -- normally context will not end up here often (if so there is an issue somewhere)
+ local forced = specification.forced or ""
+ if forced ~= "" then
+ local reader = readers[lower(forced)] -- normally forced is already lowered
+ tfmdata = reader and reader(specification)
+ if not tfmdata then
+ report_defining("forced type %a of %a not found",forced,specification.name)
+ end
+ else
+ local sequence = readers.sequence -- can be overloaded so only a shortcut here
+ for s=1,#sequence do
+ local reader = sequence[s]
+ if readers[reader] then -- we skip not loaded readers
+ if trace_defining then
+ report_defining("trying (reader sequence driven) type %a for %a with file %a",reader,specification.name,specification.filename)
+ end
+ tfmdata = readers[reader](specification)
+ if tfmdata then
+ break
+ else
+ specification.filename = nil
+ end
+ end
+ end
+ end
+ if tfmdata then
+ tfmdata = definers.applypostprocessors(tfmdata)
+ checkembedding(tfmdata) -- todo: general postprocessor
+ loadedfonts[hash] = tfmdata
+ designsizes[specification.hash] = tfmdata.parameters.designsize
+ checkfeatures(tfmdata)
+ end
+ end
+ if not tfmdata then
+ report_defining("font with asked name %a is not found using lookup %a",specification.name,specification.lookup)
+ end
+ return tfmdata
+end
+
+function constructors.readanddefine(name,size) -- no id -- maybe a dummy first
+ local specification = definers.analyze(name,size)
+ local method = specification.method
+ if method and variants[method] then
+ specification = variants[method](specification)
+ end
+ specification = definers.resolve(specification)
+ local hash = constructors.hashinstance(specification)
+ local id = definers.registered(hash)
+ if not id then
+ local tfmdata = definers.loadfont(specification)
+ if tfmdata then
+ tfmdata.properties.hash = hash
+ id = font.define(tfmdata)
+ definers.register(tfmdata,id)
+ else
+ id = 0 -- signal
+ end
+ end
+ return fontdata[id], id
+end
+
+--[[ldx--
+<p>So far the specifiers. Now comes the real definer. Here we cache
+based on id's. Here we also intercept the virtual font handler. Since
+it evolved stepwise I may rewrite this bit (combine code).</p>
+
+In the previously defined reader (the one resulting in a <l n='tfm'/>
+table) we cached the (scaled) instances. Here we cache them again, but
+this time based on id. We could combine this in one cache but this does
+not gain much. By the way, passing id's back to in the callback was
+introduced later in the development.</p>
+--ldx]]--
+
+function definers.current() -- or maybe current
+ return lastdefined
+end
+
+function definers.registered(hash)
+ local id = internalized[hash]
+ return id, id and fontdata[id]
+end
+
+function definers.register(tfmdata,id)
+ if tfmdata and id then
+ local hash = tfmdata.properties.hash
+ if not hash then
+ report_defining("registering font, id %a, name %a, invalid hash",id,tfmdata.properties.filename or "?")
+ elseif not internalized[hash] then
+ internalized[hash] = id
+ if trace_defining then
+ report_defining("registering font, id %s, hash %a",id,hash)
+ end
+ fontdata[id] = tfmdata
+ end
+ end
+end
+
+function definers.read(specification,size,id) -- id can be optional, name can already be table
+ statistics.starttiming(fonts)
+ if type(specification) == "string" then
+ specification = definers.analyze(specification,size)
+ end
+ local method = specification.method
+ if method and variants[method] then
+ specification = variants[method](specification)
+ end
+ specification = definers.resolve(specification)
+ local hash = constructors.hashinstance(specification)
+ local tfmdata = definers.registered(hash) -- id
+ if tfmdata then
+ if trace_defining then
+ report_defining("already hashed: %s",hash)
+ end
+ else
+ tfmdata = definers.loadfont(specification) -- can be overloaded
+ if tfmdata then
+ if trace_defining then
+ report_defining("loaded and hashed: %s",hash)
+ end
+ tfmdata.properties.hash = hash
+ if id then
+ definers.register(tfmdata,id)
+ end
+ else
+ if trace_defining then
+ report_defining("not loaded and hashed: %s",hash)
+ end
+ end
+ end
+ lastdefined = tfmdata or id -- todo ! ! ! ! !
+ if not tfmdata then -- or id?
+ report_defining( "unknown font %a, loading aborted",specification.name)
+ elseif trace_defining and type(tfmdata) == "table" then
+ local properties = tfmdata.properties or { }
+ local parameters = tfmdata.parameters or { }
+ report_defining("using %a font with id %a, name %a, size %a, bytes %a, encoding %a, fullname %a, filename %a",
+ properties.format or "unknown", id or "-", properties.name, parameters.size, properties.encodingbytes,
+ properties.encodingname, properties.fullname, basename(properties.filename))
+ end
+ statistics.stoptiming(fonts)
+ return tfmdata
+end
+
+function font.getfont(id)
+ return fontdata[id] -- otherwise issues
+end
+
+--[[ldx--
+<p>We overload the <l n='tfm'/> reader.</p>
+--ldx]]--
+
+callbacks.register('define_font', definers.read, "definition of fonts (tfmdata preparation)")
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-dsp.lua b/macros/luatex/generic/luaotfload/fontloader-font-dsp.lua
new file mode 100644
index 0000000000..79749741c3
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-dsp.lua
@@ -0,0 +1,3902 @@
+if not modules then modules = { } end modules ['font-dsp'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- many 0,0 entry/exit
+
+-- This loader went through a few iterations. First I made a ff compatible one so
+-- that we could do some basic checking. Also some verbosity was added (named
+-- glyphs). Eventually all that was dropped for a context friendly format, simply
+-- because keeping the different table models in sync too to much time. I have the
+-- old file somewhere. A positive side effect is that we get an (upto) much smaller
+-- smaller tma/tmc file. In the end the loader will be not much slower than the
+-- c based ff one.
+
+-- Being binary encoded, an opentype is rather compact. When expanded into a Lua table
+-- quite some memory can be used. This is very noticeable in the ff loader, which for
+-- a good reason uses a verbose format. However, when we use that data we create a couple
+-- of hashes. In the Lua loader we create these hashes directly, which save quite some
+-- memory.
+--
+-- We convert a font file only once and then cache it. Before creating the cached instance
+-- packing takes place: common tables get shared. After (re)loading and unpacking we then
+-- get a rather efficient internal representation of the font. In the new loader there is a
+-- pitfall. Because we use some common coverage magic we put a bit more information in
+-- the mark and cursive coverage tables than strickly needed: a reference to the coverage
+-- itself. This permits a fast lookup of the second glyph involved. In the marks we
+-- expand the class indicator to a class hash, in the cursive we use a placeholder that gets
+-- a self reference. This means that we cannot pack these subtables unless we add a unique
+-- id per entry (the same one per coverage) and that makes the tables larger. Because only a
+-- few fonts benefit from this, I decided to not do this. Experiments demonstrated that it
+-- only gives a few percent gain (on for instance husayni we can go from 845K to 828K
+-- bytecode). Better stay conceptually clean than messy compact.
+
+-- When we can reduce all basic lookups to one step we might safe a bit in the processing
+-- so then only chains are multiple.
+
+-- I used to flatten kerns here but that has been moved elsewhere because it polutes the code
+-- here and can be done fast afterwards. One can even wonder if it makes sense to do it as we
+-- pack anyway. In a similar fashion the unique placeholders in anchors in marks have been
+-- removed because packing doesn't save much there anyway.
+
+-- Although we have a bit more efficient tables in the cached files, the internals are still
+-- pretty similar. And although we have a slightly more direct coverage access the processing
+-- of node lists is not noticeable faster for latin texts, but for arabic we gain some 10%
+-- (and could probably gain a bit more).
+
+-- All this packing in the otf format is somewhat obsessive as nowadays 4K resolution
+-- multi-gig videos pass through our networks and storage and memory is abundant.
+
+-- Although we use a few table readers there i sno real gain in there (apart from having
+-- less code. After all there are often not that many demanding features.
+
+local next, type, tonumber = next, type, tonumber
+local band = bit32.band
+local extract = bit32.extract
+local bor = bit32.bor
+local lshift = bit32.lshift
+local rshift = bit32.rshift
+local gsub = string.gsub
+local lower = string.lower
+local sub = string.sub
+local strip = string.strip
+local tohash = table.tohash
+local concat = table.concat
+local copy = table.copy
+local reversed = table.reversed
+local sort = table.sort
+local insert = table.insert
+local round = math.round
+
+local settings_to_hash = utilities.parsers.settings_to_hash_colon_too
+local setmetatableindex = table.setmetatableindex
+local formatters = string.formatters
+local sortedkeys = table.sortedkeys
+local sortedhash = table.sortedhash
+local sequenced = table.sequenced
+
+local report = logs.reporter("otf reader")
+
+local readers = fonts.handlers.otf.readers
+local streamreader = readers.streamreader
+
+local setposition = streamreader.setposition
+local getposition = streamreader.getposition
+local readuinteger = streamreader.readcardinal1
+local readushort = streamreader.readcardinal2
+local readulong = streamreader.readcardinal4
+local readinteger = streamreader.readinteger1
+local readshort = streamreader.readinteger2
+local readstring = streamreader.readstring
+local readtag = streamreader.readtag
+local readbytes = streamreader.readbytes
+local readfixed = streamreader.readfixed4
+local read2dot14 = streamreader.read2dot14
+local skipshort = streamreader.skipshort
+local skipbytes = streamreader.skip
+local readbytetable = streamreader.readbytetable
+local readbyte = streamreader.readbyte
+local readcardinaltable = streamreader.readcardinaltable
+local readintegertable = streamreader.readintegertable
+local readfword = readshort
+
+local short = 2
+local ushort = 2
+local ulong = 4
+
+directives.register("fonts.streamreader",function()
+
+ streamreader = utilities.streams
+
+ setposition = streamreader.setposition
+ getposition = streamreader.getposition
+ readuinteger = streamreader.readcardinal1
+ readushort = streamreader.readcardinal2
+ readulong = streamreader.readcardinal4
+ readinteger = streamreader.readinteger1
+ readshort = streamreader.readinteger2
+ readstring = streamreader.readstring
+ readtag = streamreader.readtag
+ readbytes = streamreader.readbytes
+ readfixed = streamreader.readfixed4
+ read2dot14 = streamreader.read2dot14
+ skipshort = streamreader.skipshort
+ skipbytes = streamreader.skip
+ readbytetable = streamreader.readbytetable
+ readbyte = streamreader.readbyte
+ readcardinaltable = streamreader.readcardinaltable
+ readintegertable = streamreader.readintegertable
+ readfword = readshort
+
+end)
+
+local gsubhandlers = { }
+local gposhandlers = { }
+
+readers.gsubhandlers = gsubhandlers
+readers.gposhandlers = gposhandlers
+
+local helpers = readers.helpers
+local gotodatatable = helpers.gotodatatable
+local setvariabledata = helpers.setvariabledata
+
+local lookupidoffset = -1 -- will become 1 when we migrate (only -1 for comparign with old)
+
+local classes = {
+ "base",
+ "ligature",
+ "mark",
+ "component",
+}
+
+local gsubtypes = {
+ "single",
+ "multiple",
+ "alternate",
+ "ligature",
+ "context",
+ "chainedcontext",
+ "extension",
+ "reversechainedcontextsingle",
+}
+
+local gpostypes = {
+ "single",
+ "pair",
+ "cursive",
+ "marktobase",
+ "marktoligature",
+ "marktomark",
+ "context",
+ "chainedcontext",
+ "extension",
+}
+
+local chaindirections = {
+ context = 0,
+ chainedcontext = 1,
+ reversechainedcontextsingle = -1,
+}
+
+local function setmetrics(data,where,tag,d)
+ local w = data[where]
+ if w then
+ local v = w[tag]
+ if v then
+ -- it looks like some fonts set the value and not the delta
+ -- report("adding %s to %s.%s value %s",d,where,tag,v)
+ w[tag] = v + d
+ end
+ end
+end
+
+local variabletags = {
+ hasc = function(data,d) setmetrics(data,"windowsmetrics","typoascender",d) end,
+ hdsc = function(data,d) setmetrics(data,"windowsmetrics","typodescender",d) end,
+ hlgp = function(data,d) setmetrics(data,"windowsmetrics","typolinegap",d) end,
+ hcla = function(data,d) setmetrics(data,"windowsmetrics","winascent",d) end,
+ hcld = function(data,d) setmetrics(data,"windowsmetrics","windescent",d) end,
+ vasc = function(data,d) setmetrics(data,"vhea not done","ascent",d) end,
+ vdsc = function(data,d) setmetrics(data,"vhea not done","descent",d) end,
+ vlgp = function(data,d) setmetrics(data,"vhea not done","linegap",d) end,
+ xhgt = function(data,d) setmetrics(data,"windowsmetrics","xheight",d) end,
+ cpht = function(data,d) setmetrics(data,"windowsmetrics","capheight",d) end,
+ sbxs = function(data,d) setmetrics(data,"windowsmetrics","subscriptxsize",d) end,
+ sbys = function(data,d) setmetrics(data,"windowsmetrics","subscriptysize",d) end,
+ sbxo = function(data,d) setmetrics(data,"windowsmetrics","subscriptxoffset",d) end,
+ sbyo = function(data,d) setmetrics(data,"windowsmetrics","subscriptyoffset",d) end,
+ spxs = function(data,d) setmetrics(data,"windowsmetrics","superscriptxsize",d) end,
+ spys = function(data,d) setmetrics(data,"windowsmetrics","superscriptysize",d) end,
+ spxo = function(data,d) setmetrics(data,"windowsmetrics","superscriptxoffset",d) end,
+ spyo = function(data,d) setmetrics(data,"windowsmetrics","superscriptyoffset",d) end,
+ strs = function(data,d) setmetrics(data,"windowsmetrics","strikeoutsize",d) end,
+ stro = function(data,d) setmetrics(data,"windowsmetrics","strikeoutpos",d) end,
+ unds = function(data,d) setmetrics(data,"postscript","underlineposition",d) end,
+ undo = function(data,d) setmetrics(data,"postscript","underlinethickness",d) end,
+}
+
+local read_cardinal = {
+ streamreader.readcardinal1,
+ streamreader.readcardinal2,
+ streamreader.readcardinal3,
+ streamreader.readcardinal4,
+}
+
+local read_integer = {
+ streamreader.readinteger1,
+ streamreader.readinteger2,
+ streamreader.readinteger3,
+ streamreader.readinteger4,
+}
+
+-- Traditionally we use these unique names (so that we can flatten the lookup list
+-- (we create subsets runtime) but I will adapt the old code to newer names.
+
+-- chainsub
+-- reversesub
+
+local lookupnames = {
+ gsub = {
+ single = "gsub_single",
+ multiple = "gsub_multiple",
+ alternate = "gsub_alternate",
+ ligature = "gsub_ligature",
+ context = "gsub_context",
+ chainedcontext = "gsub_contextchain",
+ reversechainedcontextsingle = "gsub_reversecontextchain", -- reversesub
+ },
+ gpos = {
+ single = "gpos_single",
+ pair = "gpos_pair",
+ cursive = "gpos_cursive",
+ marktobase = "gpos_mark2base",
+ marktoligature = "gpos_mark2ligature",
+ marktomark = "gpos_mark2mark",
+ context = "gpos_context",
+ chainedcontext = "gpos_contextchain",
+ }
+}
+
+-- keep this as reference:
+--
+-- local lookupbits = {
+-- [0x0001] = "righttoleft",
+-- [0x0002] = "ignorebaseglyphs",
+-- [0x0004] = "ignoreligatures",
+-- [0x0008] = "ignoremarks",
+-- [0x0010] = "usemarkfilteringset",
+-- [0x00E0] = "reserved",
+-- [0xFF00] = "markattachmenttype",
+-- }
+--
+-- local lookupstate = setmetatableindex(function(t,k)
+-- local v = { }
+-- for kk, vv in next, lookupbits do
+-- if band(k,kk) ~= 0 then
+-- v[vv] = true
+-- end
+-- end
+-- t[k] = v
+-- return v
+-- end)
+
+local lookupflags = setmetatableindex(function(t,k)
+ local v = {
+ band(k,0x0008) ~= 0 and true or false, -- ignoremarks
+ band(k,0x0004) ~= 0 and true or false, -- ignoreligatures
+ band(k,0x0002) ~= 0 and true or false, -- ignorebaseglyphs
+ band(k,0x0001) ~= 0 and true or false, -- r2l
+ }
+ t[k] = v
+ return v
+end)
+
+-- Variation stores: it's not entirely clear if the regions are a shared
+-- resource (it looks like they are). Anyway, we play safe and use a
+-- share.
+
+-- values can be anything the min/max permits so we can either think of
+-- real values of a fraction along the axis (probably easier)
+
+-- wght:400,wdth:100,ital:1
+
+local function axistofactors(str)
+ local t = settings_to_hash(str)
+ for k, v in next, t do
+ t[k] = tonumber(v) or v -- this also normalizes numbers itself
+ end
+ return t
+end
+
+local hash = table.setmetatableindex(function(t,k)
+ local v = sequenced(axistofactors(k),",")
+ t[k] = v
+ return v
+end)
+
+helpers.normalizedaxishash = hash
+
+local cleanname = fonts.names and fonts.names.cleanname or function(name)
+ return name and (gsub(lower(name),"[^%a%d]","")) or nil
+end
+
+helpers.cleanname = cleanname
+
+function helpers.normalizedaxis(str)
+ return hash[str] or str
+end
+
+-- contradicting spec ... (signs) so i'll check it and fix it once we have
+-- proper fonts
+
+local function getaxisscale(segments,minimum,default,maximum,user)
+ --
+ -- returns the right values cf example in standard
+ --
+ if not minimum or not default or not maximum then
+ return false
+ end
+ if user < minimum then
+ user = minimum
+ elseif user > maximum then
+ user = maximum
+ end
+ if user < default then
+ default = - (default - user) / (default - minimum)
+ elseif user > default then
+ default = (user - default) / (maximum - default)
+ else
+ default = 0
+ end
+ if not segments then
+ return default
+ end
+ local e
+ for i=1,#segments do
+ local s = segments[i]
+ if type(s) ~= "number" then
+ report("using default axis scale")
+ return default
+ elseif s[1] >= default then
+ if s[2] == default then
+ return default
+ else
+ e = i
+ break
+ end
+ end
+ end
+ if e then
+ local b = segments[e-1]
+ local e = segments[e]
+ return b[2] + (e[2] - b[2]) * (default - b[1]) / (e[1] - b[1])
+ else
+ return false
+ end
+end
+
+local function getfactors(data,instancespec)
+ if instancespec == true then
+ -- take default
+ elseif type(instancespec) ~= "string" or instancespec == "" then
+ return
+ end
+ local variabledata = data.variabledata
+ if not variabledata then
+ return
+ end
+ local instances = variabledata.instances
+ local axis = variabledata.axis
+ local segments = variabledata.segments
+ if instances and axis then
+ local values
+ if instancespec == true then
+ -- first instance:
+ -- values = instances[1].values
+ -- axis defaults:
+ values = { }
+ for i=1,#axis do
+ values[i] = {
+ -- axis = axis[i].tag,
+ value = axis[i].default,
+ }
+ end
+
+ else
+ for i=1,#instances do
+ local instance = instances[i]
+ if cleanname(instance.subfamily) == instancespec then
+ values = instance.values
+ break
+ end
+ end
+ end
+ if values then
+ local factors = { }
+ for i=1,#axis do
+ local a = axis[i]
+ factors[i] = getaxisscale(segments,a.minimum,a.default,a.maximum,values[i].value)
+ end
+ return factors
+ end
+ local values = axistofactors(hash[instancespec] or instancespec)
+ if values then
+ local factors = { }
+ for i=1,#axis do
+ local a = axis[i]
+ local d = a.default
+ factors[i] = getaxisscale(segments,a.minimum,d,a.maximum,values[a.name or a.tag] or d)
+ end
+ return factors
+ end
+ end
+end
+
+local function getscales(regions,factors)
+ local scales = { }
+ for i=1,#regions do
+ local region = regions[i]
+ local s = 1
+ for j=1,#region do
+ local axis = region[j]
+ local f = factors[j]
+ local start = axis.start
+ local peak = axis.peak
+ local stop = axis.stop
+ -- get rid of these tests, false flag
+ if start > peak or peak > stop then
+ -- * 1
+ elseif start < 0 and stop > 0 and peak ~= 0 then
+ -- * 1
+ elseif peak == 0 then
+ -- * 1
+ elseif f < start or f > stop then
+ -- * 0
+ s = 0
+ break
+ elseif f < peak then
+ -- s = - s * (f - start) / (peak - start)
+ s = s * (f - start) / (peak - start)
+ elseif f > peak then
+ s = s * (stop - f) / (stop - peak)
+ else
+ -- * 1
+ end
+ end
+ scales[i] = s
+ end
+ return scales
+end
+
+helpers.getaxisscale = getaxisscale
+helpers.getfactors = getfactors
+helpers.getscales = getscales
+helpers.axistofactors = axistofactors
+
+local function readvariationdata(f,storeoffset,factors) -- store
+ local position = getposition(f)
+ setposition(f,storeoffset)
+ -- header
+ local format = readushort(f)
+ local regionoffset = storeoffset + readulong(f)
+ local nofdeltadata = readushort(f)
+ local deltadata = readcardinaltable(f,nofdeltadata,ulong)
+ -- regions
+ setposition(f,regionoffset)
+ local nofaxis = readushort(f)
+ local nofregions = readushort(f)
+ local regions = { }
+ for i=1,nofregions do -- 0
+ local t = { }
+ for i=1,nofaxis do
+ t[i] = { -- maybe no keys, just 1..3
+ start = read2dot14(f),
+ peak = read2dot14(f),
+ stop = read2dot14(f),
+ }
+ end
+ regions[i] = t
+ end
+ -- deltas
+ if factors then
+ for i=1,nofdeltadata do
+ setposition(f,storeoffset+deltadata[i])
+ local nofdeltasets = readushort(f)
+ local nofshorts = readushort(f)
+ local nofregions = readushort(f)
+ local usedregions = { }
+ local deltas = { }
+ for i=1,nofregions do
+ usedregions[i] = regions[readushort(f)+1]
+ end
+ -- we could test before and save a for
+ for i=1,nofdeltasets do
+ local t = readintegertable(f,nofshorts,short)
+ for i=nofshorts+1,nofregions do
+ t[i] = readinteger(f)
+ end
+ deltas[i] = t
+ end
+ deltadata[i] = {
+ regions = usedregions,
+ deltas = deltas,
+ scales = factors and getscales(usedregions,factors) or nil,
+ }
+ end
+ end
+ setposition(f,position)
+ return regions, deltadata
+end
+
+helpers.readvariationdata = readvariationdata
+
+-- Beware: only use the simple variant if we don't set keys/values (otherwise too many entries). We
+-- could also have a variant that applies a function but there is no real benefit in this.
+
+local function readcoverage(f,offset,simple)
+ setposition(f,offset)
+ local coverageformat = readushort(f)
+ if coverageformat == 1 then
+ local nofcoverage = readushort(f)
+ if simple then
+ -- often 1 or 2
+ if nofcoverage == 1 then
+ return { readushort(f) }
+ elseif nofcoverage == 2 then
+ return { readushort(f), readushort(f) }
+ else
+ return readcardinaltable(f,nofcoverage,ushort)
+ end
+ elseif nofcoverage == 1 then
+ return { [readushort(f)] = 0 }
+ elseif nofcoverage == 2 then
+ return { [readushort(f)] = 0, [readushort(f)] = 1 }
+ else
+ local coverage = { }
+ for i=0,nofcoverage-1 do
+ coverage[readushort(f)] = i -- index in record
+ end
+ return coverage
+ end
+ elseif coverageformat == 2 then
+ local nofranges = readushort(f)
+ local coverage = { }
+ local n = simple and 1 or 0 -- needs checking
+ for i=1,nofranges do
+ local firstindex = readushort(f)
+ local lastindex = readushort(f)
+ local coverindex = readushort(f)
+ if simple then
+ for i=firstindex,lastindex do
+ coverage[n] = i
+ n = n + 1
+ end
+ else
+ for i=firstindex,lastindex do
+ coverage[i] = n
+ n = n + 1
+ end
+ end
+ end
+ return coverage
+ else
+ report("unknown coverage format %a ",coverageformat)
+ return { }
+ end
+end
+
+local function readclassdef(f,offset,preset)
+ setposition(f,offset)
+ local classdefformat = readushort(f)
+ local classdef = { }
+ if type(preset) == "number" then
+ for k=0,preset-1 do
+ classdef[k] = 1
+ end
+ end
+ if classdefformat == 1 then
+ local index = readushort(f)
+ local nofclassdef = readushort(f)
+ for i=1,nofclassdef do
+ classdef[index] = readushort(f) + 1
+ index = index + 1
+ end
+ elseif classdefformat == 2 then
+ local nofranges = readushort(f)
+ local n = 0
+ for i=1,nofranges do
+ local firstindex = readushort(f)
+ local lastindex = readushort(f)
+ local class = readushort(f) + 1
+ for i=firstindex,lastindex do
+ classdef[i] = class
+ end
+ end
+ else
+ report("unknown classdef format %a ",classdefformat)
+ end
+ if type(preset) == "table" then
+ for k in next, preset do
+ if not classdef[k] then
+ classdef[k] = 1
+ end
+ end
+ end
+ return classdef
+end
+
+local function classtocoverage(defs)
+ if defs then
+ local list = { }
+ for index, class in next, defs do
+ local c = list[class]
+ if c then
+ c[#c+1] = index
+ else
+ list[class] = { index }
+ end
+ end
+ return list
+ end
+end
+
+-- extra readers
+
+local skips = { [0] =
+ 0, -- ----
+ 1, -- ---x
+ 1, -- --y-
+ 2, -- --yx
+ 1, -- -h--
+ 2, -- -h-x
+ 2, -- -hy-
+ 3, -- -hyx
+ 2, -- v--x
+ 2, -- v-y-
+ 3, -- v-yx
+ 2, -- vh--
+ 3, -- vh-x
+ 3, -- vhy-
+ 4, -- vhyx
+}
+
+-- We can assume that 0 is nothing and in fact we can start at 1 as
+-- usual in Lua to make sure of that.
+
+local function readvariation(f,offset)
+ local p = getposition(f)
+ setposition(f,offset)
+ local outer = readushort(f)
+ local inner = readushort(f)
+ local format = readushort(f)
+ setposition(f,p)
+ if format == 0x8000 then
+ return outer, inner
+ end
+end
+
+local function readposition(f,format,mainoffset,getdelta)
+ if format == 0 then
+ return false
+ end
+ -- a few happen often
+ if format == 0x04 then
+ local h = readshort(f)
+ if h == 0 then
+ return true -- all zero
+ else
+ return { 0, 0, h, 0 }
+ end
+ end
+ if format == 0x05 then
+ local x = readshort(f)
+ local h = readshort(f)
+ if x == 0 and h == 0 then
+ return true -- all zero
+ else
+ return { x, 0, h, 0 }
+ end
+ end
+ if format == 0x44 then
+ local h = readshort(f)
+ if getdelta then
+ local d = readshort(f) -- short or ushort
+ if d > 0 then
+ local outer, inner = readvariation(f,mainoffset+d)
+ if outer then
+ h = h + getdelta(outer,inner)
+ end
+ end
+ else
+ skipshort(f,1)
+ end
+ if h == 0 then
+ return true -- all zero
+ else
+ return { 0, 0, h, 0 }
+ end
+ end
+ --
+ -- todo:
+ --
+ -- if format == 0x55 then
+ -- local x = readshort(f)
+ -- local h = readshort(f)
+ -- ....
+ -- end
+ --
+ local x = band(format,0x1) ~= 0 and readshort(f) or 0 -- x placement
+ local y = band(format,0x2) ~= 0 and readshort(f) or 0 -- y placement
+ local h = band(format,0x4) ~= 0 and readshort(f) or 0 -- h advance
+ local v = band(format,0x8) ~= 0 and readshort(f) or 0 -- v advance
+ if format >= 0x10 then
+ local X = band(format,0x10) ~= 0 and skipshort(f) or 0
+ local Y = band(format,0x20) ~= 0 and skipshort(f) or 0
+ local H = band(format,0x40) ~= 0 and skipshort(f) or 0
+ local V = band(format,0x80) ~= 0 and skipshort(f) or 0
+ local s = skips[extract(format,4,4)]
+ if s > 0 then
+ skipshort(f,s)
+ end
+ if getdelta then
+ if X > 0 then
+ local outer, inner = readvariation(f,mainoffset+X)
+ if outer then
+ x = x + getdelta(outer,inner)
+ end
+ end
+ if Y > 0 then
+ local outer, inner = readvariation(f,mainoffset+Y)
+ if outer then
+ y = y + getdelta(outer,inner)
+ end
+ end
+ if H > 0 then
+ local outer, inner = readvariation(f,mainoffset+H)
+ if outer then
+ h = h + getdelta(outer,inner)
+ end
+ end
+ if V > 0 then
+ local outer, inner = readvariation(f,mainoffset+V)
+ if outer then
+ v = v + getdelta(outer,inner)
+ end
+ end
+ end
+ return { x, y, h, v }
+ elseif x == 0 and y == 0 and h == 0 and v == 0 then
+ return true -- all zero
+ else
+ return { x, y, h, v }
+ end
+end
+
+local function readanchor(f,offset,getdelta) -- maybe also ignore 0's as in pos
+ if not offset or offset == 0 then
+ return nil -- false
+ end
+ setposition(f,offset)
+ -- no need to skip as we position each
+ local format = readshort(f) -- 1: x y 2: x y index 3 x y X Y
+ local x = readshort(f)
+ local y = readshort(f)
+ if format == 3 then
+ if getdelta then
+ local X = readshort(f)
+ local Y = readshort(f)
+ if X > 0 then
+ local outer, inner = readvariation(f,offset+X)
+ if outer then
+ x = x + getdelta(outer,inner)
+ end
+ end
+ if Y > 0 then
+ local outer, inner = readvariation(f,offset+Y)
+ if outer then
+ y = y + getdelta(outer,inner)
+ end
+ end
+ else
+ skipshort(f,2)
+ end
+ return { x, y } -- , { xindex, yindex }
+ else
+ return { x, y }
+ end
+end
+
+-- common handlers: inlining can be faster but we cache anyway
+-- so we don't bother too much about speed here
+
+local function readfirst(f,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ return { readushort(f) }
+end
+
+-- quite often 0, 1, 2
+
+function readarray(f,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ local n = readushort(f)
+ if n == 1 then
+ return { readushort(f) }, 1
+ elseif n > 0 then
+ return readcardinaltable(f,n,ushort), n
+ end
+end
+
+local function readcoveragearray(f,offset,t,simple)
+ if not t then
+ return nil
+ end
+ local n = #t
+ if n == 0 then
+ return nil
+ end
+ for i=1,n do
+ t[i] = readcoverage(f,offset+t[i],simple)
+ end
+ return t
+end
+
+local function covered(subset,all)
+ local used, u
+ for i=1,#subset do
+ local s = subset[i]
+ if all[s] then
+ if used then
+ u = u + 1
+ used[u] = s
+ else
+ u = 1
+ used = { s }
+ end
+ end
+ end
+ return used
+end
+
+-- We generalize the chained lookups so that we can do with only one handler
+-- when processing them.
+
+-- pruned
+
+local function readlookuparray(f,noflookups,nofcurrent)
+ local lookups = { }
+ if noflookups > 0 then
+ local length = 0
+ for i=1,noflookups do
+ local index = readushort(f) + 1
+ if index > length then
+ length = index
+ end
+ local lookup = readushort(f) + 1
+ local list = lookups[index]
+ if list then
+ list[#list+1] = lookup
+ else
+ lookups[index] = { lookup }
+ end
+ end
+ for index=1,length do
+ if not lookups[index] then
+ lookups[index] = false
+ end
+ end
+ -- if length > nofcurrent then
+ -- report("more lookups than currently matched characters")
+ -- end
+ end
+ return lookups
+end
+
+-- not pruned
+--
+-- local function readlookuparray(f,noflookups,nofcurrent)
+-- local lookups = { }
+-- for i=1,nofcurrent do
+-- lookups[i] = false
+-- end
+-- for i=1,noflookups do
+-- local index = readushort(f) + 1
+-- if index > nofcurrent then
+-- report("more lookups than currently matched characters")
+-- for i=nofcurrent+1,index-1 do
+-- lookups[i] = false
+-- end
+-- nofcurrent = index
+-- end
+-- lookups[index] = readushort(f) + 1
+-- end
+-- return lookups
+-- end
+
+local function unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local subclasssets = readarray(f)
+ local rules = { }
+ if subclasssets then
+ coverage = readcoverage(f,tableoffset+coverage,true)
+ for i=1,#subclasssets do
+ local offset = subclasssets[i]
+ if offset > 0 then
+ local firstcoverage = coverage[i]
+ local rulesoffset = tableoffset + offset
+ local subclassrules = readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset + subclassrules[rule])
+ local nofcurrent = readushort(f)
+ local noflookups = readushort(f)
+ local current = { { firstcoverage } }
+ for i=2,nofcurrent do
+ current[i] = { readushort(f) }
+ end
+ local lookups = readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1] = {
+ current = current,
+ lookups = lookups
+ }
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","unchainedcontext",subtype)
+ end
+ return {
+ format = "glyphs",
+ rules = rules,
+ }
+ elseif subtype == 2 then
+ -- We expand the classes as later on we do a pack over the whole table so then we get
+ -- back efficiency. This way we can also apply the coverage to the first current.
+ local coverage = readushort(f)
+ local currentclassdef = readushort(f)
+ local subclasssets = readarray(f)
+ local rules = { }
+ if subclasssets then
+ coverage = readcoverage(f,tableoffset + coverage)
+ currentclassdef = readclassdef(f,tableoffset + currentclassdef,coverage)
+ local currentclasses = classtocoverage(currentclassdef,fontdata.glyphs)
+ for class=1,#subclasssets do
+ local offset = subclasssets[class]
+ if offset > 0 then
+ local firstcoverage = currentclasses[class]
+ if firstcoverage then
+ firstcoverage = covered(firstcoverage,coverage) -- bonus
+ if firstcoverage then
+ local rulesoffset = tableoffset + offset
+ local subclassrules = readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset + subclassrules[rule])
+ local nofcurrent = readushort(f)
+ local noflookups = readushort(f)
+ local current = { firstcoverage }
+ for i=2,nofcurrent do
+ current[i] = currentclasses[readushort(f) + 1]
+ end
+ local lookups = readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1] = {
+ current = current,
+ lookups = lookups
+ }
+ end
+ else
+ report("no coverage")
+ end
+ else
+ report("no coverage class")
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","unchainedcontext",subtype)
+ end
+ return {
+ format = "class",
+ rules = rules,
+ }
+ elseif subtype == 3 then
+ local nofglyphs = readushort(f)
+ local noflookups = readushort(f)
+ local current = readcardinaltable(f,nofglyphs,ushort)
+ local lookups = readlookuparray(f,noflookups,#current)
+ current = readcoveragearray(f,tableoffset,current,true)
+ return {
+ format = "coverage",
+ rules = {
+ {
+ current = current,
+ lookups = lookups,
+ }
+ }
+ }
+ else
+ report("unsupported subtype %a in %a %s",subtype,"unchainedcontext",what)
+ end
+end
+
+-- todo: optimize for n=1 ?
+
+-- class index needs checking, probably no need for +1
+
+local function chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local subclasssets = readarray(f)
+ local rules = { }
+ if subclasssets then
+ coverage = readcoverage(f,tableoffset+coverage,true)
+ for i=1,#subclasssets do
+ local offset = subclasssets[i]
+ if offset > 0 then
+ local firstcoverage = coverage[i]
+ local rulesoffset = tableoffset + offset
+ local subclassrules = readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset + subclassrules[rule])
+ local nofbefore = readushort(f)
+ local before
+ if nofbefore > 0 then
+ before = { }
+ for i=1,nofbefore do
+ before[i] = { readushort(f) }
+ end
+ end
+ local nofcurrent = readushort(f)
+ local current = { { firstcoverage } }
+ for i=2,nofcurrent do
+ current[i] = { readushort(f) }
+ end
+ local nofafter = readushort(f)
+ local after
+ if nofafter > 0 then
+ after = { }
+ for i=1,nofafter do
+ after[i] = { readushort(f) }
+ end
+ end
+ local noflookups = readushort(f)
+ local lookups = readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1] = {
+ before = before,
+ current = current,
+ after = after,
+ lookups = lookups,
+ }
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","chainedcontext",subtype)
+ end
+ return {
+ format = "glyphs",
+ rules = rules,
+ }
+ elseif subtype == 2 then
+ local coverage = readushort(f)
+ local beforeclassdef = readushort(f)
+ local currentclassdef = readushort(f)
+ local afterclassdef = readushort(f)
+ local subclasssets = readarray(f)
+ local rules = { }
+ if subclasssets then
+ local coverage = readcoverage(f,tableoffset + coverage)
+ local beforeclassdef = readclassdef(f,tableoffset + beforeclassdef,nofglyphs)
+ local currentclassdef = readclassdef(f,tableoffset + currentclassdef,coverage)
+ local afterclassdef = readclassdef(f,tableoffset + afterclassdef,nofglyphs)
+ local beforeclasses = classtocoverage(beforeclassdef,fontdata.glyphs)
+ local currentclasses = classtocoverage(currentclassdef,fontdata.glyphs)
+ local afterclasses = classtocoverage(afterclassdef,fontdata.glyphs)
+ for class=1,#subclasssets do
+ local offset = subclasssets[class]
+ if offset > 0 then
+ local firstcoverage = currentclasses[class]
+ if firstcoverage then
+ firstcoverage = covered(firstcoverage,coverage) -- bonus
+ if firstcoverage then
+ local rulesoffset = tableoffset + offset
+ local subclassrules = readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ -- watch out, in context we first get the counts and then the arrays while
+ -- here we get them mixed
+ setposition(f,rulesoffset + subclassrules[rule])
+ local nofbefore = readushort(f)
+ local before
+ if nofbefore > 0 then
+ before = { }
+ for i=1,nofbefore do
+ before[i] = beforeclasses[readushort(f) + 1]
+ end
+ end
+ local nofcurrent = readushort(f)
+ local current = { firstcoverage }
+ for i=2,nofcurrent do
+ current[i] = currentclasses[readushort(f)+ 1]
+ end
+ local nofafter = readushort(f)
+ local after
+ if nofafter > 0 then
+ after = { }
+ for i=1,nofafter do
+ after[i] = afterclasses[readushort(f) + 1]
+ end
+ end
+ -- no sequence index here (so why in context as it saves nothing)
+ local noflookups = readushort(f)
+ local lookups = readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1] = {
+ before = before,
+ current = current,
+ after = after,
+ lookups = lookups,
+ }
+ end
+ else
+ report("no coverage")
+ end
+ else
+ report("class is not covered")
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","chainedcontext",subtype)
+ end
+ return {
+ format = "class",
+ rules = rules,
+ }
+ elseif subtype == 3 then
+ local before = readarray(f)
+ local current = readarray(f)
+ local after = readarray(f)
+ local noflookups = readushort(f)
+ local lookups = readlookuparray(f,noflookups,#current)
+ before = readcoveragearray(f,tableoffset,before,true)
+ current = readcoveragearray(f,tableoffset,current,true)
+ after = readcoveragearray(f,tableoffset,after,true)
+ return {
+ format = "coverage",
+ rules = {
+ {
+ before = before,
+ current = current,
+ after = after,
+ lookups = lookups,
+ }
+ }
+ }
+ else
+ report("unsupported subtype %a in %a %s",subtype,"chainedcontext",what)
+ end
+end
+
+local function extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,types,handlers,what)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then
+ local lookuptype = types[readushort(f)]
+ local faroffset = readulong(f)
+ local handler = handlers[lookuptype]
+ if handler then
+ -- maybe we can just pass one offset (or tableoffset first)
+ return handler(f,fontdata,lookupid,tableoffset + faroffset,0,glyphs,nofglyphs), lookuptype
+ else
+ report("no handler for lookuptype %a subtype %a in %s %s",lookuptype,subtype,what,"extension")
+ end
+ else
+ report("unsupported subtype %a in %s %s",subtype,what,"extension")
+ end
+end
+
+-- gsub handlers
+
+function gsubhandlers.single(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local delta = readshort(f) -- can be negative
+ local coverage = readcoverage(f,tableoffset+coverage) -- not simple as we need to set key/value anyway
+ for index in next, coverage do
+ local newindex = (index + delta) % 65536 -- modulo is new in 1.8.3
+ if index > nofglyphs or newindex > nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)","single",subtype,index,newindex,nofglyphs)
+ coverage[index] = nil
+ else
+ coverage[index] = newindex
+ end
+ end
+ return {
+ coverage = coverage
+ }
+ elseif subtype == 2 then -- in streamreader a seek and fetch is faster than a temp table
+ local coverage = readushort(f)
+ local nofreplacements = readushort(f)
+ local replacements = readcardinaltable(f,nofreplacements,ushort)
+ local coverage = readcoverage(f,tableoffset + coverage) -- not simple as we need to set key/value anyway
+ for index, newindex in next, coverage do
+ newindex = newindex + 1
+ if index > nofglyphs or newindex > nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)","single",subtype,index,newindex,nofglyphs)
+ coverage[index] = nil
+ else
+ coverage[index] = replacements[newindex]
+ end
+ end
+ return {
+ coverage = coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"single")
+ end
+end
+
+-- we see coverage format 0x300 in some old ms fonts
+
+local function sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local nofsequence = readushort(f)
+ local sequences = readcardinaltable(f,nofsequence,ushort)
+ for i=1,nofsequence do
+ setposition(f,tableoffset + sequences[i])
+ sequences[i] = readcardinaltable(f,readushort(f),ushort)
+ end
+ local coverage = readcoverage(f,tableoffset + coverage)
+ for index, newindex in next, coverage do
+ newindex = newindex + 1
+ if index > nofglyphs or newindex > nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)",what,subtype,index,newindex,nofglyphs)
+ coverage[index] = nil
+ else
+ coverage[index] = sequences[newindex]
+ end
+ end
+ return {
+ coverage = coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,what)
+ end
+end
+
+function gsubhandlers.multiple(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"multiple")
+end
+
+function gsubhandlers.alternate(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"alternate")
+end
+
+function gsubhandlers.ligature(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local nofsets = readushort(f)
+ local ligatures = readcardinaltable(f,nofsets,ushort)
+ for i=1,nofsets do
+ local offset = lookupoffset + offset + ligatures[i]
+ setposition(f,offset)
+ local n = readushort(f)
+ if n == 1 then
+ ligatures[i] = { offset + readushort(f) }
+ else
+ local l = { }
+ for i=1,n do
+ l[i] = offset + readushort(f)
+ end
+ ligatures[i] = l
+ end
+ end
+ local coverage = readcoverage(f,tableoffset + coverage)
+ for index, newindex in next, coverage do
+ local hash = { }
+ local ligatures = ligatures[newindex+1]
+ for i=1,#ligatures do
+ local offset = ligatures[i]
+ setposition(f,offset)
+ local lig = readushort(f)
+ local cnt = readushort(f)
+ local hsh = hash
+ for i=2,cnt do
+ local c = readushort(f)
+ local h = hsh[c]
+ if not h then
+ h = { }
+ hsh[c] = h
+ end
+ hsh = h
+ end
+ hsh.ligature = lig
+ end
+ coverage[index] = hash
+ end
+ return {
+ coverage = coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"ligature")
+ end
+end
+
+function gsubhandlers.context(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"substitution"), "context"
+end
+
+function gsubhandlers.chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"substitution"), "chainedcontext"
+end
+
+function gsubhandlers.extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,gsubtypes,gsubhandlers,"substitution")
+end
+
+function gsubhandlers.reversechainedcontextsingle(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ if subtype == 1 then -- NEEDS CHECKING
+ local current = readfirst(f)
+ local before = readarray(f)
+ local after = readarray(f)
+ local replacements = readarray(f)
+ current = readcoveragearray(f,tableoffset,current,true)
+ before = readcoveragearray(f,tableoffset,before,true)
+ after = readcoveragearray(f,tableoffset,after,true)
+ return {
+ format = "reversecoverage", -- reversesub
+ rules = {
+ {
+ before = before,
+ current = current,
+ after = after,
+ replacements = replacements,
+ }
+ }
+ }, "reversechainedcontextsingle"
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"reversechainedcontextsingle")
+ end
+end
+
+-- gpos handlers
+
+local function readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+ local done = { }
+ for i=1,#sets do
+ local offset = sets[i]
+ local reused = done[offset]
+ if not reused then
+ offset = tableoffset + offset
+ setposition(f,offset)
+ local n = readushort(f)
+ reused = { }
+ for i=1,n do
+ reused[i] = {
+ readushort(f), -- second glyph id
+ readposition(f,format1,offset,getdelta),
+ readposition(f,format2,offset,getdelta),
+ }
+ end
+ done[offset] = reused
+ end
+ sets[i] = reused
+ end
+ return sets
+end
+
+local function readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,mainoffset,getdelta)
+ local classlist1 = { }
+ for i=1,nofclasses1 do
+ local classlist2 = { }
+ classlist1[i] = classlist2
+ for j=1,nofclasses2 do
+ local one = readposition(f,format1,mainoffset,getdelta)
+ local two = readposition(f,format2,mainoffset,getdelta)
+ if one or two then
+ classlist2[j] = { one, two }
+ else
+ classlist2[j] = false
+ end
+ end
+ end
+ return classlist1
+end
+
+-- no real gain in kerns as we pack
+
+function gposhandlers.single(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ local getdelta = fontdata.temporary.getdelta
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local format = readushort(f)
+ local value = readposition(f,format,tableoffset,getdelta)
+ local coverage = readcoverage(f,tableoffset+coverage)
+ for index, newindex in next, coverage do
+ coverage[index] = value -- will be packed and shared anyway
+ end
+ return {
+ format = "single",
+ coverage = coverage,
+ }
+ elseif subtype == 2 then
+ local coverage = readushort(f)
+ local format = readushort(f)
+ local nofvalues = readushort(f)
+ local values = { }
+ for i=1,nofvalues do
+ values[i] = readposition(f,format,tableoffset,getdelta)
+ end
+ local coverage = readcoverage(f,tableoffset+coverage)
+ for index, newindex in next, coverage do
+ coverage[index] = values[newindex+1]
+ end
+ return {
+ format = "single",
+ coverage = coverage,
+ }
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"single")
+ end
+end
+
+-- this needs checking! if no second pair then another advance over the list
+
+-- ValueFormat1 applies to the ValueRecord of the first glyph in each pair. ValueRecords for all first glyphs must use ValueFormat1. If ValueFormat1 is set to zero (0), the corresponding glyph has no ValueRecord and, therefore, should not be repositioned.
+-- ValueFormat2 applies to the ValueRecord of the second glyph in each pair. ValueRecords for all second glyphs must use ValueFormat2. If ValueFormat2 is set to null, then the second glyph of the pair is the “next” glyph for which a lookup should be performed.
+
+-- local simple = {
+-- [true] = { [true] = { true, true }, [false] = { true } },
+-- [false] = { [true] = { false, true }, [false] = { false } },
+-- }
+
+-- function gposhandlers.pair(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+-- local tableoffset = lookupoffset + offset
+-- setposition(f,tableoffset)
+-- local subtype = readushort(f)
+-- local getdelta = fontdata.temporary.getdelta
+-- if subtype == 1 then
+-- local coverage = readushort(f)
+-- local format1 = readushort(f)
+-- local format2 = readushort(f)
+-- local sets = readarray(f)
+-- sets = readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+-- coverage = readcoverage(f,tableoffset + coverage)
+-- local shared = { } -- partial sparse, when set also needs to be handled in the packer
+-- for index, newindex in next, coverage do
+-- local set = sets[newindex+1]
+-- local hash = { }
+-- for i=1,#set do
+-- local value = set[i]
+-- if value then
+-- local other = value[1]
+-- if shared then
+-- local s = shared[value]
+-- if s == nil then
+-- local first = value[2]
+-- local second = value[3]
+-- if first or second then
+-- s = { first, second or nil } -- needs checking
+-- else
+-- s = false
+-- end
+-- shared[value] = s
+-- end
+-- hash[other] = s or nil
+-- else
+-- local first = value[2]
+-- local second = value[3]
+-- if first or second then
+-- hash[other] = { first, second or nil } -- needs checking
+-- else
+-- hash[other] = nil -- what if set, maybe warning
+-- end
+-- end
+-- end
+-- end
+-- coverage[index] = hash
+-- end
+-- return {
+-- shared = shared and true or nil,
+-- format = "pair",
+-- coverage = coverage,
+-- }
+-- elseif subtype == 2 then
+-- local coverage = readushort(f)
+-- local format1 = readushort(f)
+-- local format2 = readushort(f)
+-- local classdef1 = readushort(f)
+-- local classdef2 = readushort(f)
+-- local nofclasses1 = readushort(f) -- incl class 0
+-- local nofclasses2 = readushort(f) -- incl class 0
+-- local classlist = readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,tableoffset,getdelta)
+-- coverage = readcoverage(f,tableoffset+coverage)
+-- classdef1 = readclassdef(f,tableoffset+classdef1,coverage)
+-- classdef2 = readclassdef(f,tableoffset+classdef2,nofglyphs)
+-- local usedcoverage = { }
+-- local shared = { } -- partial sparse, when set also needs to be handled in the packer
+-- for g1, c1 in next, classdef1 do
+-- if coverage[g1] then
+-- local l1 = classlist[c1]
+-- if l1 then
+-- local hash = { }
+-- for paired, class in next, classdef2 do
+-- local offsets = l1[class]
+-- if offsets then
+-- local first = offsets[1]
+-- local second = offsets[2]
+-- if first or second then
+-- if shared then
+-- local s1 = shared[first]
+-- if s1 == nil then
+-- s1 = { }
+-- shared[first] = s1
+-- end
+-- local s2 = s1[second]
+-- if s2 == nil then
+-- s2 = { first, second or nil }
+-- s1[second] = s2
+-- end
+-- hash[paired] = s2
+-- else
+-- hash[paired] = { first, second or nil }
+-- end
+-- else
+-- -- upto the next lookup for this combination
+-- end
+-- end
+-- end
+-- usedcoverage[g1] = hash
+-- end
+-- end
+-- end
+-- return {
+-- shared = shared and true or nil,
+-- format = "pair",
+-- coverage = usedcoverage,
+-- }
+-- elseif subtype == 3 then
+-- report("yet unsupported subtype %a in %a positioning",subtype,"pair")
+-- else
+-- report("unsupported subtype %a in %a positioning",subtype,"pair")
+-- end
+-- end
+
+function gposhandlers.pair(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ local getdelta = fontdata.temporary.getdelta
+ if subtype == 1 then
+ local coverage = readushort(f)
+ local format1 = readushort(f)
+ local format2 = readushort(f)
+ local sets = readarray(f)
+ sets = readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+ coverage = readcoverage(f,tableoffset + coverage)
+ local shared = { } -- partial sparse, when set also needs to be handled in the packer
+ for index, newindex in next, coverage do
+ local set = sets[newindex+1]
+ local hash = { }
+ for i=1,#set do
+ local value = set[i]
+ if value then
+ local other = value[1]
+ local share = shared[value]
+ if share == nil then
+ local first = value[2]
+ local second = value[3]
+ if first or second then
+ share = { first, second or nil } -- needs checking
+ else
+ share = false
+ end
+ shared[value] = share
+ end
+ hash[other] = share or nil -- really overload ?
+ end
+ end
+ coverage[index] = hash
+ end
+ return {
+ shared = shared and true or nil,
+ format = "pair",
+ coverage = coverage,
+ }
+ elseif subtype == 2 then
+ local coverage = readushort(f)
+ local format1 = readushort(f)
+ local format2 = readushort(f)
+ local classdef1 = readushort(f)
+ local classdef2 = readushort(f)
+ local nofclasses1 = readushort(f) -- incl class 0
+ local nofclasses2 = readushort(f) -- incl class 0
+ local classlist = readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,tableoffset,getdelta)
+ coverage = readcoverage(f,tableoffset+coverage)
+ classdef1 = readclassdef(f,tableoffset+classdef1,coverage)
+ classdef2 = readclassdef(f,tableoffset+classdef2,nofglyphs)
+ local usedcoverage = { }
+ local shared = { } -- partial sparse, when set also needs to be handled in the packer
+ for g1, c1 in next, classdef1 do
+ if coverage[g1] then
+ local l1 = classlist[c1]
+ if l1 then
+ local hash = { }
+ for paired, class in next, classdef2 do
+ local offsets = l1[class]
+ if offsets then
+ local first = offsets[1]
+ local second = offsets[2]
+ if first or second then
+ local s1 = shared[first]
+ if s1 == nil then
+ s1 = { }
+ shared[first] = s1
+ end
+ local s2 = s1[second]
+ if s2 == nil then
+ s2 = { first, second or nil }
+ s1[second] = s2
+ end
+ hash[paired] = s2
+ end
+ end
+ end
+ usedcoverage[g1] = hash
+ end
+ end
+ end
+ return {
+ shared = shared and true or nil,
+ format = "pair",
+ coverage = usedcoverage,
+ }
+ elseif subtype == 3 then
+ report("yet unsupported subtype %a in %a positioning",subtype,"pair")
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"pair")
+ end
+end
+
+function gposhandlers.cursive(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ local getdelta = fontdata.temporary.getdelta
+ if subtype == 1 then
+ local coverage = tableoffset + readushort(f)
+ local nofrecords = readushort(f)
+ local records = { }
+ for i=1,nofrecords do
+ local entry = readushort(f)
+ local exit = readushort(f)
+ records[i] = {
+ -- entry = entry ~= 0 and (tableoffset + entry) or false,
+ -- exit = exit ~= 0 and (tableoffset + exit ) or nil,
+ entry ~= 0 and (tableoffset + entry) or false,
+ exit ~= 0 and (tableoffset + exit ) or nil,
+ }
+ end
+ -- slot 1 will become hash after loading and it must be unique because we
+ -- pack the tables (packed we turn the cc-* into a zero)
+ local cc = (fontdata.temporary.cursivecount or 0) + 1
+ fontdata.temporary.cursivecount = cc
+ cc = "cc-" .. cc
+ coverage = readcoverage(f,coverage)
+ for i=1,nofrecords do
+ local r = records[i]
+ records[i] = {
+ -- 1,
+ cc,
+ -- readanchor(f,r.entry,getdelta) or false,
+ -- readanchor(f,r.exit, getdelta) or nil,
+ readanchor(f,r[1],getdelta) or false,
+ readanchor(f,r[2],getdelta) or nil,
+ }
+ end
+ for index, newindex in next, coverage do
+ coverage[index] = records[newindex+1]
+ end
+ return {
+ coverage = coverage,
+ }
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"cursive")
+ end
+end
+
+local function handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,ligature)
+ local tableoffset = lookupoffset + offset
+ setposition(f,tableoffset)
+ local subtype = readushort(f)
+ local getdelta = fontdata.temporary.getdelta
+ if subtype == 1 then
+ -- we are one based, not zero
+ local markcoverage = tableoffset + readushort(f)
+ local basecoverage = tableoffset + readushort(f)
+ local nofclasses = readushort(f)
+ local markoffset = tableoffset + readushort(f)
+ local baseoffset = tableoffset + readushort(f)
+ --
+ local markcoverage = readcoverage(f,markcoverage)
+ local basecoverage = readcoverage(f,basecoverage,true) -- TO BE CHECKED: true
+ --
+ setposition(f,markoffset)
+ local markclasses = { }
+ local nofmarkclasses = readushort(f)
+ --
+ local lastanchor = fontdata.lastanchor or 0
+ local usedanchors = { }
+ --
+ for i=1,nofmarkclasses do
+ local class = readushort(f) + 1
+ local offset = readushort(f)
+ if offset == 0 then
+ markclasses[i] = false
+ else
+ markclasses[i] = { class, markoffset + offset }
+ end
+ usedanchors[class] = true
+ end
+ for i=1,nofmarkclasses do
+ local mc = markclasses[i]
+ if mc then
+ mc[2] = readanchor(f,mc[2],getdelta)
+ end
+ end
+ --
+ setposition(f,baseoffset)
+ local nofbaserecords = readushort(f)
+ local baserecords = { }
+ --
+ if ligature then
+ -- 3 components
+ -- 1 : class .. nofclasses -- NULL when empty
+ -- 2 : class .. nofclasses -- NULL when empty
+ -- 3 : class .. nofclasses -- NULL when empty
+ for i=1,nofbaserecords do -- here i is the class
+ local offset = readushort(f)
+ if offset == 0 then
+ baserecords[i] = false
+ else
+ baserecords[i] = baseoffset + offset
+ end
+ end
+ for i=1,nofbaserecords do
+ local recordoffset = baserecords[i]
+ if recordoffset then
+ setposition(f,recordoffset)
+ local nofcomponents = readushort(f)
+ local components = { }
+ for i=1,nofcomponents do
+ local classes = { }
+ for i=1,nofclasses do
+ local offset = readushort(f)
+ if offset ~= 0 then
+ classes[i] = recordoffset + offset
+ else
+ classes[i] = false
+ end
+ end
+ components[i] = classes
+ end
+ baserecords[i] = components
+ end
+ end
+ local baseclasses = { } -- setmetatableindex("table")
+ for i=1,nofclasses do
+ baseclasses[i] = { }
+ end
+ for i=1,nofbaserecords do
+ local components = baserecords[i]
+ if components then
+ local b = basecoverage[i]
+ for c=1,#components do
+ local classes = components[c]
+ if classes then
+ for i=1,nofclasses do
+ local anchor = readanchor(f,classes[i],getdelta)
+ local bclass = baseclasses[i]
+ local bentry = bclass[b]
+ if bentry then
+ bentry[c] = anchor
+ else
+ bclass[b]= { [c] = anchor }
+ end
+ end
+ end
+ end
+ end
+ end
+ for index, newindex in next, markcoverage do
+ markcoverage[index] = markclasses[newindex+1] or nil
+ end
+ return {
+ format = "ligature",
+ baseclasses = baseclasses,
+ coverage = markcoverage,
+ }
+ else
+ for i=1,nofbaserecords do
+ local r = { }
+ for j=1,nofclasses do
+ local offset = readushort(f)
+ if offset == 0 then
+ r[j] = false
+ else
+ r[j] = baseoffset + offset
+ end
+ end
+ baserecords[i] = r
+ end
+ local baseclasses = { } -- setmetatableindex("table")
+ for i=1,nofclasses do
+ baseclasses[i] = { }
+ end
+ for i=1,nofbaserecords do
+ local r = baserecords[i]
+ local b = basecoverage[i]
+ for j=1,nofclasses do
+ baseclasses[j][b] = readanchor(f,r[j],getdelta)
+ end
+ end
+ for index, newindex in next, markcoverage do
+ markcoverage[index] = markclasses[newindex+1] or nil
+ end
+ -- we could actually already calculate the displacement if we want
+ return {
+ format = "base",
+ baseclasses = baseclasses,
+ coverage = markcoverage,
+ }
+ end
+ else
+ report("unsupported subtype %a in",subtype)
+ end
+
+end
+
+function gposhandlers.marktobase(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+end
+
+function gposhandlers.marktoligature(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,true)
+end
+
+function gposhandlers.marktomark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+end
+
+function gposhandlers.context(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"positioning"), "context"
+end
+
+function gposhandlers.chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"positioning"), "chainedcontext"
+end
+
+function gposhandlers.extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,gpostypes,gposhandlers,"positioning")
+end
+
+-- main loader
+
+do
+
+ local plugins = { }
+
+ function plugins.size(f,fontdata,tableoffset,feature)
+ if fontdata.designsize then
+ -- yes, there are fonts with multiple size entries ... it probably relates
+ -- to the other two fields (menu entries in some language)
+ else
+ local function check(offset)
+ setposition(f,offset)
+ local designsize = readushort(f)
+ if designsize > 0 then -- we could also have a threshold
+ local fontstyleid = readushort(f)
+ local guimenuid = readushort(f)
+ local minsize = readushort(f)
+ local maxsize = readushort(f)
+ if minsize == 0 and maxsize == 0 and fontstyleid == 0 and guimenuid == 0 then
+ minsize = designsize
+ maxsize = designsize
+ end
+ if designsize >= minsize and designsize <= maxsize then
+ return minsize, maxsize, designsize
+ end
+ end
+ end
+ local minsize, maxsize, designsize = check(tableoffset+feature.offset+feature.parameters)
+ if not designsize then
+ -- some old adobe fonts have: tableoffset+feature.parameters and we could
+ -- use some heuristic but why bother ... this extra check will be removed
+ -- some day and/or when we run into an issue
+ minsize, maxsize, designsize = check(tableoffset+feature.parameters)
+ if designsize then
+ report("bad size feature in %a, falling back to wrong offset",fontdata.filename or "?")
+ else
+ report("bad size feature in %a,",fontdata.filename or "?")
+ end
+ end
+ if designsize then
+ fontdata.minsize = minsize
+ fontdata.maxsize = maxsize
+ fontdata.designsize = designsize
+ end
+ end
+ end
+
+ -- function plugins.rvrn(f,fontdata,tableoffset,feature)
+ -- -- todo, at least a message
+ -- end
+
+ -- feature order needs checking ... as we loop over a hash ... however, in the file
+ -- they are sorted so order is not that relevant
+
+ local function reorderfeatures(fontdata,scripts,features)
+ local scriptlangs = { }
+ local featurehash = { }
+ local featureorder = { }
+ for script, languages in next, scripts do
+ for language, record in next, languages do
+ local hash = { }
+ local list = record.featureindices
+ for k=1,#list do
+ local index = list[k]
+ local feature = features[index]
+ local lookups = feature.lookups
+ local tag = feature.tag
+ if tag then
+ hash[tag] = true
+ end
+ if lookups then
+ for i=1,#lookups do
+ local lookup = lookups[i]
+ local o = featureorder[lookup]
+ if o then
+ local okay = true
+ for i=1,#o do
+ if o[i] == tag then
+ okay = false
+ break
+ end
+ end
+ if okay then
+ o[#o+1] = tag
+ end
+ else
+ featureorder[lookup] = { tag }
+ end
+ local f = featurehash[lookup]
+ if f then
+ local h = f[tag]
+ if h then
+ local s = h[script]
+ if s then
+ s[language] = true
+ else
+ h[script] = { [language] = true }
+ end
+ else
+ f[tag] = { [script] = { [language] = true } }
+ end
+ else
+ featurehash[lookup] = { [tag] = { [script] = { [language] = true } } }
+ end
+ --
+ local h = scriptlangs[tag]
+ if h then
+ local s = h[script]
+ if s then
+ s[language] = true
+ else
+ h[script] = { [language] = true }
+ end
+ else
+ scriptlangs[tag] = { [script] = { [language] = true } }
+ end
+ end
+ end
+ end
+ end
+ end
+ return scriptlangs, featurehash, featureorder
+ end
+
+ local function readscriplan(f,fontdata,scriptoffset)
+ setposition(f,scriptoffset)
+ local nofscripts = readushort(f)
+ local scripts = { }
+ for i=1,nofscripts do
+ scripts[readtag(f)] = scriptoffset + readushort(f)
+ end
+ -- script list -> language system info
+ local languagesystems = setmetatableindex("table")
+ for script, offset in next, scripts do
+ setposition(f,offset)
+ local defaultoffset = readushort(f)
+ local noflanguages = readushort(f)
+ local languages = { }
+ if defaultoffset > 0 then
+ languages.dflt = languagesystems[offset + defaultoffset]
+ end
+ for i=1,noflanguages do
+ local language = readtag(f)
+ local offset = offset + readushort(f)
+ languages[language] = languagesystems[offset]
+ end
+ scripts[script] = languages
+ end
+ -- script list -> language system info -> feature list
+ for offset, usedfeatures in next, languagesystems do
+ if offset > 0 then
+ setposition(f,offset)
+ local featureindices = { }
+ usedfeatures.featureindices = featureindices
+ usedfeatures.lookuporder = readushort(f) -- reserved, not used (yet)
+ usedfeatures.requiredindex = readushort(f) -- relates to required (can be 0xFFFF)
+ local noffeatures = readushort(f)
+ for i=1,noffeatures do
+ featureindices[i] = readushort(f) + 1
+ end
+ end
+ end
+ return scripts
+ end
+
+ local function readfeatures(f,fontdata,featureoffset)
+ setposition(f,featureoffset)
+ local features = { }
+ local noffeatures = readushort(f)
+ for i=1,noffeatures do
+ -- also shared?
+ features[i] = {
+ tag = readtag(f),
+ offset = readushort(f)
+ }
+ end
+ --
+ for i=1,noffeatures do
+ local feature = features[i]
+ local offset = featureoffset+feature.offset
+ setposition(f,offset)
+ local parameters = readushort(f) -- feature.parameters
+ local noflookups = readushort(f)
+ if noflookups > 0 then
+-- local lookups = { }
+-- feature.lookups = lookups
+-- for j=1,noflookups do
+-- lookups[j] = readushort(f) + 1
+-- end
+ local lookups = readcardinaltable(f,noflookups,ushort)
+ feature.lookups = lookups
+ for j=1,noflookups do
+ lookups[j] = lookups[j] + 1
+ end
+ end
+ if parameters > 0 then
+ feature.parameters = parameters
+ local plugin = plugins[feature.tag]
+ if plugin then
+ plugin(f,fontdata,featureoffset,feature)
+ end
+ end
+ end
+ return features
+ end
+
+ local function readlookups(f,lookupoffset,lookuptypes,featurehash,featureorder)
+ setposition(f,lookupoffset)
+ local noflookups = readushort(f)
+ local lookups = readcardinaltable(f,noflookups,ushort)
+ for lookupid=1,noflookups do
+ local offset = lookups[lookupid]
+ setposition(f,lookupoffset+offset)
+ local subtables = { }
+ local typebits = readushort(f)
+ local flagbits = readushort(f)
+ local lookuptype = lookuptypes[typebits]
+ local lookupflags = lookupflags[flagbits]
+ local nofsubtables = readushort(f)
+ for j=1,nofsubtables do
+ subtables[j] = offset + readushort(f) -- we can probably put lookupoffset here
+ end
+ -- which one wins?
+ local markclass = band(flagbits,0x0010) ~= 0 -- usemarkfilteringset
+ if markclass then
+ markclass = readushort(f) -- + 1
+ end
+ local markset = rshift(flagbits,8)
+ if markset > 0 then
+ markclass = markset -- + 1
+ end
+ lookups[lookupid] = {
+ type = lookuptype,
+ -- chain = chaindirections[lookuptype] or nil,
+ flags = lookupflags,
+ name = lookupid,
+ subtables = subtables,
+ markclass = markclass,
+ features = featurehash[lookupid], -- not if extension
+ order = featureorder[lookupid],
+ }
+ end
+ return lookups
+ end
+
+ local f_lookupname = formatters["%s_%s_%s"]
+
+ local function resolvelookups(f,lookupoffset,fontdata,lookups,lookuptypes,lookuphandlers,what,tableoffset)
+
+ local sequences = fontdata.sequences or { }
+ local sublookuplist = fontdata.sublookups or { }
+ fontdata.sequences = sequences
+ fontdata.sublookups = sublookuplist
+ local nofsublookups = #sublookuplist
+ local nofsequences = #sequences -- 0
+ local lastsublookup = nofsublookups
+ local lastsequence = nofsequences
+ local lookupnames = lookupnames[what]
+ local sublookuphash = { }
+ local sublookupcheck = { }
+ local glyphs = fontdata.glyphs
+ local nofglyphs = fontdata.nofglyphs or #glyphs
+ local noflookups = #lookups
+ local lookupprefix = sub(what,2,2) -- g[s|p][ub|os]
+ --
+ local usedlookups = false -- setmetatableindex("number")
+ --
+ for lookupid=1,noflookups do
+ local lookup = lookups[lookupid]
+ local lookuptype = lookup.type
+ local subtables = lookup.subtables
+ local features = lookup.features
+ local handler = lookuphandlers[lookuptype]
+ if handler then
+ local nofsubtables = #subtables
+ local order = lookup.order
+ local flags = lookup.flags
+ -- this is expected in the font handler (faster checking)
+ if flags[1] then flags[1] = "mark" end
+ if flags[2] then flags[2] = "ligature" end
+ if flags[3] then flags[3] = "base" end
+ --
+ local markclass = lookup.markclass
+ -- local chain = lookup.chain
+ if nofsubtables > 0 then
+ local steps = { }
+ local nofsteps = 0
+ local oldtype = nil
+ for s=1,nofsubtables do
+ local step, lt = handler(f,fontdata,lookupid,lookupoffset,subtables[s],glyphs,nofglyphs)
+ if lt then
+ lookuptype = lt
+ if oldtype and lt ~= oldtype then
+ report("messy %s lookup type %a and %a",what,lookuptype,oldtype)
+ end
+ oldtype = lookuptype
+ end
+ if not step then
+ report("unsupported %s lookup type %a",what,lookuptype)
+ else
+ nofsteps = nofsteps + 1
+ steps[nofsteps] = step
+ local rules = step.rules
+ if rules then
+ for i=1,#rules do
+ local rule = rules[i]
+ local before = rule.before
+ local current = rule.current
+ local after = rule.after
+ local replacements = rule.replacements
+ if before then
+ for i=1,#before do
+ before[i] = tohash(before[i])
+ end
+ -- as with original ctx ff loader
+ rule.before = reversed(before)
+ end
+ if current then
+ if replacements then
+ -- We have a reverse lookup and therefore only one current entry. We might need
+ -- to reverse the order in the before and after lists so that needs checking.
+ local first = current[1]
+ local hash = { }
+ local repl = { }
+ for i=1,#first do
+ local c = first[i]
+ hash[c] = true
+ repl[c] = replacements[i]
+ end
+ rule.current = { hash }
+ rule.replacements = repl
+ else
+ for i=1,#current do
+ current[i] = tohash(current[i])
+ end
+ end
+ else
+ -- weird lookup
+ end
+ if after then
+ for i=1,#after do
+ after[i] = tohash(after[i])
+ end
+ end
+ if usedlookups then
+ local lookups = rule.lookups
+ if lookups then
+ for k, v in next, lookups do
+ if v then
+ for k, v in next, v do
+ usedlookups[v] = usedlookups[v] + 1
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if nofsteps ~= nofsubtables then
+ report("bogus subtables removed in %s lookup type %a",what,lookuptype)
+ end
+ lookuptype = lookupnames[lookuptype] or lookuptype
+ if features then
+ nofsequences = nofsequences + 1
+ -- report("registering %i as sequence step %i",lookupid,nofsequences)
+ local l = {
+ index = nofsequences,
+ name = f_lookupname(lookupprefix,"s",lookupid+lookupidoffset),
+ steps = steps,
+ nofsteps = nofsteps,
+ type = lookuptype,
+ markclass = markclass or nil,
+ flags = flags,
+ -- chain = chain,
+ order = order,
+ features = features,
+ }
+ sequences[nofsequences] = l
+ lookup.done = l
+ else
+ nofsublookups = nofsublookups + 1
+ -- report("registering %i as sublookup %i",lookupid,nofsublookups)
+ local l = {
+ index = nofsublookups,
+ name = f_lookupname(lookupprefix,"l",lookupid+lookupidoffset),
+ steps = steps,
+ nofsteps = nofsteps,
+ type = lookuptype,
+ markclass = markclass or nil,
+ flags = flags,
+ -- chain = chain,
+ }
+ sublookuplist[nofsublookups] = l
+ sublookuphash[lookupid] = nofsublookups
+ sublookupcheck[lookupid] = 0
+ lookup.done = l
+ end
+ else
+ report("no subtables for lookup %a",lookupid)
+ end
+ else
+ report("no handler for lookup %a with type %a",lookupid,lookuptype)
+ end
+ end
+
+ if usedlookups then
+ report("used %s lookups: % t",what,sortedkeys(usedlookups))
+ end
+
+ -- When we have a context, we have sublookups that resolve into lookups for which we need to
+ -- know the type. We split the main lookuptable in two parts: sequences (the main lookups)
+ -- and subtable lookups (simple specs with no features). We could keep them merged and might do
+ -- that once we only use this loader. Then we can also move the simple specs into the sequence.
+ -- After all, we pack afterwards.
+
+ local reported = { }
+
+ local function report_issue(i,what,sequence,kind)
+ local name = sequence.name
+ if not reported[name] then
+ report("rule %i in %s lookup %a has %s lookups",i,what,name,kind)
+ reported[name] = true
+ end
+ end
+
+ for i=lastsequence+1,nofsequences do
+ local sequence = sequences[i]
+ local steps = sequence.steps
+ for i=1,#steps do
+ local step = steps[i]
+ local rules = step.rules
+ if rules then
+ for i=1,#rules do
+ local rule = rules[i]
+ local rlookups = rule.lookups
+ if not rlookups then
+ report_issue(i,what,sequence,"no")
+ elseif not next(rlookups) then
+ -- can be ok as it aborts a chain sequence
+ -- report_issue(i,what,sequence,"empty")
+ rule.lookups = nil
+ else
+ -- we can have holes in rlookups flagged false and we can have multiple lookups
+ -- applied (first time seen in seguemj)
+ local length = #rlookups
+ for index=1,length do
+ local lookuplist = rlookups[index]
+ if lookuplist then
+ local length = #lookuplist
+ local found = { }
+ local noffound = 0
+ for index=1,length do
+ local lookupid = lookuplist[index]
+ if lookupid then
+ local h = sublookuphash[lookupid]
+ if not h then
+ -- here we have a lookup that is used independent as well
+ -- as in another one
+ local lookup = lookups[lookupid]
+ if lookup then
+ local d = lookup.done
+ if d then
+ nofsublookups = nofsublookups + 1
+ -- report("registering %i as sublookup %i",lookupid,nofsublookups)
+ local l = {
+ index = nofsublookups, -- handy for tracing
+ name = f_lookupname(lookupprefix,"d",lookupid+lookupidoffset),
+ derived = true, -- handy for tracing
+ steps = d.steps,
+ nofsteps = d.nofsteps,
+ type = d.lookuptype or "gsub_single", -- todo: check type
+ markclass = d.markclass or nil,
+ flags = d.flags,
+ -- chain = d.chain,
+ }
+ sublookuplist[nofsublookups] = copy(l) -- we repack later
+ sublookuphash[lookupid] = nofsublookups
+ sublookupcheck[lookupid] = 1
+ h = nofsublookups
+ else
+ report_issue(i,what,sequence,"missing")
+ rule.lookups = nil
+ break
+ end
+ else
+ report_issue(i,what,sequence,"bad")
+ rule.lookups = nil
+ break
+ end
+ else
+ sublookupcheck[lookupid] = sublookupcheck[lookupid] + 1
+ end
+ if h then
+ noffound = noffound + 1
+ found[noffound] = h
+ end
+ end
+ end
+ rlookups[index] = noffound > 0 and found or false
+ else
+ rlookups[index] = false
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+
+ for i, n in sortedhash(sublookupcheck) do
+ local l = lookups[i]
+ local t = l.type
+ if n == 0 and t ~= "extension" then
+ local d = l.done
+ report("%s lookup %s of type %a is not used",what,d and d.name or l.name,t)
+ end
+ end
+
+ end
+
+ local function loadvariations(f,fontdata,variationsoffset,lookuptypes,featurehash,featureorder)
+ setposition(f,variationsoffset)
+ local version = readulong(f) -- two times readushort
+ local nofrecords = readulong(f)
+ local records = { }
+ for i=1,nofrecords do
+ records[i] = {
+ conditions = readulong(f),
+ substitutions = readulong(f),
+ }
+ end
+ for i=1,nofrecords do
+ local record = records[i]
+ local offset = record.conditions
+ if offset == 0 then
+ record.condition = nil
+ record.matchtype = "always"
+ else
+ local offset = variationsoffset+offset
+ setposition(f,offset)
+ local nofconditions = readushort(f)
+ local conditions = { }
+ for i=1,nofconditions do
+ conditions[i] = offset + readulong(f)
+ end
+ record.conditions = conditions
+ record.matchtype = "condition"
+ end
+ end
+ for i=1,nofrecords do
+ local record = records[i]
+ if record.matchtype == "condition" then
+ local conditions = record.conditions
+ for i=1,#conditions do
+ setposition(f,conditions[i])
+ conditions[i] = {
+ format = readushort(f),
+ axis = readushort(f),
+ minvalue = read2dot14(f),
+ maxvalue = read2dot14(f),
+ }
+ end
+ end
+ end
+
+ for i=1,nofrecords do
+ local record = records[i]
+ local offset = record.substitutions
+ if offset == 0 then
+ record.substitutions = { }
+ else
+ setposition(f,variationsoffset + offset)
+ local version = readulong(f)
+ local nofsubstitutions = readushort(f)
+ local substitutions = { }
+ for i=1,nofsubstitutions do
+ substitutions[readushort(f)] = readulong(f)
+ end
+ for index, alternates in sortedhash(substitutions) do
+ if index == 0 then
+ record.substitutions = false
+ else
+ local tableoffset = variationsoffset + offset + alternates
+ setposition(f,tableoffset)
+ local parameters = readulong(f) -- feature parameters
+ local noflookups = readushort(f)
+ local lookups = readcardinaltable(f,noflookups,ushort) -- not sure what to do with these
+ -- todo : resolve to proper lookups
+ record.substitutions = lookups
+ end
+ end
+ end
+ end
+ setvariabledata(fontdata,"features",records)
+ end
+
+ local function readscripts(f,fontdata,what,lookuptypes,lookuphandlers,lookupstoo)
+ local tableoffset = gotodatatable(f,fontdata,what,true)
+ if tableoffset then
+ local version = readulong(f)
+ local scriptoffset = tableoffset + readushort(f)
+ local featureoffset = tableoffset + readushort(f)
+ local lookupoffset = tableoffset + readushort(f)
+ local variationsoffset = version > 0x00010000 and (tableoffset + readulong(f)) or 0
+ if not scriptoffset then
+ return
+ end
+ local scripts = readscriplan(f,fontdata,scriptoffset)
+ local features = readfeatures(f,fontdata,featureoffset)
+ --
+ local scriptlangs, featurehash, featureorder = reorderfeatures(fontdata,scripts,features)
+ --
+ if fontdata.features then
+ fontdata.features[what] = scriptlangs
+ else
+ fontdata.features = { [what] = scriptlangs }
+ end
+ --
+ if not lookupstoo then
+ return
+ end
+ --
+ local lookups = readlookups(f,lookupoffset,lookuptypes,featurehash,featureorder)
+ --
+ if lookups then
+ resolvelookups(f,lookupoffset,fontdata,lookups,lookuptypes,lookuphandlers,what,tableoffset)
+ end
+ --
+ if variationsoffset > 0 then
+ loadvariations(f,fontdata,variationsoffset,lookuptypes,featurehash,featureorder)
+ end
+ end
+ end
+
+ local function checkkerns(f,fontdata,specification)
+ local datatable = fontdata.tables.kern
+ if not datatable then
+ return -- no kerns
+ end
+ local features = fontdata.features
+ local gposfeatures = features and features.gpos
+ local name
+ if not gposfeatures or not gposfeatures.kern then
+ name = "kern"
+ elseif specification.globalkerns then
+ name = "globalkern"
+ else
+ report("ignoring global kern table, using gpos kern feature")
+ return
+ end
+ setposition(f,datatable.offset)
+ local version = readushort(f)
+ local noftables = readushort(f)
+ if noftables > 1 then
+ report("adding global kern table as gpos feature %a",name)
+ local kerns = setmetatableindex("table")
+ for i=1,noftables do
+ local version = readushort(f)
+ local length = readushort(f)
+ local coverage = readushort(f)
+ -- bit 8-15 of coverage: format 0 or 2
+ local format = rshift(coverage,8) -- is this ok
+ if format == 0 then
+ local nofpairs = readushort(f)
+ local searchrange = readushort(f)
+ local entryselector = readushort(f)
+ local rangeshift = readushort(f)
+ for i=1,nofpairs do
+ kerns[readushort(f)][readushort(f)] = readfword(f)
+ end
+ elseif format == 2 then
+ -- apple specific so let's ignore it
+ else
+ -- not supported by ms
+ end
+ end
+ local feature = { dflt = { dflt = true } }
+ if not features then
+ fontdata.features = { gpos = { [name] = feature } }
+ elseif not gposfeatures then
+ fontdata.features.gpos = { [name] = feature }
+ else
+ gposfeatures[name] = feature
+ end
+ local sequences = fontdata.sequences
+ if not sequences then
+ sequences = { }
+ fontdata.sequences = sequences
+ end
+ local nofsequences = #sequences + 1
+ sequences[nofsequences] = {
+ index = nofsequences,
+ name = name,
+ steps = {
+ {
+ coverage = kerns,
+ format = "kern",
+ },
+ },
+ nofsteps = 1,
+ type = "gpos_pair",
+ flags = { false, false, false, false },
+ order = { name },
+ features = { [name] = feature },
+ }
+ else
+ report("ignoring empty kern table of feature %a",name)
+ end
+ end
+
+ function readers.gsub(f,fontdata,specification)
+ if specification.details then
+ readscripts(f,fontdata,"gsub",gsubtypes,gsubhandlers,specification.lookups)
+ end
+ end
+
+ function readers.gpos(f,fontdata,specification)
+ if specification.details then
+ readscripts(f,fontdata,"gpos",gpostypes,gposhandlers,specification.lookups)
+ if specification.lookups then
+ checkkerns(f,fontdata,specification)
+ end
+ end
+ end
+
+end
+
+function readers.gdef(f,fontdata,specification)
+ if not specification.glyphs then
+ return
+ end
+ local datatable = fontdata.tables.gdef
+ if datatable then
+ local tableoffset = datatable.offset
+ setposition(f,tableoffset)
+ local version = readulong(f)
+ local classoffset = readushort(f)
+ local attachmentoffset = readushort(f) -- used for bitmaps
+ local ligaturecarets = readushort(f) -- used in editors (maybe nice for tracing)
+ local markclassoffset = readushort(f)
+ local marksetsoffset = version >= 0x00010002 and readushort(f) or 0
+ local varsetsoffset = version >= 0x00010003 and readulong(f) or 0
+ local glyphs = fontdata.glyphs
+ local marks = { }
+ local markclasses = setmetatableindex("table")
+ local marksets = setmetatableindex("table")
+ fontdata.marks = marks
+ fontdata.markclasses = markclasses
+ fontdata.marksets = marksets
+ -- class definitions
+ if classoffset ~= 0 then
+ setposition(f,tableoffset + classoffset)
+ local classformat = readushort(f)
+ if classformat == 1 then
+ local firstindex = readushort(f)
+ local lastindex = firstindex + readushort(f) - 1
+ for index=firstindex,lastindex do
+ local class = classes[readushort(f)]
+ if class == "mark" then
+ marks[index] = true
+ end
+ glyphs[index].class = class
+ end
+ elseif classformat == 2 then
+ local nofranges = readushort(f)
+ for i=1,nofranges do
+ local firstindex = readushort(f)
+ local lastindex = readushort(f)
+ local class = classes[readushort(f)]
+ if class then
+ for index=firstindex,lastindex do
+ glyphs[index].class = class
+ if class == "mark" then
+ marks[index] = true
+ end
+ end
+ end
+ end
+ end
+ end
+ -- mark classes
+ if markclassoffset ~= 0 then
+ setposition(f,tableoffset + markclassoffset)
+ local classformat = readushort(f)
+ if classformat == 1 then
+ local firstindex = readushort(f)
+ local lastindex = firstindex + readushort(f) - 1
+ for index=firstindex,lastindex do
+ markclasses[readushort(f)][index] = true
+ end
+ elseif classformat == 2 then
+ local nofranges = readushort(f)
+ for i=1,nofranges do
+ local firstindex = readushort(f)
+ local lastindex = readushort(f)
+ local class = markclasses[readushort(f)]
+ for index=firstindex,lastindex do
+ class[index] = true
+ end
+ end
+ end
+ end
+ -- mark sets : todo: just make the same as class sets above
+ if marksetsoffset ~= 0 then
+ marksetsoffset = tableoffset + marksetsoffset
+ setposition(f,marksetsoffset)
+ local format = readushort(f)
+ if format == 1 then
+ local nofsets = readushort(f)
+ local sets = readcardinaltable(f,nofsets,ulong)
+ for i=1,nofsets do
+ local offset = sets[i]
+ if offset ~= 0 then
+ marksets[i] = readcoverage(f,marksetsoffset+offset)
+ end
+ end
+ end
+ end
+
+ local factors = specification.factors
+
+ if (specification.variable or factors) and varsetsoffset ~= 0 then
+
+ local regions, deltas = readvariationdata(f,tableoffset+varsetsoffset,factors)
+
+ -- setvariabledata(fontdata,"gregions",regions)
+
+ if factors then
+ fontdata.temporary.getdelta = function(outer,inner)
+ local delta = deltas[outer+1]
+ if delta then
+ local d = delta.deltas[inner+1]
+ if d then
+ local scales = delta.scales
+ local dd = 0
+ for i=1,#scales do
+ local di = d[i]
+ if di then
+ dd = dd + scales[i] * di
+ else
+ break
+ end
+ end
+ return round(dd)
+ end
+ end
+ return 0
+ end
+ end
+
+ end
+ end
+end
+
+-- We keep this code here instead of font-otm.lua because we need coverage
+-- helpers. Okay, these helpers could go to the main reader file some day.
+
+local function readmathvalue(f)
+ local v = readshort(f)
+ skipshort(f,1) -- offset to device table
+ return v
+end
+
+local function readmathconstants(f,fontdata,offset)
+ setposition(f,offset)
+ fontdata.mathconstants = {
+ ScriptPercentScaleDown = readshort(f),
+ ScriptScriptPercentScaleDown = readshort(f),
+ DelimitedSubFormulaMinHeight = readushort(f),
+ DisplayOperatorMinHeight = readushort(f),
+ MathLeading = readmathvalue(f),
+ AxisHeight = readmathvalue(f),
+ AccentBaseHeight = readmathvalue(f),
+ FlattenedAccentBaseHeight = readmathvalue(f),
+ SubscriptShiftDown = readmathvalue(f),
+ SubscriptTopMax = readmathvalue(f),
+ SubscriptBaselineDropMin = readmathvalue(f),
+ SuperscriptShiftUp = readmathvalue(f),
+ SuperscriptShiftUpCramped = readmathvalue(f),
+ SuperscriptBottomMin = readmathvalue(f),
+ SuperscriptBaselineDropMax = readmathvalue(f),
+ SubSuperscriptGapMin = readmathvalue(f),
+ SuperscriptBottomMaxWithSubscript = readmathvalue(f),
+ SpaceAfterScript = readmathvalue(f),
+ UpperLimitGapMin = readmathvalue(f),
+ UpperLimitBaselineRiseMin = readmathvalue(f),
+ LowerLimitGapMin = readmathvalue(f),
+ LowerLimitBaselineDropMin = readmathvalue(f),
+ StackTopShiftUp = readmathvalue(f),
+ StackTopDisplayStyleShiftUp = readmathvalue(f),
+ StackBottomShiftDown = readmathvalue(f),
+ StackBottomDisplayStyleShiftDown = readmathvalue(f),
+ StackGapMin = readmathvalue(f),
+ StackDisplayStyleGapMin = readmathvalue(f),
+ StretchStackTopShiftUp = readmathvalue(f),
+ StretchStackBottomShiftDown = readmathvalue(f),
+ StretchStackGapAboveMin = readmathvalue(f),
+ StretchStackGapBelowMin = readmathvalue(f),
+ FractionNumeratorShiftUp = readmathvalue(f),
+ FractionNumeratorDisplayStyleShiftUp = readmathvalue(f),
+ FractionDenominatorShiftDown = readmathvalue(f),
+ FractionDenominatorDisplayStyleShiftDown = readmathvalue(f),
+ FractionNumeratorGapMin = readmathvalue(f),
+ FractionNumeratorDisplayStyleGapMin = readmathvalue(f),
+ FractionRuleThickness = readmathvalue(f),
+ FractionDenominatorGapMin = readmathvalue(f),
+ FractionDenominatorDisplayStyleGapMin = readmathvalue(f),
+ SkewedFractionHorizontalGap = readmathvalue(f),
+ SkewedFractionVerticalGap = readmathvalue(f),
+ OverbarVerticalGap = readmathvalue(f),
+ OverbarRuleThickness = readmathvalue(f),
+ OverbarExtraAscender = readmathvalue(f),
+ UnderbarVerticalGap = readmathvalue(f),
+ UnderbarRuleThickness = readmathvalue(f),
+ UnderbarExtraDescender = readmathvalue(f),
+ RadicalVerticalGap = readmathvalue(f),
+ RadicalDisplayStyleVerticalGap = readmathvalue(f),
+ RadicalRuleThickness = readmathvalue(f),
+ RadicalExtraAscender = readmathvalue(f),
+ RadicalKernBeforeDegree = readmathvalue(f),
+ RadicalKernAfterDegree = readmathvalue(f),
+ RadicalDegreeBottomRaisePercent = readshort(f),
+ }
+end
+
+local function readmathglyphinfo(f,fontdata,offset)
+ setposition(f,offset)
+ local italics = readushort(f)
+ local accents = readushort(f)
+ local extensions = readushort(f)
+ local kerns = readushort(f)
+ local glyphs = fontdata.glyphs
+ if italics ~= 0 then
+ setposition(f,offset+italics)
+ local coverage = readushort(f)
+ local nofglyphs = readushort(f)
+ coverage = readcoverage(f,offset+italics+coverage,true)
+ setposition(f,offset+italics+4)
+ for i=1,nofglyphs do
+ local italic = readmathvalue(f)
+ if italic ~= 0 then
+ local glyph = glyphs[coverage[i]]
+ local math = glyph.math
+ if not math then
+ glyph.math = { italic = italic }
+ else
+ math.italic = italic
+ end
+ end
+ end
+ fontdata.hasitalics = true
+ end
+ if accents ~= 0 then
+ setposition(f,offset+accents)
+ local coverage = readushort(f)
+ local nofglyphs = readushort(f)
+ coverage = readcoverage(f,offset+accents+coverage,true)
+ setposition(f,offset+accents+4)
+ for i=1,nofglyphs do
+ local accent = readmathvalue(f)
+ if accent ~= 0 then
+ local glyph = glyphs[coverage[i]]
+ local math = glyph.math
+ if not math then
+ glyph.math = { accent = accent }
+ else
+ math.accent = accent
+ end
+ end
+ end
+ end
+ if extensions ~= 0 then
+ setposition(f,offset+extensions)
+ end
+ if kerns ~= 0 then
+ local kernoffset = offset + kerns
+ setposition(f,kernoffset)
+ local coverage = readushort(f)
+ local nofglyphs = readushort(f)
+ if nofglyphs > 0 then
+ local function get(offset)
+ setposition(f,kernoffset+offset)
+ local n = readushort(f)
+ if n == 0 then
+ local k = readmathvalue(f)
+ if k == 0 then
+ -- no need for it (happens sometimes)
+ else
+ return { { kern = k } }
+ end
+ else
+ local l = { }
+ for i=1,n do
+ l[i] = { height = readmathvalue(f) }
+ end
+ for i=1,n do
+ l[i].kern = readmathvalue(f)
+ end
+ l[n+1] = { kern = readmathvalue(f) }
+ return l
+ end
+ end
+ local kernsets = { }
+ for i=1,nofglyphs do
+ local topright = readushort(f)
+ local topleft = readushort(f)
+ local bottomright = readushort(f)
+ local bottomleft = readushort(f)
+ kernsets[i] = {
+ topright = topright ~= 0 and topright or nil,
+ topleft = topleft ~= 0 and topleft or nil,
+ bottomright = bottomright ~= 0 and bottomright or nil,
+ bottomleft = bottomleft ~= 0 and bottomleft or nil,
+ }
+ end
+ coverage = readcoverage(f,kernoffset+coverage,true)
+ for i=1,nofglyphs do
+ local kernset = kernsets[i]
+ if next(kernset) then
+ local k = kernset.topright if k then kernset.topright = get(k) end
+ local k = kernset.topleft if k then kernset.topleft = get(k) end
+ local k = kernset.bottomright if k then kernset.bottomright = get(k) end
+ local k = kernset.bottomleft if k then kernset.bottomleft = get(k) end
+ if next(kernset) then
+ local glyph = glyphs[coverage[i]]
+ local math = glyph.math
+ if math then
+ math.kerns = kernset
+ else
+ glyph.math = { kerns = kernset }
+ end
+ end
+ end
+ end
+ end
+ end
+end
+
+local function readmathvariants(f,fontdata,offset)
+ setposition(f,offset)
+ local glyphs = fontdata.glyphs
+ local minoverlap = readushort(f)
+ local vcoverage = readushort(f)
+ local hcoverage = readushort(f)
+ local vnofglyphs = readushort(f)
+ local hnofglyphs = readushort(f)
+ local vconstruction = readcardinaltable(f,vnofglyphs,ushort)
+ local hconstruction = readcardinaltable(f,hnofglyphs,ushort)
+
+ fontdata.mathconstants.MinConnectorOverlap = minoverlap
+
+ -- variants[i] = {
+ -- glyph = readushort(f),
+ -- advance = readushort(f),
+ -- }
+
+ local function get(offset,coverage,nofglyphs,construction,kvariants,kparts,kitalic)
+ if coverage ~= 0 and nofglyphs > 0 then
+ local coverage = readcoverage(f,offset+coverage,true)
+ for i=1,nofglyphs do
+ local c = construction[i]
+ if c ~= 0 then
+ local index = coverage[i]
+ local glyph = glyphs[index]
+ local math = glyph.math
+ setposition(f,offset+c)
+ local assembly = readushort(f)
+ local nofvariants = readushort(f)
+ if nofvariants > 0 then
+ local variants, v = nil, 0
+ for i=1,nofvariants do
+ local variant = readushort(f)
+ if variant == index then
+ -- ignore
+ elseif variants then
+ v = v + 1
+ variants[v] = variant
+ else
+ v = 1
+ variants = { variant }
+ end
+ skipshort(f)
+ end
+ if not variants then
+ -- only self
+ elseif not math then
+ math = { [kvariants] = variants }
+ glyph.math = math
+ else
+ math[kvariants] = variants
+ end
+ end
+ if assembly ~= 0 then
+ setposition(f,offset + c + assembly)
+ local italic = readmathvalue(f)
+ local nofparts = readushort(f)
+ local parts = { }
+ for i=1,nofparts do
+ local p = {
+ glyph = readushort(f),
+ start = readushort(f),
+ ["end"] = readushort(f),
+ advance = readushort(f),
+ }
+ local flags = readushort(f)
+ if band(flags,0x0001) ~= 0 then
+ p.extender = 1 -- true
+ end
+ parts[i] = p
+ end
+ if not math then
+ math = {
+ [kparts] = parts
+ }
+ glyph.math = math
+ else
+ math[kparts] = parts
+ end
+ if italic and italic ~= 0 then
+ math[kitalic] = italic
+ end
+ end
+ end
+ end
+ end
+ end
+
+ get(offset,vcoverage,vnofglyphs,vconstruction,"vvariants","vparts","vitalic")
+ get(offset,hcoverage,hnofglyphs,hconstruction,"hvariants","hparts","hitalic")
+end
+
+function readers.math(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"math",specification.glyphs)
+ if tableoffset then
+ local version = readulong(f)
+ -- if version ~= 0x00010000 then
+ -- report("table version %a of %a is not supported (yet), maybe font %s is bad",version,"math",fontdata.filename)
+ -- return
+ -- end
+ local constants = readushort(f)
+ local glyphinfo = readushort(f)
+ local variants = readushort(f)
+ if constants == 0 then
+ report("the math table of %a has no constants",fontdata.filename)
+ else
+ readmathconstants(f,fontdata,tableoffset+constants)
+ end
+ if glyphinfo ~= 0 then
+ readmathglyphinfo(f,fontdata,tableoffset+glyphinfo)
+ end
+ if variants ~= 0 then
+ readmathvariants(f,fontdata,tableoffset+variants)
+ end
+ end
+end
+
+function readers.colr(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"colr",specification.glyphs)
+ if tableoffset then
+ local version = readushort(f)
+ if version ~= 0 then
+ report("table version %a of %a is not supported (yet), maybe font %s is bad",version,"colr",fontdata.filename)
+ return
+ end
+ if not fontdata.tables.cpal then
+ report("color table %a in font %a has no mandate %a table","colr",fontdata.filename,"cpal")
+ fontdata.colorpalettes = { }
+ end
+ local glyphs = fontdata.glyphs
+ local nofglyphs = readushort(f)
+ local baseoffset = readulong(f)
+ local layeroffset = readulong(f)
+ local noflayers = readushort(f)
+ local layerrecords = { }
+ local maxclass = 0
+ -- The special value 0xFFFF is foreground (but we index from 1). It
+ -- more looks like indices into a palette so 'class' is a better name
+ -- than 'palette'.
+ setposition(f,tableoffset + layeroffset)
+ for i=1,noflayers do
+ local slot = readushort(f)
+ local class = readushort(f)
+ if class < 0xFFFF then
+ class = class + 1
+ if class > maxclass then
+ maxclass = class
+ end
+ end
+ layerrecords[i] = {
+ slot = slot,
+ class = class,
+ }
+ end
+ fontdata.maxcolorclass = maxclass
+ setposition(f,tableoffset + baseoffset)
+ for i=0,nofglyphs-1 do
+ local glyphindex = readushort(f)
+ local firstlayer = readushort(f)
+ local noflayers = readushort(f)
+ local t = { }
+ for i=1,noflayers do
+ t[i] = layerrecords[firstlayer+i]
+ end
+ glyphs[glyphindex].colors = t
+ end
+ end
+ fontdata.hascolor = true
+end
+
+function readers.cpal(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"cpal",specification.glyphs)
+ if tableoffset then
+ local version = readushort(f)
+ -- if version > 1 then
+ -- report("table version %a of %a is not supported (yet), maybe font %s is bad",version,"cpal",fontdata.filename)
+ -- return
+ -- end
+ local nofpaletteentries = readushort(f)
+ local nofpalettes = readushort(f)
+ local nofcolorrecords = readushort(f)
+ local firstcoloroffset = readulong(f)
+ local colorrecords = { }
+ local palettes = readcardinaltable(f,nofpalettes,ushort)
+ if version == 1 then
+ -- used for guis
+ local palettettypesoffset = readulong(f)
+ local palettelabelsoffset = readulong(f)
+ local paletteentryoffset = readulong(f)
+ end
+ setposition(f,tableoffset+firstcoloroffset)
+ for i=1,nofcolorrecords do
+ local b, g, r, a = readbytes(f,4)
+ colorrecords[i] = {
+ r, g, b, a ~= 255 and a or nil,
+ }
+ end
+ for i=1,nofpalettes do
+ local p = { }
+ local o = palettes[i]
+ for j=1,nofpaletteentries do
+ p[j] = colorrecords[o+j]
+ end
+ palettes[i] = p
+ end
+ fontdata.colorpalettes = palettes
+ end
+end
+
+function readers.svg(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"svg",specification.glyphs)
+ if tableoffset then
+ local version = readushort(f)
+ -- if version ~= 0 then
+ -- report("table version %a of %a is not supported (yet), maybe font %s is bad",version,"svg",fontdata.filename)
+ -- return
+ -- end
+ local glyphs = fontdata.glyphs
+ local indexoffset = tableoffset + readulong(f)
+ local reserved = readulong(f)
+ setposition(f,indexoffset)
+ local nofentries = readushort(f)
+ local entries = { }
+ for i=1,nofentries do
+ entries[i] = {
+ first = readushort(f),
+ last = readushort(f),
+ offset = indexoffset + readulong(f),
+ length = readulong(f),
+ }
+ end
+ for i=1,nofentries do
+ local entry = entries[i]
+ setposition(f,entry.offset)
+ entries[i] = {
+ first = entry.first,
+ last = entry.last,
+ data = readstring(f,entry.length)
+ }
+ end
+ fontdata.svgshapes = entries
+ end
+ fontdata.hascolor = true
+end
+
+function readers.sbix(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"sbix",specification.glyphs)
+ if tableoffset then
+ local version = readushort(f)
+ local flags = readushort(f)
+ local nofstrikes = readulong(f)
+ local strikes = { }
+ local nofglyphs = fontdata.nofglyphs
+ for i=1,nofstrikes do
+ strikes[i] = readulong(f)
+ end
+ local shapes = { }
+ local done = 0
+ for i=1,nofstrikes do
+ local strikeoffset = strikes[i] + tableoffset
+ setposition(f,strikeoffset)
+ strikes[i] = {
+ ppem = readushort(f),
+ ppi = readushort(f),
+ offset = strikeoffset
+ }
+ end
+ -- highest first
+ sort(strikes,function(a,b)
+ if b.ppem == a.ppem then
+ return b.ppi < a.ppi
+ else
+ return b.ppem < a.ppem
+ end
+ end)
+ local glyphs = { }
+ for i=1,nofstrikes do
+ local strike = strikes[i]
+ local strikeppem = strike.ppem
+ local strikeppi = strike.ppi
+ local strikeoffset = strike.offset
+ setposition(f,strikeoffset)
+ for i=0,nofglyphs do
+ glyphs[i] = readulong(f)
+ end
+ local glyphoffset = glyphs[0]
+ for i=0,nofglyphs-1 do
+ local nextoffset = glyphs[i+1]
+ if not shapes[i] then
+ local datasize = nextoffset - glyphoffset
+ if datasize > 0 then
+ setposition(f,strikeoffset + glyphoffset)
+ shapes[i] = {
+ x = readshort(f),
+ y = readshort(f),
+ tag = readtag(f), -- maybe for tracing
+ data = readstring(f,datasize-8),
+ ppem = strikeppem, -- not used, for tracing
+ ppi = strikeppi, -- not used, for tracing
+ }
+ done = done + 1
+ if done == nofglyphs then
+ break
+ end
+ end
+ end
+ glyphoffset = nextoffset
+ end
+ end
+ fontdata.pngshapes = shapes
+ end
+end
+
+-- Another bitmap (so not that useful) format. But Luigi found a font that
+-- has them , so ...
+
+do
+
+ local function getmetrics(f)
+ return {
+ ascender = readinteger(f),
+ descender = readinteger(f),
+ widthmax = readuinteger(f),
+ caretslopedumerator = readinteger(f),
+ caretslopedenominator = readinteger(f),
+ caretoffset = readinteger(f),
+ minorigin = readinteger(f),
+ minadvance = readinteger(f),
+ maxbefore = readinteger(f),
+ minafter = readinteger(f),
+ pad1 = readinteger(f),
+ pad2 = readinteger(f),
+ }
+ end
+
+ -- bad names
+
+ local function getbigmetrics(f)
+ -- bigmetrics, maybe just skip 9 bytes
+ return {
+ height = readuinteger(f),
+ width = readuinteger(f),
+ horiBearingX = readinteger(f),
+ horiBearingY = readinteger(f),
+ horiAdvance = readuinteger(f),
+ vertBearingX = readinteger(f),
+ vertBearingY = readinteger(f),
+ vertAdvance = readuinteger(f),
+ }
+ end
+
+ local function getsmallmetrics(f)
+ -- smallmetrics, maybe just skip 5 bytes
+ return {
+ height = readuinteger(f),
+ width = readuinteger(f),
+ bearingX = readinteger(f),
+ bearingY = readinteger(f),
+ advance = readuinteger(f),
+ }
+ end
+
+ function readers.cblc(f,fontdata,specification)
+ -- should we delay this ?
+ local ctdttableoffset = gotodatatable(f,fontdata,"cbdt",specification.glyphs)
+ if not ctdttableoffset then
+ return
+ end
+ local cblctableoffset = gotodatatable(f,fontdata,"cblc",specification.glyphs)
+ if cblctableoffset then
+ local majorversion = readushort(f)
+ local minorversion = readushort(f)
+ local nofsizetables = readulong(f)
+ local sizetables = { }
+ local shapes = { }
+ local subtables = { }
+ for i=1,nofsizetables do
+ sizetables[i] = {
+ subtables = readulong(f),
+ indexsize = readulong(f),
+ nofsubtables = readulong(f),
+ colorref = readulong(f),
+ hormetrics = getmetrics(f),
+ vermetrics = getmetrics(f),
+ firstindex = readushort(f),
+ lastindex = readushort(f),
+ ppemx = readbyte(f),
+ ppemy = readbyte(f),
+ bitdepth = readbyte(f),
+ flags = readbyte(f),
+ }
+ end
+ sort(sizetables,function(a,b)
+ if b.ppemx == a.ppemx then
+ return b.bitdepth < a.bitdepth
+ else
+ return b.ppemx < a.ppemx
+ end
+ end)
+ for i=1,nofsizetables do
+ local s = sizetables[i]
+ local d = false
+ for j=s.firstindex,s.lastindex do
+ if not shapes[j] then
+ shapes[j] = i
+ d = true
+ end
+ end
+ if d then
+ s.used = true
+ end
+ end
+ for i=1,nofsizetables do
+ local s = sizetables[i]
+ if s.used then
+ local offset = s.subtables
+ setposition(f,cblctableoffset+offset)
+ for j=1,s.nofsubtables do
+ local firstindex = readushort(f)
+ local lastindex = readushort(f)
+ local tableoffset = readulong(f) + offset
+ for k=firstindex,lastindex do
+ if shapes[k] == i then
+ local s = subtables[tableoffset]
+ if not s then
+ s = {
+ firstindex = firstindex,
+ lastindex = lastindex,
+ }
+ subtables[tableoffset] = s
+ end
+ shapes[k] = s
+ end
+ end
+ end
+ end
+ end
+
+ -- there is no need to sort in string stream but we have a nicer trace
+ -- if needed
+
+ for offset, subtable in sortedhash(subtables) do
+ local tabletype = readushort(f)
+ subtable.format = readushort(f)
+ local baseoffset = readulong(f) + ctdttableoffset
+ local offsets = { }
+ local metrics = nil
+ if tabletype == 1 then
+ -- we have the usual one more to get the size
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i] = readulong(f) + baseoffset
+ end
+ skipbytes(f,4)
+ elseif tabletype == 2 then
+ local size = readulong(f)
+ local done = baseoffset
+ metrics = getbigmetrics(f)
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i] = done
+ done = done + size
+ end
+ elseif tabletype == 3 then
+ -- we have the usual one more to get the size
+ local n = subtable.lastindex - subtable.firstindex + 2
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i] = readushort(f) + baseoffset
+ end
+ if math.odd(n) then
+ skipbytes(f,4)
+ else
+ skipbytes(f,2)
+ end
+ elseif tabletype == 4 then
+ for i=1,readulong(f) do
+ offsets[readushort(f)] = readushort(f) + baseoffset
+ end
+ elseif tabletype == 5 then
+ local size = readulong(f)
+ local done = baseoffset
+ metrics = getbigmetrics(f)
+ local n = readulong(f)
+ for i=1,n do
+ offsets[readushort(f)] = done
+ done = done + size
+ end
+ if math.odd(n) then
+ skipbytes(f,2)
+ end
+ else
+ return -- unsupported format
+ end
+ subtable.offsets = offsets
+ subtable.metrics = metrics
+ end
+
+ -- we only support a few sensible types ... there are hardly any fonts so
+ -- why are there so many variants ... not the best spec
+
+ local default = { width = 0, height = 0 }
+ local glyphs = fontdata.glyphs
+
+ for index, subtable in sortedhash(shapes) do
+ if type(subtable) == "table" then
+ local data = nil
+ local metrics = default
+ local format = subtable.format
+ local offset = subtable.offsets[index]
+ setposition(f,offset)
+ if format == 17 then
+ metrics = getsmallmetrics(f)
+ data = readstring(f,readulong(f))
+ elseif format == 18 then
+ metrics = getbigmetrics(f)
+ data = readstring(f,readulong(f))
+ elseif format == 19 then
+ metrics = subtable.metrics
+ data = readstring(f,readulong(f))
+ else
+ -- forget about it
+ end
+ local x = metrics.width
+ local y = metrics.height
+ shapes[index] = {
+ -- maybe some metrics
+ x = x,
+ y = y,
+ data = data,
+ }
+ -- I'll look into this in more details when needed
+ -- as we can use the bearings to get better boxes.
+ local glyph = glyphs[index]
+ if not glyph.boundingbox then
+ local width = glyph.width
+ local height = width * y/x
+ glyph.boundingbox = { 0, 0, width, height }
+ end
+
+ else
+ shapes[index] = {
+ x = 0,
+ y = 0,
+ data = "",
+ }
+ end
+ end
+
+ fontdata.pngshapes = shapes -- we cheat
+ end
+ end
+
+ function readers.cbdt(f,fontdata,specification)
+ -- local tableoffset = gotodatatable(f,fontdata,"ctdt",specification.glyphs)
+ -- if tableoffset then
+ -- local majorversion = readushort(f)
+ -- local minorversion = readushort(f)
+ -- end
+ end
+
+ -- function readers.ebdt(f,fontdata,specification)
+ -- if specification.glyphs then
+ -- end
+ -- end
+
+ -- function readers.ebsc(f,fontdata,specification)
+ -- if specification.glyphs then
+ -- end
+ -- end
+
+ -- function readers.eblc(f,fontdata,specification)
+ -- if specification.glyphs then
+ -- end
+ -- end
+
+end
+
+-- + AVAR : optional
+-- + CFF2 : otf outlines
+-- - CVAR : ttf hinting, not needed
+-- + FVAR : the variations
+-- + GVAR : ttf outline changes
+-- + HVAR : horizontal changes
+-- + MVAR : metric changes
+-- + STAT : relations within fonts
+-- * VVAR : vertical changes
+--
+-- * BASE : extra baseline adjustments
+-- - GASP : not needed
+-- + GDEF : not needed (carets)
+-- + GPOS : adapted device tables (needed?)
+-- + GSUB : new table
+-- + NAME : 25 added
+
+function readers.stat(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"stat",true) -- specification.variable
+ if tableoffset then
+ local extras = fontdata.extras
+ local version = readulong(f) -- 0x00010000
+ local axissize = readushort(f)
+ local nofaxis = readushort(f)
+ local axisoffset = readulong(f)
+ local nofvalues = readushort(f)
+ local valuesoffset = readulong(f)
+ local fallbackname = extras[readushort(f)] -- beta fonts mess up
+ local axis = { }
+ local values = { }
+ setposition(f,tableoffset+axisoffset)
+ for i=1,nofaxis do
+ local tag = readtag(f)
+ axis[i] = {
+ tag = tag,
+ name = lower(extras[readushort(f)] or tag),
+ ordering = readushort(f), -- maybe gaps
+ variants = { }
+ }
+ end
+ -- flags:
+ --
+ -- 0x0001 : OlderSiblingFontAttribute
+ -- 0x0002 : ElidableAxisValueName
+ -- 0xFFFC : reservedFlags
+ --
+ setposition(f,tableoffset+valuesoffset)
+ for i=1,nofvalues do
+ values[i] = readushort(f)
+ end
+ for i=1,nofvalues do
+ setposition(f,tableoffset + valuesoffset + values[i])
+ local format = readushort(f)
+ local index = readushort(f) + 1
+ local flags = readushort(f)
+ local name = lower(extras[readushort(f)] or "no name")
+ local value = readfixed(f)
+ local variant
+ if format == 1 then
+ variant = {
+ flags = flags,
+ name = name,
+ value = value,
+ }
+ elseif format == 2 then
+ variant = {
+ flags = flags,
+ name = name,
+ value = value,
+ minimum = readfixed(f),
+ maximum = readfixed(f),
+ }
+ elseif format == 3 then
+ variant = {
+ flags = flags,
+ name = name,
+ value = value,
+ link = readfixed(f),
+ }
+ end
+ insert(axis[index].variants,variant)
+ end
+ sort(axis,function(a,b)
+ return a.ordering < b.ordering
+ end)
+ for i=1,#axis do
+ local a = axis[i]
+ sort(a.variants,function(a,b)
+ return a.name < b.name
+ end)
+ a.ordering = nil
+ end
+ setvariabledata(fontdata,"designaxis",axis)
+ setvariabledata(fontdata,"fallbackname",fallbackname)
+ end
+end
+
+-- The avar table is optional and used in combination with fvar. Given the
+-- detailed explanation about bad values we expect the worst and do some
+-- checking.
+
+function readers.avar(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"avar",true) -- specification.variable
+ if tableoffset then
+
+ local function collect()
+ local nofvalues = readushort(f)
+ local values = { }
+ local lastfrom = false
+ local lastto = false
+ for i=1,nofvalues do
+ local from = read2dot14(f)
+ local to = read2dot14(f)
+ if lastfrom and from <= lastfrom then
+ -- ignore
+ elseif lastto and to >= lastto then
+ -- ignore
+ else
+ values[#values+1] = { from, to }
+ lastfrom, lastto = from, to
+ end
+ end
+ nofvalues = #values
+ if nofvalues > 2 then
+ local some = values[1]
+ if some[1] == -1 and some[2] == -1 then
+ some = values[nofvalues]
+ if some[1] == 1 and some[2] == 1 then
+ for i=2,nofvalues-1 do
+ some = values[i]
+ if some[1] == 0 and some[2] == 0 then
+ return values
+ end
+ end
+ end
+ end
+ end
+ return false
+ end
+
+ local version = readulong(f) -- 0x00010000
+ local reserved = readushort(f)
+ local nofaxis = readushort(f)
+ local segments = { }
+ for i=1,nofaxis do
+ segments[i] = collect()
+ end
+ setvariabledata(fontdata,"segments",segments)
+ end
+end
+
+function readers.fvar(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"fvar",true) -- specification.variable or specification.instancenames
+ if tableoffset then
+ local version = readulong(f) -- 0x00010000
+ local offsettoaxis = tableoffset + readushort(f)
+ local reserved = skipshort(f)
+ -- pair 1
+ local nofaxis = readushort(f)
+ local sizeofaxis = readushort(f)
+ -- pair 2
+ local nofinstances = readushort(f)
+ local sizeofinstances = readushort(f)
+ --
+ local extras = fontdata.extras
+ local axis = { }
+ local instances = { }
+ --
+ setposition(f,offsettoaxis)
+ --
+ for i=1,nofaxis do
+ axis[i] = {
+ tag = readtag(f), -- ital opsz slnt wdth wght
+ minimum = readfixed(f),
+ default = readfixed(f),
+ maximum = readfixed(f),
+ flags = readushort(f),
+ name = lower(extras[readushort(f)] or "bad name"),
+ }
+ local n = sizeofaxis - 20
+ if n > 0 then
+ skipbytes(f,n)
+ elseif n < 0 then
+ -- error
+ end
+ end
+ --
+ local nofbytes = 2 + 2 + 2 + nofaxis * 4
+ local readpsname = nofbytes <= sizeofinstances
+ local skippable = sizeofinstances - nofbytes
+ for i=1,nofinstances do
+ local subfamid = readushort(f)
+ local flags = readushort(f) -- 0, not used yet
+ local values = { }
+ for i=1,nofaxis do
+ values[i] = {
+ axis = axis[i].tag,
+ value = readfixed(f),
+ }
+ end
+ local psnameid = readpsname and readushort(f) or 0xFFFF
+ if subfamid == 2 or subfamid == 17 then
+ -- okay
+ elseif subfamid == 0xFFFF then
+ subfamid = nil
+ elseif subfamid <= 256 or subfamid >= 32768 then
+ subfamid = nil -- actually an error
+ end
+ if psnameid == 6 then
+ -- okay
+ elseif psnameid == 0xFFFF then
+ psnameid = nil
+ elseif psnameid <= 256 or psnameid >= 32768 then
+ psnameid = nil -- actually an error
+ end
+ instances[i] = {
+ -- flags = flags,
+ subfamily = extras[subfamid],
+ psname = psnameid and extras[psnameid] or nil,
+ values = values,
+ }
+ if skippable > 0 then
+ skipbytes(f,skippable)
+ end
+ end
+ setvariabledata(fontdata,"axis",axis)
+ setvariabledata(fontdata,"instances",instances)
+ end
+end
+
+function readers.hvar(f,fontdata,specification)
+ local factors = specification.factors
+ if not factors then
+ return
+ end
+ local tableoffset = gotodatatable(f,fontdata,"hvar",specification.variable)
+ if not tableoffset then
+ return
+ end
+
+ local version = readulong(f) -- 0x00010000
+ local variationoffset = tableoffset + readulong(f) -- the store
+ local advanceoffset = tableoffset + readulong(f)
+ local lsboffset = tableoffset + readulong(f)
+ local rsboffset = tableoffset + readulong(f)
+
+ local regions = { }
+ local variations = { }
+ local innerindex = { } -- size is mapcount
+ local outerindex = { } -- size is mapcount
+
+ if variationoffset > 0 then
+ regions, deltas = readvariationdata(f,variationoffset,factors)
+ end
+
+ if not regions then
+ -- for now .. what to do ?
+ return
+ end
+
+ if advanceoffset > 0 then
+ --
+ -- innerIndexBitCountMask = 0x000F
+ -- mapEntrySizeMask = 0x0030
+ -- reservedFlags = 0xFFC0
+ --
+ -- outerIndex = entry >> ((entryFormat & innerIndexBitCountMask) + 1)
+ -- innerIndex = entry & ((1 << ((entryFormat & innerIndexBitCountMask) + 1)) - 1)
+ --
+ setposition(f,advanceoffset)
+ local format = readushort(f) -- todo: check
+ local mapcount = readushort(f)
+ local entrysize = rshift(band(format,0x0030),4) + 1
+ local nofinnerbits = band(format,0x000F) + 1 -- n of inner bits
+ local innermask = lshift(1,nofinnerbits) - 1
+ local readcardinal = read_cardinal[entrysize] -- 1 upto 4 bytes
+ for i=0,mapcount-1 do
+ local mapdata = readcardinal(f)
+ outerindex[i] = rshift(mapdata,nofinnerbits)
+ innerindex[i] = band(mapdata,innermask)
+ end
+ -- use last entry when no match i
+ setvariabledata(fontdata,"hvarwidths",true)
+ local glyphs = fontdata.glyphs
+ for i=0,fontdata.nofglyphs-1 do
+ local glyph = glyphs[i]
+ local width = glyph.width
+ if width then
+ local outer = outerindex[i] or 0
+ local inner = innerindex[i] or i
+ if outer and inner then -- not needed
+ local delta = deltas[outer+1]
+ if delta then
+ local d = delta.deltas[inner+1]
+ if d then
+ local scales = delta.scales
+ local deltaw = 0
+ for i=1,#scales do
+ local di = d[i]
+ if di then
+ deltaw = deltaw + scales[i] * di
+ else
+ break -- can't happen
+ end
+ end
+-- report("index: %i, outer: %i, inner: %i, deltas: %|t, scales: %|t, width: %i, delta %i",
+-- i,outer,inner,d,scales,width,round(deltaw))
+ glyph.width = width + round(deltaw)
+ end
+ end
+ end
+ end
+ end
+
+ end
+
+ -- if lsboffset > 0 then
+ -- -- we don't use left side bearings
+ -- end
+
+ -- if rsboffset > 0 then
+ -- -- we don't use right side bearings
+ -- end
+
+ -- setvariabledata(fontdata,"hregions",regions)
+
+end
+
+function readers.vvar(f,fontdata,specification)
+ if not specification.variable then
+ return
+ end
+end
+
+function readers.mvar(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"mvar",specification.variable)
+ if tableoffset then
+ local version = readulong(f) -- 0x00010000
+ local reserved = skipshort(f,1)
+ local recordsize = readushort(f)
+ local nofrecords = readushort(f)
+ local offsettostore = tableoffset + readushort(f)
+ local dimensions = { }
+ local factors = specification.factors
+ if factors then
+ local regions, deltas = readvariationdata(f,offsettostore,factors)
+ for i=1,nofrecords do
+ local tag = readtag(f)
+ local var = variabletags[tag]
+ if var then
+ local outer = readushort(f)
+ local inner = readushort(f)
+ local delta = deltas[outer+1]
+ if delta then
+ local d = delta.deltas[inner+1]
+ if d then
+ local scales = delta.scales
+ local dd = 0
+ for i=1,#scales do
+ dd = dd + scales[i] * d[i]
+ end
+ var(fontdata,round(dd))
+ end
+ end
+ else
+ skipshort(f,2)
+ end
+ if recordsize > 8 then -- 4 + 2 + 2
+ skipbytes(recordsize-8)
+ end
+ end
+ end
+ -- setvariabledata(fontdata,"mregions",regions)
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-imp-effects.lua b/macros/luatex/generic/luaotfload/fontloader-font-imp-effects.lua
new file mode 100644
index 0000000000..cc6e4c0bf8
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-imp-effects.lua
@@ -0,0 +1,414 @@
+if not modules then modules = { } end modules ['font-imp-effects'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- todo: pickup from goodies: if type(effect) then ...
+
+local next, type, tonumber = next, type, tonumber
+local is_boolean = string.is_boolean
+
+local fonts = fonts
+
+local handlers = fonts.handlers
+local registerotffeature = handlers.otf.features.register
+local registerafmfeature = handlers.afm.features.register
+
+local settings_to_hash = utilities.parsers.settings_to_hash_colon_too
+
+local helpers = fonts.helpers
+local prependcommands = helpers.prependcommands
+local charcommand = helpers.commands.char
+local leftcommand = helpers.commands.left
+local rightcommand = helpers.commands.right
+local upcommand = helpers.commands.up
+local downcommand = helpers.commands.down
+local dummycommand = helpers.commands.dummy
+
+----- constructors = fonts.constructors
+----- getmathparameter = constructors.getmathparameter
+----- setmathparameter = constructors.setmathparameter
+
+local report_effect = logs.reporter("fonts","effect")
+local report_slant = logs.reporter("fonts","slant")
+local report_extend = logs.reporter("fonts","extend")
+local report_squeeze = logs.reporter("fonts","squeeze")
+
+local trace = false
+
+trackers.register("fonts.effect", function(v) trace = v end)
+trackers.register("fonts.slant", function(v) trace = v end)
+trackers.register("fonts.extend", function(v) trace = v end)
+trackers.register("fonts.squeeze",function(v) trace = v end)
+
+local function initializeslant(tfmdata,value)
+ value = tonumber(value)
+ if not value then
+ value = 0
+ elseif value > 1 then
+ value = 1
+ elseif value < -1 then
+ value = -1
+ end
+ if trace then
+ report_slant("applying %0.3f",value)
+ end
+ tfmdata.parameters.slantfactor = value
+end
+
+local specification = {
+ name = "slant",
+ description = "slant glyphs",
+ initializers = {
+ base = initializeslant,
+ node = initializeslant,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+local function initializeextend(tfmdata,value)
+ value = tonumber(value)
+ if not value then
+ value = 0
+ elseif value > 10 then
+ value = 10
+ elseif value < -10 then
+ value = -10
+ end
+ if trace then
+ report_extend("applying %0.3f",value)
+ end
+ tfmdata.parameters.extendfactor = value
+end
+
+local specification = {
+ name = "extend",
+ description = "scale glyphs horizontally",
+ initializers = {
+ base = initializeextend,
+ node = initializeextend,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+local function initializesqueeze(tfmdata,value)
+ value = tonumber(value)
+ if not value then
+ value = 0
+ elseif value > 10 then
+ value = 10
+ elseif value < -10 then
+ value = -10
+ end
+ if trace then
+ report_squeeze("applying %0.3f",value)
+ end
+ tfmdata.parameters.squeezefactor = value
+end
+
+local specification = {
+ name = "squeeze",
+ description = "scale glyphs vertically",
+ initializers = {
+ base = initializesqueeze,
+ node = initializesqueeze,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+local effects = {
+ inner = 0,
+ normal = 0,
+ outer = 1,
+ outline = 1,
+ both = 2,
+ hidden = 3,
+}
+
+local function initializeeffect(tfmdata,value)
+ local spec
+ if type(value) == "number" then
+ spec = { width = value }
+ else
+ spec = settings_to_hash(value)
+ end
+ local effect = spec.effect or "both"
+ local width = tonumber(spec.width) or 0
+ local mode = effects[effect]
+ if not mode then
+ report_effect("invalid effect %a",effect)
+ elseif width == 0 and mode == 0 then
+ report_effect("invalid width %a for effect %a",width,effect)
+ else
+ local parameters = tfmdata.parameters
+ local properties = tfmdata.properties
+ parameters.mode = mode
+ parameters.width = width * 1000
+ if is_boolean(spec.auto) == true then
+ local squeeze = 1 - width/20
+ local average = (1 - squeeze) * width * 100
+ spec.squeeze = squeeze
+ spec.extend = 1 + width/2
+ spec.wdelta = average
+ spec.hdelta = average/2
+ spec.ddelta = average/2
+ spec.vshift = average/2
+ end
+ local factor = tonumber(spec.factor) or 0
+ local hfactor = tonumber(spec.hfactor) or factor
+ local vfactor = tonumber(spec.vfactor) or factor
+ local delta = tonumber(spec.delta) or 1
+ local wdelta = tonumber(spec.wdelta) or delta
+ local hdelta = tonumber(spec.hdelta) or delta
+ local ddelta = tonumber(spec.ddelta) or hdelta
+ local vshift = tonumber(spec.vshift) or 0
+ local slant = spec.slant
+ local extend = spec.extend
+ local squeeze = spec.squeeze
+ if slant then
+ initializeslant(tfmdata,slant)
+ end
+ if extend then
+ initializeextend(tfmdata,extend)
+ end
+ if squeeze then
+ initializesqueeze(tfmdata,squeeze)
+ end
+ properties.effect = {
+ effect = effect,
+ width = width,
+ factor = factor,
+ hfactor = hfactor,
+ vfactor = vfactor,
+ wdelta = wdelta,
+ hdelta = hdelta,
+ ddelta = ddelta,
+ vshift = vshift,
+ slant = tfmdata.parameters.slantfactor,
+ extend = tfmdata.parameters.extendfactor,
+ squeeze = tfmdata.parameters.squeezefactor,
+ }
+ end
+end
+
+local rules = {
+ "RadicalRuleThickness",
+ "OverbarRuleThickness",
+ "FractionRuleThickness",
+ "UnderbarRuleThickness",
+}
+
+-- local commands = char.commands
+-- if commands then
+-- local command = commands[1]
+-- if command and command[1] == "right" then
+-- commands[1] = rightcommand[command[2]-snap]
+-- end
+-- end
+
+local function setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze)
+ if delta ~= 0 then
+ for i=1,#rules do
+ local name = rules[i]
+ local value = mathparameters[name]
+ if value then
+ mathparameters[name] = (squeeze or 1) * (value + dx)
+ end
+ end
+ end
+end
+
+local function setmathcharacters(tfmdata,characters,mathparameters,dx,dy,squeeze,wdelta,hdelta,ddelta)
+
+ local function wdpatch(char)
+ if wsnap ~= 0 then
+ char.width = char.width + wdelta/2
+ end
+ end
+
+ local function htpatch(char)
+ if hsnap ~= 0 then
+ local height = char.height
+ if height then
+ char.height = char.height + 2 * dy
+ end
+ end
+ end
+
+ local character = characters[0x221A]
+
+ if character and character.next then
+-- print("base char",0x221A,table.sequenced(character))
+ local char = character
+ local next = character.next
+ wdpatch(char)
+ htpatch(char)
+ while next do
+ char = characters[next]
+ wdpatch(char)
+ htpatch(char)
+-- print("next char",next,table.sequenced(char))
+ next = char.next
+ end
+ if char then
+ local v = char.vert_variants
+ if v then
+ local top = v[#v]
+ if top then
+ local char = characters[top.glyph]
+-- print("top char",top.glyph,table.sequenced(char))
+ htpatch(char)
+ end
+ end
+ end
+ end
+end
+
+-- local show_effect = { "lua", function(f,c)
+-- report_effect("font id %i, char %C",f,c)
+-- inspect(fonts.hashes.characters[f][c])
+-- end }
+
+-- local show_effect = { "lua", "print('!')" }
+
+local function manipulateeffect(tfmdata)
+ local effect = tfmdata.properties.effect
+ if effect then
+ local characters = tfmdata.characters
+ local parameters = tfmdata.parameters
+ local mathparameters = tfmdata.mathparameters
+ local multiplier = effect.width * 100
+ local factor = parameters.factor
+ local hfactor = parameters.hfactor
+ local vfactor = parameters.vfactor
+ local wdelta = effect.wdelta * hfactor * multiplier
+ local hdelta = effect.hdelta * vfactor * multiplier
+ local ddelta = effect.ddelta * vfactor * multiplier
+ local vshift = effect.vshift * vfactor * multiplier
+ local squeeze = effect.squeeze
+ local hshift = wdelta / 2
+ local dx = multiplier * vfactor
+ local dy = vshift
+ local factor = (1 + effect.factor) * factor
+ local hfactor = (1 + effect.hfactor) * hfactor
+ local vfactor = (1 + effect.vfactor) * vfactor
+ local vshift = vshift ~= 0 and upcommand[vshift] or false
+ for unicode, character in next, characters do
+ local oldwidth = character.width
+ local oldheight = character.height
+ local olddepth = character.depth
+ if oldwidth and oldwidth > 0 then
+ character.width = oldwidth + wdelta
+ local commands = character.commands
+ local hshift = rightcommand[hshift]
+ if vshift then
+ if commands then
+ prependcommands ( commands,
+-- show_effect,
+ hshift,
+ vshift
+ )
+ else
+ character.commands = {
+-- show_effect,
+ hshift,
+ vshift,
+ charcommand[unicode]
+ }
+ end
+ else
+ if commands then
+ prependcommands ( commands,
+-- show_effect,
+ hshift
+ )
+ else
+ character.commands = {
+-- show_effect,
+ hshift,
+ charcommand[unicode]
+ }
+ end
+ end
+ end
+ if oldheight and oldheight > 0 then
+ character.height = oldheight + hdelta
+ end
+ if olddepth and olddepth > 0 then
+ character.depth = olddepth + ddelta
+ end
+ end
+ if mathparameters then
+ setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze)
+ setmathcharacters(tfmdata,characters,mathparameters,dx,dy,squeeze,wdelta,hdelta,ddelta)
+ end
+ parameters.factor = factor
+ parameters.hfactor = hfactor
+ parameters.vfactor = vfactor
+ if trace then
+ report_effect("applying")
+ report_effect(" effect : %s", effect.effect)
+ report_effect(" width : %s => %s", effect.width, multiplier)
+ report_effect(" factor : %s => %s", effect.factor, factor )
+ report_effect(" hfactor : %s => %s", effect.hfactor,hfactor)
+ report_effect(" vfactor : %s => %s", effect.vfactor,vfactor)
+ report_effect(" wdelta : %s => %s", effect.wdelta, wdelta)
+ report_effect(" hdelta : %s => %s", effect.hdelta, hdelta)
+ report_effect(" ddelta : %s => %s", effect.ddelta, ddelta)
+ end
+ end
+end
+
+local specification = {
+ name = "effect",
+ description = "apply effects to glyphs",
+ initializers = {
+ base = initializeeffect,
+ node = initializeeffect,
+ },
+ manipulators = {
+ base = manipulateeffect,
+ node = manipulateeffect,
+ },
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+local function initializeoutline(tfmdata,value)
+ value = tonumber(value)
+ if not value then
+ value = 0
+ else
+ value = tonumber(value) or 0
+ end
+ local parameters = tfmdata.parameters
+ local properties = tfmdata.properties
+ parameters.mode = effects.outline
+ parameters.width = value * 1000
+ properties.effect = {
+ effect = effect,
+ width = width,
+ }
+end
+
+local specification = {
+ name = "outline",
+ description = "outline glyphs",
+ initializers = {
+ base = initializeoutline,
+ node = initializeoutline,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-imp-italics.lua b/macros/luatex/generic/luaotfload/fontloader-font-imp-italics.lua
new file mode 100644
index 0000000000..83c785d387
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-imp-italics.lua
@@ -0,0 +1,147 @@
+if not modules then modules = { } end modules ['font-imp-italics'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv and hand-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local next = next
+
+local fonts = fonts
+local handlers = fonts.handlers
+local registerotffeature = handlers.otf.features.register
+local registerafmfeature = handlers.afm.features.register
+
+local function initialize(tfmdata,key,value)
+ for unicode, character in next, tfmdata.characters do
+ local olditalic = character.italic
+ if olditalic and olditalic ~= 0 then
+ character.width = character.width + olditalic
+ character.italic = 0
+ end
+ end
+end
+
+local specification = {
+ name = "italicwidths",
+ description = "add italic to width",
+ manipulators = {
+ base = initialize,
+ node = initialize, -- only makes sense for math
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+local function initialize(tfmdata,value) -- hm, always value
+ if value then
+ -- the magic 40 and it formula come from Dohyun Kim but we might need another guess
+ local parameters = tfmdata.parameters
+ local italicangle = parameters.italicangle
+ if italicangle and italicangle ~= 0 then
+ local properties = tfmdata.properties
+ local factor = tonumber(value) or 1
+ properties.hasitalics = true
+ properties.autoitalicamount = factor * (parameters.uwidth or 40)/2
+ end
+ end
+end
+
+local specification = {
+ name = "itlc",
+ description = "italic correction",
+ initializers = {
+ base = initialize,
+ node = initialize,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+if context then
+
+ local function initialize(tfmdata,value) -- yes no delay
+ tfmdata.properties.textitalics = toboolean(value)
+ end
+
+ local specification = {
+ name = "textitalics",
+ description = "use alternative text italic correction",
+ initializers = {
+ base = initialize,
+ node = initialize,
+ }
+ }
+
+ registerotffeature(specification)
+ registerafmfeature(specification)
+
+end
+
+-- no longer used
+
+-- if context then
+--
+-- -- local function initializemathitalics(tfmdata,value) -- yes no delay
+-- -- tfmdata.properties.mathitalics = toboolean(value)
+-- -- end
+-- --
+-- -- local specification = {
+-- -- name = "mathitalics",
+-- -- description = "use alternative math italic correction",
+-- -- initializers = {
+-- -- base = initializemathitalics,
+-- -- node = initializemathitalics,
+-- -- }
+-- -- }
+-- --
+-- -- registerotffeature(specification)
+-- -- registerafmfeature(specification)
+--
+-- end
+
+-- -- also not used, only when testing
+
+if context then
+
+ local letter = characters.is_letter
+ local always = true
+
+ local function collapseitalics(tfmdata,key,value)
+ local threshold = value == true and 100 or tonumber(value)
+ if threshold and threshold > 0 then
+ if threshold > 100 then
+ threshold = 100
+ end
+ for unicode, data in next, tfmdata.characters do
+ if always or letter[unicode] or letter[data.unicode] then
+ local italic = data.italic
+ if italic and italic ~= 0 then
+ local width = data.width
+ if width and width ~= 0 then
+ local delta = threshold * italic / 100
+ data.width = width + delta
+ data.italic = italic - delta
+ end
+ end
+ end
+ end
+ end
+ end
+
+ local dimensions_specification = {
+ name = "collapseitalics",
+ description = "collapse italics",
+ manipulators = {
+ base = collapseitalics,
+ node = collapseitalics,
+ }
+ }
+
+ registerotffeature(dimensions_specification)
+ registerafmfeature(dimensions_specification)
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-imp-ligatures.lua b/macros/luatex/generic/luaotfload/fontloader-font-imp-ligatures.lua
new file mode 100644
index 0000000000..091eb5d4b4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-imp-ligatures.lua
@@ -0,0 +1,136 @@
+if not modules then modules = { } end modules ['font-imp-ligatures'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local lpegmatch = lpeg.match
+local utfsplit = utf.split
+local settings_to_array = utilities.parsers.settings_to_array
+
+local fonts = fonts
+local otf = fonts.handlers.otf
+local registerotffeature = otf.features.register
+local addotffeature = otf.addfeature
+
+-- This is a quick and dirty hack.
+
+local lookups = { }
+local protect = { }
+local revert = { }
+local zwjchar = 0x200C
+local zwj = { zwjchar }
+
+addotffeature {
+ name = "blockligatures",
+ type = "chainsubstitution",
+ nocheck = true, -- because there is no 0x200C in the font
+ prepend = true, -- make sure we do it early
+ future = true, -- avoid nilling due to no steps yet
+ lookups = {
+ {
+ type = "multiple",
+ data = lookups,
+ },
+ },
+ data = {
+ rules = protect,
+ }
+}
+
+addotffeature {
+ name = "blockligatures",
+ type = "chainsubstitution",
+ nocheck = true, -- because there is no 0x200C in the font
+ append = true, -- this is done late
+ overload = false, -- we don't want to overload the previous definition
+ lookups = {
+ {
+ type = "ligature",
+ data = lookups,
+ },
+ },
+ data = {
+ rules = revert,
+ }
+}
+
+registerotffeature {
+ name = 'blockligatures',
+ description = 'block certain ligatures',
+}
+
+local splitter = lpeg.splitat(":")
+
+local function blockligatures(str)
+
+ local t = settings_to_array(str)
+
+ for i=1,#t do
+ local ti = t[i]
+ local before, current, after = lpegmatch(splitter,ti)
+ if current and after then -- before is returned when no match
+ -- experimental joke
+ if before then
+ before = utfsplit(before)
+ for i=1,#before do
+ before[i] = { before[i] }
+ end
+ end
+ if current then
+ current = utfsplit(current)
+ end
+ if after then
+ after = utfsplit(after)
+ for i=1,#after do
+ after[i] = { after[i] }
+ end
+ end
+ else
+ before = nil
+ current = utfsplit(ti)
+ after = nil
+ end
+ if #current > 1 then
+ local one = current[1]
+ local two = current[2]
+ lookups[one] = { one, zwjchar }
+ local one = { one }
+ local two = { two }
+ local new = #protect + 1
+ protect[new] = {
+ before = before,
+ current = { one, two },
+ after = after,
+ lookups = { 1 }, -- not shared !
+ }
+ revert[new] = {
+ -- before = before,
+ current = { one, zwj },
+ -- after = { two, unpack(after) },
+ after = { two },
+ lookups = { 1 }, -- not shared !
+ }
+ end
+ end
+end
+
+-- blockligatures("\0\0")
+
+otf.helpers.blockligatures = blockligatures
+
+-- blockligatures("fi,ff")
+-- blockligatures("fl")
+-- blockligatures("u:fl:age")
+
+if context then
+
+ interfaces.implement {
+ name = "blockligatures",
+ arguments = "string",
+ actions = blockligatures,
+ }
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-imp-tex.lua b/macros/luatex/generic/luaotfload/fontloader-font-imp-tex.lua
new file mode 100644
index 0000000000..b4b9a7b694
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-imp-tex.lua
@@ -0,0 +1,144 @@
+if not modules then modules = { } end modules ['font-imp-tex'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local next = next
+
+local fonts = fonts
+local otf = fonts.handlers.otf
+local registerotffeature = otf.features.register
+local addotffeature = otf.addfeature
+
+-- tlig (we need numbers for some fonts so ...)
+
+local specification = {
+ type = "ligature",
+ order = { "tlig" },
+ prepend = true,
+ data = {
+ -- endash = "hyphen hyphen",
+ -- emdash = "hyphen hyphen hyphen",
+ [0x2013] = { 0x002D, 0x002D },
+ [0x2014] = { 0x002D, 0x002D, 0x002D },
+ -- quotedblleft = "quoteleft quoteleft",
+ -- quotedblright = "quoteright quoteright",
+ -- quotedblleft = "grave grave",
+ -- quotedblright = "quotesingle quotesingle",
+ -- quotedblbase = "comma comma",
+ },
+}
+
+addotffeature("tlig",specification)
+
+registerotffeature {
+ -- this makes it a known feature (in tables)
+ name = "tlig",
+ description = "tex ligatures",
+}
+
+-- trep
+
+local specification = {
+ type = "substitution",
+ order = { "trep" },
+ prepend = true,
+ data = {
+ -- [0x0022] = 0x201D,
+ [0x0027] = 0x2019,
+ -- [0x0060] = 0x2018,
+ },
+}
+
+addotffeature("trep",specification)
+
+registerotffeature {
+ -- this makes it a known feature (in tables)
+ name = "trep",
+ description = "tex replacements",
+}
+
+-- some day this will be moved to font-imp-scripts.lua
+
+-- anum
+
+local anum_arabic = {
+ [0x0030] = 0x0660,
+ [0x0031] = 0x0661,
+ [0x0032] = 0x0662,
+ [0x0033] = 0x0663,
+ [0x0034] = 0x0664,
+ [0x0035] = 0x0665,
+ [0x0036] = 0x0666,
+ [0x0037] = 0x0667,
+ [0x0038] = 0x0668,
+ [0x0039] = 0x0669,
+}
+
+local anum_persian = {
+ [0x0030] = 0x06F0,
+ [0x0031] = 0x06F1,
+ [0x0032] = 0x06F2,
+ [0x0033] = 0x06F3,
+ [0x0034] = 0x06F4,
+ [0x0035] = 0x06F5,
+ [0x0036] = 0x06F6,
+ [0x0037] = 0x06F7,
+ [0x0038] = 0x06F8,
+ [0x0039] = 0x06F9,
+}
+
+local function valid(data)
+ local features = data.resources.features
+ if features then
+ for k, v in next, features do
+ for k, v in next, v do
+ if v.arab then
+ return true
+ end
+ end
+ end
+ end
+end
+
+local specification = {
+ {
+ type = "substitution",
+ features = { arab = { urd = true, dflt = true } },
+ order = { "anum" },
+ data = anum_arabic,
+ valid = valid,
+ },
+ {
+ type = "substitution",
+ features = { arab = { urd = true } },
+ order = { "anum" },
+ data = anum_persian,
+ valid = valid,
+ },
+}
+
+addotffeature("anum",specification)
+
+registerotffeature {
+ -- this makes it a known feature (in tables)
+ name = "anum",
+ description = "arabic digits",
+}
+
+-- -- example:
+--
+-- fonts.handlers.otf.addfeature {
+-- name = "hangulfix",
+-- type = "substitution",
+-- features = { ["hang"] = { ["*"] = true } },
+-- data = {
+-- [0x1160] = 0x119E,
+-- },
+-- order = { "hangulfix" },
+-- flags = { },
+-- prepend = true,
+-- })
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-ini.lua b/macros/luatex/generic/luaotfload/fontloader-font-ini.lua
new file mode 100644
index 0000000000..462e30bf90
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-ini.lua
@@ -0,0 +1,54 @@
+if not modules then modules = { } end modules ['font-ini'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+--[[ldx--
+<p>Not much is happening here.</p>
+--ldx]]--
+
+local allocate = utilities.storage.allocate
+local sortedhash = table.sortedhash
+
+fonts = fonts or { }
+local fonts = fonts
+
+local identifiers = allocate()
+
+fonts.hashes = fonts.hashes or { identifiers = identifiers }
+fonts.tables = fonts.tables or { }
+fonts.helpers = fonts.helpers or { }
+fonts.tracers = fonts.tracers or { } -- for the moment till we have move to moduledata
+fonts.specifiers = fonts.specifiers or { } -- in format !
+
+fonts.analyzers = { } -- not needed here
+fonts.readers = { }
+fonts.definers = { methods = { } }
+fonts.loggers = { register = function() end }
+
+if context then
+
+ font.originaleach = font.each
+
+ function font.each()
+ return sortedhash(identifiers)
+ end
+
+ fontloader = nil
+
+end
+
+-- Outside context one can bump textbase to some higher value but only the
+-- textbase given here is officially supported (read: bug testing etc will
+-- use the values below).
+
+fonts.privateoffsets = {
+ textbase = 0xF0000, -- used for hidden (opentype features)
+ textextrabase = 0xFD000, -- used for visible by name
+ mathextrabase = 0xFE000, -- used for visible by code
+ mathbase = 0xFF000, -- used for hidden (virtual math)
+ keepnames = false, -- when set to true names are always kept (not for context)
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-lua.lua b/macros/luatex/generic/luaotfload/fontloader-font-lua.lua
new file mode 100644
index 0000000000..6fbbcf17e4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-lua.lua
@@ -0,0 +1,46 @@
+if not modules then modules = { } end modules ['font-lua'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local trace_defining = false trackers.register("fonts.defining", function(v) trace_defining = v end)
+
+local report_lua = logs.reporter("fonts","lua loading")
+
+local fonts = fonts
+local readers = fonts.readers
+fonts.formats.lua = "lua"
+
+-- we could add support for features here
+
+local function check_lua(specification,fullname)
+ -- standard tex file lookup
+ local fullname = resolvers.findfile(fullname) or ""
+ if fullname ~= "" then
+ local loader = loadfile(fullname)
+ loader = loader and loader()
+ return loader and loader(specification)
+ end
+end
+
+readers.check_lua = check_lua
+
+function readers.lua(specification)
+ local original = specification.specification
+ if trace_defining then
+ report_lua("using lua reader for %a",original)
+ end
+ local fullname = specification.filename or ""
+ if fullname == "" then
+ local forced = specification.forced or ""
+ if forced ~= "" then
+ fullname = specification.name .. "." .. forced
+ else
+ fullname = specification.name
+ end
+ end
+ return check_lua(specification,fullname)
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-map.lua b/macros/luatex/generic/luaotfload/fontloader-font-map.lua
new file mode 100644
index 0000000000..d931b822e5
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-map.lua
@@ -0,0 +1,693 @@
+if not modules then modules = { } end modules ['font-map'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local tonumber, next, type = tonumber, next, type
+
+local match, format, find, concat, gsub, lower = string.match, string.format, string.find, table.concat, string.gsub, string.lower
+local P, R, S, C, Ct, Cc, lpegmatch = lpeg.P, lpeg.R, lpeg.S, lpeg.C, lpeg.Ct, lpeg.Cc, lpeg.match
+local formatters = string.formatters
+local sortedhash, sortedkeys = table.sortedhash, table.sortedkeys
+local rshift = bit32.rshift
+
+local trace_loading = false trackers.register("fonts.loading", function(v) trace_loading = v end)
+local trace_mapping = false trackers.register("fonts.mapping", function(v) trace_mapping = v end)
+
+local report_fonts = logs.reporter("fonts","loading") -- not otf only
+
+-- force_ligatures was true for a while so that these emoji's with bad names work too
+
+local force_ligatures = false directives.register("fonts.mapping.forceligatures",function(v) force_ligatures = v end)
+
+local fonts = fonts or { }
+local mappings = fonts.mappings or { }
+fonts.mappings = mappings
+
+local allocate = utilities.storage.allocate
+
+--[[ldx--
+<p>Eventually this code will disappear because map files are kind
+of obsolete. Some code may move to runtime or auxiliary modules.</p>
+<p>The name to unciode related code will stay of course.</p>
+--ldx]]--
+
+-- local function loadlumtable(filename) -- will move to font goodies
+-- local lumname = file.replacesuffix(file.basename(filename),"lum")
+-- local lumfile = resolvers.findfile(lumname,"map") or ""
+-- if lumfile ~= "" and lfs.isfile(lumfile) then
+-- if trace_loading or trace_mapping then
+-- report_fonts("loading map table %a",lumfile)
+-- end
+-- lumunic = dofile(lumfile)
+-- return lumunic, lumfile
+-- end
+-- end
+
+local hex = R("AF","af","09")
+----- hexfour = (hex*hex*hex*hex) / function(s) return tonumber(s,16) end
+----- hexsix = (hex*hex*hex*hex*hex*hex) / function(s) return tonumber(s,16) end
+local hexfour = (hex*hex*hex^-2) / function(s) return tonumber(s,16) end
+local hexsix = (hex*hex*hex^-4) / function(s) return tonumber(s,16) end
+local dec = (R("09")^1) / tonumber
+local period = P(".")
+local unicode = (P("uni") + P("UNI")) * (hexfour * (period + P(-1)) * Cc(false) + Ct(hexfour^1) * Cc(true)) -- base planes
+local ucode = (P("u") + P("U") ) * (hexsix * (period + P(-1)) * Cc(false) + Ct(hexsix ^1) * Cc(true)) -- extended
+local index = P("index") * dec * Cc(false)
+
+local parser = unicode + ucode + index
+
+local parsers = { }
+
+local function makenameparser(str)
+ if not str or str == "" then
+ return parser
+ else
+ local p = parsers[str]
+ if not p then
+ p = P(str) * period * dec * Cc(false)
+ parsers[str] = p
+ end
+ return p
+ end
+end
+
+local f_single = formatters["%04X"]
+local f_double = formatters["%04X%04X"]
+
+-- floor(x/256) => rshift(x, 8)
+-- floor(x/1024) => rshift(x,10)
+
+-- 0.684 0.661 0,672 0.650 : cache at lua end (more mem)
+-- 0.682 0,672 0.698 0.657 : no cache (moderate mem i.e. lua strings)
+-- 0.644 0.647 0.655 0.645 : convert in c (less mem in theory)
+
+-- local tounicodes = table.setmetatableindex(function(t,unicode)
+-- local s
+-- if unicode < 0xD7FF or (unicode > 0xDFFF and unicode <= 0xFFFF) then
+-- s = f_single(unicode)
+-- else
+-- unicode = unicode - 0x10000
+-- s = f_double(rshift(unicode,10)+0xD800,unicode%1024+0xDC00)
+-- end
+-- t[unicode] = s
+-- return s
+-- end)
+--
+-- local function tounicode16(unicode,name)
+-- local s = tounicodes[unicode]
+-- if s then
+-- return s
+-- else
+-- report_fonts("can't convert %a in %a into tounicode",unicode,name)
+-- end
+-- end
+--
+-- local function tounicode16sequence(unicodes,name)
+-- local t = { }
+-- for l=1,#unicodes do
+-- local u = unicodes[l]
+-- local s = tounicodes[u]
+-- if s then
+-- t[l] = s
+-- else
+-- report_fonts ("can't convert %a in %a into tounicode",u,name)
+-- return
+-- end
+-- end
+-- return concat(t)
+-- end
+--
+-- local function tounicode(unicode,name)
+-- if type(unicode) == "table" then
+-- local t = { }
+-- for l=1,#unicode do
+-- local u = unicode[l]
+-- local s = tounicodes[u]
+-- if s then
+-- t[l] = s
+-- else
+-- report_fonts ("can't convert %a in %a into tounicode",u,name)
+-- return
+-- end
+-- end
+-- return concat(t)
+-- else
+-- local s = tounicodes[unicode]
+-- if s then
+-- return s
+-- else
+-- report_fonts("can't convert %a in %a into tounicode",unicode,name)
+-- end
+-- end
+-- end
+
+local function tounicode16(unicode)
+ if unicode < 0xD7FF or (unicode > 0xDFFF and unicode <= 0xFFFF) then
+ return f_single(unicode)
+ else
+ unicode = unicode - 0x10000
+ return f_double(rshift(unicode,10)+0xD800,unicode%1024+0xDC00)
+ end
+end
+
+local function tounicode16sequence(unicodes)
+ local t = { }
+ for l=1,#unicodes do
+ local u = unicodes[l]
+ if u < 0xD7FF or (u > 0xDFFF and u <= 0xFFFF) then
+ t[l] = f_single(u)
+ else
+ u = u - 0x10000
+ t[l] = f_double(rshift(u,10)+0xD800,u%1024+0xDC00)
+ end
+ end
+ return concat(t)
+end
+
+-- local function tounicode(unicode)
+-- if type(unicode) == "table" then
+-- local t = { }
+-- for l=1,#unicode do
+-- local u = unicode[l]
+-- if u < 0xD7FF or (u > 0xDFFF and u <= 0xFFFF) then
+-- t[l] = f_single(u)
+-- else
+-- u = u - 0x10000
+-- t[l] = f_double(rshift(u,10)+0xD800,u%1024+0xDC00)
+-- end
+-- end
+-- return concat(t)
+-- else
+-- if unicode < 0xD7FF or (unicode > 0xDFFF and unicode <= 0xFFFF) then
+-- return f_single(unicode)
+-- else
+-- unicode = unicode - 0x10000
+-- return f_double(rshift(unicode,10)+0xD800,unicode%1024+0xDC00)
+-- end
+-- end
+-- end
+
+local unknown = f_single(0xFFFD)
+
+-- local function tounicode(unicode)
+-- if type(unicode) == "table" then
+-- local t = { }
+-- for l=1,#unicode do
+-- t[l] = tounicode(unicode[l])
+-- end
+-- return concat(t)
+-- elseif unicode >= 0x00E000 and unicode <= 0x00F8FF then
+-- return unknown
+-- elseif unicode >= 0x0F0000 and unicode <= 0x0FFFFF then
+-- return unknown
+-- elseif unicode >= 0x100000 and unicode <= 0x10FFFF then
+-- return unknown
+-- elseif unicode < 0xD7FF or (unicode > 0xDFFF and unicode <= 0xFFFF) then
+-- return f_single(unicode)
+-- else
+-- unicode = unicode - 0x10000
+-- return f_double(rshift(unicode,10)+0xD800,unicode%1024+0xDC00)
+-- end
+-- end
+
+-- local hash = table.setmetatableindex(function(t,k)
+-- local v
+-- if k >= 0x00E000 and k <= 0x00F8FF then
+-- v = unknown
+-- elseif k >= 0x0F0000 and k <= 0x0FFFFF then
+-- v = unknown
+-- elseif k >= 0x100000 and k <= 0x10FFFF then
+-- v = unknown
+-- elseif k < 0xD7FF or (k > 0xDFFF and k <= 0xFFFF) then
+-- v = f_single(k)
+-- else
+-- local k = k - 0x10000
+-- v = f_double(rshift(k,10)+0xD800,k%1024+0xDC00)
+-- end
+-- t[k] = v
+-- return v
+-- end)
+--
+-- table.makeweak(hash)
+--
+-- local function tounicode(unicode)
+-- if type(unicode) == "table" then
+-- local t = { }
+-- for l=1,#unicode do
+-- t[l] = hash[unicode[l]]
+-- end
+-- return concat(t)
+-- else
+-- return hash[unicode]
+-- end
+-- end
+
+local hash = { }
+local conc = { }
+
+-- table.makeweak(hash)
+
+-- table.setmetatableindex(hash,function(t,k)
+-- if type(k) == "table" then
+-- local n = #k
+-- for l=1,n do
+-- conc[l] = hash[k[l]]
+-- end
+-- return concat(conc,"",1,n)
+-- end
+-- local v
+-- if k >= 0x00E000 and k <= 0x00F8FF then
+-- v = unknown
+-- elseif k >= 0x0F0000 and k <= 0x0FFFFF then
+-- v = unknown
+-- elseif k >= 0x100000 and k <= 0x10FFFF then
+-- v = unknown
+-- elseif k < 0xD7FF or (k > 0xDFFF and k <= 0xFFFF) then
+-- v = f_single(k)
+-- else
+-- local k = k - 0x10000
+-- v = f_double(rshift(k,10)+0xD800,k%1024+0xDC00)
+-- end
+-- t[k] = v
+-- return v
+-- end)
+--
+-- local function tounicode(unicode)
+-- return hash[unicode]
+-- end
+
+table.setmetatableindex(hash,function(t,k)
+ if k < 0xD7FF or (k > 0xDFFF and k <= 0xFFFF) then
+ v = f_single(k)
+ else
+ local k = k - 0x10000
+ v = f_double(rshift(k,10)+0xD800,k%1024+0xDC00)
+ end
+ t[k] = v
+ return v
+end)
+
+local function tounicode(k)
+ if type(k) == "table" then
+ local n = #k
+ for l=1,n do
+ conc[l] = hash[k[l]]
+ end
+ return concat(conc,"",1,n)
+ elseif k >= 0x00E000 and k <= 0x00F8FF then
+ return unknown
+ elseif k >= 0x0F0000 and k <= 0x0FFFFF then
+ return unknown
+ elseif k >= 0x100000 and k <= 0x10FFFF then
+ return unknown
+ else
+ return hash[k]
+ end
+end
+
+local function fromunicode16(str)
+ if #str == 4 then
+ return tonumber(str,16)
+ else
+ local l, r = match(str,"(....)(....)")
+ -- return (tonumber(l,16))*0x400 + tonumber(r,16) - 0xDC00
+ return 0x10000 + (tonumber(l,16)-0xD800)*0x400 + tonumber(r,16) - 0xDC00
+ end
+end
+
+-- Slightly slower:
+--
+-- local p = C(4) * (C(4)^-1) / function(l,r)
+-- if r then
+-- return (tonumber(l,16))*0x400 + tonumber(r,16) - 0xDC00
+-- else
+-- return tonumber(l,16)
+-- end
+-- end
+--
+-- local function fromunicode16(str)
+-- return lpegmatch(p,str)
+-- end
+
+mappings.makenameparser = makenameparser
+mappings.tounicode = tounicode
+mappings.tounicode16 = tounicode16
+mappings.tounicode16sequence = tounicode16sequence
+mappings.fromunicode16 = fromunicode16
+
+-- mozilla emoji has bad lig names: name = gsub(name,"(u[a-f0-9_]+)%-([a-f0-9_]+)","%1_%2")
+
+local ligseparator = P("_")
+local varseparator = P(".")
+local namesplitter = Ct(C((1 - ligseparator - varseparator)^1) * (ligseparator * C((1 - ligseparator - varseparator)^1))^0)
+
+-- maybe: ff fi fl ffi ffl => f_f f_i f_l f_f_i f_f_l
+
+-- local function test(name)
+-- local split = lpegmatch(namesplitter,name)
+-- print(string.formatters["%s: [% t]"](name,split))
+-- end
+
+-- test("i.f_")
+-- test("this")
+-- test("this.that")
+-- test("japan1.123")
+-- test("such_so_more")
+-- test("such_so_more.that")
+
+-- to be completed .. for fonts that use unicodes for ligatures which
+-- is a actually a bad thing and should be avoided in the first place
+
+do
+
+ local overloads = {
+ IJ = { name = "I_J", unicode = { 0x49, 0x4A }, mess = 0x0132 },
+ ij = { name = "i_j", unicode = { 0x69, 0x6A }, mess = 0x0133 },
+ ff = { name = "f_f", unicode = { 0x66, 0x66 }, mess = 0xFB00 },
+ fi = { name = "f_i", unicode = { 0x66, 0x69 }, mess = 0xFB01 },
+ fl = { name = "f_l", unicode = { 0x66, 0x6C }, mess = 0xFB02 },
+ ffi = { name = "f_f_i", unicode = { 0x66, 0x66, 0x69 }, mess = 0xFB03 },
+ ffl = { name = "f_f_l", unicode = { 0x66, 0x66, 0x6C }, mess = 0xFB04 },
+ fj = { name = "f_j", unicode = { 0x66, 0x6A } },
+ fk = { name = "f_k", unicode = { 0x66, 0x6B } },
+
+ -- endash = { name = "endash", unicode = 0x2013, mess = 0x2013 },
+ -- emdash = { name = "emdash", unicode = 0x2014, mess = 0x2014 },
+ }
+
+ local o = allocate { }
+
+ for k, v in next, overloads do
+ local name = v.name
+ local mess = v.mess
+ if name then
+ o[name] = v
+ end
+ if mess then
+ o[mess] = v
+ end
+ o[k] = v
+ end
+
+ mappings.overloads = o
+
+end
+
+function mappings.addtounicode(data,filename,checklookups,forceligatures)
+ local resources = data.resources
+ local unicodes = resources.unicodes
+ if not unicodes then
+ if trace_mapping then
+ report_fonts("no unicode list, quitting tounicode for %a",filename)
+ end
+ return
+ end
+ local properties = data.properties
+ local descriptions = data.descriptions
+ local overloads = mappings.overloads
+ -- we need to move this code
+ unicodes['space'] = unicodes['space'] or 32
+ unicodes['hyphen'] = unicodes['hyphen'] or 45
+ unicodes['zwj'] = unicodes['zwj'] or 0x200D
+ unicodes['zwnj'] = unicodes['zwnj'] or 0x200C
+ --
+ local private = fonts.constructors and fonts.constructors.privateoffset or 0xF0000 -- 0x10FFFF
+ local unicodevector = fonts.encodings.agl.unicodes or { } -- loaded runtime in context
+ local contextvector = fonts.encodings.agl.ctxcodes or { } -- loaded runtime in context
+ local missing = { }
+ local nofmissing = 0
+ local oparser = nil
+ local cidnames = nil
+ local cidcodes = nil
+ local cidinfo = properties.cidinfo
+ local usedmap = cidinfo and fonts.cid.getmap(cidinfo)
+ local uparser = makenameparser() -- hm, every time?
+ if usedmap then
+ oparser = usedmap and makenameparser(cidinfo.ordering)
+ cidnames = usedmap.names
+ cidcodes = usedmap.unicodes
+ end
+ local ns = 0
+ local nl = 0
+ --
+ -- in order to avoid differences between runs due to hash randomization we
+ -- run over a sorted list
+ --
+ local dlist = sortedkeys(descriptions)
+ --
+ -- for du, glyph in next, descriptions do
+ for i=1,#dlist do
+ local du = dlist[i]
+ local glyph = descriptions[du]
+ local name = glyph.name
+ if name then
+ local overload = overloads[name] or overloads[du]
+ if overload then
+ -- get rid of weird ligatures
+ -- glyph.name = overload.name
+ glyph.unicode = overload.unicode
+ else
+ local gu = glyph.unicode -- can already be set (number or table)
+ if not gu or gu == -1 or du >= private or (du >= 0xE000 and du <= 0xF8FF) or du == 0xFFFE or du == 0xFFFF then
+ local unicode = unicodevector[name] or contextvector[name]
+ if unicode then
+ glyph.unicode = unicode
+ ns = ns + 1
+ end
+ -- cidmap heuristics, beware, there is no guarantee for a match unless
+ -- the chain resolves
+ if (not unicode) and usedmap then
+ local foundindex = lpegmatch(oparser,name)
+ if foundindex then
+ unicode = cidcodes[foundindex] -- name to number
+ if unicode then
+ glyph.unicode = unicode
+ ns = ns + 1
+ else
+ local reference = cidnames[foundindex] -- number to name
+ if reference then
+ local foundindex = lpegmatch(oparser,reference)
+ if foundindex then
+ unicode = cidcodes[foundindex]
+ if unicode then
+ glyph.unicode = unicode
+ ns = ns + 1
+ end
+ end
+ if not unicode or unicode == "" then
+ local foundcodes, multiple = lpegmatch(uparser,reference)
+ if foundcodes then
+ glyph.unicode = foundcodes
+ if multiple then
+ nl = nl + 1
+ unicode = true
+ else
+ ns = ns + 1
+ unicode = foundcodes
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ -- a.whatever or a_b_c.whatever or a_b_c (no numbers) a.b_
+ --
+ -- It is not trivial to find a solution that suits all fonts. We tried several alternatives
+ -- and this one seems to work reasonable also with fonts that use less standardized naming
+ -- schemes. The extra private test is tested by KE and seems to work okay with non-typical
+ -- fonts as well.
+ --
+ if not unicode or unicode == "" then
+ local split = lpegmatch(namesplitter,name)
+ local nsplit = split and #split or 0 -- add if
+ if nsplit == 0 then
+ -- skip
+ elseif nsplit == 1 then
+ local base = split[1]
+ local u = unicodes[base] or unicodevector[base] or contextvector[name]
+ if not u then
+ -- skip
+ elseif type(u) == "table" then
+ -- unlikely
+ if u[1] < private then
+ unicode = u
+ glyph.unicode = unicode
+ end
+ elseif u < private then
+ unicode = u
+ glyph.unicode = unicode
+ end
+ else
+ local t = { }
+ local n = 0
+ for l=1,nsplit do
+ local base = split[l]
+ local u = unicodes[base] or unicodevector[base] or contextvector[name]
+ if not u then
+ break
+ elseif type(u) == "table" then
+ if u[1] >= private then
+ break
+ end
+ n = n + 1
+ t[n] = u[1]
+ else
+ if u >= private then
+ break
+ end
+ n = n + 1
+ t[n] = u
+ end
+ end
+ if n > 0 then
+ if n == 1 then
+ unicode = t[1]
+ else
+ unicode = t
+ end
+ glyph.unicode = unicode
+ end
+ end
+ nl = nl + 1
+ end
+ -- last resort (we might need to catch private here as well)
+ if not unicode or unicode == "" then
+ local foundcodes, multiple = lpegmatch(uparser,name)
+ if foundcodes then
+ glyph.unicode = foundcodes
+ if multiple then
+ nl = nl + 1
+ unicode = true
+ else
+ ns = ns + 1
+ unicode = foundcodes
+ end
+ end
+ end
+ -- check using substitutes and alternates
+ local r = overloads[unicode]
+ if r then
+ unicode = r.unicode
+ glyph.unicode = unicode
+ end
+ --
+ if not unicode then
+ missing[du] = true
+ nofmissing = nofmissing + 1
+ end
+ else
+ -- maybe a message or so
+ end
+ end
+ else
+ local overload = overloads[du]
+ if overload then
+ glyph.unicode = overload.unicode
+ elseif not glyph.unicode then
+ missing[du] = true
+ nofmissing = nofmissing + 1
+ end
+ end
+ end
+ if type(checklookups) == "function" then
+ checklookups(data,missing,nofmissing)
+ end
+
+ local unicoded = 0
+ local collected = fonts.handlers.otf.readers.getcomponents(data) -- neglectable overhead
+
+ local function resolve(glyph,u)
+ local n = #u
+ for i=1,n do
+ if u[i] > private then
+ n = 0
+ break
+ end
+ end
+ if n > 0 then
+ if n > 1 then
+ glyph.unicode = u
+ else
+ glyph.unicode = u[1]
+ end
+ unicoded = unicoded + 1
+ end
+ end
+
+ if not collected then
+ -- move on
+ elseif forceligatures or force_ligatures then
+ for i=1,#dlist do
+ local du = dlist[i]
+ if du >= private or (du >= 0xE000 and du <= 0xF8FF) then
+ local u = collected[du] -- always tables
+ if u then
+ resolve(descriptions[du],u)
+ end
+ end
+ end
+ else
+ for i=1,#dlist do
+ local du = dlist[i]
+ if du >= private or (du >= 0xE000 and du <= 0xF8FF) then
+ local glyph = descriptions[du]
+ if glyph.class == "ligature" and not glyph.unicode then
+ local u = collected[du] -- always tables
+ if u then
+ resolve(glyph,u)
+ end
+ end
+ end
+ end
+ end
+
+ if trace_mapping and unicoded > 0 then
+ report_fonts("%n ligature tounicode mappings deduced from gsub ligature features",unicoded)
+ end
+ if trace_mapping then
+ -- for unic, glyph in sortedhash(descriptions) do
+ for i=1,#dlist do
+ local du = dlist[i]
+ local glyph = descriptions[du]
+ local name = glyph.name or "-"
+ local index = glyph.index or 0
+ local unicode = glyph.unicode
+ if unicode then
+ if type(unicode) == "table" then
+ local unicodes = { }
+ for i=1,#unicode do
+ unicodes[i] = formatters("%U",unicode[i])
+ end
+ report_fonts("internal slot %U, name %a, unicode %U, tounicode % t",index,name,du,unicodes)
+ else
+ report_fonts("internal slot %U, name %a, unicode %U, tounicode %U",index,name,du,unicode)
+ end
+ else
+ report_fonts("internal slot %U, name %a, unicode %U",index,name,du)
+ end
+ end
+ end
+ if trace_loading and (ns > 0 or nl > 0) then
+ report_fonts("%s tounicode entries added, ligatures %s",nl+ns,ns)
+ end
+end
+
+-- local parser = makenameparser("Japan1")
+-- local parser = makenameparser()
+-- local function test(str)
+-- local b, a = lpegmatch(parser,str)
+-- print((a and table.serialize(b)) or b)
+-- end
+-- test("a.sc")
+-- test("a")
+-- test("uni1234")
+-- test("uni1234.xx")
+-- test("uni12349876")
+-- test("u123400987600")
+-- test("index1234")
+-- test("Japan1.123")
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-ocl.lua b/macros/luatex/generic/luaotfload/fontloader-font-ocl.lua
new file mode 100644
index 0000000000..d79ed657e0
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-ocl.lua
@@ -0,0 +1,670 @@
+if not modules then modules = { } end modules ['font-ocl'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- todo : user list of colors
+
+local tostring, tonumber, next = tostring, tonumber, next
+local round, max = math.round, math.round
+local sortedkeys, sortedhash = table.sortedkeys, table.sortedhash
+local setmetatableindex = table.setmetatableindex
+
+local formatters = string.formatters
+local tounicode = fonts.mappings.tounicode
+
+local helpers = fonts.helpers
+
+local charcommand = helpers.commands.char
+local rightcommand = helpers.commands.right
+local leftcommand = helpers.commands.left
+local downcommand = helpers.commands.down
+
+local otf = fonts.handlers.otf
+
+local f_color = formatters["%.3f %.3f %.3f rg"]
+local f_gray = formatters["%.3f g"]
+
+if context then
+
+ local startactualtext = nil
+ local stopactualtext = nil
+
+ function otf.getactualtext(s)
+ if not startactualtext then
+ startactualtext = backends.codeinjections.startunicodetoactualtextdirect
+ stopactualtext = backends.codeinjections.stopunicodetoactualtextdirect
+ end
+ return startactualtext(s), stopactualtext()
+ end
+
+else
+
+ local tounicode = fonts.mappings.tounicode16
+
+ function otf.getactualtext(s)
+ return
+ "/Span << /ActualText <feff" .. s .. "> >> BDC",
+ "EMC"
+ end
+
+end
+
+local sharedpalettes = { }
+
+local hash = setmetatableindex(function(t,k)
+ local v = { "pdf", "direct", k }
+ t[k] = v
+ return v
+end)
+
+if context then
+
+ -- \definefontcolorpalette [emoji-r] [emoji-red,emoji-gray,textcolor] -- looks bad
+ -- \definefontcolorpalette [emoji-r] [emoji-red,emoji-gray] -- looks okay
+
+ local colors = attributes.list[attributes.private('color')] or { }
+ local transparencies = attributes.list[attributes.private('transparency')] or { }
+
+ function otf.registerpalette(name,values)
+ sharedpalettes[name] = values
+ local color = lpdf.color
+ local transparency = lpdf.transparency
+ local register = colors.register
+ for i=1,#values do
+ local v = values[i]
+ if v == "textcolor" then
+ values[i] = false
+ else
+ local c = nil
+ local t = nil
+ if type(v) == "table" then
+ c = register(name,"rgb",
+ max(round((v.r or 0)*255),255)/255,
+ max(round((v.g or 0)*255),255)/255,
+ max(round((v.b or 0)*255),255)/255
+ )
+ else
+ c = colors[v]
+ t = transparencies[v]
+ end
+ if c and t then
+ values[i] = hash[color(1,c) .. " " .. transparency(t)]
+ elseif c then
+ values[i] = hash[color(1,c)]
+ elseif t then
+ values[i] = hash[color(1,t)]
+ end
+ end
+ end
+ end
+
+else -- for generic
+
+ function otf.registerpalette(name,values)
+ sharedpalettes[name] = values
+ for i=1,#values do
+ local v = values[i]
+ if v then
+ values[i] = hash[f_color(
+ max(round((v.r or 0)*255),255)/255,
+ max(round((v.g or 0)*255),255)/255,
+ max(round((v.b or 0)*255),255)/255
+ )]
+ end
+ end
+ end
+
+end
+
+-- We need to force page first because otherwise the q's get outside the font switch and
+-- as a consequence the next character has no font set (well, it has: the preceding one). As
+-- a consequence these fonts are somewhat inefficient as each glyph gets the font set. It's
+-- a side effect of the fact that a font is handled when a character gets flushed. Okay, from
+-- now on we can use text as literal mode.
+
+local function convert(t,k)
+ local v = { }
+ for i=1,#k do
+ local p = k[i]
+ local r, g, b = p[1], p[2], p[3]
+ if r == g and g == b then
+ v[i] = hash[f_gray(r/255)]
+ else
+ v[i] = hash[f_color(r/255,g/255,b/255)]
+ end
+ end
+ t[k] = v
+ return v
+end
+
+local start = { "pdf", "mode", "font" } -- force text mode (so get q Q right)
+----- stop = { "pdf", "mode", "page" } -- force page mode (else overlap)
+local push = { "pdf", "page", "q" }
+local pop = { "pdf", "page", "Q" }
+
+-- -- This one results in color directives inside BT ET but has less q Q pairs. It
+-- -- only shows the first glyph in acrobat and nothing more. No problem with other
+-- -- renderers.
+--
+-- local function initialize(tfmdata,kind,value) -- hm, always value
+-- if value then
+-- local resources = tfmdata.resources
+-- local palettes = resources.colorpalettes
+-- if palettes then
+-- --
+-- local converted = resources.converted
+-- if not converted then
+-- converted = setmetatableindex(convert)
+-- resources.converted = converted
+-- end
+-- local colorvalues = sharedpalettes[value] or converted[palettes[tonumber(value) or 1] or palettes[1]] or { }
+-- local classes = #colorvalues
+-- if classes == 0 then
+-- return
+-- end
+-- --
+-- local characters = tfmdata.characters
+-- local descriptions = tfmdata.descriptions
+-- local properties = tfmdata.properties
+-- --
+-- properties.virtualized = true
+-- tfmdata.fonts = {
+-- { id = 0 }
+-- }
+-- --
+-- local getactualtext = otf.getactualtext
+-- local default = colorvalues[#colorvalues]
+-- local b, e = getactualtext(tounicode(0xFFFD))
+-- local actualb = { "pdf", "page", b } -- saves tables
+-- local actuale = { "pdf", "page", e } -- saves tables
+-- --
+-- for unicode, character in next, characters do
+-- local description = descriptions[unicode]
+-- if description then
+-- local colorlist = description.colors
+-- if colorlist then
+-- local u = description.unicode or characters[unicode].unicode
+-- local w = character.width or 0
+-- local s = #colorlist
+-- local goback = w ~= 0 and leftcommand[w] or nil -- needs checking: are widths the same
+-- local t = {
+-- start,
+-- not u and actualb or { "pdf", "page", (getactualtext(tounicode(u))) }
+-- }
+-- local n = 2
+-- local l = nil
+-- n = n + 1 t[n] = push
+-- for i=1,s do
+-- local entry = colorlist[i]
+-- local v = colorvalues[entry.class] or default
+-- if v and l ~= v then
+-- n = n + 1 t[n] = v
+-- l = v
+-- end
+-- n = n + 1 t[n] = charcommand[entry.slot]
+-- if s > 1 and i < s and goback then
+-- n = n + 1 t[n] = goback
+-- end
+-- end
+-- n = n + 1 t[n] = pop
+-- n = n + 1 t[n] = actuale
+-- n = n + 1 t[n] = stop
+-- character.commands = t
+-- end
+-- end
+-- end
+-- end
+-- end
+-- end
+--
+-- -- Here we have no color change in BT .. ET and more q Q pairs but even then acrobat
+-- -- fails displaying the overlays correctly. Other renderers do it right.
+
+local function initialize(tfmdata,kind,value)
+ if value then
+ local resources = tfmdata.resources
+ local palettes = resources.colorpalettes
+ if palettes then
+ --
+ local converted = resources.converted
+ if not converted then
+ converted = setmetatableindex(convert)
+ resources.converted = converted
+ end
+ local colorvalues = sharedpalettes[value]
+ local default = false -- so the text color (bad for icon overloads)
+ if colorvalues then
+ default = colorvalues[#colorvalues]
+ else
+ colorvalues = converted[palettes[tonumber(value) or 1] or palettes[1]] or { }
+ end
+ local classes = #colorvalues
+ if classes == 0 then
+ return
+ end
+ --
+ local characters = tfmdata.characters
+ local descriptions = tfmdata.descriptions
+ local properties = tfmdata.properties
+ --
+ properties.virtualized = true
+ tfmdata.fonts = {
+ { id = 0 }
+ }
+ --
+ local getactualtext = otf.getactualtext
+ local b, e = getactualtext(tounicode(0xFFFD))
+ local actualb = { "pdf", "page", b } -- saves tables
+ local actuale = { "pdf", "page", e } -- saves tables
+ --
+ for unicode, character in next, characters do
+ local description = descriptions[unicode]
+ if description then
+ local colorlist = description.colors
+ if colorlist then
+ local u = description.unicode or characters[unicode].unicode
+ local w = character.width or 0
+ local s = #colorlist
+ local goback = w ~= 0 and leftcommand[w] or nil -- needs checking: are widths the same
+ local t = {
+ start, -- really needed
+ not u and actualb or { "pdf", "page", (getactualtext(tounicode(u))) }
+ }
+ local n = 2
+ local l = nil
+ local f = false
+ for i=1,s do
+ local entry = colorlist[i]
+ local v = colorvalues[entry.class] or default
+ if v and l ~= v then
+ if f then
+ n = n + 1 t[n] = pop
+ end
+ n = n + 1 t[n] = push
+ f = true
+ n = n + 1 t[n] = v
+ l = v
+ else
+ if f then
+ n = n + 1 t[n] = pop
+ end
+ f = false
+ l = nil
+ end
+ n = n + 1 t[n] = charcommand[entry.slot]
+ if s > 1 and i < s and goback then
+ n = n + 1 t[n] = goback
+ end
+ end
+ if f then
+ n = n + 1 t[n] = pop
+ end
+ n = n + 1 t[n] = actuale
+ -- n = n + 1 t[n] = stop -- not needed
+ character.commands = t
+ end
+ end
+ end
+ end
+ end
+end
+
+fonts.handlers.otf.features.register {
+ name = "colr",
+ description = "color glyphs",
+ manipulators = {
+ base = initialize,
+ node = initialize,
+ }
+}
+
+do
+
+ local nofstreams = 0
+ local f_name = formatters[ [[pdf-glyph-%05i]] ]
+ local f_used = context and formatters[ [[original:///%s]] ] or formatters[ [[%s]] ]
+ local hashed = { }
+ local cache = { }
+
+ local openpdf = pdfe.new
+ ----- prefix = "data:application/pdf,"
+
+ function otf.storepdfdata(pdf)
+ local done = hashed[pdf]
+ if not done then
+ nofstreams = nofstreams + 1
+ local f = f_name(nofstreams)
+ local n = openpdf(pdf,#pdf,f)
+ done = f_used(n)
+ hashed[pdf] = done
+ end
+ return done
+ end
+
+end
+
+-- I'll probably make a variant for context as we can do it more efficient there than in
+-- generic.
+
+local function pdftovirtual(tfmdata,pdfshapes,kind) -- kind = png|svg
+ if not tfmdata or not pdfshapes or not kind then
+ return
+ end
+ --
+ local characters = tfmdata.characters
+ local properties = tfmdata.properties
+ local parameters = tfmdata.parameters
+ local hfactor = parameters.hfactor
+ --
+ properties.virtualized = true
+ --
+ tfmdata.fonts = {
+ { id = 0 } -- not really needed
+ }
+ --
+ local getactualtext = otf.getactualtext
+ local storepdfdata = otf.storepdfdata
+ --
+ local b, e = getactualtext(tounicode(0xFFFD))
+ local actualb = { "pdf", "page", b } -- saves tables
+ local actuale = { "pdf", "page", e } -- saves tables
+ --
+ local vfimage = lpdf and lpdf.vfimage or function(wd,ht,dp,data,name)
+ -- needed for generic (if used there at all)
+ local name = storepdfdata(data)
+ return { "image", { filename = name, width = wd, height = ht, depth = dp } }
+ end
+ --
+ for unicode, character in sortedhash(characters) do -- sort is nicer for svg
+ local index = character.index
+ if index then
+ local pdf = pdfshapes[index]
+ local typ = type(pdf)
+ local data = nil
+ local dx = nil
+ local dy = nil
+ if typ == "table" then
+ data = pdf.data
+ dx = pdf.dx or 0
+ dy = pdf.dy or 0
+ elseif typ == "string" then
+ data = pdf
+ dx = 0
+ dy = 0
+ end
+ if data then
+ -- We can delay storage by a lua function in commands: but then we need to
+ -- be able to provide our own mem stream name (so that we can reserve it).
+ -- Anyway, we will do this different in a future version of context.
+ local bt = unicode and getactualtext(unicode)
+ local wd = character.width or 0
+ local ht = character.height or 0
+ local dp = character.depth or 0
+ -- The down and right will change too (we can move that elsewhere).
+ character.commands = {
+ not unicode and actualb or { "pdf", "page", (getactualtext(unicode)) },
+ downcommand[dp + dy * hfactor],
+ rightcommand[dx * hfactor],
+ vfimage(wd,ht,dp,data,name),
+ actuale,
+ }
+ character[kind] = true
+ end
+ end
+ end
+end
+
+local otfsvg = otf.svg or { }
+otf.svg = otfsvg
+otf.svgenabled = true
+
+do
+
+ local report_svg = logs.reporter("fonts","svg conversion")
+
+ local loaddata = io.loaddata
+ local savedata = io.savedata
+ local remove = os.remove
+
+ if context and xml.convert then
+
+ local xmlconvert = xml.convert
+ local xmlfirst = xml.first
+
+ function otfsvg.filterglyph(entry,index)
+ local svg = xmlconvert(entry.data)
+ local root = svg and xmlfirst(svg,"/svg[@id='glyph"..index.."']")
+ local data = root and tostring(root)
+ -- report_svg("data for glyph %04X: %s",index,data)
+ return data
+ end
+
+ else
+
+ function otfsvg.filterglyph(entry,index) -- can be overloaded
+ return entry.data
+ end
+
+ end
+
+ local runner = sandbox and sandbox.registerrunner {
+ name = "otfsvg",
+ program = "inkscape",
+ method = "pipeto",
+ template = "--shell > temp-otf-svg-shape.log",
+ reporter = report_svg,
+ }
+
+ if not runner then
+ --
+ -- poor mans variant for generic:
+ --
+ runner = function()
+ return io.open("inkscape --shell > temp-otf-svg-shape.log","w")
+ end
+ end
+
+ function otfsvg.topdf(svgshapes)
+ local pdfshapes = { }
+ local inkscape = runner()
+ if inkscape then
+ local nofshapes = #svgshapes
+ local f_svgfile = formatters["temp-otf-svg-shape-%i.svg"]
+ local f_pdffile = formatters["temp-otf-svg-shape-%i.pdf"]
+ local f_convert = formatters["%s --export-pdf=%s\n"]
+ local filterglyph = otfsvg.filterglyph
+ local nofdone = 0
+ report_svg("processing %i svg containers",nofshapes)
+ statistics.starttiming()
+ for i=1,nofshapes do
+ local entry = svgshapes[i]
+ for index=entry.first,entry.last do
+ local data = filterglyph(entry,index)
+ if data and data ~= "" then
+ local svgfile = f_svgfile(index)
+ local pdffile = f_pdffile(index)
+ savedata(svgfile,data)
+ inkscape:write(f_convert(svgfile,pdffile))
+ pdfshapes[index] = true
+ nofdone = nofdone + 1
+ if nofdone % 100 == 0 then
+ report_svg("%i shapes processed",nofdone)
+ end
+ end
+ end
+ end
+ inkscape:write("quit\n")
+ inkscape:close()
+ report_svg("processing %i pdf results",nofshapes)
+ for index in next, pdfshapes do
+ local svgfile = f_svgfile(index)
+ local pdffile = f_pdffile(index)
+ pdfshapes[index] = loaddata(pdffile)
+ remove(svgfile)
+ remove(pdffile)
+ end
+ statistics.stoptiming()
+ if statistics.elapsedseconds then
+ report_svg("svg conversion time %s",statistics.elapsedseconds() or "-")
+ end
+ end
+ return pdfshapes
+ end
+
+end
+
+local function initializesvg(tfmdata,kind,value) -- hm, always value
+ if value and otf.svgenabled then
+ local svg = tfmdata.properties.svg
+ local hash = svg and svg.hash
+ local timestamp = svg and svg.timestamp
+ if not hash then
+ return
+ end
+ local pdffile = containers.read(otf.pdfcache,hash)
+ local pdfshapes = pdffile and pdffile.pdfshapes
+ if not pdfshapes or pdffile.timestamp ~= timestamp then
+ local svgfile = containers.read(otf.svgcache,hash)
+ local svgshapes = svgfile and svgfile.svgshapes
+ pdfshapes = svgshapes and otfsvg.topdf(svgshapes) or { }
+ containers.write(otf.pdfcache, hash, {
+ pdfshapes = pdfshapes,
+ timestamp = timestamp,
+ })
+ end
+ pdftovirtual(tfmdata,pdfshapes,"svg")
+ end
+end
+
+fonts.handlers.otf.features.register {
+ name = "svg",
+ description = "svg glyphs",
+ manipulators = {
+ base = initializesvg,
+ node = initializesvg,
+ }
+}
+
+-- This can be done differently e.g. with ffi and gm and we can share code anway. Using
+-- batchmode in gm is not faster and as it accumulates we would need to flush all
+-- individual shapes. But ... in context lmtx (and maybe the backport) we will use
+-- a different and more efficient method anyway. I'm still wondering if I should
+-- keep color code in generic. Maybe it should be optional.
+
+local otfpng = otf.png or { }
+otf.png = otfpng
+otf.pngenabled = true
+
+do
+
+ local report_png = logs.reporter("fonts","png conversion")
+
+ local loaddata = io.loaddata
+ local savedata = io.savedata
+ local remove = os.remove
+
+ local runner = sandbox and sandbox.registerrunner {
+ name = "otfpng",
+ program = "gm",
+ template = "convert -quality 100 temp-otf-png-shape.png temp-otf-png-shape.pdf > temp-otf-svg-shape.log",
+ -- reporter = report_png,
+ }
+
+ if not runner then
+ --
+ -- poor mans variant for generic:
+ --
+ runner = function()
+ return os.execute("gm convert -quality 100 temp-otf-png-shape.png temp-otf-png-shape.pdf > temp-otf-svg-shape.log")
+ end
+ end
+
+ -- Alternatively we can create a single pdf file with -adjoin and then pick up pages from
+ -- that file but creating thousands of small files is no fun either.
+
+ function otfpng.topdf(pngshapes)
+ local pdfshapes = { }
+ local pngfile = "temp-otf-png-shape.png"
+ local pdffile = "temp-otf-png-shape.pdf"
+ local nofdone = 0
+ local indices = sortedkeys(pngshapes) -- can be sparse
+ local nofindices = #indices
+ report_png("processing %i png containers",nofindices)
+ statistics.starttiming()
+ for i=1,nofindices do
+ local index = indices[i]
+ local entry = pngshapes[index]
+ local data = entry.data -- or placeholder
+ local x = entry.x
+ local y = entry.y
+ savedata(pngfile,data)
+ runner()
+ pdfshapes[index] = {
+ x = x ~= 0 and x or nil,
+ y = y ~= 0 and y or nil,
+ data = loaddata(pdffile),
+ }
+ nofdone = nofdone + 1
+ if nofdone % 100 == 0 then
+ report_png("%i shapes processed",nofdone)
+ end
+ end
+ report_png("processing %i pdf results",nofindices)
+ remove(pngfile)
+ remove(pdffile)
+ statistics.stoptiming()
+ if statistics.elapsedseconds then
+ report_png("png conversion time %s",statistics.elapsedseconds() or "-")
+ end
+ return pdfshapes
+ end
+
+end
+
+-- This will change in a future version of context. More direct.
+
+local function initializepng(tfmdata,kind,value) -- hm, always value
+ if value and otf.pngenabled then
+ local png = tfmdata.properties.png
+ local hash = png and png.hash
+ local timestamp = png and png.timestamp
+ if not hash then
+ return
+ end
+ local pdffile = containers.read(otf.pdfcache,hash)
+ local pdfshapes = pdffile and pdffile.pdfshapes
+ if not pdfshapes or pdffile.timestamp ~= timestamp then
+ local pngfile = containers.read(otf.pngcache,hash)
+ local pngshapes = pngfile and pngfile.pngshapes
+ pdfshapes = pngshapes and otfpng.topdf(pngshapes) or { }
+ containers.write(otf.pdfcache, hash, {
+ pdfshapes = pdfshapes,
+ timestamp = timestamp,
+ })
+ end
+ --
+ pdftovirtual(tfmdata,pdfshapes,"png")
+ end
+end
+
+fonts.handlers.otf.features.register {
+ name = "sbix",
+ description = "sbix glyphs",
+ manipulators = {
+ base = initializepng,
+ node = initializepng,
+ }
+}
+
+fonts.handlers.otf.features.register {
+ name = "cblc",
+ description = "cblc glyphs",
+ manipulators = {
+ base = initializepng,
+ node = initializepng,
+ }
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-one.lua b/macros/luatex/generic/luaotfload/fontloader-font-one.lua
new file mode 100644
index 0000000000..5387516b4d
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-one.lua
@@ -0,0 +1,842 @@
+if not modules then modules = { } end modules ['font-one'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+--[[ldx--
+<p>Some code may look a bit obscure but this has to do with the fact that we also use
+this code for testing and much code evolved in the transition from <l n='tfm'/> to
+<l n='afm'/> to <l n='otf'/>.</p>
+
+<p>The following code still has traces of intermediate font support where we handles
+font encodings. Eventually font encoding went away but we kept some code around in
+other modules.</p>
+
+<p>This version implements a node mode approach so that users can also more easily
+add features.</p>
+--ldx]]--
+
+local fonts, logs, trackers, containers, resolvers = fonts, logs, trackers, containers, resolvers
+
+local next, type, tonumber, rawget = next, type, tonumber, rawget
+local match, gsub = string.match, string.gsub
+local abs = math.abs
+local P, S, R, Cmt, C, Ct, Cs, Carg = lpeg.P, lpeg.S, lpeg.R, lpeg.Cmt, lpeg.C, lpeg.Ct, lpeg.Cs, lpeg.Carg
+local lpegmatch, patterns = lpeg.match, lpeg.patterns
+local sortedhash = table.sortedhash
+
+local trace_features = false trackers.register("afm.features", function(v) trace_features = v end)
+local trace_indexing = false trackers.register("afm.indexing", function(v) trace_indexing = v end)
+local trace_loading = false trackers.register("afm.loading", function(v) trace_loading = v end)
+local trace_defining = false trackers.register("fonts.defining", function(v) trace_defining = v end)
+
+local report_afm = logs.reporter("fonts","afm loading")
+
+local setmetatableindex = table.setmetatableindex
+local derivetable = table.derive
+
+local findbinfile = resolvers.findbinfile
+
+local privateoffset = fonts.constructors and fonts.constructors.privateoffset or 0xF0000 -- 0x10FFFF
+
+local definers = fonts.definers
+local readers = fonts.readers
+local constructors = fonts.constructors
+
+local afm = constructors.handlers.afm
+local pfb = constructors.handlers.pfb
+local otf = fonts.handlers.otf
+
+local otfreaders = otf.readers
+local otfenhancers = otf.enhancers
+
+local afmfeatures = constructors.features.afm
+local registerafmfeature = afmfeatures.register
+
+local afmenhancers = constructors.enhancers.afm
+local registerafmenhancer = afmenhancers.register
+
+afm.version = 1.513 -- incrementing this number one up will force a re-cache
+afm.cache = containers.define("fonts", "one", afm.version, true)
+afm.autoprefixed = true -- this will become false some day (catches texnansi-blabla.*)
+
+afm.helpdata = { } -- set later on so no local for this
+afm.syncspace = true -- when true, nicer stretch values
+
+local overloads = fonts.mappings.overloads
+
+local applyruntimefixes = fonts.treatments and fonts.treatments.applyfixes
+
+--[[ldx--
+<p>We cache files. Caching is taken care of in the loader. We cheat a bit by adding
+ligatures and kern information to the afm derived data. That way we can set them faster
+when defining a font.</p>
+
+<p>We still keep the loading two phased: first we load the data in a traditional
+fashion and later we transform it to sequences. Then we apply some methods also
+used in opentype fonts (like <t>tlig</t>).</p>
+--ldx]]--
+
+function afm.load(filename)
+ filename = resolvers.findfile(filename,'afm') or ""
+ if filename ~= "" and not fonts.names.ignoredfile(filename) then
+ local name = file.removesuffix(file.basename(filename))
+ local data = containers.read(afm.cache,name)
+ local attr = lfs.attributes(filename)
+ local size = attr and attr.size or 0
+ local time = attr and attr.modification or 0
+ --
+ local pfbfile = file.replacesuffix(name,"pfb")
+ local pfbname = resolvers.findfile(pfbfile,"pfb") or ""
+ if pfbname == "" then
+ pfbname = resolvers.findfile(file.basename(pfbfile),"pfb") or ""
+ end
+ local pfbsize = 0
+ local pfbtime = 0
+ if pfbname ~= "" then
+ local attr = lfs.attributes(pfbname)
+ pfbsize = attr.size or 0
+ pfbtime = attr.modification or 0
+ end
+ if not data or data.size ~= size or data.time ~= time or data.pfbsize ~= pfbsize or data.pfbtime ~= pfbtime then
+ report_afm("reading %a",filename)
+ data = afm.readers.loadfont(filename,pfbname)
+ if data then
+ afmenhancers.apply(data,filename)
+ -- otfreaders.addunicodetable(data) -- only when not done yet
+ fonts.mappings.addtounicode(data,filename)
+ otfreaders.stripredundant(data)
+ -- otfreaders.extend(data)
+ otfreaders.pack(data)
+ data.size = size
+ data.time = time
+ data.pfbsize = pfbsize
+ data.pfbtime = pfbtime
+ report_afm("saving %a in cache",name)
+ -- data.resources.unicodes = nil -- consistent with otf but here we save not much
+ data = containers.write(afm.cache, name, data)
+ data = containers.read(afm.cache,name)
+ end
+ end
+ if data then
+ -- constructors.addcoreunicodes(unicodes)
+ otfreaders.unpack(data)
+ otfreaders.expand(data) -- inline tables
+ otfreaders.addunicodetable(data) -- only when not done yet
+ otfenhancers.apply(data,filename,data)
+ if applyruntimefixes then
+ applyruntimefixes(filename,data)
+ end
+ end
+ return data
+ end
+end
+
+-- we run a more advanced analyzer later on anyway
+
+local uparser = fonts.mappings.makenameparser() -- each time
+
+local function enhance_unify_names(data, filename)
+ local unicodevector = fonts.encodings.agl.unicodes -- loaded runtime in context
+ local unicodes = { }
+ local names = { }
+ local private = data.private or privateoffset
+ local descriptions = data.descriptions
+ for name, blob in sortedhash(data.characters) do -- sorting is nicer for privates
+ local code = unicodevector[name] -- or characters.name_to_unicode[name]
+ if not code then
+ code = lpegmatch(uparser,name)
+ if type(code) ~= "number" then
+ code = private
+ private = private + 1
+ report_afm("assigning private slot %U for unknown glyph name %a",code,name)
+ end
+ end
+ local index = blob.index
+ unicodes[name] = code
+ names[name] = index
+ blob.name = name
+ descriptions[code] = {
+ boundingbox = blob.boundingbox,
+ width = blob.width,
+ kerns = blob.kerns,
+ index = index,
+ name = name,
+ }
+ end
+ for unicode, description in next, descriptions do
+ local kerns = description.kerns
+ if kerns then
+ local krn = { }
+ for name, kern in next, kerns do
+ local unicode = unicodes[name]
+ if unicode then
+ krn[unicode] = kern
+ else
+ -- print(unicode,name)
+ end
+ end
+ description.kerns = krn
+ end
+ end
+ data.characters = nil
+ data.private = private
+ local resources = data.resources
+ local filename = resources.filename or file.removesuffix(file.basename(filename))
+ resources.filename = resolvers.unresolve(filename) -- no shortcut
+ resources.unicodes = unicodes -- name to unicode
+ resources.marks = { } -- todo
+ -- resources.names = names -- name to index
+end
+
+local everywhere = { ["*"] = { ["*"] = true } } -- or: { ["*"] = { "*" } }
+local noflags = { false, false, false, false }
+
+local function enhance_normalize_features(data)
+ local ligatures = setmetatableindex("table")
+ local kerns = setmetatableindex("table")
+ local extrakerns = setmetatableindex("table")
+ for u, c in next, data.descriptions do
+ local l = c.ligatures
+ local k = c.kerns
+ local e = c.extrakerns
+ if l then
+ ligatures[u] = l
+ for u, v in next, l do
+ l[u] = { ligature = v }
+ end
+ c.ligatures = nil
+ end
+ if k then
+ kerns[u] = k
+ for u, v in next, k do
+ k[u] = v -- { v, 0 }
+ end
+ c.kerns = nil
+ end
+ if e then
+ extrakerns[u] = e
+ for u, v in next, e do
+ e[u] = v -- { v, 0 }
+ end
+ c.extrakerns = nil
+ end
+ end
+ local features = {
+ gpos = { },
+ gsub = { },
+ }
+ local sequences = {
+ -- only filled ones
+ }
+ if next(ligatures) then
+ features.gsub.liga = everywhere
+ data.properties.hasligatures = true
+ sequences[#sequences+1] = {
+ features = {
+ liga = everywhere,
+ },
+ flags = noflags,
+ name = "s_s_0",
+ nofsteps = 1,
+ order = { "liga" },
+ type = "gsub_ligature",
+ steps = {
+ {
+ coverage = ligatures,
+ },
+ },
+ }
+ end
+ if next(kerns) then
+ features.gpos.kern = everywhere
+ data.properties.haskerns = true
+ sequences[#sequences+1] = {
+ features = {
+ kern = everywhere,
+ },
+ flags = noflags,
+ name = "p_s_0",
+ nofsteps = 1,
+ order = { "kern" },
+ type = "gpos_pair",
+ steps = {
+ {
+ format = "kern",
+ coverage = kerns,
+ },
+ },
+ }
+ end
+ if next(extrakerns) then
+ features.gpos.extrakerns = everywhere
+ data.properties.haskerns = true
+ sequences[#sequences+1] = {
+ features = {
+ extrakerns = everywhere,
+ },
+ flags = noflags,
+ name = "p_s_1",
+ nofsteps = 1,
+ order = { "extrakerns" },
+ type = "gpos_pair",
+ steps = {
+ {
+ format = "kern",
+ coverage = extrakerns,
+ },
+ },
+ }
+ end
+ -- todo: compress kerns
+ data.resources.features = features
+ data.resources.sequences = sequences
+end
+
+local function enhance_fix_names(data)
+ for k, v in next, data.descriptions do
+ local n = v.name
+ local r = overloads[n]
+ if r then
+ local name = r.name
+ if trace_indexing then
+ report_afm("renaming characters %a to %a",n,name)
+ end
+ v.name = name
+ v.unicode = r.unicode
+ end
+ end
+end
+
+--[[ldx--
+<p>These helpers extend the basic table with extra ligatures, texligatures
+and extra kerns. This saves quite some lookups later.</p>
+--ldx]]--
+
+local addthem = function(rawdata,ligatures)
+ if ligatures then
+ local descriptions = rawdata.descriptions
+ local resources = rawdata.resources
+ local unicodes = resources.unicodes
+ -- local names = resources.names
+ for ligname, ligdata in next, ligatures do
+ local one = descriptions[unicodes[ligname]]
+ if one then
+ for _, pair in next, ligdata do
+ local two = unicodes[pair[1]]
+ local three = unicodes[pair[2]]
+ if two and three then
+ local ol = one.ligatures
+ if ol then
+ if not ol[two] then
+ ol[two] = three
+ end
+ else
+ one.ligatures = { [two] = three }
+ end
+ end
+ end
+ end
+ end
+ end
+end
+
+local function enhance_add_ligatures(rawdata)
+ addthem(rawdata,afm.helpdata.ligatures)
+end
+
+--[[ldx--
+<p>We keep the extra kerns in separate kerning tables so that we can use
+them selectively.</p>
+--ldx]]--
+
+-- This is rather old code (from the beginning when we had only tfm). If
+-- we unify the afm data (now we have names all over the place) then
+-- we can use shcodes but there will be many more looping then. But we
+-- could get rid of the tables in char-cmp then. Als, in the generic version
+-- we don't use the character database. (Ok, we can have a context specific
+-- variant).
+
+local function enhance_add_extra_kerns(rawdata) -- using shcodes is not robust here
+ local descriptions = rawdata.descriptions
+ local resources = rawdata.resources
+ local unicodes = resources.unicodes
+ local function do_it_left(what)
+ if what then
+ for unicode, description in next, descriptions do
+ local kerns = description.kerns
+ if kerns then
+ local extrakerns
+ for complex, simple in next, what do
+ complex = unicodes[complex]
+ simple = unicodes[simple]
+ if complex and simple then
+ local ks = kerns[simple]
+ if ks and not kerns[complex] then
+ if extrakerns then
+ extrakerns[complex] = ks
+ else
+ extrakerns = { [complex] = ks }
+ end
+ end
+ end
+ end
+ if extrakerns then
+ description.extrakerns = extrakerns
+ end
+ end
+ end
+ end
+ end
+ local function do_it_copy(what)
+ if what then
+ for complex, simple in next, what do
+ complex = unicodes[complex]
+ simple = unicodes[simple]
+ if complex and simple then
+ local complexdescription = descriptions[complex]
+ if complexdescription then -- optional
+ local simpledescription = descriptions[complex]
+ if simpledescription then
+ local extrakerns
+ local kerns = simpledescription.kerns
+ if kerns then
+ for unicode, kern in next, kerns do
+ if extrakerns then
+ extrakerns[unicode] = kern
+ else
+ extrakerns = { [unicode] = kern }
+ end
+ end
+ end
+ local extrakerns = simpledescription.extrakerns
+ if extrakerns then
+ for unicode, kern in next, extrakerns do
+ if extrakerns then
+ extrakerns[unicode] = kern
+ else
+ extrakerns = { [unicode] = kern }
+ end
+ end
+ end
+ if extrakerns then
+ complexdescription.extrakerns = extrakerns
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ -- add complex with values of simplified when present
+ do_it_left(afm.helpdata.leftkerned)
+ do_it_left(afm.helpdata.bothkerned)
+ -- copy kerns from simple char to complex char unless set
+ do_it_copy(afm.helpdata.bothkerned)
+ do_it_copy(afm.helpdata.rightkerned)
+end
+
+--[[ldx--
+<p>The copying routine looks messy (and is indeed a bit messy).</p>
+--ldx]]--
+
+local function adddimensions(data) -- we need to normalize afm to otf i.e. indexed table instead of name
+ if data then
+ for unicode, description in next, data.descriptions do
+ local bb = description.boundingbox
+ if bb then
+ local ht = bb[4]
+ local dp = -bb[2]
+ if ht == 0 or ht < 0 then
+ -- no need to set it and no negative heights, nil == 0
+ else
+ description.height = ht
+ end
+ if dp == 0 or dp < 0 then
+ -- no negative depths and no negative depths, nil == 0
+ else
+ description.depth = dp
+ end
+ end
+ end
+ end
+end
+
+local function copytotfm(data)
+ if data and data.descriptions then
+ local metadata = data.metadata
+ local resources = data.resources
+ local properties = derivetable(data.properties)
+ local descriptions = derivetable(data.descriptions)
+ local goodies = derivetable(data.goodies)
+ local characters = { }
+ local parameters = { }
+ local unicodes = resources.unicodes
+ --
+ for unicode, description in next, data.descriptions do -- use parent table
+ characters[unicode] = { }
+ end
+ --
+ local filename = constructors.checkedfilename(resources)
+ local fontname = metadata.fontname or metadata.fullname
+ local fullname = metadata.fullname or metadata.fontname
+ local endash = 0x2013
+ local emdash = 0x2014
+ local space = 0x0020 -- space
+ local spacer = "space"
+ local spaceunits = 500
+ --
+ local monospaced = metadata.monospaced
+ local charwidth = metadata.charwidth
+ local italicangle = metadata.italicangle
+ local charxheight = metadata.xheight and metadata.xheight > 0 and metadata.xheight
+ properties.monospaced = monospaced
+ parameters.italicangle = italicangle
+ parameters.charwidth = charwidth
+ parameters.charxheight = charxheight
+ -- nearly the same as otf, catches
+ local d_endash = descriptions[endash]
+ local d_emdash = descriptions[emdash]
+ local d_space = descriptions[space]
+ if not d_space or d_space == 0 then
+ d_space = d_endash
+ end
+ if d_space then
+ spaceunits, spacer = d_space.width or 0, "space"
+ end
+ if properties.monospaced then
+ if spaceunits == 0 and d_emdash then
+ spaceunits, spacer = d_emdash.width or 0, "emdash"
+ end
+ else
+ if spaceunits == 0 and d_endash then
+ spaceunits, spacer = d_emdash.width or 0, "endash"
+ end
+ end
+ if spaceunits == 0 and charwidth then
+ spaceunits, spacer = charwidth or 0, "charwidth"
+ end
+ if spaceunits == 0 then
+ spaceunits = tonumber(spaceunits) or 500
+ end
+ if spaceunits == 0 then
+ spaceunits = 500
+ end
+ --
+ parameters.slant = 0
+ parameters.space = spaceunits
+ parameters.space_stretch = 500
+ parameters.space_shrink = 333
+ parameters.x_height = 400
+ parameters.quad = 1000
+ --
+ if italicangle and italicangle ~= 0 then
+ parameters.italicangle = italicangle
+ parameters.italicfactor = math.cos(math.rad(90+italicangle))
+ parameters.slant = - math.tan(italicangle*math.pi/180)
+ end
+ if monospaced then
+ parameters.space_stretch = 0
+ parameters.space_shrink = 0
+ elseif afm.syncspace then
+ parameters.space_stretch = spaceunits/2
+ parameters.space_shrink = spaceunits/3
+ end
+ parameters.extra_space = parameters.space_shrink
+ if charxheight then
+ parameters.x_height = charxheight
+ else
+ -- same as otf
+ local x = 0x0078 -- x
+ if x then
+ local x = descriptions[x]
+ if x then
+ parameters.x_height = x.height
+ end
+ end
+ --
+ end
+ --
+ if metadata.sup then
+ local dummy = { 0, 0, 0 }
+ parameters[ 1] = metadata.designsize or 0
+ parameters[ 2] = metadata.checksum or 0
+ parameters[ 3],
+ parameters[ 4],
+ parameters[ 5] = unpack(metadata.space or dummy)
+ parameters[ 6] = metadata.quad or 0
+ parameters[ 7] = metadata.extraspace or 0
+ parameters[ 8],
+ parameters[ 9],
+ parameters[10] = unpack(metadata.num or dummy)
+ parameters[11],
+ parameters[12] = unpack(metadata.denom or dummy)
+ parameters[13],
+ parameters[14],
+ parameters[15] = unpack(metadata.sup or dummy)
+ parameters[16],
+ parameters[17] = unpack(metadata.sub or dummy)
+ parameters[18] = metadata.supdrop or 0
+ parameters[19] = metadata.subdrop or 0
+ parameters[20],
+ parameters[21] = unpack(metadata.delim or dummy)
+ parameters[22] = metadata.axisheight or 0
+ end
+ --
+ parameters.designsize = (metadata.designsize or 10)*65536
+ parameters.ascender = abs(metadata.ascender or 0)
+ parameters.descender = abs(metadata.descender or 0)
+ parameters.units = 1000
+ --
+ properties.spacer = spacer
+ properties.encodingbytes = 2
+ properties.format = fonts.formats[filename] or "type1"
+ properties.filename = filename
+ properties.fontname = fontname
+ properties.fullname = fullname
+ properties.psname = fullname
+ properties.name = filename or fullname or fontname
+ properties.private = properties.private or data.private or privateoffset
+ --
+ if next(characters) then
+ return {
+ characters = characters,
+ descriptions = descriptions,
+ parameters = parameters,
+ resources = resources,
+ properties = properties,
+ goodies = goodies,
+ }
+ end
+ end
+ return nil
+end
+
+--[[ldx--
+<p>Originally we had features kind of hard coded for <l n='afm'/> files but since I
+expect to support more font formats, I decided to treat this fontformat like any
+other and handle features in a more configurable way.</p>
+--ldx]]--
+
+function afm.setfeatures(tfmdata,features)
+ local okay = constructors.initializefeatures("afm",tfmdata,features,trace_features,report_afm)
+ if okay then
+ return constructors.collectprocessors("afm",tfmdata,features,trace_features,report_afm)
+ else
+ return { } -- will become false
+ end
+end
+
+local function addtables(data)
+ local resources = data.resources
+ local lookuptags = resources.lookuptags
+ local unicodes = resources.unicodes
+ if not lookuptags then
+ lookuptags = { }
+ resources.lookuptags = lookuptags
+ end
+ setmetatableindex(lookuptags,function(t,k)
+ local v = type(k) == "number" and ("lookup " .. k) or k
+ t[k] = v
+ return v
+ end)
+ if not unicodes then
+ unicodes = { }
+ resources.unicodes = unicodes
+ setmetatableindex(unicodes,function(t,k)
+ setmetatableindex(unicodes,nil)
+ for u, d in next, data.descriptions do
+ local n = d.name
+ if n then
+ t[n] = u
+ end
+ end
+ return rawget(t,k)
+ end)
+ end
+ constructors.addcoreunicodes(unicodes) -- do we really need this?
+end
+
+local function afmtotfm(specification)
+ local afmname = specification.filename or specification.name
+ if specification.forced == "afm" or specification.format == "afm" then -- move this one up
+ if trace_loading then
+ report_afm("forcing afm format for %a",afmname)
+ end
+ else
+ local tfmname = findbinfile(afmname,"ofm") or ""
+ if tfmname ~= "" then
+ if trace_loading then
+ report_afm("fallback from afm to tfm for %a",afmname)
+ end
+ return -- just that
+ end
+ end
+ if afmname ~= "" then
+ -- weird, isn't this already done then?
+ local features = constructors.checkedfeatures("afm",specification.features.normal)
+ specification.features.normal = features
+ constructors.hashinstance(specification,true) -- also weird here
+ --
+ specification = definers.resolve(specification) -- new, was forgotten
+ local cache_id = specification.hash
+ local tfmdata = containers.read(constructors.cache, cache_id) -- cache with features applied
+ if not tfmdata then
+ local rawdata = afm.load(afmname)
+ if rawdata and next(rawdata) then
+ addtables(rawdata)
+ adddimensions(rawdata)
+ tfmdata = copytotfm(rawdata)
+ if tfmdata and next(tfmdata) then
+ local shared = tfmdata.shared
+ if not shared then
+ shared = { }
+ tfmdata.shared = shared
+ end
+ shared.rawdata = rawdata
+ shared.dynamics = { }
+ tfmdata.changed = { }
+ shared.features = features
+ shared.processes = afm.setfeatures(tfmdata,features)
+ end
+ elseif trace_loading then
+ report_afm("no (valid) afm file found with name %a",afmname)
+ end
+ tfmdata = containers.write(constructors.cache,cache_id,tfmdata)
+ end
+ return tfmdata
+ end
+end
+
+--[[ldx--
+<p>As soon as we could intercept the <l n='tfm'/> reader, I implemented an
+<l n='afm'/> reader. Since traditional <l n='pdftex'/> could use <l n='opentype'/>
+fonts with <l n='afm'/> companions, the following method also could handle
+those cases, but now that we can handle <l n='opentype'/> directly we no longer
+need this features.</p>
+--ldx]]--
+
+local function read_from_afm(specification)
+ local tfmdata = afmtotfm(specification)
+ if tfmdata then
+ tfmdata.properties.name = specification.name
+ tfmdata = constructors.scale(tfmdata, specification)
+ local allfeatures = tfmdata.shared.features or specification.features.normal
+ constructors.applymanipulators("afm",tfmdata,allfeatures,trace_features,report_afm)
+ fonts.loggers.register(tfmdata,'afm',specification)
+ end
+ return tfmdata
+end
+
+--[[ldx--
+<p>We have the usual two modes and related features initializers and processors.</p>
+--ldx]]--
+
+registerafmfeature {
+ name = "mode",
+ description = "mode",
+ initializers = {
+ base = otf.modeinitializer,
+ node = otf.modeinitializer,
+ }
+}
+
+registerafmfeature {
+ name = "features",
+ description = "features",
+ default = true,
+ initializers = {
+ node = otf.nodemodeinitializer,
+ base = otf.basemodeinitializer,
+ },
+ processors = {
+ node = otf.featuresprocessor,
+ }
+}
+
+-- readers
+
+fonts.formats.afm = "type1"
+fonts.formats.pfb = "type1"
+
+local function check_afm(specification,fullname)
+ local foundname = findbinfile(fullname, 'afm') or "" -- just to be sure
+ if foundname == "" then
+ foundname = fonts.names.getfilename(fullname,"afm") or ""
+ end
+ if fullname and foundname == "" and afm.autoprefixed then
+ local encoding, shortname = match(fullname,"^(.-)%-(.*)$") -- context: encoding-name.*
+ if encoding and shortname and fonts.encodings.known[encoding] then
+ shortname = findbinfile(shortname,'afm') or "" -- just to be sure
+ if shortname ~= "" then
+ foundname = shortname
+ if trace_defining then
+ report_afm("stripping encoding prefix from filename %a",afmname)
+ end
+ end
+ end
+ end
+ if foundname ~= "" then
+ specification.filename = foundname
+ specification.format = "afm"
+ return read_from_afm(specification)
+ end
+end
+
+function readers.afm(specification,method)
+ local fullname = specification.filename or ""
+ local tfmdata = nil
+ if fullname == "" then
+ local forced = specification.forced or ""
+ if forced ~= "" then
+ tfmdata = check_afm(specification,specification.name .. "." .. forced)
+ end
+ if not tfmdata then
+ local check_tfm = readers.check_tfm
+ method = (check_tfm and (method or definers.method or "afm or tfm")) or "afm"
+ if method == "tfm" then
+ tfmdata = check_tfm(specification,specification.name)
+ elseif method == "afm" then
+ tfmdata = check_afm(specification,specification.name)
+ elseif method == "tfm or afm" then
+ tfmdata = check_tfm(specification,specification.name) or check_afm(specification,specification.name)
+ else -- method == "afm or tfm" or method == "" then
+ tfmdata = check_afm(specification,specification.name) or check_tfm(specification,specification.name)
+ end
+ end
+ else
+ tfmdata = check_afm(specification,fullname)
+ end
+ return tfmdata
+end
+
+function readers.pfb(specification,method) -- only called when forced
+ local original = specification.specification
+ if trace_defining then
+ report_afm("using afm reader for %a",original)
+ end
+ specification.forced = "afm"
+ local function swap(name)
+ local value = specification[swap]
+ if value then
+ specification[swap] = gsub("%.pfb",".afm",1)
+ end
+ end
+ swap("filename")
+ swap("fullname")
+ swap("forcedname")
+ swap("specification")
+ return readers.afm(specification,method)
+end
+
+-- now we register them
+
+registerafmenhancer("unify names", enhance_unify_names)
+registerafmenhancer("add ligatures", enhance_add_ligatures)
+registerafmenhancer("add extra kerns", enhance_add_extra_kerns)
+registerafmenhancer("normalize features", enhance_normalize_features)
+registerafmenhancer("check extra features", otfenhancers.enhance)
+registerafmenhancer("fix names", enhance_fix_names)
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-onr.lua b/macros/luatex/generic/luaotfload/fontloader-font-onr.lua
new file mode 100644
index 0000000000..188aaf6449
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-onr.lua
@@ -0,0 +1,550 @@
+if not modules then modules = { } end modules ['font-onr'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+--[[ldx--
+<p>Some code may look a bit obscure but this has to do with the fact that we also use
+this code for testing and much code evolved in the transition from <l n='tfm'/> to
+<l n='afm'/> to <l n='otf'/>.</p>
+
+<p>The following code still has traces of intermediate font support where we handles
+font encodings. Eventually font encoding went away but we kept some code around in
+other modules.</p>
+
+<p>This version implements a node mode approach so that users can also more easily
+add features.</p>
+--ldx]]--
+
+local fonts, logs, trackers, resolvers = fonts, logs, trackers, resolvers
+
+local next, type, tonumber, rawget, rawset = next, type, tonumber, rawget, rawset
+local match, lower, gsub, strip, find = string.match, string.lower, string.gsub, string.strip, string.find
+local char, byte, sub = string.char, string.byte, string.sub
+local abs = math.abs
+local bxor, rshift = bit32.bxor, bit32.rshift
+local P, S, R, V, Cmt, C, Ct, Cs, Carg, Cf, Cg, Cc = lpeg.P, lpeg.S, lpeg.R, lpeg.V, lpeg.Cmt, lpeg.C, lpeg.Ct, lpeg.Cs, lpeg.Carg, lpeg.Cf, lpeg.Cg, lpeg.Cc
+local lpegmatch, patterns = lpeg.match, lpeg.patterns
+
+local trace_indexing = false trackers.register("afm.indexing", function(v) trace_indexing = v end)
+local trace_loading = false trackers.register("afm.loading", function(v) trace_loading = v end)
+
+local report_afm = logs.reporter("fonts","afm loading")
+local report_pfb = logs.reporter("fonts","pfb loading")
+
+local handlers = fonts.handlers
+local afm = handlers.afm or { }
+handlers.afm = afm
+local readers = afm.readers or { }
+afm.readers = readers
+
+afm.version = 1.513 -- incrementing this number one up will force a re-cache
+
+--[[ldx--
+<p>We start with the basic reader which we give a name similar to the built in <l n='tfm'/>
+and <l n='otf'/> reader.</p>
+<p>We use a new (unfinished) pfb loader but I see no differences between the old
+and new vectors (we actually had one bad vector with the old loader).</p>
+--ldx]]--
+
+local get_indexes, get_shapes
+
+do
+
+ local decrypt
+
+ do
+
+ local r, c1, c2, n = 0, 0, 0, 0
+
+ local function step(c)
+ local cipher = byte(c)
+ local plain = bxor(cipher,rshift(r,8))
+ r = ((cipher + r) * c1 + c2) % 65536
+ return char(plain)
+ end
+
+ decrypt = function(binary,initial,seed)
+ r, c1, c2, n = initial, 52845, 22719, seed
+ binary = gsub(binary,".",step)
+ return sub(binary,n+1)
+ end
+
+ -- local pattern = Cs((P(1) / step)^1)
+ --
+ -- decrypt = function(binary,initial,seed)
+ -- r, c1, c2, n = initial, 52845, 22719, seed
+ -- binary = lpegmatch(pattern,binary)
+ -- return sub(binary,n+1)
+ -- end
+
+ end
+
+ local charstrings = P("/CharStrings")
+ local subroutines = P("/Subrs")
+ local encoding = P("/Encoding")
+ local dup = P("dup")
+ local put = P("put")
+ local array = P("array")
+ local name = P("/") * C((R("az","AZ","09")+S("-_."))^1)
+ local digits = R("09")^1
+ local cardinal = digits / tonumber
+ local spaces = P(" ")^1
+ local spacing = patterns.whitespace^0
+
+ local routines, vector, chars, n, m
+
+ local initialize = function(str,position,size)
+ n = 0
+ m = size
+ return position + 1
+ end
+
+ local setroutine = function(str,position,index,size,filename)
+ if routines[index] then
+ -- we have passed the end
+ return false
+ end
+ local forward = position + size
+ local stream = decrypt(sub(str,position+1,forward),4330,4)
+ routines[index] = { byte(stream,1,#stream) }
+ n = n + 1
+ if n >= m then
+ -- m should be index now but can we assume ordering?
+ return #str
+ end
+ return forward + 1
+ end
+
+ local setvector = function(str,position,name,size,filename)
+ local forward = position + tonumber(size)
+ if n >= m then
+ return #str
+ elseif forward < #str then
+ if n == 0 and name ~= ".notdef" then
+ report_pfb("reserving .notdef at index 0 in %a",filename) -- luatex needs that
+ n = n + 1
+ end
+ vector[n] = name
+ n = n + 1
+ return forward
+ else
+ return #str
+ end
+ end
+
+ local setshapes = function(str,position,name,size,filename)
+ local forward = position + tonumber(size)
+ local stream = sub(str,position+1,forward)
+ if n > m then
+ return #str
+ elseif forward < #str then
+ if n == 0 and name ~= ".notdef" then
+ report_pfb("reserving .notdef at index 0 in %a",filename) -- luatex needs that
+ n = n + 1
+ end
+ vector[n] = name
+ n = n + 1
+ chars [n] = decrypt(stream,4330,4)
+ return forward
+ else
+ return #str
+ end
+ end
+
+ local p_rd = spacing * (P("RD") + P("-|"))
+ local p_np = spacing * (P("NP") + P( "|"))
+ local p_nd = spacing * (P("ND") + P( "|"))
+
+ local p_filterroutines = -- dup <i> <n> RD or -| <n encrypted bytes> NP or |
+ (1-subroutines)^0 * subroutines * spaces * Cmt(cardinal,initialize)
+ * (Cmt(cardinal * spaces * cardinal * p_rd * Carg(1), setroutine) * p_np + (1-p_nd))^1
+
+ local p_filtershapes = -- /foo <n> RD <n encrypted bytes> ND
+ (1-charstrings)^0 * charstrings * spaces * Cmt(cardinal,initialize)
+ * (Cmt(name * spaces * cardinal * p_rd * Carg(1) , setshapes) * p_nd + P(1))^1
+
+ local p_filternames = Ct (
+ (1-charstrings)^0 * charstrings * spaces * Cmt(cardinal,initialize)
+ * (Cmt(name * spaces * cardinal * Carg(1), setvector) + P(1))^1
+ )
+
+ -- /Encoding 256 array
+ -- 0 1 255 {1 index exch /.notdef put} for
+ -- dup 0 /Foo put
+
+ local p_filterencoding =
+ (1-encoding)^0 * encoding * spaces * digits * spaces * array * (1-dup)^0
+ * Cf(
+ Ct("") * Cg(spacing * dup * spaces * cardinal * spaces * name * spaces * put)^1
+ ,rawset)
+
+ -- if one of first 4 not 0-9A-F then binary else hex
+
+ local key = spacing * P("/") * R("az","AZ")
+ local str = spacing * Cs { (P("(")/"") * ((1 - P("\\(") - P("\\)") - S("()")) + V(1))^0 * (P(")")/"") }
+ local num = spacing * (R("09") + S("+-."))^1 / tonumber
+ local arr = spacing * Ct (S("[{") * (num)^0 * spacing * S("]}"))
+ local boo = spacing * (P("true") * Cc(true) + P("false") * Cc(false))
+ local nam = spacing * P("/") * Cs(R("az","AZ")^1)
+
+ local p_filtermetadata = (
+ P("/") * Carg(1) * ( (
+ C("version") * str
+ + C("Copyright") * str
+ + C("Notice") * str
+ + C("FullName") * str
+ + C("FamilyName") * str
+ + C("Weight") * str
+ + C("ItalicAngle") * num
+ + C("isFixedPitch") * boo
+ + C("UnderlinePosition") * num
+ + C("UnderlineThickness") * num
+ + C("FontName") * nam
+ + C("FontMatrix") * arr
+ + C("FontBBox") * arr
+ ) ) / function(t,k,v) t[lower(k)] = v end
+ + P(1)
+ )^0 * Carg(1)
+
+ local function loadpfbvector(filename,shapestoo,streams)
+ -- for the moment limited to encoding only
+
+ local data = io.loaddata(resolvers.findfile(filename))
+
+ if not data then
+ report_pfb("no data in %a",filename)
+ return
+ end
+
+ if not (find(data,"!PS-AdobeFont-",1,true) or find(data,"%!FontType1",1,true)) then
+ report_pfb("no font in %a",filename)
+ return
+ end
+
+ local ascii, binary = match(data,"(.*)eexec%s+......(.*)")
+
+ if not binary then
+ report_pfb("no binary data in %a",filename)
+ return
+ end
+
+ binary = decrypt(binary,55665,4)
+
+ local names = { }
+ local encoding = lpegmatch(p_filterencoding,ascii)
+ local metadata = lpegmatch(p_filtermetadata,ascii,1,{})
+ local glyphs = { }
+
+ routines, vector, chars = { }, { }, { }
+ if shapestoo or streams then
+ -- io.savedata("foo.txt",binary)
+ lpegmatch(p_filterroutines,binary,1,filename)
+ lpegmatch(p_filtershapes,binary,1,filename)
+ local data = {
+ dictionaries = {
+ {
+ charstrings = chars,
+ charset = vector,
+ subroutines = routines,
+ }
+ },
+ }
+ -- only cff 1 in type 1 fonts
+ fonts.handlers.otf.readers.parsecharstrings(false,data,glyphs,true,"cff",streams,true)
+ else
+ lpegmatch(p_filternames,binary,1,filename)
+ end
+
+ names = vector
+
+ routines, vector, chars = nil, nil, nil
+
+ return names, encoding, glyphs, metadata
+
+ end
+
+ local pfb = handlers.pfb or { }
+ handlers.pfb = pfb
+ pfb.loadvector = loadpfbvector
+
+ get_indexes = function(data,pfbname)
+ local vector = loadpfbvector(pfbname)
+ if vector then
+ local characters = data.characters
+ if trace_loading then
+ report_afm("getting index data from %a",pfbname)
+ end
+ for index=0,#vector do -- hm, zero, often space or notdef
+ local name = vector[index]
+ local char = characters[name]
+ if char then
+ if trace_indexing then
+ report_afm("glyph %a has index %a",name,index)
+ end
+ char.index = index
+ else
+ if trace_indexing then
+ report_afm("glyph %a has index %a but no data",name,index)
+ end
+ end
+ end
+ end
+ end
+
+ get_shapes = function(pfbname)
+ local vector, encoding, glyphs = loadpfbvector(pfbname,true)
+ return glyphs
+ end
+
+end
+
+--[[ldx--
+<p>We start with the basic reader which we give a name similar to the built in <l n='tfm'/>
+and <l n='otf'/> reader. We only need data that is relevant for our use. We don't support
+more complex arrangements like multiple master (obsolete), direction specific kerning, etc.</p>
+--ldx]]--
+
+local spacer = patterns.spacer
+local whitespace = patterns.whitespace
+local lineend = patterns.newline
+local spacing = spacer^0
+local number = spacing * S("+-")^-1 * (R("09") + S("."))^1 / tonumber
+local name = spacing * C((1 - whitespace)^1)
+local words = spacing * ((1 - lineend)^1 / strip)
+local rest = (1 - lineend)^0
+local fontdata = Carg(1)
+local semicolon = spacing * P(";")
+local plus = spacing * P("plus") * number
+local minus = spacing * P("minus") * number
+
+-- kern pairs
+
+local function addkernpair(data,one,two,value)
+ local chr = data.characters[one]
+ if chr then
+ local kerns = chr.kerns
+ if kerns then
+ kerns[two] = tonumber(value)
+ else
+ chr.kerns = { [two] = tonumber(value) }
+ end
+ end
+end
+
+local p_kernpair = (fontdata * P("KPX") * name * name * number) / addkernpair
+
+-- char metrics
+
+local chr = false
+local ind = 0
+
+local function start(data,version)
+ data.metadata.afmversion = version
+ ind = 0
+ chr = { }
+end
+
+local function stop()
+ ind = 0
+ chr = false
+end
+
+local function setindex(i)
+ if i < 0 then
+ ind = ind + 1 -- ?
+ else
+ ind = i
+ end
+ chr = {
+ index = ind
+ }
+end
+
+local function setwidth(width)
+ chr.width = width
+end
+
+local function setname(data,name)
+ data.characters[name] = chr
+end
+
+local function setboundingbox(boundingbox)
+ chr.boundingbox = boundingbox
+end
+
+local function setligature(plus,becomes)
+ local ligatures = chr.ligatures
+ if ligatures then
+ ligatures[plus] = becomes
+ else
+ chr.ligatures = { [plus] = becomes }
+ end
+end
+
+local p_charmetric = ( (
+ P("C") * number / setindex
+ + P("WX") * number / setwidth
+ + P("N") * fontdata * name / setname
+ + P("B") * Ct((number)^4) / setboundingbox
+ + P("L") * (name)^2 / setligature
+ ) * semicolon )^1
+
+local p_charmetrics = P("StartCharMetrics") * number * (p_charmetric + (1-P("EndCharMetrics")))^0 * P("EndCharMetrics")
+local p_kernpairs = P("StartKernPairs") * number * (p_kernpair + (1-P("EndKernPairs" )))^0 * P("EndKernPairs" )
+
+local function set_1(data,key,a) data.metadata[lower(key)] = a end
+local function set_2(data,key,a,b) data.metadata[lower(key)] = { a, b } end
+local function set_3(data,key,a,b,c) data.metadata[lower(key)] = { a, b, c } end
+
+-- Notice string
+-- EncodingScheme string
+-- MappingScheme integer
+-- EscChar integer
+-- CharacterSet string
+-- Characters integer
+-- IsBaseFont boolean
+-- VVector number number
+-- IsFixedV boolean
+
+local p_parameters = P(false)
+ + fontdata
+ * ((P("FontName") + P("FullName") + P("FamilyName"))/lower)
+ * words / function(data,key,value)
+ data.metadata[key] = value
+ end
+ + fontdata
+ * ((P("Weight") + P("Version"))/lower)
+ * name / function(data,key,value)
+ data.metadata[key] = value
+ end
+ + fontdata
+ * P("IsFixedPitch")
+ * name / function(data,pitch)
+ data.metadata.monospaced = toboolean(pitch,true)
+ end
+ + fontdata
+ * P("FontBBox")
+ * Ct(number^4) / function(data,boundingbox)
+ data.metadata.boundingbox = boundingbox
+ end
+ + fontdata
+ * ((P("CharWidth") + P("CapHeight") + P("XHeight") + P("Descender") + P("Ascender") + P("ItalicAngle"))/lower)
+ * number / function(data,key,value)
+ data.metadata[key] = value
+ end
+ + P("Comment") * spacing * ( P(false)
+ + (fontdata * C("DESIGNSIZE") * number * rest) / set_1 -- 1
+ + (fontdata * C("TFM designsize") * number * rest) / set_1
+ + (fontdata * C("DesignSize") * number * rest) / set_1
+ + (fontdata * C("CODINGSCHEME") * words * rest) / set_1 --
+ + (fontdata * C("CHECKSUM") * number * words * rest) / set_1 -- 2
+ + (fontdata * C("SPACE") * number * plus * minus * rest) / set_3 -- 3 4 5
+ + (fontdata * C("QUAD") * number * rest) / set_1 -- 6
+ + (fontdata * C("EXTRASPACE") * number * rest) / set_1 -- 7
+ + (fontdata * C("NUM") * number * number * number * rest) / set_3 -- 8 9 10
+ + (fontdata * C("DENOM") * number * number * rest) / set_2 -- 11 12
+ + (fontdata * C("SUP") * number * number * number * rest) / set_3 -- 13 14 15
+ + (fontdata * C("SUB") * number * number * rest) / set_2 -- 16 17
+ + (fontdata * C("SUPDROP") * number * rest) / set_1 -- 18
+ + (fontdata * C("SUBDROP") * number * rest) / set_1 -- 19
+ + (fontdata * C("DELIM") * number * number * rest) / set_2 -- 20 21
+ + (fontdata * C("AXISHEIGHT") * number * rest) / set_1 -- 22
+ )
+
+local fullparser = ( P("StartFontMetrics") * fontdata * name / start )
+ * ( p_charmetrics + p_kernpairs + p_parameters + (1-P("EndFontMetrics")) )^0
+ * ( P("EndFontMetrics") / stop )
+
+local infoparser = ( P("StartFontMetrics") * fontdata * name / start )
+ * ( p_parameters + (1-P("EndFontMetrics")) )^0
+ * ( P("EndFontMetrics") / stop )
+
+-- infoparser = ( P("StartFontMetrics") * fontdata * name / start )
+-- * ( p_parameters + (1-P("EndFontMetrics") - P("StartCharMetrics")) )^0
+-- * ( (P("EndFontMetrics") + P("StartCharMetrics")) / stop )
+
+local function read(filename,parser)
+ local afmblob = io.loaddata(filename)
+ if afmblob then
+ local data = {
+ resources = {
+ filename = resolvers.unresolve(filename),
+ version = afm.version,
+ creator = "context mkiv",
+ },
+ properties = {
+ hasitalics = false,
+ },
+ goodies = {
+ },
+ metadata = {
+ filename = file.removesuffix(file.basename(filename))
+ },
+ characters = {
+ -- a temporary store
+ },
+ descriptions = {
+ -- the final store
+ },
+ }
+ if trace_loading then
+ report_afm("parsing afm file %a",filename)
+ end
+ lpegmatch(parser,afmblob,1,data)
+ return data
+ else
+ if trace_loading then
+ report_afm("no valid afm file %a",filename)
+ end
+ return nil
+ end
+end
+
+function readers.loadfont(afmname,pfbname)
+ local data = read(resolvers.findfile(afmname),fullparser)
+ if data then
+ if not pfbname or pfbname == "" then
+ pfbname = resolvers.findfile(file.replacesuffix(file.nameonly(afmname),"pfb"))
+ end
+ if pfbname and pfbname ~= "" then
+ data.resources.filename = resolvers.unresolve(pfbname)
+ get_indexes(data,pfbname)
+ return data
+ else -- if trace_loading then
+ report_afm("no pfb file for %a",afmname)
+ -- better than loading the afm file: data.resources.filename = rawname
+ -- but that will still crash the backend so we just return nothing now
+ end
+ end
+end
+
+-- for now, todo: n and check with otf (no afm needed here)
+
+function readers.loadshapes(filename)
+ local fullname = resolvers.findfile(filename) or ""
+ if fullname == "" then
+ return {
+ filename = "not found: " .. filename,
+ glyphs = { }
+ }
+ else
+ return {
+ filename = fullname,
+ format = "opentype",
+ glyphs = get_shapes(fullname) or { },
+ units = 1000,
+ }
+ end
+end
+
+
+function readers.getinfo(filename)
+ local data = read(resolvers.findfile(filename),infoparser)
+ if data then
+ return data.metadata
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-osd.lua b/macros/luatex/generic/luaotfload/fontloader-font-osd.lua
new file mode 100644
index 0000000000..203c1d79d4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-osd.lua
@@ -0,0 +1,2859 @@
+if not modules then modules = { } end modules ['font-osd'] = { -- script devanagari
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Kai Eigner, TAT Zetwerk / Hans Hagen, PRAGMA ADE",
+ copyright = "TAT Zetwerk / PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+
+-- we need to check nbsphash (context only)
+
+-- A few remarks:
+--
+-- This code is a partial rewrite of the code that deals with devanagari. The data
+-- and logic is by Kai Eigner and based based on Microsoft's OpenType specifications
+-- for specific scripts, but with a few improvements. More information can be found
+-- at:
+--
+-- deva: http://www.microsoft.com/typography/OpenType%20Dev/devanagari/introO.mspx
+-- dev2: http://www.microsoft.com/typography/OpenType%20Dev/devanagari/intro.mspx
+--
+-- Rajeesh Nambiar provided patches for the malayalam variant. Thanks to feedback
+-- from the mailing list some aspects could be improved.
+--
+-- As I touched nearly all code, reshuffled it, optimized a lot, etc. etc. (imagine
+-- how much can get messed up in over a week work) it could be that I introduced
+-- bugs. There is more to gain (esp in the functions applied to a range) but I'll do
+-- that when everything works as expected. Kai's original code is kept in
+-- font-odk.lua as a reference so blame me (HH) for bugs. (We no longer ship that
+-- file as the code below has diverted too much and in the meantime has more than
+-- doubled in size.)
+--
+-- Interesting is that Kai managed to write this on top of the existing otf handler.
+-- Only a few extensions were needed, like a few more analyzing states and dealing
+-- with changed head nodes in the core scanner as that only happens here. There's a
+-- lot going on here and it's only because I touched nearly all code that I got a
+-- bit of a picture of what happens. For in-depth knowledge one needs to consult
+-- Kai.
+--
+-- The rewrite mostly deals with efficiency, both in terms of speed and code. We
+-- also made sure that it suits generic use as well as use in ConTeXt. I removed
+-- some buglets but can as well have messed up the logic by doing this. For this we
+-- keep the original around as that serves as reference. Due to the lots of
+-- reshuffling glyphs quite some leaks occur(red) but once I'm satisfied with the
+-- rewrite I'll weed them. I also integrated initialization etc into the regular
+-- mechanisms.
+--
+-- In the meantime, we're down from 25.5-3.5=22 seconds to 17.7-3.5=14.2 seconds for
+-- a 100 page sample (mid 2012) with both variants so it's worth the effort. Some
+-- more speedup is to be expected. Due to the method chosen it will never be real
+-- fast. If I ever become a power user I'll have a go at some further speed up. I
+-- will rename some functions (and features) once we don't need to check the
+-- original code. We now use a special subset sequence for use inside the analyzer
+-- (after all we could can store this in the dataset and save redundant analysis).
+--
+-- By now we have yet another incremental improved version. In the end I might
+-- rewrite the code.
+--
+-- Hans Hagen, PRAGMA-ADE, Hasselt NL
+
+-- Todo:
+--
+-- Matras: according to Microsoft typography specifications "up to one of each type:
+-- pre-, above-, below- or post- base", but that does not seem to be right. It could
+-- become an option.
+--
+-- Resources:
+--
+-- The tables that we had here are now generated from char-def.lua or in the case of
+-- generic usage loaded from luatex-basics-chr.lua. Still a couple of entries need
+-- to be added to char-def.lua but finally I moved the indic specific tables there.
+-- For generic usage one can create the relevant resources by running:
+--
+-- context luatex-basics-prepare.tex
+--
+-- and an overview with:
+--
+-- context --global s-fonts-basics.mkiv
+--
+-- For now we have defined: bengali, devanagari, gujarati, gurmukhi, kannada,
+-- malayalam, oriya, tamil and tolugu but not all are checked. Also, some of the
+-- code below might need to be adapted to the extra scripts.
+
+local insert, imerge, copy, tohash = table.insert, table.imerge, table.copy, table.tohash
+local next, type = next, type
+
+local report = logs.reporter("otf","devanagari")
+
+fonts = fonts or { }
+fonts.analyzers = fonts.analyzers or { }
+fonts.analyzers.methods = fonts.analyzers.methods or { node = { otf = { } } }
+
+local otf = fonts.handlers.otf
+
+local handlers = otf.handlers
+local methods = fonts.analyzers.methods
+
+local otffeatures = fonts.constructors.features.otf
+local registerotffeature = otffeatures.register
+
+local nuts = nodes.nuts
+
+local getnext = nuts.getnext
+local getprev = nuts.getprev
+local getboth = nuts.getboth
+local getid = nuts.getid
+local getchar = nuts.getchar
+local getfont = nuts.getfont
+local getsubtype = nuts.getsubtype
+local setlink = nuts.setlink
+local setnext = nuts.setnext
+local setprev = nuts.setprev
+local setchar = nuts.setchar
+local getprop = nuts.getprop
+local setprop = nuts.setprop
+
+local ischar = nuts.ischar
+
+local insert_node_after = nuts.insert_after
+local copy_node = nuts.copy
+local remove_node = nuts.remove
+local flush_list = nuts.flush_list
+local flush_node = nuts.flush_node
+
+local copyinjection = nodes.injections.copy -- KE: is this necessary? HH: probably not as positioning comes later and we rawget/set
+
+local unsetvalue = attributes.unsetvalue
+
+local fontdata = fonts.hashes.identifiers
+
+local a_state = attributes.private('state')
+local a_syllabe = attributes.private('syllabe')
+
+local dotted_circle = 0x25CC
+local c_nbsp = 0x00A0
+local c_zwnj = 0x200C
+local c_zwj = 0x200D
+
+local states = fonts.analyzers.states -- not features
+
+local s_rphf = states.rphf
+local s_half = states.half
+local s_pref = states.pref
+local s_blwf = states.blwf
+local s_pstf = states.pstf
+local s_init = states.init
+
+local replace_all_nbsp = nil
+
+replace_all_nbsp = function(head) -- delayed definition
+ replace_all_nbsp = typesetters and typesetters.characters and typesetters.characters.replacenbspaces or function(head)
+ return head
+ end
+ return replace_all_nbsp(head)
+end
+
+local processcharacters = nil
+
+if context then
+ local fontprocesses = fonts.hashes.processes
+ function processcharacters(head,font)
+ local processors = fontprocesses[font]
+ for i=1,#processors do
+ head = processors[i](head,font,0)
+ end
+ return head
+ end
+else
+ function processcharacters(head,font)
+ local processors = fontdata[font].shared.processes
+ for i=1,#processors do
+ head = processors[i](head,font,0)
+ end
+ return head
+ end
+end
+
+-- We can assume that script are not mixed in the source but if that is the case
+-- we might need to have consonants etc per script and initialize a local table
+-- pointing to the right one. But not now.
+
+local indicgroups = characters and characters.indicgroups
+
+if not indicgroups and characters then
+
+ local indic = {
+ c = { }, -- consonant
+ i = { }, -- independent vowel
+ d = { }, -- dependent vowel
+ m = { }, -- vowel modifier
+ s = { }, -- stress tone mark
+ o = { }, -- other
+ }
+
+ local indicmarks = {
+ l = { }, -- left | pre_mark
+ t = { }, -- top | above_mark
+ b = { }, -- bottom | below_mark
+ r = { }, -- right | post_mark
+ s = { }, -- split | twopart_mark
+ }
+
+ local indicclasses = {
+ nukta = { },
+ halant = { },
+ ra = { },
+ anudatta = { },
+ }
+
+ local indicorders = {
+ bp = { }, -- before_postscript
+ ap = { }, -- after_postscript
+ bs = { }, -- before_subscript
+ as = { }, -- after_subscript
+ bh = { }, -- before_half
+ ah = { }, -- after_half
+ bm = { }, -- before_main
+ am = { }, -- after_main
+ }
+
+ for k, v in next, characters.data do
+ local i = v.indic
+ if i then
+ indic[i][k] = true
+ i = v.indicmark
+ if i then
+ if i == "s" then
+ local s = v.specials
+ indicmarks[i][k] = { s[2], s[3] }
+ else
+ indicmarks[i][k] = true
+ end
+ end
+ i = v.indicclass
+ if i then
+ indicclasses[i][k] = true
+ end
+ i = v.indicorder
+ if i then
+ indicorders[i][k] = true
+ end
+ end
+ end
+
+ indicgroups = {
+ consonant = indic.c,
+ independent_vowel = indic.i,
+ dependent_vowel = indic.d,
+ vowel_modifier = indic.m,
+ stress_tone_mark = indic.s,
+ -- other = indic.o,
+ pre_mark = indicmarks.l,
+ above_mark = indicmarks.t,
+ below_mark = indicmarks.b,
+ post_mark = indicmarks.r,
+ twopart_mark = indicmarks.s,
+ nukta = indicclasses.nukta,
+ halant = indicclasses.halant,
+ ra = indicclasses.ra,
+ anudatta = indicclasses.anudatta,
+ before_postscript = indicorders.bp,
+ after_postscript = indicorders.ap,
+ before_half = indicorders.bh,
+ after_half = indicorders.ah,
+ before_subscript = indicorders.bs,
+ after_subscript = indicorders.as,
+ before_main = indicorders.bm,
+ after_main = indicorders.am,
+ }
+
+ indic = nil
+ indicmarks = nil
+ indicclasses = nil
+ indicorders = nil
+
+ characters.indicgroups = indicgroups
+
+end
+
+local consonant = indicgroups.consonant
+local independent_vowel = indicgroups.independent_vowel
+local dependent_vowel = indicgroups.dependent_vowel
+local vowel_modifier = indicgroups.vowel_modifier
+local stress_tone_mark = indicgroups.stress_tone_mark
+local pre_mark = indicgroups.pre_mark
+local above_mark = indicgroups.above_mark
+local below_mark = indicgroups.below_mark
+local post_mark = indicgroups.post_mark
+local twopart_mark = indicgroups.twopart_mark
+local nukta = indicgroups.nukta
+local halant = indicgroups.halant
+local ra = indicgroups.ra
+local anudatta = indicgroups.anudatta
+
+local before_postscript = indicgroups.before_postscript
+local after_postscript = indicgroups.after_postscript
+local before_half = indicgroups.before_half
+local after_half = indicgroups.after_half
+local before_subscript = indicgroups.before_subscript
+local after_subscript = indicgroups.after_subscript
+local before_main = indicgroups.before_main
+local after_main = indicgroups.after_main
+
+local mark_four = table.merged (
+ pre_mark,
+ above_mark,
+ below_mark,
+ post_mark
+)
+
+local mark_above_below_post = table.merged (
+ above_mark,
+ below_mark,
+ post_mark
+)
+
+-- We use some pseudo features as we need to manipulate the nodelist based
+-- on information in the font as well as already applied features. We can
+-- probably replace some of the code below by injecting 'real' features
+-- using the extension mechanism.
+
+local zw_char = { -- both_joiners_true
+ [c_zwnj] = true,
+ [c_zwj ] = true,
+}
+
+local dflt_true = {
+ dflt = true,
+}
+
+local two_defaults = { }
+local one_defaults = { }
+
+local false_flags = { false, false, false, false }
+
+local sequence_reorder_matras = {
+ features = { dv01 = two_defaults },
+ flags = false_flags,
+ name = "dv01_reorder_matras",
+ order = { "dv01" },
+ type = "devanagari_reorder_matras",
+ nofsteps = 1,
+ steps = {
+ {
+ coverage = pre_mark,
+ }
+ }
+}
+
+local sequence_reorder_reph = {
+ features = { dv02 = two_defaults },
+ flags = false_flags,
+ name = "dv02_reorder_reph",
+ order = { "dv02" },
+ type = "devanagari_reorder_reph",
+ nofsteps = 1,
+ steps = {
+ {
+ coverage = { },
+ }
+ }
+}
+
+local sequence_reorder_pre_base_reordering_consonants = {
+ features = { dv03 = one_defaults },
+ flags = false_flags,
+ name = "dv03_reorder_pre_base_reordering_consonants",
+ order = { "dv03" },
+ type = "devanagari_reorder_pre_base_reordering_consonants",
+ nofsteps = 1,
+ steps = {
+ {
+ coverage = { },
+ }
+ }
+}
+
+local sequence_remove_joiners = {
+ features = { dv04 = one_defaults },
+ flags = false_flags,
+ name = "dv04_remove_joiners",
+ order = { "dv04" },
+ type = "devanagari_remove_joiners",
+ nofsteps = 1,
+ steps = {
+ {
+ coverage = zw_char, -- both_joiners_true
+ },
+ }
+}
+
+-- Looping over feature twice as efficient as looping over basic forms (some
+-- 350 checks instead of 750 for one font). This is something to keep an eye on
+-- as it might depends on the font. Not that it's a bottleneck.
+
+local basic_shaping_forms = {
+ akhn = true,
+ blwf = true,
+ cjct = true,
+ half = true,
+ nukt = true,
+ pref = true,
+ pstf = true,
+ rkrf = true,
+ rphf = true,
+ vatu = true,
+ locl = true,
+}
+
+local valid = {
+ abvs = true,
+ akhn = true,
+ blwf = true,
+ calt = true,
+ cjct = true,
+ half = true,
+ haln = true,
+ nukt = true,
+ pref = true,
+ pres = true,
+ pstf = true,
+ psts = true,
+ rkrf = true,
+ rphf = true,
+ vatu = true,
+ pres = true,
+ abvs = true,
+ blws = true,
+ psts = true,
+ haln = true,
+ calt = true,
+ locl = true,
+}
+
+local scripts = { }
+
+local scripts_one = { "deva", "mlym", "beng", "gujr", "guru", "knda", "orya", "taml", "telu" }
+local scripts_two = { "dev2", "mlm2", "bng2", "gjr2", "gur2", "knd2", "ory2", "tml2", "tel2" }
+
+local nofscripts = #scripts_one
+
+for i=1,nofscripts do
+ local one = scripts_one[i]
+ local two = scripts_two[i]
+ scripts[one] = true
+ scripts[two] = true
+ two_defaults[two] = dflt_true
+ one_defaults[one] = dflt_true
+ one_defaults[two] = dflt_true
+end
+
+local function valid_one(s) for i=1,nofscripts do if s[scripts_one[i]] then return true end end end
+local function valid_two(s) for i=1,nofscripts do if s[scripts_two[i]] then return true end end end
+
+local function initializedevanagi(tfmdata)
+ local script, language = otf.scriptandlanguage(tfmdata,attr) -- todo: take fast variant
+ if scripts[script] then
+ local resources = tfmdata.resources
+ local devanagari = resources.devanagari
+ if not devanagari then
+ --
+ report("adding devanagari features to font")
+ --
+ local gsubfeatures = resources.features.gsub
+ local sequences = resources.sequences
+ local sharedfeatures = tfmdata.shared.features
+ --
+ gsubfeatures["dv01"] = two_defaults -- reorder matras
+ gsubfeatures["dv02"] = two_defaults -- reorder reph
+ gsubfeatures["dv03"] = one_defaults -- reorder pre base reordering consonants
+ gsubfeatures["dv04"] = one_defaults -- remove joiners
+ --
+ local reorder_pre_base_reordering_consonants = copy(sequence_reorder_pre_base_reordering_consonants)
+ local reorder_reph = copy(sequence_reorder_reph)
+ local reorder_matras = copy(sequence_reorder_matras)
+ local remove_joiners = copy(sequence_remove_joiners)
+
+ local lastmatch = 0
+ for s=1,#sequences do -- classify chars and make sure basic_shaping_forms come first
+ local features = sequences[s].features
+ if features then
+ for k, v in next, features do
+ if k == "locl" then
+ local steps = sequences[s].steps
+ local nofsteps = sequences[s].nofsteps
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ for k, v in next, pre_mark do
+ local locl = coverage[k]
+ if locl then
+ if #locl > 0 then --contextchain; KE: is this right?
+ for j=1,#locl do
+ local ck = locl[j]
+ local f = ck[4]
+ local chainlookups = ck[6]
+ if chainlookups then
+ local chainlookup = chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep = chainlookup[j]
+ local steps = chainstep.steps
+ local nofsteps = chainstep.nofsteps
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ locl = coverage[k]
+ end
+ end
+ end
+ end
+ end
+ end
+ if locl then
+ reorder_matras.steps[1].coverage[locl] = true
+ end
+ end
+ end
+ end
+ end
+ end
+ if basic_shaping_forms[k] then
+ lastmatch = lastmatch + 1
+ if s ~= lastmatch then
+ table.insert(sequences, lastmatch, table.remove(sequences, s))
+ end
+ end
+ end
+ end
+ end
+ local insertindex = lastmatch + 1
+ --
+ if tfmdata.properties.language then
+ dflt_true[tfmdata.properties.language] = true
+ end
+ --
+ insert(sequences,insertindex,reorder_pre_base_reordering_consonants)
+ insert(sequences,insertindex,reorder_reph)
+ insert(sequences,insertindex,reorder_matras)
+ insert(sequences,insertindex,remove_joiners)
+ --
+ local blwfcache = { }
+ local vatucache = { }
+ local pstfcache = { }
+ local seqsubset = { }
+ local rephstep = {
+ coverage = { } -- will be adapted each work
+ }
+ local devanagari = {
+ reph = false,
+ vattu = false,
+ blwfcache = blwfcache,
+ vatucache = vatucache,
+ pstfcache = pstfcache,
+ seqsubset = seqsubset,
+ reorderreph = rephstep,
+
+ }
+ --
+ reorder_reph.steps = { rephstep }
+ --
+ local pre_base_reordering_consonants = { }
+ reorder_pre_base_reordering_consonants.steps[1].coverage = pre_base_reordering_consonants
+ --
+ resources.devanagari = devanagari
+ --
+ for s=1,#sequences do
+ local sequence = sequences[s]
+ local steps = sequence.steps
+ local nofsteps = sequence.nofsteps
+ local features = sequence.features
+ local has_rphf = features.rphf
+ local has_blwf = features.blwf
+ local has_vatu = features.vatu
+ local has_pstf = features.pstf
+ if has_rphf and has_rphf[script] then
+ devanagari.reph = true
+ elseif (has_blwf and has_blwf[script] ) or (has_vatu and has_vatu[script] ) then
+ devanagari.vattu = true
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ for k, v in next, coverage do
+ for h, w in next, halant do
+ if v[h] then
+ if not blwfcache[k] then
+ blwfcache[k] = v
+ end
+ end
+ if has_vatu and has_vatu[script] and not vatucache[k] then
+ vatucache[k] = v
+ end
+ end
+ end
+ end
+ end
+ elseif has_pstf and has_pstf[script] then
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ for k, v in next, coverage do
+ if not pstfcache[k] then
+ pstfcache[k] = v
+ end
+ end
+ for k, v in next, ra do
+ local r = coverage[k]
+ if r then
+ local found = false
+ if #r > 0 then -- contextchain; KE: is this right?
+ for j=1,#r do
+ local ck = r[j]
+ local f = ck[4]
+ local chainlookups = ck[6]
+ if chainlookups and chainlookups[f] then --KE: why is check for chainlookups[f] necessacy???
+ local chainlookup = chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep = chainlookup[j]
+ local steps = chainstep.steps
+ local nofsteps = chainstep.nofsteps
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ local h = coverage[k]
+ if h then
+ for k, v in next, h do
+ found = v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found] = true
+ break
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k, v in next, r do
+ found = v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found] = true
+ break
+ end
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ for kind, spec in next, features do
+ if valid[kind] and valid_two(spec)then
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ local reph, rephbase = false, false
+ if kind == "rphf" then
+ -- rphf acts on consonant + halant
+ for k, v in next, ra do
+ local r = coverage[k]
+ if r then
+ rephbase = k
+ local h = false
+ if #r > 0 then --contextchain; KE: is this right?
+ for j=1,#r do
+ local ck = r[j]
+ local f = ck[4]
+ local chainlookups = ck[6]
+ if chainlookups then
+ local chainlookup = chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep = chainlookup[j]
+ local steps = chainstep.steps
+ local nofsteps = chainstep.nofsteps
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ local r = coverage[k]
+ if r then
+ for k, v in next, halant do
+ local h = r[k]
+ if h then
+ reph = h.ligature or false
+ break
+ end
+ end
+ if h then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k, v in next, halant do
+ local h = r[k]
+ if h then
+ reph = h.ligature or false
+ break
+ end
+ end
+ end
+ if reph then
+ break
+ end
+ end
+ end
+ end
+ seqsubset[#seqsubset+1] = { kind, coverage, reph, rephbase }
+ end
+ end
+ end
+ if kind == "pref" then
+ local steps = sequence.steps
+ local nofsteps = sequence.nofsteps
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ for k, v in next, halant do
+ local h = coverage[k]
+ if h then
+ local found = false
+ if #h > 0 then -- contextchain; KE: is this right?
+ for j=1,#h do
+ local ck = h[j]
+ local f = ck[4]
+ local chainlookups = ck[6]
+ if chainlookups then
+ local chainlookup = chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep = chainlookup[j]
+ local steps = chainstep.steps
+ local nofsteps = chainstep.nofsteps
+ for i=1,nofsteps do
+ local step = steps[i]
+ local coverage = step.coverage
+ if coverage then
+ local h = coverage[k]
+ if h then
+ for k, v in next, h do
+ found = v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found] = true
+ break
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k, v in next, h do
+ found = v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found] = true
+ break
+ end
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ --
+ if two_defaults[script] then
+ sharedfeatures["dv01"] = true -- dv01_reorder_matras
+ sharedfeatures["dv02"] = true -- dv02_reorder_reph
+ sharedfeatures["dv03"] = true -- dv03_reorder_pre_base_reordering_consonants
+ sharedfeatures["dv04"] = true -- dv04_remove_joiners
+ elseif one_defaults[script] then
+ sharedfeatures["dv03"] = true -- dv03_reorder_pre_base_reordering_consonants
+ sharedfeatures["dv04"] = true -- dv04_remove_joiners
+ end
+ if script == "mlym" or script == "taml" then
+ devanagari.left_matra_before_base = true
+ end
+ end
+ end
+end
+
+registerotffeature {
+ name = "devanagari",
+ description = "inject additional features",
+ default = true,
+ initializers = {
+ node = initializedevanagi,
+ },
+}
+
+local show_syntax_errors = false
+
+local function inject_syntax_error(head,current,char)
+ local signal = copy_node(current)
+ copyinjection(signal,current)
+ if pre_mark[char] then
+ setchar(signal,dotted_circle)
+ else
+ setchar(current,dotted_circle)
+ end
+ return insert_node_after(head,current,signal)
+end
+
+-- hm, this is applied to one character:
+
+local function initialize_one(font,attr) -- we need a proper hook into the dataset initializer
+
+ local tfmdata = fontdata[font]
+ local datasets = otf.dataset(tfmdata,font,attr) -- don't we know this one?
+ local devanagaridata = datasets.devanagari
+
+ if not devanagaridata then
+
+ devanagaridata = {
+ reph = false,
+ vattu = false,
+ blwfcache = { },
+ vatucache = { },
+ pstfcache = { },
+ }
+ datasets.devanagari = devanagaridata
+ local resources = tfmdata.resources
+ local devanagari = resources.devanagari
+
+ for s=1,#datasets do
+ local dataset = datasets[s]
+ if dataset and dataset[1] then -- value
+ local kind = dataset[4]
+ if kind == "rphf" then
+ -- deva
+ devanagaridata.reph = true
+ elseif kind == "blwf" or kind == "vatu" then
+ -- deva
+ devanagaridata.vattu = true
+ -- dev2
+ devanagaridata.blwfcache = devanagari.blwfcache
+ devanagaridata.vatucache = devanagari.vatucache
+ devanagaridata.pstfcache = devanagari.pstfcache
+ end
+ end
+ end
+
+ end
+
+ return devanagaridata.reph, devanagaridata.vattu, devanagaridata.blwfcache, devanagaridata.vatucache, devanagaridata.pstfcache
+
+end
+
+local function contextchain(contexts, n)
+ local char = getchar(n)
+ for k=1,#contexts do
+ local ck = contexts[k]
+ local seq = ck[3]
+ local f = ck[4]
+ local l = ck[5]
+ if (l - f) == 1 and seq[f+1][char] then
+ local ok = true
+ local c = n
+ for i=l+1,#seq do
+ c = getnext(c)
+ if not c or not seq[i][ischar(c)] then
+ ok = false
+ break
+ end
+ end
+ if ok then
+ c = getprev(n)
+ for i=1,f-1 do
+ c = getprev(c)
+ if not c or not seq[f-i][ischar(c)] then
+ ok = false
+ end
+ end
+ end
+ if ok then
+ return true
+ end
+ end
+ end
+ return false
+end
+
+local function order_matras(c)
+ local cn = getnext(c)
+ local char = getchar(cn)
+ while dependent_vowel[char] do
+ local next = getnext(cn)
+ local cc = c
+ local cchar = getchar(cc)
+ while cc ~= cn do
+ if (above_mark[char] and (below_mark[cchar] or post_mark[cchar])) or (below_mark[char] and (post_mark[cchar])) then
+ local prev, next = getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ -- todo: setlink
+ setnext(prev,next)
+ setnext(getprev(cc),cn)
+ setprev(cn,getprev(cc))
+ setnext(cn,cc)
+ setprev(cc,cn)
+ break
+ end
+ cc = getnext(cc)
+ cchar = getchar(cc)
+ end
+ cn = next
+ char = getchar(cn)
+ end
+end
+
+local function reorder_one(head,start,stop,font,attr,nbspaces)
+
+ local reph, vattu, blwfcache, vatucache, pstfcache = initialize_one(font,attr) -- todo: a hash[font]
+
+ local devanagari = fontdata[font].resources.devanagari
+ local current = start
+ local n = getnext(start)
+ local base = nil
+ local firstcons = nil
+ local lastcons = nil
+ local basefound = false
+
+ if reph and ra[getchar(start)] and halant[getchar(n)] then
+ -- if syllable starts with Ra + H and script has 'Reph' then exclude Reph
+ -- from candidates for base consonants
+ if n == stop then
+ return head, stop, nbspaces
+ end
+ if getchar(getnext(n)) == c_zwj then
+ current = start
+ else
+ current = getnext(n)
+ setprop(start,a_state,s_rphf)
+ end
+ end
+
+ if getchar(current) == c_nbsp then
+ -- Stand Alone cluster
+ if current == stop then
+ stop = getprev(stop)
+ head = remove_node(head,current)
+ flush_node(current)
+ return head, stop, nbspaces
+ else
+ nbspaces = nbspaces + 1
+ base = current
+ firstcons = current
+ lastcons = current
+ current = getnext(current)
+ if current ~= stop then
+ local char = getchar(current)
+ if nukta[char] then
+ current = getnext(current)
+ char = getchar(current)
+ end
+ if char == c_zwj and current ~= stop then
+ local next = getnext(current)
+ if next ~= stop and halant[getchar(next)] then
+ current = next
+ next = getnext(current)
+ local tmp = next and getnext(next) or nil -- needs checking
+ local changestop = next == stop
+ local tempcurrent = copy_node(next)
+ copyinjection(tempcurrent,next)
+ local nextcurrent = copy_node(current)
+ copyinjection(nextcurrent,current) -- KE: necessary? HH: probably not as positioning comes later and we rawget/set
+ setlink(tempcurrent,nextcurrent)
+ setprop(tempcurrent,a_state,s_blwf)
+ tempcurrent = processcharacters(tempcurrent,font)
+ setprop(tempcurrent,a_state,unsetvalue)
+ if getchar(next) == getchar(tempcurrent) then
+ flush_list(tempcurrent)
+ if show_syntax_errors then
+ head, current = inject_syntax_error(head,current,char)
+ end
+ else
+ setchar(current,getchar(tempcurrent)) -- we assumes that the result of blwf consists of one node
+ local freenode = getnext(current)
+ setlink(current,tmp)
+ flush_node(freenode)
+ flush_list(tempcurrent)
+ if changestop then
+ stop = current
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+
+ while not basefound do
+ -- find base consonant
+ local char = getchar(current)
+ if consonant[char] then
+ setprop(current,a_state,s_half)
+ if not firstcons then
+ firstcons = current
+ end
+ lastcons = current
+ if not base then
+ base = current
+ elseif blwfcache[char] then
+ -- consonant has below-base form
+ setprop(current,a_state,s_blwf)
+ elseif pstfcache[char] then
+ -- consonant has post-base form
+ setprop(current,a_state,s_pstf)
+ else
+ base = current
+ end
+ end
+ basefound = current == stop
+ current = getnext(current)
+ end
+
+ if base ~= lastcons then
+ -- if base consonant is not last one then move halant from base consonant to last one
+ local np = base
+ local n = getnext(base)
+ local ch = getchar(n)
+ if nukta[ch] then
+ np = n
+ n = getnext(n)
+ ch = getchar(n)
+ end
+ if halant[ch] then
+ if lastcons ~= stop then
+ local ln = getnext(lastcons)
+ if nukta[getchar(ln)] then
+ lastcons = ln
+ end
+ end
+ -- local np = getprev(n)
+ local nn = getnext(n)
+ local ln = getnext(lastcons) -- what if lastcons is nn ?
+ setlink(np,nn)
+ setnext(lastcons,n)
+ if ln then
+ setprev(ln,n)
+ end
+ setnext(n,ln)
+ setprev(n,lastcons)
+ if lastcons == stop then
+ stop = n
+ end
+ end
+ end
+
+ n = getnext(start)
+ if n ~= stop and ra[getchar(start)] and halant[getchar(n)] and not zw_char[getchar(getnext(n))] then
+ -- if syllable starts with Ra + H then move this combination so that it follows either:
+ -- the post-base 'matra' (if any) or the base consonant
+ local matra = base
+ if base ~= stop then
+ local next = getnext(base)
+ if dependent_vowel[getchar(next)] then
+ matra = next
+ end
+ end
+ -- [sp][start][n][nn] [matra|base][?]
+ -- [matra|base][start] [n][?] [sp][nn]
+ local sp = getprev(start)
+ local nn = getnext(n)
+ local mn = getnext(matra)
+ setlink(sp,nn)
+ setlink(matra,start)
+ setlink(n,mn)
+ if head == start then
+ head = nn
+ end
+ start = nn
+ if matra == stop then
+ stop = n
+ end
+ end
+
+ local current = start
+ while current ~= stop do
+ local next = getnext(current)
+ if next ~= stop and halant[getchar(next)] and getchar(getnext(next)) == c_zwnj then
+ setprop(current,a_state,unsetvalue)
+ end
+ current = next
+ end
+
+ if base ~= stop and getprop(base,a_state) then -- a_state can also be init
+ local next = getnext(base)
+ if halant[getchar(next)] and not (next ~= stop and getchar(getnext(next)) == c_zwj) then
+ setprop(base,a_state,unsetvalue)
+ end
+ end
+
+ -- split two- or three-part matras into their parts. Then, move the left 'matra' part to the beginning of the syllable.
+ -- classify consonants and 'matra' parts as pre-base, above-base (Reph), below-base or post-base, and group elements of the syllable (consonants and 'matras') according to this classification
+
+ local current, allreordered, moved = start, false, { [base] = true }
+ local a, b, p, bn = base, base, base, getnext(base)
+ if base ~= stop and nukta[getchar(bn)] then
+ a, b, p = bn, bn, bn
+ end
+ while not allreordered do
+ -- current is always consonant
+ local c = current
+ local n = getnext(current)
+ local l = nil -- used ?
+ if c ~= stop then
+ local ch = getchar(n)
+ if nukta[ch] then
+ c = n
+ n = getnext(n)
+ ch = getchar(n)
+ end
+ if c ~= stop then
+ if halant[ch] then
+ c = n
+ n = getnext(n)
+ ch = getchar(n)
+ end
+
+ local tpm = twopart_mark[ch]
+ while tpm do
+ local extra = copy_node(n)
+ copyinjection(extra,n)
+ ch = tpm[1]
+ setchar(n,ch)
+ setchar(extra,tpm[2])
+ head = insert_node_after(head,current,extra)
+ tpm = twopart_mark[ch]
+ end
+ while c ~= stop and dependent_vowel[ch] do
+ c = n
+ n = getnext(n)
+ ch = getchar(n)
+ end
+ if c ~= stop then
+ if vowel_modifier[ch] then
+ c = n
+ n = getnext(n)
+ ch = getchar(n)
+ end
+ if c ~= stop and stress_tone_mark[ch] then
+ c = n
+ n = getnext(n)
+ end
+ end
+ end
+ end
+ local bp = getprev(firstcons)
+ local cn = getnext(current)
+ local last = getnext(c)
+ while cn ~= last do
+ -- move pre-base matras...
+ if pre_mark[getchar(cn)] then
+ if devanagari.left_matra_before_base then
+ local prev, next = getboth(cn)
+ setlink(prev,next)
+ if cn == stop then
+ stop = getprev(cn)
+ end
+ if base == start then
+ if head == start then
+ head = cn
+ end
+ start = cn
+ end
+ setlink(getprev(base),cn)
+ setlink(cn,base)
+ -- setlink(getprev(base),cn,base) -- maybe
+ cn = next
+ else
+ if bp then
+ setnext(bp,cn)
+ end
+ local prev, next = getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ if cn == stop then
+ stop = prev
+ end
+ setprev(cn,bp)
+ setlink(cn,firstcons)
+ if firstcons == start then
+ if head == start then
+ head = cn
+ end
+ start = cn
+ end
+ cn = next
+ end
+ elseif current ~= base and dependent_vowel[getchar(cn)] then
+ local prev, next = getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ if cn == stop then
+ stop = prev
+ end
+ setlink(b,cn,getnext(b))
+ order_matras(cn)
+ cn = next
+ elseif current == base and dependent_vowel[getchar(cn)] then
+ local cnn = getnext(cn)
+ order_matras(cn)
+ cn = cnn
+ while cn ~= last and dependent_vowel[getchar(cn)] do
+ cn = getnext(cn)
+ end
+ else
+ cn = getnext(cn)
+ end
+ end
+ allreordered = c == stop
+ current = getnext(c)
+ end
+
+ if reph or vattu then
+ local current, cns = start, nil
+ while current ~= stop do
+ local c = current
+ local n = getnext(current)
+ if ra[getchar(current)] and halant[getchar(n)] then
+ c = n
+ n = getnext(n)
+ local b, bn = base, base
+ while bn ~= stop do
+ local next = getnext(bn)
+ if dependent_vowel[getchar(next)] then
+ b = next
+ end
+ bn = next
+ end
+ if getprop(current,a_state) == s_rphf then
+ -- position Reph (Ra + H) after post-base 'matra' (if any) since these
+ -- become marks on the 'matra', not on the base glyph
+ if b ~= current then
+ if current == start then
+ if head == start then
+ head = n
+ end
+ start = n
+ end
+ if b == stop then
+ stop = c
+ end
+ local prev = getprev(current)
+ setlink(prev,n)
+ local next = getnext(b)
+ setlink(c,next)
+ setlink(b,current)
+ end
+ elseif cns and getnext(cns) ~= current then -- todo: optimize next
+ -- position below-base Ra (vattu) following the consonants on which it is placed (either the base consonant or one of the pre-base consonants)
+ local cp = getprev(current)
+ local cnsn = getnext(cns)
+ setlink(cp,n)
+ setlink(cns,current)
+ setlink(c,cnsn)
+ if c == stop then
+ stop = cp
+ break
+ end
+ current = getprev(n)
+ end
+ else
+ local char = getchar(current)
+ if consonant[char] then
+ cns = current
+ local next = getnext(cns)
+ if halant[getchar(next)] then
+ cns = next
+ end
+ if not vatucache[char] then
+ next = getnext(cns)
+ while dependent_vowel[getchar(next)] do
+ cns = next
+ next = getnext(cns)
+ end
+ end
+ elseif char == c_nbsp then
+ nbspaces = nbspaces + 1
+ cns = current
+ local next = getnext(cns)
+ if halant[getchar(next)] then
+ cns = next
+ end
+ if not vatucache[char] then
+ next = getnext(cns)
+ while dependent_vowel[getchar(next)] do
+ cns = next
+ next = getnext(cns)
+ end
+ end
+ end
+ end
+ current = getnext(current)
+ end
+ end
+
+ if getchar(base) == c_nbsp then
+ nbspaces = nbspaces - 1
+ if base == stop then
+ stop = getprev(stop)
+ end
+ head = remove_node(head,base)
+ flush_node(base)
+ end
+
+ return head, stop, nbspaces
+end
+
+-- If a pre-base matra character had been reordered before applying basic features,
+-- the glyph can be moved closer to the main consonant based on whether half-forms had been formed.
+-- Actual position for the matra is defined as “after last standalone halant glyph,
+-- after initial matra position and before the main consonant”.
+-- If ZWJ or ZWNJ follow this halant, position is moved after it.
+
+-- so we break out ... this is only done for the first 'word' (if we feed words we can as
+-- well test for non glyph.
+
+function handlers.devanagari_reorder_matras(head,start) -- no leak
+ local current = start -- we could cache attributes here
+ local startfont = getfont(start)
+ local startattr = getprop(start,a_syllabe)
+ while current do
+ local char = ischar(current,startfont)
+ local next = getnext(current)
+ if char and getprop(current,a_syllabe) == startattr then
+ if halant[char] then -- a_state can also be init
+ if next then
+ local char = ischar(next,startfont)
+ if char and zw_char[char] and getprop(next,a_syllabe) == startattr then
+ current = next
+ next = getnext(current)
+ end
+ end
+ -- can be optimzied
+ local startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ -- setlink(current,start,next) -- maybe
+ start = startnext
+ break
+ -- elseif consonant[char] and ( not getprop(current,a_state) or getprop(current,a_state) == s_init) then
+ -- startnext = getnext(start)
+ -- head = remove_node(head,start)
+ -- if current == head then
+ -- setlink(start,current)
+ -- head = start
+ -- else
+ -- setlink(getprev(current),start)
+ -- setlink(start,current)
+ -- end
+ -- start = startnext
+ -- break
+ end
+ else
+ break
+ end
+ current = next
+ end
+ return head, start, true
+end
+
+-- Reph’s original position is always at the beginning of the syllable, (i.e. it is
+-- not reordered at the character reordering stage). However, it will be reordered
+-- according to the basic-forms shaping results. Possible positions for reph,
+-- depending on the script, are; after main, before post-base consonant forms, and
+-- after post-base consonant forms.
+
+-- In Devanagari reph has reordering position 'before postscript' and dev2 only
+-- follows step 2, 4, and 6.
+
+local rephbase = { }
+
+function handlers.devanagari_reorder_reph(head,start)
+ local current = getnext(start)
+ local startnext = nil
+ local startprev = nil
+ local startfont = getfont(start)
+ local startattr = getprop(start,a_syllabe)
+ --
+ ::step_1::
+ --
+ -- If reph should be positioned after post-base consonant forms, proceed to step 5.
+ --
+ local char = ischar(start,startfont)
+ local rephbase = rephbase[startfont][char]
+ if char and after_subscript[rephbase] then
+ goto step_5
+ end
+ --
+ ::step_2::
+ --
+ -- If the reph repositioning class is not after post-base: target position is after
+ -- the first explicit halant glyph between the first post-reph consonant and last
+ -- main consonant. If ZWJ or ZWNJ are following this halant, position is moved after
+ -- it. If such position is found, this is the target position. Otherwise, proceed to
+ -- the next step. Note: in old-implementation fonts, where classifications were
+ -- fixed in shaping engine, there was no case where reph position will be found on
+ -- this step.
+ --
+ if char and not after_postscript[rephbase] then
+ while current do
+ local char = ischar(current,startfont)
+ if char and getprop(current,a_syllabe) == startattr then
+ if halant[char] then
+ local next = getnext(current)
+ if next then
+ local nextchar = ischar(next,startfont)
+ if nextchar and zw_char[nextchar] and getprop(next,a_syllabe) == startattr then
+ current = next
+ next = getnext(current)
+ end
+ end
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ -- setlink(current,start,next) -- maybe
+ start = startnext
+ startattr = getprop(start,a_syllabe)
+ break
+ end
+ current = getnext(current)
+ else
+ break
+ end
+ end
+ end
+ --
+ ::step_3::
+ --
+ -- If reph should be repositioned after the main consonant: find the first consonant
+ -- not ligated with main, or find the first consonant that is not a potential
+ -- pre-base reordering Ra.
+ --
+ if not startnext then
+ if char and after_main[rephbase] then
+ current = getnext(start)
+ while current do
+ local char = ischar(current,startfont)
+ if char and getprop(current,a_syllabe) == startattr then
+ if consonant[char] and not getprop(current,a_state) == s_pref then
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(current,start)
+ setlink(start,getnext(current))
+ -- setlink(current,start,getnext(current)) -- maybe
+ start = startnext
+ startattr = getprop(start,a_syllabe)
+ break
+ end
+ current = getnext(current)
+ else
+ break
+ end
+ end
+ end
+ end
+ --
+ ::step_4::
+ --
+ -- If reph should be positioned before post-base consonant, find first post-base
+ -- classified consonant not ligated with main. If no consonant is found, the target
+ -- position should be before the first matra, syllable modifier sign or vedic sign.
+ --
+ if not startnext then
+ if char and before_postscript[rephbase] then
+ current = getnext(start)
+ local c = nil
+ while current do
+ local char = ischar(current,startfont)
+ if char and getprop(current,a_syllabe) == startattr then
+ if getprop(current,a_state) == s_pstf then -- post-base
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(getprev(current),start)
+ setlink(start,current)
+ -- setlink(getprev(current),start,current) -- maybe
+ start = startnext
+ startattr = getprop(start,a_syllabe)
+ break
+ elseif not c and ( vowel_modifier[char] or stress_tone_mark[char] ) then
+ c = current
+ end
+ current = getnext(current)
+ else
+ if c then
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(getprev(c),start)
+ setlink(start,c)
+ -- setlink(getprev(c),start,c) -- maybe
+ start = startnext
+ startattr = getprop(start,a_syllabe)
+ end
+ break
+ end
+ end
+ end
+ end
+ --
+ ::step_5::
+ --
+ -- If no consonant is found in steps 3 or 4, move reph to a position immediately
+ -- before the first post-base matra, syllable modifier sign or vedic sign that has a
+ -- reordering class after the intended reph position. For example, if the reordering
+ -- position for reph is post-main, it will skip above-base matras that also have a
+ -- post-main position.
+ --
+ if not startnext then
+ current = getnext(start)
+ local c = nil
+ while current do
+ local char = ischar(current,startfont)
+ if char and getprop(current,a_syllabe) == startattr then
+ local state = getprop(current,a_state)
+ if before_subscript[rephbase] and (state == s_blwf or state == s_pstf) then
+ c = current
+ elseif after_subscript[rephbase] and (state == s_pstf) then
+ c = current
+ end
+ current = getnext(current)
+ else
+ break
+ end
+ end
+ -- here we can loose the old start node: maybe best split cases
+ if c then
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(getprev(c),start)
+ setlink(start,c)
+ -- setlink(getprev(c),start,c) -- maybe
+ -- end
+ start = startnext
+ startattr = getprop(start,a_syllabe)
+ end
+ end
+ --
+ ::step_6::
+ --
+ -- Otherwise, reorder reph to the end of the syllable.
+ --
+ if not startnext then
+ current = start
+ local next = getnext(current)
+ while next do
+ local nextchar = ischar(next,startfont)
+ if nextchar and getprop(next,a_syllabe) == startattr then
+ current = next
+ next = getnext(current)
+ else
+ break
+ end
+ end
+ if start ~= current then
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(start,getnext(current))
+ setlink(current,start)
+ -- setlink(current,start,getnext(current)) -- maybe
+ start = startnext
+ end
+ end
+ --
+ return head, start, true
+end
+
+-- If a pre-base reordering consonant is found, reorder it according to the following rules:
+--
+-- 1 Only reorder a glyph produced by substitution during application of the feature. (Note
+-- that a font may shape a Ra consonant with the feature generally but block it in certain
+-- contexts.)
+-- 2 Try to find a target position the same way as for pre-base matra. If it is found, reorder
+-- pre-base consonant glyph.
+-- 3 If position is not found, reorder immediately before main consonant.
+
+-- Here we implement a few handlers:
+--
+-- function(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+-- return head, start, done
+-- end
+
+local reordered_pre_base_reordering_consonants = { } -- shared ? not reset ?
+
+function handlers.devanagari_reorder_pre_base_reordering_consonants(head,start)
+ if reordered_pre_base_reordering_consonants[start] then
+ return head, start, true
+ end
+ local current = start -- we could cache attributes here
+ local startfont = getfont(start)
+ local startattr = getprop(start,a_syllabe)
+ while current do
+ local char = ischar(current,startfont)
+ local next = getnext(current)
+ if char and getprop(current,a_syllabe) == startattr then
+ if halant[char] then -- a_state can also be init
+ if next then
+ local char = ischar(next,startfont)
+ if char and zw_char[char] and getprop(next,a_syllabe) == startattr then
+ current = next
+ next = getnext(current)
+ end
+ end
+ -- can be optimzied
+ local startnext = getnext(start)
+ head = remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ -- setlink(current,start,next) -- maybe
+ reordered_pre_base_reordering_consonants[start] = true
+ start = startnext
+ return head, start, true
+ -- elseif consonant[char] and ( not getprop(current,a_state) or getprop(current,a_state) == s_init) then
+ -- startnext = getnext(start)
+ -- head = remove_node(head,start)
+ -- if current == head then
+ -- setlink(start,current)
+ -- head = start
+ -- else
+ -- setlink(getprev(current),start)
+ -- setlink(start,current)
+ -- end
+ -- start = startnext
+ -- break
+ end
+ else
+ break
+ end
+ current = next
+ end
+
+ local startattr = getprop(start,a_syllabe)
+ local current = getprev(start)
+ while current and getprop(current,a_syllabe) == startattr do
+ local char = ischar(current)
+ if ( not dependent_vowel[char] and not getprop(current,a_state) or getprop(current,a_state) == s_init) then
+ startnext = getnext(start)
+ head = remove_node(head,start)
+ if current == head then
+ setlink(start,current)
+ head = start
+ else
+ setlink(getprev(current),start)
+ setlink(start,current)
+ end
+ reordered_pre_base_reordering_consonants[start] = true
+ start = startnext
+ break
+ end
+ current = getprev(current)
+ end
+
+ return head, start, true
+end
+
+function handlers.devanagari_remove_joiners(head,start,kind,lookupname,replacement)
+ local stop = getnext(start)
+ local font = getfont(start)
+ local last = start
+ while stop do
+ local char = ischar(stop,font)
+ if char and (char == c_zwnj or char == c_zwj) then
+ last = stop
+ stop = getnext(stop)
+ else
+ break
+ end
+ end
+ local prev = getprev(start)
+ if stop then
+ setnext(last)
+ setlink(prev,stop)
+ elseif prev then
+ setnext(prev)
+ end
+ if head == start then
+ head = stop
+ end
+ flush_list(start)
+ return head, stop, true
+end
+
+local function initialize_two(font,attr)
+
+ local devanagari = fontdata[font].resources.devanagari
+
+ if devanagari then
+ return devanagari.seqsubset or { }, devanagari.reorderreph or { }
+ else
+ return { }, { }
+ end
+
+end
+
+-- this one will be merged into the caller: it saves a call, but we will then make function
+-- of the actions
+
+local function reorder_two(head,start,stop,font,attr,nbspaces) -- maybe do a pass over (determine stop in sweep)
+ local seqsubset, reorderreph = initialize_two(font,attr)
+
+ local halfpos = nil
+ local basepos = nil
+ local subpos = nil
+ local postpos = nil
+
+ reorderreph.coverage = { }
+ rephbase[font] = { }
+
+ for i=1,#seqsubset do
+
+ -- this can be done more efficient, the last test and less getnext
+
+ local subset = seqsubset[i]
+ local kind = subset[1]
+ local lookupcache = subset[2]
+ if kind == "rphf" then
+ reorderreph.coverage[subset[3]] = true -- neat
+ rephbase[font][subset[3]] = subset[4]
+ local current = start
+ local last = getnext(stop)
+ while current ~= last do
+ if current ~= stop then
+ local c = getchar(current)
+ local found = lookupcache[c]
+ if found then
+ local next = getnext(current)
+ if found[getchar(next)] or contextchain(found, next) then --above-base: rphf Consonant + Halant
+ local afternext = next ~= stop and getnext(next)
+ if afternext and zw_char[getchar(afternext)] then -- ZWJ and ZWNJ prevent creation of reph
+ current = afternext -- getnext(next)
+ elseif current == start then
+ setprop(current,a_state,s_rphf)
+ current = next
+ else
+ current = next
+ end
+ end
+ end
+ end
+ current = getnext(current)
+ end
+ elseif kind == "pref" then
+ local current = start
+ local last = getnext(stop)
+ while current ~= last do
+ if current ~= stop then
+ local c = getchar(current)
+ local found = lookupcache[c]
+ if found then -- pre-base: pref Halant + Consonant
+ local next = getnext(current)
+ if found[getchar(next)] or contextchain(found, next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then --KE: a_state can also be init...
+ setprop(current,a_state,s_pref)
+ setprop(next,a_state,s_pref)
+ current = next
+ end
+ end
+ end
+ end
+ current = getnext(current)
+ end
+ elseif kind == "half" then -- half forms: half / Consonant + Halant
+ local current = start
+ local last = getnext(stop)
+ while current ~= last do
+ if current ~= stop then
+ local c = getchar(current)
+ local found = lookupcache[c]
+ if found then
+ local next = getnext(current)
+ if found[getchar(next)] or contextchain(found, next) then
+ if next ~= stop and getchar(getnext(next)) == c_zwnj then -- zwnj prevent creation of half
+ current = next
+ elseif (not getprop(current,a_state)) then --KE: a_state can also be init...
+ setprop(current,a_state,s_half)
+ if not halfpos then
+ halfpos = current
+ end
+ end
+ current = getnext(current)
+ end
+ end
+ end
+ current = getnext(current)
+ end
+ elseif kind == "blwf" or kind == "vatu" then -- below-base: blwf / Halant + Consonant
+ local current = start
+ local last = getnext(stop)
+ while current ~= last do
+ if current ~= stop then
+ local c = getchar(current)
+ local found = lookupcache[c]
+ if found then
+ local next = getnext(current)
+ if found[getchar(next)] or contextchain(found, next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then --KE: a_state can also be init...
+ setprop(current,a_state,s_blwf)
+ setprop(next,a_state,s_blwf)
+ current = next
+ subpos = current
+ end
+ end
+ end
+ end
+ current = getnext(current)
+ end
+ elseif kind == "pstf" then -- post-base: pstf / Halant + Consonant
+ local current = start
+ local last = getnext(stop)
+ while current ~= last do
+ if current ~= stop then
+ local c = getchar(current)
+ local found = lookupcache[c]
+ if found then
+ local next = getnext(current)
+ if found[getchar(next)] or contextchain(found, next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then --KE: a_state can also be init...
+ setprop(current,a_state,s_pstf)
+ setprop(next,a_state,s_pstf)
+ current = next
+ postpos = current
+ end
+ end
+ end
+ end
+ current = getnext(current)
+ end
+ end
+ end
+
+ local current, base, firstcons = start, nil, nil
+
+ if getprop(start,a_state) == s_rphf then
+ -- if syllable starts with Ra + H and script has 'Reph' then exclude Reph from candidates for base consonants
+ current = getnext(getnext(start))
+ end
+
+ if current ~= getnext(stop) and getchar(current) == c_nbsp then
+ -- Stand Alone cluster
+ if current == stop then
+ stop = getprev(stop)
+ head = remove_node(head,current)
+ flush_node(current)
+ return head, stop, nbspaces
+ else
+ nbspaces = nbspaces + 1
+ base = current
+ current = getnext(current)
+ if current ~= stop then
+ local char = getchar(current)
+ if nukta[char] then
+ current = getnext(current)
+ char = getchar(current)
+ end
+ if char == c_zwj then
+ local next = getnext(current)
+ if current ~= stop and next ~= stop and halant[getchar(next)] then
+ current = next
+ next = getnext(current)
+ local tmp = getnext(next)
+ local changestop = next == stop
+ setnext(next)
+ setprop(current,a_state,s_pref)
+ current = processcharacters(current,font)
+ setprop(current,a_state,s_blwf)
+ current = processcharacters(current,font)
+ setprop(current,a_state,s_pstf)
+ current = processcharacters(current,font)
+ setprop(current,a_state,unsetvalue)
+ if halant[getchar(current)] then
+ setnext(getnext(current),tmp)
+ if show_syntax_errors then
+ head, current = inject_syntax_error(head,current,char)
+ end
+ else
+ setnext(current,tmp) -- assumes that result of pref, blwf, or pstf consists of one node
+ if changestop then
+ stop = current
+ end
+ end
+ end
+ end
+ end
+ end
+ else -- not Stand Alone cluster
+ local last = getnext(stop)
+ while current ~= last do -- find base consonant
+ local next = getnext(current)
+ if consonant[getchar(current)] then
+ if not (current ~= stop and next ~= stop and halant[getchar(next)] and getchar(getnext(next)) == c_zwj) then
+ if not firstcons then
+ firstcons = current
+ end
+ -- check whether consonant has below-base or post-base form or is pre-base reordering Ra
+ local a = getprop(current,a_state)
+ if not (a == s_blwf or a == s_pstf or (a ~= s_rphf and a ~= s_blwf and ra[getchar(current)])) then
+ base = current
+ end
+ end
+ end
+ current = next
+ end
+ if not base then
+ base = firstcons
+ end
+ end
+
+ if not base then
+ if getprop(start,a_state) == s_rphf then
+ setprop(start,a_state,unsetvalue)
+ end
+ return head, stop, nbspaces
+ else
+ if getprop(base,a_state) then -- a_state can also be init
+ setprop(base,a_state,unsetvalue)
+ end
+ basepos = base
+ end
+ if not halfpos then
+ halfpos = base
+ end
+ if not subpos then
+ subpos = base
+ end
+ if not postpos then
+ postpos = subpos or base
+ end
+
+ -- Matra characters are classified and reordered by which consonant in a conjunct they have affinity for
+
+ local moved = { }
+ local current = start
+ local last = getnext(stop)
+ while current ~= last do
+ local char = getchar(current)
+ local target = nil
+ local cn = getnext(current)
+ -- not so efficient (needed for malayalam)
+ local tpm = twopart_mark[char]
+ while tpm do
+ local extra = copy_node(current)
+ copyinjection(extra,current)
+ char = tpm[1]
+ setchar(current,char)
+ setchar(extra,tpm[2])
+ head = insert_node_after(head,current,extra)
+ tpm = twopart_mark[char]
+ end
+ --
+ if not moved[current] and dependent_vowel[char] then
+ if pre_mark[char] then -- or: if before_main or before_half
+ moved[current] = true
+ -- can be helper to remove one node
+ local prev, next = getboth(current)
+ setlink(prev,next)
+ if current == stop then
+ stop = getprev(current)
+ end
+
+ local pos
+ if before_main[char] then
+ pos = basepos
+ -- basepos = current -- is this correct?
+ else
+ -- must be before_half
+ pos = halfpos
+ -- halfpos = current -- is this correct?
+ end
+
+ local ppos = getprev(pos) -- necessary?
+ while ppos and getprop(ppos,a_syllabe) == getprop(pos,a_syllabe) do
+ if getprop(ppos,a_state) == s_pref then
+ pos = ppos
+ end
+ ppos = getprev(ppos)
+ end
+
+ local ppos = getprev(pos) -- necessary?
+ while ppos and getprop(ppos,a_syllabe) == getprop(pos,a_syllabe) and halant[ischar(ppos)] do
+ ppos = getprev(ppos)
+ if ppos and getprop(ppos,a_syllabe) == getprop(pos,a_syllabe) and consonant[ischar(ppos)] then
+ pos = ppos
+ ppos = getprev(ppos)
+ else
+ break
+ end
+ end
+
+ if pos == start then
+ if head == start then
+ head = current
+ end
+ start = current
+ end
+ setlink(getprev(pos),current)
+ setlink(current,pos)
+ -- setlink(getprev(pos),current,pos) -- maybe
+ elseif above_mark[char] then
+ -- after main consonant
+ target = basepos
+ if subpos == basepos then
+ subpos = current
+ end
+ if postpos == basepos then
+ postpos = current
+ end
+ basepos = current
+ elseif below_mark[char] then
+ -- after subjoined consonants
+ target = subpos
+ if postpos == subpos then
+ postpos = current
+ end
+ subpos = current
+ elseif post_mark[char] then
+ -- after post-form consonant
+ local n = getnext(postpos) -- nukta and vedic sign come first - is that right? and also halant+ra
+ while n do
+ local v = ischar(n,font)
+ if nukta[v] or stress_tone_mark[v] or vowel_modifier[v] then
+ postpos = n
+ else
+ break
+ end
+ n = getnext(n)
+ end
+ target = postpos
+ postpos = current
+ end
+ if mark_above_below_post[char] then
+ local prev = getprev(current)
+ if prev ~= target then
+ local next = getnext(current)
+ setlink(prev,next)
+ if current == stop then
+ stop = prev
+ end
+ setlink(current,getnext(target))
+ setlink(target,current)
+ -- setlink(target,current,getnext(target)) -- maybe
+ end
+ end
+ end
+ current = cn
+ end
+
+ -- reorder halant+Ra
+
+ local current = getnext(start)
+ local last = getnext(stop)
+ while current ~= last do
+ local char = getchar(current)
+ local cn = getnext(current)
+ if halant[char] and ra[ischar(cn)] and getprop(cn,a_state) ~= s_rphf and getprop(cn,a_state) ~= s_blwf then
+ if after_main[ischar(cn)] then
+ local prev = getprev(current)
+ local next = getnext(cn)
+ local bpn = getnext(basepos)
+ while bpn and dependent_vowel[ischar(bpn)] do
+ basepos = bpn
+ bpn = getnext(bpn)
+ end
+ if basepos ~= prev then
+ setlink(prev,next)
+ setlink(cn, getnext(basepos))
+ setlink(basepos, current)
+ if cn == stop then
+ stop = prev
+ end
+ cn = next
+ end
+ end
+ -- after_postscript
+ -- after_subscript
+ -- before_postscript
+ -- before_subscript
+ end
+ current = cn
+ end
+
+ -- Reorder marks to canonical order: Adjacent nukta and halant or nukta and vedic sign are always repositioned if necessary, so that the nukta is first.
+
+ local current = start
+ local c = nil
+ while current ~= stop do
+ local char = getchar(current)
+ if halant[char] or stress_tone_mark[char] then
+ if not c then
+ c = current
+ end
+ else
+ c = nil
+ end
+ local next = getnext(current)
+ if c and nukta[getchar(next)] then
+ if head == c then
+ head = next
+ end
+ if stop == next then
+ stop = current
+ end
+ setlink(getprev(c),next)
+ local nextnext = getnext(next)
+ setnext(current,nextnext)
+ local nextnextnext = getnext(nextnext)
+ if nextnextnext then
+ setprev(nextnextnext,current)
+ end
+ setlink(nextnext,c)
+ end
+ if stop == current then break end
+ current = getnext(current)
+ end
+
+ if getchar(base) == c_nbsp then
+ if base == stop then
+ stop = getprev(stop)
+ end
+ nbspaces = nbspaces - 1
+ head = remove_node(head, base)
+ flush_node(base)
+ end
+
+ return head, stop, nbspaces
+end
+
+-- cleaned up and optimized ... needs checking (local, check order, fixes, extra hash, etc)
+
+local separator = { }
+
+imerge(separator,consonant)
+imerge(separator,independent_vowel)
+imerge(separator,dependent_vowel)
+imerge(separator,vowel_modifier)
+imerge(separator,stress_tone_mark)
+
+for k, v in next, nukta do separator[k] = true end
+for k, v in next, halant do separator[k] = true end
+
+local function analyze_next_chars_one(c,font,variant) -- skip one dependent vowel
+ -- why two variants ... the comment suggests that it's the same ruleset
+ local n = getnext(c)
+ if not n then
+ return c
+ end
+ if variant == 1 then
+ local v = ischar(n,font)
+ if v and nukta[v] then
+ n = getnext(n)
+ if n then
+ v = ischar(n,font)
+ end
+ end
+ if n and v then
+ local nn = getnext(n)
+ if nn then
+ local vv = ischar(nn,font)
+ if vv then
+ local nnn = getnext(nn)
+ if nnn then
+ local vvv = ischar(nnn,font)
+ if vvv then
+ if vv == c_zwj and consonant[vvv] then
+ c = nnn
+ elseif (vv == c_zwnj or vv == c_zwj) and halant[vvv] then
+ local nnnn = getnext(nnn)
+ if nnnn then
+ local vvvv = ischar(nnnn,font)
+ if vvvv and consonant[vvvv] then
+ c = nnnn
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ elseif variant == 2 then
+ local v = ischar(n,font)
+ if v and nukta[v] then
+ c = n
+ end
+ n = getnext(c)
+ if n then
+ v = ischar(n,font)
+ if v then
+ local nn = getnext(n)
+ if nn then
+ local vv = ischar(nn,font)
+ if vv and zw_char[v] then
+ n = nn
+ v = vv
+ nn = getnext(nn)
+ vv = nn and ischar(nn,font)
+ end
+ if vv and halant[v] and consonant[vv] then
+ c = nn
+ end
+ end
+ end
+ end
+ end
+ -- c = ms_matra(c)
+ local n = getnext(c)
+ if not n then
+ return c
+ end
+ local v = ischar(n,font)
+ if not v then
+ return c
+ end
+ local already_pre_mark -- = false
+ local already_above_mark -- = false
+ local already_below_mark -- = false
+ local already_post_mark -- = false
+ while dependent_vowel[v] do
+ local vowels = twopart_mark[v] or { v }
+ for k, v in next, vowels do
+ if pre_mark[v] and not already_pre_mark then
+ already_pre_mark = true
+ elseif above_mark[v] and not already_above_mark then
+ already_above_mark = true
+ elseif below_mark[v] and not already_below_mark then
+ already_below_mark = true
+ elseif post_mark[v] and not already_post_mark then
+ already_post_mark = true
+ else
+ return c
+ end
+ end
+ c = getnext(c)
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if nukta[v] then
+ c = getnext(c)
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c = getnext(c)
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if vowel_modifier[v] then
+ c = getnext(c)
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ c = getnext(c)
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ return n
+ else
+ return c
+ end
+end
+
+local function analyze_next_chars_two(c,font)
+ local n = getnext(c)
+ if not n then
+ return c
+ end
+ local v = ischar(n,font)
+ if v and nukta[v] then
+ c = n
+ end
+ n = c
+ while true do
+ local nn = getnext(n)
+ if nn then
+ local vv = ischar(nn,font)
+ if vv then
+ if halant[vv] then
+ n = nn
+ local nnn = getnext(nn)
+ if nnn then
+ local vvv = ischar(nnn,font)
+ if vvv and zw_char[vvv] then
+ n = nnn
+ end
+ end
+ elseif vv == c_zwnj or vv == c_zwj then
+ -- n = nn -- not here (?)
+ local nnn = getnext(nn)
+ if nnn then
+ local vvv = ischar(nnn,font)
+ if vvv and halant[vvv] then
+ n = nnn
+ end
+ end
+ else
+ break
+ end
+ local nn = getnext(n)
+ if nn then
+ local vv = ischar(nn,font)
+ if vv and consonant[vv] then
+ n = nn
+ local nnn = getnext(nn)
+ if nnn then
+ local vvv = ischar(nnn,font)
+ if vvv and nukta[vvv] then
+ n = nnn
+ end
+ end
+ c = n
+ else
+ break
+ end
+ else
+ break
+ end
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ --
+ if not c then
+ -- This shouldn't happen I guess.
+ return
+ end
+ local n = getnext(c)
+ if not n then
+ return c
+ end
+ local v = ischar(n,font)
+ if not v then
+ return c
+ end
+ if anudatta[v] then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ if v == c_zwnj or v == c_zwj then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ else
+ -- c = ms_matra(c)
+ -- same as one
+ local already_pre_mark -- = false
+ local already_above_mark -- = false
+ local already_below_mark -- = false
+ local already_post_mark -- = false
+ while dependent_vowel[v] do
+ local vowels = twopart_mark[v] or { v }
+ for k, v in next, vowels do
+ if pre_mark[v] and not already_pre_mark then
+ already_pre_mark = true
+ elseif above_mark[v] and not already_above_mark then
+ already_above_mark = true
+ elseif below_mark[v] and not already_below_mark then
+ already_below_mark = true
+ elseif post_mark[v] and not already_post_mark then
+ already_post_mark = true
+ else
+ return c
+ end
+ end
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if nukta[v] then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ end
+ -- same as one
+ if vowel_modifier[v] then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ c = n
+ n = getnext(c)
+ if not n then
+ return c
+ end
+ v = ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ return n
+ else
+ return c
+ end
+end
+
+-- It looks like these two analyzers were written independently but they share
+-- a lot. Common code has been synced.
+
+local function method_one(head,font,attr)
+ local current = head
+ local start = true
+ local done = false
+ local nbspaces = 0
+ local syllabe = 0
+ while current do
+ local char = ischar(current,font)
+ if char then
+ done = true
+ local syllablestart = current
+ local syllableend = nil
+ local c = current
+ local n = getnext(c)
+ local first = char
+ if n and ra[first] then
+ local second = ischar(n,font)
+ if second and halant[second] then
+ local n = getnext(n)
+ if n then
+ local third = ischar(n,font)
+ if third then
+ c = n
+ first = third
+ end
+ end
+ end
+ end
+ local standalone = first == c_nbsp
+ if standalone then
+ local prev = getprev(current)
+ if prev then
+ local prevchar = ischar(prev,font)
+ if not prevchar then
+ -- different font or language so quite certainly a different word
+ elseif not separator[prevchar] then
+ -- something that separates words
+ else
+ standalone = false
+ end
+ else
+ -- begin of paragraph or box
+ end
+ end
+ if standalone then
+ -- stand alone cluster (at the start of the word only): #[Ra+H]+NBSP+[N]+[<[<ZWJ|ZWNJ>]+H+C>]+[{M}+[N]+[H]]+[SM]+[(VD)]
+ local syllableend = analyze_next_chars_one(c,font,2)
+ current = getnext(syllableend)
+ if syllablestart ~= syllableend then
+ head, current, nbspaces = reorder_one(head,syllablestart,syllableend,font,attr,nbspaces)
+ current = getnext(current)
+ end
+ else
+ -- we can delay the getsubtype(n) and getfont(n) and test for say halant first
+ -- as an table access is faster than two function calls (subtype and font are
+ -- pseudo fields) but the code becomes messy (unless we make it a function)
+ if consonant[char] then
+ -- syllable containing consonant
+ local prevc = true
+ while prevc do
+ prevc = false
+ local n = getnext(current)
+ if not n then
+ break
+ end
+ local v = ischar(n,font)
+ if not v then
+ break
+ end
+ if nukta[v] then
+ n = getnext(n)
+ if not n then
+ break
+ end
+ v = ischar(n,font)
+ if not v then
+ break
+ end
+ end
+ if halant[v] then
+ n = getnext(n)
+ if not n then
+ break
+ end
+ v = ischar(n,font)
+ if not v then
+ break
+ end
+ if v == c_zwnj or v == c_zwj then
+ n = getnext(n)
+ if not n then
+ break
+ end
+ v = ischar(n,font)
+ if not v then
+ break
+ end
+ end
+ if consonant[v] then
+ prevc = true
+ current = n
+ end
+ end
+ end
+ local n = getnext(current)
+ if n then
+ local v = ischar(n,font)
+ if v and nukta[v] then
+ -- nukta (not specified in Microsft Devanagari OpenType specification)
+ current = n
+ n = getnext(current)
+ end
+ end
+ syllableend = current
+ current = n
+ if current then
+ local v = ischar(current,font)
+ if not v then
+ -- skip
+ elseif halant[v] then
+ -- syllable containing consonant without vowels: {C + [Nukta] + H} + C + H
+ local n = getnext(current)
+ if n then
+ local v = ischar(n,font)
+ if v and zw_char[v] then
+ -- code collapsed, probably needs checking with intention
+ syllableend = n
+ current = getnext(n)
+ else
+ syllableend = current
+ current = n
+ end
+ else
+ syllableend = current
+ current = n
+ end
+ else
+ -- syllable containing consonant with vowels: {C + [Nukta] + H} + C + [M] + [VM] + [SM]
+ if dependent_vowel[v] then
+ syllableend = current
+ current = getnext(current)
+ v = ischar(current,font)
+ end
+ if v and vowel_modifier[v] then
+ syllableend = current
+ current = getnext(current)
+ v = ischar(current,font)
+ end
+ if v and stress_tone_mark[v] then
+ syllableend = current
+ current = getnext(current)
+ end
+ end
+ end
+ if syllablestart ~= syllableend then
+ if syllableend then
+ syllabe = syllabe + 1
+ local c = syllablestart
+ local n = getnext(syllableend)
+ while c ~= n do
+ setprop(c,a_syllabe,syllabe)
+ c = getnext(c)
+ end
+ end
+ head, current, nbspaces = reorder_one(head,syllablestart,syllableend,font,attr,nbspaces)
+ current = getnext(current)
+ end
+ elseif independent_vowel[char] then
+ -- syllable without consonants: VO + [VM] + [SM]
+ syllableend = current
+ current = getnext(current)
+ if current then
+ local v = ischar(current,font)
+ if v then
+ if vowel_modifier[v] then
+ syllableend = current
+ current = getnext(current)
+ v = ischar(current,font)
+ end
+ if v and stress_tone_mark[v] then
+ syllableend = current
+ current = getnext(current)
+ end
+ end
+ end
+ else
+ if show_syntax_errors then
+ local mark = mark_four[char]
+ if mark then
+ head, current = inject_syntax_error(head,current,char)
+ end
+ end
+ current = getnext(current)
+ end
+ end
+ else
+ current = getnext(current)
+ end
+ start = false
+ end
+
+ if nbspaces > 0 then
+ head = replace_all_nbsp(head)
+ end
+
+ current = head
+ local n = 0
+ while current do
+ local char = ischar(current,font)
+ if char then
+ if n == 0 and not getprop(current,a_state) then
+ setprop(current,a_state,s_init)
+ end
+ n = n + 1
+ else
+ n = 0
+ end
+ current = getnext(current)
+ end
+
+ return head, done
+end
+
+-- there is a good change that when we run into one with subtype < 256 that the rest is also done
+-- so maybe we can omit this check (it's pretty hard to get glyphs in the stream out of the blue)
+
+local function method_two(head,font,attr)
+ local current = head
+ local start = true
+ local done = false
+ local syllabe = 0
+ local nbspaces = 0
+ while current do
+ local syllablestart = nil
+ local syllableend = nil
+ local char = ischar(current,font)
+ if char then
+ done = true
+ syllablestart = current
+ local c = current
+ local n = getnext(current)
+ if n and ra[char] then
+ local nextchar = ischar(n,font)
+ if nextchar and halant[nextchar] then
+ local n = getnext(n)
+ if n then
+ local nextnextchar = ischar(n,font)
+ if nextnextchar then
+ c = n
+ char = nextnextchar
+ end
+ end
+ end
+ end
+ if independent_vowel[char] then
+ -- vowel-based syllable: [Ra+H]+V+[N]+[<[<ZWJ|ZWNJ>]+H+C|ZWJ+C>]+[{M}+[N]+[H]]+[SM]+[(VD)]
+ current = analyze_next_chars_one(c,font,1)
+ syllableend = current
+ else
+ local standalone = char == c_nbsp
+ if standalone then
+ nbspaces = nbspaces + 1
+ local p = getprev(current)
+ if not p then
+ -- begin of paragraph or box
+ elseif ischar(p,font) then
+ -- different font or language so quite certainly a different word
+ elseif not separator[getchar(p)] then
+ -- something that separates words
+ else
+ standalone = false
+ end
+ end
+ if standalone then
+ -- Stand Alone cluster (at the start of the word only): #[Ra+H]+NBSP+[N]+[<[<ZWJ|ZWNJ>]+H+C>]+[{M}+[N]+[H]]+[SM]+[(VD)]
+ current = analyze_next_chars_one(c,font,2)
+ syllableend = current
+ elseif consonant[getchar(current)] then
+ -- WHY current INSTEAD OF c ?
+
+ -- Consonant syllable: {C+[N]+<H+[<ZWNJ|ZWJ>]|<ZWNJ|ZWJ>+H>} + C+[N]+[A] + [< H+[<ZWNJ|ZWJ>] | {M}+[N]+[H]>]+[SM]+[(VD)]
+ current = analyze_next_chars_two(current,font) -- not c !
+ syllableend = current
+ end
+ end
+ end
+ if syllableend then
+ syllabe = syllabe + 1
+ local c = syllablestart
+ local n = getnext(syllableend)
+ while c ~= n do
+ setprop(c,a_syllabe,syllabe)
+ c = getnext(c)
+ end
+ end
+ if syllableend and syllablestart ~= syllableend then
+ head, current, nbspaces = reorder_two(head,syllablestart,syllableend,font,attr,nbspaces)
+ end
+ if not syllableend and show_syntax_errors then
+ local char = ischar(current,font)
+ if char and not getprop(current,a_state) then -- a_state can also be init
+ local mark = mark_four[char]
+ if mark then
+ head, current = inject_syntax_error(head,current,char)
+ end
+ end
+ end
+ start = false
+ current = getnext(current)
+ end
+
+ if nbspaces > 0 then
+ head = replace_all_nbsp(head)
+ end
+
+ current = head
+ local n = 0
+ while current do
+ local char = ischar(current,font)
+ if char then
+ if n == 0 and not getprop(current,a_state) then -- a_state can also be init
+ setprop(current,a_state,s_init)
+ end
+ n = n + 1
+ else
+ n = 0
+ end
+ current = getnext(current)
+ end
+
+ return head, done
+end
+
+for i=1,nofscripts do
+ methods[scripts_one[i]] = method_one
+ methods[scripts_two[i]] = method_two
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-ota.lua b/macros/luatex/generic/luaotfload/fontloader-font-ota.lua
new file mode 100644
index 0000000000..3d217b3f4d
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-ota.lua
@@ -0,0 +1,448 @@
+if not modules then modules = { } end modules ['font-ota'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- context only
+
+local type = type
+
+if not trackers then trackers = { register = function() end } end
+
+----- trace_analyzing = false trackers.register("otf.analyzing", function(v) trace_analyzing = v end)
+
+local fonts, nodes, node = fonts, nodes, node
+
+local allocate = utilities.storage.allocate
+
+local otf = fonts.handlers.otf
+
+local analyzers = fonts.analyzers
+local initializers = allocate()
+local methods = allocate()
+
+analyzers.initializers = initializers
+analyzers.methods = methods
+
+local a_state = attributes.private('state')
+
+local nuts = nodes.nuts
+local tonut = nuts.tonut
+
+local getnext = nuts.getnext
+local getprev = nuts.getprev
+local getprev = nuts.getprev
+local getprop = nuts.getprop
+local setprop = nuts.setprop
+local getsubtype = nuts.getsubtype
+local getchar = nuts.getchar
+local ischar = nuts.ischar
+
+local end_of_math = nuts.end_of_math
+
+local nodecodes = nodes.nodecodes
+----- glyph_code = nodecodes.glyph
+local disc_code = nodecodes.disc
+local math_code = nodecodes.math
+
+local fontdata = fonts.hashes.identifiers
+local categories = characters and characters.categories or { } -- sorry, only in context
+local chardata = characters and characters.data
+
+local otffeatures = fonts.constructors.features.otf
+local registerotffeature = otffeatures.register
+
+--[[ldx--
+<p>Analyzers run per script and/or language and are needed in order to
+process features right.</p>
+--ldx]]--
+
+-- never use these numbers directly
+
+local s_init = 1 local s_rphf = 7
+local s_medi = 2 local s_half = 8
+local s_fina = 3 local s_pref = 9
+local s_isol = 4 local s_blwf = 10
+local s_mark = 5 local s_pstf = 11
+local s_rest = 6
+
+local states = allocate {
+ init = s_init,
+ medi = s_medi,
+ med2 = s_medi,
+ fina = s_fina,
+ fin2 = s_fina,
+ fin3 = s_fina,
+ isol = s_isol,
+ mark = s_mark,
+ rest = s_rest,
+ rphf = s_rphf,
+ half = s_half,
+ pref = s_pref,
+ blwf = s_blwf,
+ pstf = s_pstf,
+}
+
+local features = allocate {
+ init = s_init,
+ medi = s_medi,
+ med2 = s_medi,
+ fina = s_fina,
+ fin2 = s_fina,
+ fin3 = s_fina,
+ isol = s_isol,
+ -- mark = s_mark,
+ -- rest = s_rest,
+ rphf = s_rphf,
+ half = s_half,
+ pref = s_pref,
+ blwf = s_blwf,
+ pstf = s_pstf,
+}
+
+analyzers.states = states
+analyzers.features = features
+analyzers.useunicodemarks = false
+
+-- todo: analyzers per script/lang, cross font, so we need an font id hash -> script
+-- e.g. latin -> hyphenate, arab -> 1/2/3 analyze -- its own namespace
+
+-- done can go away as can tonut
+
+function analyzers.setstate(head,font)
+ local useunicodemarks = analyzers.useunicodemarks
+ local tfmdata = fontdata[font]
+ local descriptions = tfmdata.descriptions
+ local first, last, current, n, done = nil, nil, head, 0, false -- maybe make n boolean
+ current = tonut(current)
+ while current do
+ local char, id = ischar(current,font)
+ if char and not getprop(current,a_state) then
+ done = true
+ local d = descriptions[char]
+ if d then
+ if d.class == "mark" then
+ done = true
+ setprop(current,a_state,s_mark)
+ elseif useunicodemarks and categories[char] == "mn" then
+ done = true
+ setprop(current,a_state,s_mark)
+ elseif n == 0 then
+ first, last, n = current, current, 1
+ setprop(current,a_state,s_init)
+ else
+ last, n = current, n+1
+ setprop(current,a_state,s_medi)
+ end
+ else -- finish
+ if first and first == last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first, last, n = nil, nil, 0
+ end
+ elseif char == false then
+ -- other font
+ if first and first == last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first, last, n = nil, nil, 0
+ if id == math_code then
+ current = end_of_math(current)
+ end
+ elseif id == disc_code then
+ -- always in the middle .. it doesn't make much sense to assign a property
+ -- here ... we might at some point decide to flag the components when present
+ -- but even then it's kind of bogus
+ setprop(current,a_state,s_medi)
+ last = current
+ else -- finish
+ if first and first == last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first, last, n = nil, nil, 0
+ if id == math_code then
+ current = end_of_math(current)
+ end
+ end
+ current = getnext(current)
+ end
+ if first and first == last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ return head, done
+end
+
+-- in the future we will use language/script attributes instead of the
+-- font related value, but then we also need dynamic features which is
+-- somewhat slower; and .. we need a chain of them
+
+local function analyzeinitializer(tfmdata,value) -- attr
+ local script, language = otf.scriptandlanguage(tfmdata) -- attr
+ local action = initializers[script]
+ if not action then
+ -- skip
+ elseif type(action) == "function" then
+ return action(tfmdata,value)
+ else
+ local action = action[language]
+ if action then
+ return action(tfmdata,value)
+ end
+ end
+end
+
+local function analyzeprocessor(head,font,attr)
+ local tfmdata = fontdata[font]
+ local script, language = otf.scriptandlanguage(tfmdata,attr)
+ local action = methods[script]
+ if not action then
+ -- skip
+ elseif type(action) == "function" then
+ return action(head,font,attr)
+ else
+ action = action[language]
+ if action then
+ return action(head,font,attr)
+ end
+ end
+ return head, false
+end
+
+registerotffeature {
+ name = "analyze",
+ description = "analysis of character classes",
+ default = true,
+ initializers = {
+ node = analyzeinitializer,
+ },
+ processors = {
+ position = 1,
+ node = analyzeprocessor,
+ }
+}
+
+-- latin
+
+methods.latn = analyzers.setstate
+-------.dflt = analyzers.setstate % can be an option or just the default
+
+local arab_warned = { }
+
+local function warning(current,what)
+ local char = getchar(current)
+ if not arab_warned[char] then
+ log.report("analyze","arab: character %C has no %a class",char,what)
+ arab_warned[char] = true
+ end
+end
+
+local mappers = allocate {
+ l = s_init, -- left
+ d = s_medi, -- double
+ c = s_medi, -- joiner
+ r = s_fina, -- right
+ u = s_isol, -- nonjoiner
+}
+
+-- we can also use this trick for devanagari
+
+local classifiers = characters.classifiers
+
+if not classifiers then
+
+ local f_arabic, l_arabic = characters.blockrange("arabic")
+ local f_syriac, l_syriac = characters.blockrange("syriac")
+ local f_mandiac, l_mandiac = characters.blockrange("mandiac")
+ local f_nko, l_nko = characters.blockrange("nko")
+ local f_ext_a, l_ext_a = characters.blockrange("arabicextendeda")
+
+ classifiers = table.setmetatableindex(function(t,k)
+ if type(k) == "number" then
+ local c = chardata[k]
+ local v = false
+ if c then
+ local arabic = c.arabic
+ if arabic then
+ v = mappers[arabic]
+ if not v then
+ log.report("analyze","error in mapping arabic %C",k)
+ -- error
+ v = false
+ end
+ elseif (k >= f_arabic and k <= l_arabic) or
+ (k >= f_syriac and k <= l_syriac) or
+ (k >= f_mandiac and k <= l_mandiac) or
+ (k >= f_nko and k <= l_nko) or
+ (k >= f_ext_a and k <= l_ext_a) then
+ if categories[k] == "mn" then
+ v = s_mark
+ else
+ v = s_rest
+ end
+ end
+ end
+ t[k] = v
+ return v
+ end
+ end)
+
+ characters.classifiers = classifiers
+
+end
+
+function methods.arab(head,font,attr)
+ local first, last, c_first, c_last
+ local current = head
+ local done = false
+ current = tonut(current)
+ while current do
+ local char, id = ischar(current,font)
+ if char and not getprop(current,a_state) then
+ done = true
+ local classifier = classifiers[char]
+ if not classifier then
+ if last then
+ if c_last == s_medi or c_last == s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first, last = nil, nil
+ elseif first then
+ if c_first == s_medi or c_first == s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first = nil
+ end
+ elseif classifier == s_mark then
+ setprop(current,a_state,s_mark)
+ elseif classifier == s_isol then
+ if last then
+ if c_last == s_medi or c_last == s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first, last = nil, nil
+ elseif first then
+ if c_first == s_medi or c_first == s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first = nil
+ end
+ setprop(current,a_state,s_isol)
+ elseif classifier == s_medi then
+ if first then
+ last = current
+ c_last = classifier
+ setprop(current,a_state,s_medi)
+ else
+ setprop(current,a_state,s_init)
+ first = current
+ c_first = classifier
+ end
+ elseif classifier == s_fina then
+ if last then
+ if getprop(last,a_state) ~= s_init then
+ setprop(last,a_state,s_medi)
+ end
+ setprop(current,a_state,s_fina)
+ first, last = nil, nil
+ elseif first then
+ -- if getprop(first,a_state) ~= s_init then
+ -- -- needs checking
+ -- setprop(first,a_state,s_medi)
+ -- end
+ setprop(current,a_state,s_fina)
+ first = nil
+ else
+ setprop(current,a_state,s_isol)
+ end
+ else -- classifier == s_rest
+ setprop(current,a_state,s_rest)
+ if last then
+ if c_last == s_medi or c_last == s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first, last = nil, nil
+ elseif first then
+ if c_first == s_medi or c_first == s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first = nil
+ end
+ end
+ else
+ if last then
+ if c_last == s_medi or c_last == s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first, last = nil, nil
+ elseif first then
+ if c_first == s_medi or c_first == s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first = nil
+ end
+ if id == math_code then -- a bit duplicate as we test for glyphs twice
+ current = end_of_math(current)
+ end
+ end
+ current = getnext(current)
+ end
+ if last then
+ if c_last == s_medi or c_last == s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ elseif first then
+ if c_first == s_medi or c_first == s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ end
+ return head, done
+end
+
+methods.syrc = methods.arab
+methods.mand = methods.arab
+methods.nko = methods.arab
+
+directives.register("otf.analyze.useunicodemarks",function(v)
+ analyzers.useunicodemarks = v
+end)
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-otc.lua b/macros/luatex/generic/luaotfload/fontloader-font-otc.lua
new file mode 100644
index 0000000000..a774a81c2c
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-otc.lua
@@ -0,0 +1,875 @@
+if not modules then modules = { } end modules ['font-otc'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local insert, sortedkeys, sortedhash, tohash = table.insert, table.sortedkeys, table.sortedhash, table.tohash
+local type, next, tonumber = type, next, tonumber
+local lpegmatch = lpeg.match
+local utfbyte, utflen = utf.byte, utf.len
+local sortedhash = table.sortedhash
+
+-- we assume that the other otf stuff is loaded already
+
+local trace_loading = false trackers.register("otf.loading", function(v) trace_loading = v end)
+local report_otf = logs.reporter("fonts","otf loading")
+
+local fonts = fonts
+local otf = fonts.handlers.otf
+local registerotffeature = otf.features.register
+local setmetatableindex = table.setmetatableindex
+
+local checkmerge = fonts.helpers.checkmerge
+local checkflags = fonts.helpers.checkflags
+local checksteps = fonts.helpers.checksteps
+
+local normalized = {
+ substitution = "substitution",
+ single = "substitution",
+ ligature = "ligature",
+ alternate = "alternate",
+ multiple = "multiple",
+ kern = "kern",
+ pair = "pair",
+ single = "single",
+ chainsubstitution = "chainsubstitution",
+ chainposition = "chainposition",
+}
+
+local types = {
+ substitution = "gsub_single",
+ ligature = "gsub_ligature",
+ alternate = "gsub_alternate",
+ multiple = "gsub_multiple",
+ kern = "gpos_pair",
+ pair = "gpos_pair",
+ single = "gpos_single",
+ chainsubstitution = "gsub_contextchain",
+ chainposition = "gpos_contextchain",
+}
+
+local names = {
+ gsub_single = "gsub",
+ gsub_multiple = "gsub",
+ gsub_alternate = "gsub",
+ gsub_ligature = "gsub",
+ gsub_context = "gsub",
+ gsub_contextchain = "gsub",
+ gsub_reversecontextchain = "gsub",
+ gpos_single = "gpos",
+ gpos_pair = "gpos",
+ gpos_cursive = "gpos",
+ gpos_mark2base = "gpos",
+ gpos_mark2ligature = "gpos",
+ gpos_mark2mark = "gpos",
+ gpos_context = "gpos",
+ gpos_contextchain = "gpos",
+}
+
+setmetatableindex(types, function(t,k) t[k] = k return k end) -- "key"
+
+local everywhere = { ["*"] = { ["*"] = true } } -- or: { ["*"] = { "*" } }
+local noflags = { false, false, false, false }
+
+-- beware: shared, maybe we should copy the sequence
+
+local function getrange(sequences,category)
+ local count = #sequences
+ local first = nil
+ local last = nil
+ for i=1,count do
+ local t = sequences[i].type
+ if t and names[t] == category then
+ if not first then
+ first = i
+ end
+ last = i
+ end
+ end
+ return first or 1, last or count
+end
+
+local function validspecification(specification,name)
+ local dataset = specification.dataset
+ if dataset then
+ -- okay
+ elseif specification[1] then
+ dataset = specification
+ specification = { dataset = dataset }
+ else
+ dataset = { { data = specification.data } }
+ specification.data = nil
+ specification.dataset = dataset
+ end
+ local first = dataset[1]
+ if first then
+ first = first.data
+ end
+ if not first then
+ report_otf("invalid feature specification, no dataset")
+ return
+ end
+ if type(name) ~= "string" then
+ name = specification.name or first.name
+ end
+ if type(name) ~= "string" then
+ report_otf("invalid feature specification, no name")
+ return
+ end
+ local n = #dataset
+ if n > 0 then
+ for i=1,n do
+ setmetatableindex(dataset[i],specification)
+ end
+ return specification, name
+ end
+end
+
+local function addfeature(data,feature,specifications)
+
+ -- todo: add some validator / check code so that we're more tolerant to
+ -- user errors
+
+ if not specifications then
+ report_otf("missing specification")
+ return
+ end
+
+ local descriptions = data.descriptions
+ local resources = data.resources
+ local features = resources.features
+ local sequences = resources.sequences
+
+ if not features or not sequences then
+ report_otf("missing specification")
+ return
+ end
+
+ local alreadydone = resources.alreadydone
+ if not alreadydone then
+ alreadydone = { }
+ resources.alreadydone = alreadydone
+ end
+ if alreadydone[specifications] then
+ return
+ else
+ alreadydone[specifications] = true
+ end
+
+ -- feature has to be unique but the name entry wins eventually
+
+ local fontfeatures = resources.features or everywhere
+ local unicodes = resources.unicodes
+ local splitter = lpeg.splitter(" ",unicodes)
+ local done = 0
+ local skip = 0
+ local aglunicodes = false
+
+ local specifications = validspecification(specifications,feature)
+ if not specifications then
+ -- report_otf("invalid specification")
+ return
+ end
+
+ local p = lpeg.P("P")
+ * (lpeg.patterns.hexdigit^1/function(s) return tonumber(s,16) end)
+ * lpeg.P(-1)
+
+ local function tounicode(code)
+ if not code then
+ return
+ end
+ if type(code) == "number" then
+ return code
+ end
+ local u = unicodes[code]
+ if u then
+ -- unicodes[code] = u
+ return u
+ end
+ if utflen(code) == 1 then
+ u = utfbyte(code)
+ if u then
+ return u
+ end
+ end
+ local u = lpegmatch(p,code)
+ if u then
+ -- unicodes[code] = u
+ return u
+ end
+ if not aglunicodes then
+ aglunicodes = fonts.encodings.agl.unicodes -- delayed
+ end
+ local u = aglunicodes[code]
+ if u then
+ -- unicodes[code] = u
+ return u
+ end
+ end
+
+ local coverup = otf.coverup
+ local coveractions = coverup.actions
+ local stepkey = coverup.stepkey
+ local register = coverup.register
+
+ local function prepare_substitution(list,featuretype,nocheck)
+ local coverage = { }
+ local cover = coveractions[featuretype]
+ for code, replacement in next, list do
+ local unicode = tounicode(code)
+ local description = descriptions[unicode]
+ if not nocheck and not description then
+ skip = skip + 1
+ else
+ if type(replacement) == "table" then
+ replacement = replacement[1]
+ end
+ replacement = tounicode(replacement)
+ if replacement and descriptions[replacement] then
+ cover(coverage,unicode,replacement)
+ done = done + 1
+ else
+ skip = skip + 1
+ end
+ end
+ end
+ return coverage
+ end
+
+ local function prepare_alternate(list,featuretype,nocheck)
+ local coverage = { }
+ local cover = coveractions[featuretype]
+ for code, replacement in next, list do
+ local unicode = tounicode(code)
+ local description = descriptions[unicode]
+ if not nocheck and not description then
+ skip = skip + 1
+ elseif type(replacement) == "table" then
+ local r = { }
+ for i=1,#replacement do
+ local u = tounicode(replacement[i])
+ r[i] = (nocheck or descriptions[u]) and u or unicode
+ end
+ cover(coverage,unicode,r)
+ done = done + 1
+ else
+ local u = tounicode(replacement)
+ if u then
+ cover(coverage,unicode,{ u })
+ done = done + 1
+ else
+ skip = skip + 1
+ end
+ end
+ end
+ return coverage
+ end
+
+ local function prepare_multiple(list,featuretype,nocheck)
+ local coverage = { }
+ local cover = coveractions[featuretype]
+ for code, replacement in next, list do
+ local unicode = tounicode(code)
+ local description = descriptions[unicode]
+ if not nocheck and not description then
+ skip = skip + 1
+ elseif type(replacement) == "table" then
+ local r = { }
+ local n = 0
+ for i=1,#replacement do
+ local u = tounicode(replacement[i])
+ if nocheck or descriptions[u] then
+ n = n + 1
+ r[n] = u
+ end
+ end
+ if n > 0 then
+ cover(coverage,unicode,r)
+ done = done + 1
+ else
+ skip = skip + 1
+ end
+ else
+ local u = tounicode(replacement)
+ if u then
+ cover(coverage,unicode,{ u })
+ done = done + 1
+ else
+ skip = skip + 1
+ end
+ end
+ end
+ return coverage
+ end
+
+ local function prepare_ligature(list,featuretype,nocheck)
+ local coverage = { }
+ local cover = coveractions[featuretype]
+ for code, ligature in next, list do
+ local unicode = tounicode(code)
+ local description = descriptions[unicode]
+ if not nocheck and not description then
+ skip = skip + 1
+ else
+ if type(ligature) == "string" then
+ ligature = { lpegmatch(splitter,ligature) }
+ end
+ local present = true
+ for i=1,#ligature do
+ local l = ligature[i]
+ local u = tounicode(l)
+ if nocheck or descriptions[u] then
+ ligature[i] = u
+ else
+ present = false
+ break
+ end
+ end
+ if present then
+ cover(coverage,unicode,ligature)
+ done = done + 1
+ else
+ skip = skip + 1
+ end
+ end
+ end
+ return coverage
+ end
+
+ local function resetspacekerns()
+ -- a bit of a hack, this nil setting but it forces a
+ -- rehash of the resources needed .. the feature itself
+ -- should be a kern (at least for now)
+ data.properties.hasspacekerns = true
+ data.resources .spacekerns = nil
+ end
+
+ local function prepare_kern(list,featuretype)
+ local coverage = { }
+ local cover = coveractions[featuretype]
+ local isspace = false
+ for code, replacement in next, list do
+ local unicode = tounicode(code)
+ local description = descriptions[unicode]
+ if description and type(replacement) == "table" then
+ local r = { }
+ for k, v in next, replacement do
+ local u = tounicode(k)
+ if u then
+ r[u] = v
+ if u == 32 then
+ isspace = true
+ end
+ end
+ end
+ if next(r) then
+ cover(coverage,unicode,r)
+ done = done + 1
+ if unicode == 32 then
+ isspace = true
+ end
+ else
+ skip = skip + 1
+ end
+ else
+ skip = skip + 1
+ end
+ end
+ if isspace then
+ resetspacekerns()
+ end
+ return coverage
+ end
+
+ local function prepare_pair(list,featuretype)
+ local coverage = { }
+ local cover = coveractions[featuretype]
+ if cover then
+ for code, replacement in next, list do
+ local unicode = tounicode(code)
+ local description = descriptions[unicode]
+ if description and type(replacement) == "table" then
+ local r = { }
+ for k, v in next, replacement do
+ local u = tounicode(k)
+ if u then
+ r[u] = v
+ if u == 32 then
+ isspace = true
+ end
+ end
+ end
+ if next(r) then
+ cover(coverage,unicode,r)
+ done = done + 1
+ if unicode == 32 then
+ isspace = true
+ end
+ else
+ skip = skip + 1
+ end
+ else
+ skip = skip + 1
+ end
+ end
+ if isspace then
+ resetspacekerns()
+ end
+ else
+ report_otf("unknown cover type %a",featuretype)
+ end
+ return coverage
+ end
+
+ local prepare_single = prepare_pair -- we could have a better test on the spec
+
+ local function prepare_chain(list,featuretype,sublookups)
+ -- todo: coveractions
+ local rules = list.rules
+ local coverage = { }
+ if rules then
+ local rulehash = { }
+ local rulesize = 0
+ local lookuptype = types[featuretype]
+ for nofrules=1,#rules do
+ local rule = rules[nofrules]
+ local current = rule.current
+ local before = rule.before
+ local after = rule.after
+ local replacements = rule.replacements or false
+ local sequence = { }
+ local nofsequences = 0
+ if before then
+ for n=1,#before do
+ nofsequences = nofsequences + 1
+ sequence[nofsequences] = before[n]
+ end
+ end
+ local start = nofsequences + 1
+ for n=1,#current do
+ nofsequences = nofsequences + 1
+ sequence[nofsequences] = current[n]
+ end
+ local stop = nofsequences
+ if after then
+ for n=1,#after do
+ nofsequences = nofsequences + 1
+ sequence[nofsequences] = after[n]
+ end
+ end
+ local lookups = rule.lookups or false
+ local subtype = nil
+ if lookups and sublookups then
+ for k, v in sortedhash(lookups) do
+ local t = type(v)
+ if t == "table" then
+ -- already ok
+ for i=1,#v do
+ local vi = v[i]
+ if type(vi) ~= "table" then
+ v[i] = { vi }
+ end
+ end
+ elseif t == "number" then
+ local lookup = sublookups[v]
+ if lookup then
+ lookups[k] = { lookup }
+ if not subtype then
+ subtype = lookup.type
+ end
+ elseif v == 0 then
+ lookups[k] = { { type = "gsub_remove" } }
+ else
+ lookups[k] = false -- { false } -- new
+ end
+ else
+ lookups[k] = false -- { false } -- new
+ end
+ end
+ end
+ if nofsequences > 0 then -- we merge coverage into one
+ -- we copy as we can have different fonts
+ local hashed = { }
+ for i=1,nofsequences do
+ local t = { }
+ local s = sequence[i]
+ for i=1,#s do
+ local u = tounicode(s[i])
+ if u then
+ t[u] = true
+ end
+ end
+ hashed[i] = t
+ end
+ sequence = hashed
+ -- now we create the rule
+ rulesize = rulesize + 1
+ rulehash[rulesize] = {
+ nofrules, -- 1
+ lookuptype, -- 2
+ sequence, -- 3
+ start, -- 4
+ stop, -- 5
+ lookups, -- 6 (6/7 also signal of what to do)
+ replacements, -- 7
+ subtype, -- 8
+ }
+-- for unic in next, sequence[start] do
+ for unic in sortedhash(sequence[start]) do
+ local cu = coverage[unic]
+ if not cu then
+ coverage[unic] = rulehash -- can now be done cleaner i think
+ end
+ end
+ sequence.n = nofsequences
+ end
+ end
+ rulehash.n = rulesize
+ end
+ return coverage
+ end
+
+ local dataset = specifications.dataset
+
+ local function report(name,category,position,first,last,sequences)
+ report_otf("injecting name %a of category %a at position %i in [%i,%i] of [%i,%i]",
+ name,category,position,first,last,1,#sequences)
+ end
+
+ local function inject(specification,sequences,sequence,first,last,category,name)
+ local position = specification.position or false
+ if not position then
+ position = specification.prepend
+ if position == true then
+ if trace_loading then
+ report(name,category,first,first,last,sequences)
+ end
+ insert(sequences,first,sequence)
+ return
+ end
+ end
+ if not position then
+ position = specification.append
+ if position == true then
+ if trace_loading then
+ report(name,category,last+1,first,last,sequences)
+ end
+ insert(sequences,last+1,sequence)
+ return
+ end
+ end
+ local kind = type(position)
+ if kind == "string" then
+ local index = false
+ for i=first,last do
+ local s = sequences[i]
+ local f = s.features
+ if f then
+ for k in sortedhash(f) do -- next, f do
+ if k == position then
+ index = i
+ break
+ end
+ end
+ if index then
+ break
+ end
+ end
+ end
+ if index then
+ position = index
+ else
+ position = last + 1
+ end
+ elseif kind == "number" then
+ if position < 0 then
+ position = last - position + 1
+ end
+ if position > last then
+ position = last + 1
+ elseif position < first then
+ position = first
+ end
+ else
+ position = last + 1
+ end
+ if trace_loading then
+ report(name,category,position,first,last,sequences)
+ end
+ insert(sequences,position,sequence)
+ end
+
+ for s=1,#dataset do
+ local specification = dataset[s]
+ local valid = specification.valid -- nowhere used
+ local feature = specification.name or feature
+ if not feature or feature == "" then
+ report_otf("no valid name given for extra feature")
+ elseif not valid or valid(data,specification,feature) then -- anum uses this
+ local initialize = specification.initialize
+ if initialize then
+ -- when false is returned we initialize only once
+ specification.initialize = initialize(specification,data) and initialize or nil
+ end
+ local askedfeatures = specification.features or everywhere
+ local askedsteps = specification.steps or specification.subtables or { specification.data } or { }
+ local featuretype = normalized[specification.type or "substitution"] or "substitution"
+ local featureflags = specification.flags or noflags
+ local nocheck = specification.nocheck
+ local futuresteps = specification.futuresteps
+ local featureorder = specification.order or { feature }
+ local featurechain = (featuretype == "chainsubstitution" or featuretype == "chainposition") and 1 or 0
+ local nofsteps = 0
+ local steps = { }
+ local sublookups = specification.lookups
+ local category = nil
+ --
+ checkflags(specification,resources)
+ --
+ if sublookups then
+ local s = { }
+ for i=1,#sublookups do
+ local specification = sublookups[i]
+ local askedsteps = specification.steps or specification.subtables or { specification.data } or { }
+ local featuretype = normalized[specification.type or "substitution"] or "substitution"
+ local featureflags = specification.flags or noflags
+ local nofsteps = 0
+ local steps = { }
+ for i=1,#askedsteps do
+ local list = askedsteps[i]
+ local coverage = nil
+ local format = nil
+ if featuretype == "substitution" then
+ coverage = prepare_substitution(list,featuretype,nocheck)
+ elseif featuretype == "ligature" then
+ coverage = prepare_ligature(list,featuretype,nocheck)
+ elseif featuretype == "alternate" then
+ coverage = prepare_alternate(list,featuretype,nocheck)
+ elseif featuretype == "multiple" then
+ coverage = prepare_multiple(list,featuretype,nocheck)
+ elseif featuretype == "kern" or featuretype == "move" then
+ format = featuretype
+ coverage = prepare_kern(list,featuretype)
+ elseif featuretype == "pair" then
+ format = "pair"
+ coverage = prepare_pair(list,featuretype)
+ elseif featuretype == "single" then
+ format = "single"
+ coverage = prepare_single(list,featuretype)
+ end
+ if coverage and next(coverage) then
+ nofsteps = nofsteps + 1
+ steps[nofsteps] = register(coverage,featuretype,format,feature,nofsteps,descriptions,resources)
+ end
+ end
+ --
+ checkmerge(specification)
+ checksteps(specification)
+ --
+ s[i] = {
+ [stepkey] = steps,
+ nofsteps = nofsteps,
+ flags = featureflags,
+ type = types[featuretype],
+ }
+ end
+ sublookups = s
+ end
+ for i=1,#askedsteps do
+ local list = askedsteps[i]
+ local coverage = nil
+ local format = nil
+ if featuretype == "substitution" then
+ category = "gsub"
+ coverage = prepare_substitution(list,featuretype,nocheck)
+ elseif featuretype == "ligature" then
+ category = "gsub"
+ coverage = prepare_ligature(list,featuretype,nocheck)
+ elseif featuretype == "alternate" then
+ category = "gsub"
+ coverage = prepare_alternate(list,featuretype,nocheck)
+ elseif featuretype == "multiple" then
+ category = "gsub"
+ coverage = prepare_multiple(list,featuretype,nocheck)
+ elseif featuretype == "kern" or featuretype == "move" then
+ category = "gpos"
+ format = featuretype
+ coverage = prepare_kern(list,featuretype)
+ elseif featuretype == "pair" then
+ category = "gpos"
+ format = "pair"
+ coverage = prepare_pair(list,featuretype)
+ elseif featuretype == "single" then
+ category = "gpos"
+ format = "single"
+ coverage = prepare_single(list,featuretype)
+ elseif featuretype == "chainsubstitution" then
+ category = "gsub"
+ coverage = prepare_chain(list,featuretype,sublookups)
+ elseif featuretype == "chainposition" then
+ category = "gpos"
+ coverage = prepare_chain(list,featuretype,sublookups)
+ else
+ report_otf("not registering feature %a, unknown category",feature)
+ return
+ end
+ if coverage and next(coverage) then
+ nofsteps = nofsteps + 1
+ steps[nofsteps] = register(coverage,featuretype,format,feature,nofsteps,descriptions,resources)
+ end
+ end
+ if nofsteps > 0 then
+ -- script = { lang1, lang2, lang3 } or script = { lang1 = true, ... }
+ for k, v in next, askedfeatures do
+ if v[1] then
+ askedfeatures[k] = tohash(v)
+ end
+ end
+ --
+ if featureflags[1] then featureflags[1] = "mark" end
+ if featureflags[2] then featureflags[2] = "ligature" end
+ if featureflags[3] then featureflags[3] = "base" end
+ local steptype = types[featuretype]
+ local sequence = {
+ chain = featurechain,
+ features = { [feature] = askedfeatures },
+ flags = featureflags,
+ name = feature, -- redundant
+ order = featureorder,
+ [stepkey] = steps,
+ nofsteps = nofsteps,
+ type = steptype,
+ }
+ --
+ checkflags(sequence,resources)
+ checkmerge(sequence)
+ checksteps(sequence)
+ -- position | prepend | append
+ local first, last = getrange(sequences,category)
+ inject(specification,sequences,sequence,first,last,category,feature)
+ -- register in metadata (merge as there can be a few)
+ local features = fontfeatures[category]
+ if not features then
+ features = { }
+ fontfeatures[category] = features
+ end
+ local k = features[feature]
+ if not k then
+ k = { }
+ features[feature] = k
+ end
+ --
+ for script, languages in next, askedfeatures do
+ local kk = k[script]
+ if not kk then
+ kk = { }
+ k[script] = kk
+ end
+ for language, value in next, languages do
+ kk[language] = value
+ end
+ end
+ end
+ end
+ end
+ if trace_loading then
+ report_otf("registering feature %a, affected glyphs %a, skipped glyphs %a",feature,done,skip)
+ end
+end
+
+otf.enhancers.addfeature = addfeature
+
+local extrafeatures = { }
+local knownfeatures = { }
+
+function otf.addfeature(name,specification)
+ if type(name) == "table" then
+ specification = name
+ end
+ if type(specification) ~= "table" then
+ report_otf("invalid feature specification, no valid table")
+ return
+ end
+ specification, name = validspecification(specification,name)
+ if name and specification then
+ local slot = knownfeatures[name]
+ if not slot then
+ -- we have a new one
+ slot = #extrafeatures + 1
+ knownfeatures[name] = slot
+ elseif specification.overload == false then
+ -- we add an extre one
+ slot = #extrafeatures + 1
+ knownfeatures[name] = slot
+ else
+ -- we overload a previous one
+ end
+ specification.name = name -- to be sure
+ extrafeatures[slot] = specification
+ -- report_otf("adding feature %a @ %i",name,slot)
+ end
+end
+
+-- for feature, specification in next, extrafeatures do
+-- addfeature(data,feature,specification)
+-- end
+
+local function enhance(data,filename,raw)
+ for slot=1,#extrafeatures do
+ local specification = extrafeatures[slot]
+ addfeature(data,specification.name,specification)
+ end
+end
+
+otf.enhancers.enhance = enhance
+
+otf.enhancers.register("check extra features",enhance)
+
+-- fonts.handlers.otf.features.register {
+-- name = 'hangulfix',
+-- description = 'fixes for hangul',
+-- }
+
+-- fonts.handlers.otf.addfeature {
+-- name = "stest",
+-- type = "substitution",
+-- data = {
+-- a = "X",
+-- b = "P",
+-- }
+-- }
+-- fonts.handlers.otf.addfeature {
+-- name = "atest",
+-- type = "alternate",
+-- data = {
+-- a = { "X", "Y" },
+-- b = { "P", "Q" },
+-- }
+-- }
+-- fonts.handlers.otf.addfeature {
+-- name = "mtest",
+-- type = "multiple",
+-- data = {
+-- a = { "X", "Y" },
+-- b = { "P", "Q" },
+-- }
+-- }
+-- fonts.handlers.otf.addfeature {
+-- name = "ltest",
+-- type = "ligature",
+-- data = {
+-- X = { "a", "b" },
+-- Y = { "d", "a" },
+-- }
+-- }
+-- fonts.handlers.otf.addfeature {
+-- name = "ktest",
+-- type = "kern",
+-- data = {
+-- a = { b = -500 },
+-- }
+-- }
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-oti.lua b/macros/luatex/generic/luaotfload/fontloader-font-oti.lua
new file mode 100644
index 0000000000..4c6053be07
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-oti.lua
@@ -0,0 +1,262 @@
+if not modules then modules = { } end modules ['font-oti'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local lower = string.lower
+
+local fonts = fonts
+local constructors = fonts.constructors
+
+local otf = constructors.handlers.otf
+local otffeatures = constructors.features.otf
+local registerotffeature = otffeatures.register
+
+local otftables = otf.tables or { }
+otf.tables = otftables
+
+local allocate = utilities.storage.allocate
+
+registerotffeature {
+ name = "features",
+ description = "initialization of feature handler",
+ default = true,
+}
+
+-- these are later hooked into node and base initializaters
+
+local function setmode(tfmdata,value)
+ if value then
+ tfmdata.properties.mode = lower(value)
+ end
+end
+
+otf.modeinitializer = setmode
+
+local function setlanguage(tfmdata,value)
+ if value then
+ local cleanvalue = lower(value)
+ local languages = otftables and otftables.languages
+ local properties = tfmdata.properties
+ if not languages then
+ properties.language = cleanvalue
+ elseif languages[value] then
+ properties.language = cleanvalue
+ else
+ properties.language = "dflt"
+ end
+ end
+end
+
+local function setscript(tfmdata,value)
+ if value then
+ local cleanvalue = lower(value)
+ local scripts = otftables and otftables.scripts
+ local properties = tfmdata.properties
+ if not scripts then
+ properties.script = cleanvalue
+ elseif scripts[value] then
+ properties.script = cleanvalue
+ else
+ properties.script = "dflt"
+ end
+ end
+end
+
+registerotffeature {
+ name = "mode",
+ description = "mode",
+ initializers = {
+ base = setmode,
+ node = setmode,
+ plug = setmode,
+ }
+}
+
+registerotffeature {
+ name = "language",
+ description = "language",
+ initializers = {
+ base = setlanguage,
+ node = setlanguage,
+ plug = setlanguage,
+ }
+}
+
+registerotffeature {
+ name = "script",
+ description = "script",
+ initializers = {
+ base = setscript,
+ node = setscript,
+ plug = setscript,
+ }
+}
+
+-- here (as also in generic
+
+otftables.featuretypes = allocate {
+ gpos_single = "position",
+ gpos_pair = "position",
+ gpos_cursive = "position",
+ gpos_mark2base = "position",
+ gpos_mark2ligature = "position",
+ gpos_mark2mark = "position",
+ gpos_context = "position",
+ gpos_contextchain = "position",
+ gsub_single = "substitution",
+ gsub_multiple = "substitution",
+ gsub_alternate = "substitution",
+ gsub_ligature = "substitution",
+ gsub_context = "substitution",
+ gsub_contextchain = "substitution",
+ gsub_reversecontextchain = "substitution",
+ gsub_reversesub = "substitution",
+}
+
+function otffeatures.checkeddefaultscript(featuretype,autoscript,scripts)
+ if featuretype == "position" then
+ local default = scripts.dflt
+ if default then
+ if autoscript == "position" or autoscript == true then
+ return default
+ else
+ report_otf("script feature %s not applied, enable default positioning")
+ end
+ else
+ -- no positioning at all
+ end
+ elseif featuretype == "substitution" then
+ local default = scripts.dflt
+ if default then
+ if autoscript == "substitution" or autoscript == true then
+ return default
+ end
+ end
+ end
+end
+
+function otffeatures.checkeddefaultlanguage(featuretype,autolanguage,languages)
+ if featuretype == "position" then
+ local default = languages.dflt
+ if default then
+ if autolanguage == "position" or autolanguage == true then
+ return default
+ else
+ report_otf("language feature %s not applied, enable default positioning")
+ end
+ else
+ -- no positioning at all
+ end
+ elseif featuretype == "substitution" then
+ local default = languages.dflt
+ if default then
+ if autolanguage == "substitution" or autolanguage == true then
+ return default
+ end
+ end
+ end
+end
+
+-- the following might become available generic in due time but for now
+-- this is some context playground (development code)
+
+-- if not context then
+-- return
+-- end
+
+-- local helpers = otf.readers.helpers
+-- local axistofactors = helpers.axistofactors
+-- local normalizedaxis = helpers.normalizedaxis
+-- local getaxisscale = helpers.getaxisscale
+-- local cleanname = containers.cleanname
+
+-- local function validvariable(tfmdata)
+-- if tfmdata.properties.factors then
+-- return
+-- end
+-- local resources = tfmdata.resources
+-- local variabledata = resources and resources.variabledata
+-- if not variabledata then
+-- return
+-- end
+-- local instances = variabledata.instances
+-- local axis = variabledata.axis
+-- local segments = variabledata.segments
+-- if instances and axis then
+-- return instances, axis, segments
+-- end
+-- end
+
+-- local function initializeinstance(tfmdata,value)
+-- if type(value) == "string" then
+-- local instances, axis, segments = validvariable(tfmdata)
+-- if instances then
+-- local values
+-- for i=1,#instances do
+-- local instance = instances[i]
+-- if cleanname(instance.subfamily) == value then
+-- values = instance.values
+-- break
+-- end
+-- end
+-- if values then
+-- local factors = { }
+-- for i=1,#axis do
+-- local a = axis[i]
+-- factors[i] = getaxisscale(segments,a.minimum,a.default,a.maximum,values[i].value)
+-- end
+-- tfmdata.properties.instance = {
+-- hash = instance,
+-- factors = factors,
+-- }
+-- end
+-- else
+-- report("incomplete variable data")
+-- end
+-- end
+-- end
+
+-- local function initializeaxis(tfmdata,value)
+-- if type(value) == "string" then
+-- local instances, axis, segments = validvariable(tfmdata)
+-- if instances then
+-- local values = axistofactors(value)
+-- if values then
+-- local factors = { }
+-- for i=1,#axis do
+-- local a = axis[i]
+-- local d = a.default
+-- factors[i] = getaxisscale(segments,a.minimum,d,a.maximum,values[a.name or a.tag] or d)
+-- end
+-- tfmdata.properties.instance = {
+-- hash = cleanname(value),
+-- factors = factors,
+-- }
+-- end
+-- else
+-- report("incomplete variable data")
+-- end
+-- end
+-- end
+
+-- registerotffeature {
+-- name = "instance",
+-- description = "variation instance",
+-- initializers = {
+-- node = initializeinstance,
+-- base = initializeinstance,
+-- }
+-- }
+
+-- registerotffeature {
+-- name = "axis",
+-- description = "variation axis",
+-- initializers = {
+-- node = initializeaxis,
+-- base = initializeaxis,
+-- }
+-- }
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-otj.lua b/macros/luatex/generic/luaotfload/fontloader-font-otj.lua
new file mode 100644
index 0000000000..2e7878d3df
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-otj.lua
@@ -0,0 +1,1755 @@
+if not modules then modules = { } end modules ['font-otj'] = {
+ version = 1.001,
+ comment = "companion to font-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files",
+}
+
+-- This property based variant is not faster but looks nicer than the attribute one. We
+-- need to use rawget (which is about 4 times slower than a direct access but we cannot
+-- get/set that one for our purpose! This version does a bit more with discretionaries
+-- (and Kai has tested it with his collection of weird fonts.)
+
+-- There is some duplicate code here (especially in the the pre/post/replace branches) but
+-- we go for speed. We could store a list of glyph and mark nodes when registering but it's
+-- cleaner to have an identification pass here. Also, I need to keep tracing in mind so
+-- being too clever here is dangerous.
+
+-- As we have a rawget on properties we don't need one on injections.
+
+-- The use_advance code was just a test and is meant for testing and manuals. There is no
+-- performance (or whatever) gain and using kerns is somewhat cleaner (at least for now).
+
+-- An alternative is to have a list per base of all marks and then do a run over the node
+-- list that resolves the accumulated l/r/x/y and then do an inject pass.
+
+-- if needed we can flag a kern node as immutable
+
+-- The thing with these positioning options is that it is not clear what Uniscribe does with
+-- the 2rl flag and we keep oscillating a between experiments.
+
+if not nodes.properties then return end
+
+local next, rawget, tonumber = next, rawget, tonumber
+local fastcopy = table.fastcopy
+
+local registertracker = trackers.register
+local registerdirective = directives.register
+
+local trace_injections = false registertracker("fonts.injections", function(v) trace_injections = v end)
+local trace_marks = false registertracker("fonts.injections.marks", function(v) trace_marks = v end)
+local trace_cursive = false registertracker("fonts.injections.cursive", function(v) trace_cursive = v end)
+local trace_spaces = false registertracker("fonts.injections.spaces", function(v) trace_spaces = v end)
+
+-- local fix_cursive_marks = false
+--
+-- registerdirective("fonts.injections.fixcursivemarks", function(v)
+-- fix_cursive_marks = v
+-- end)
+
+local report_injections = logs.reporter("fonts","injections")
+local report_spaces = logs.reporter("fonts","spaces")
+
+local attributes, nodes, node = attributes, nodes, node
+
+fonts = fonts
+local hashes = fonts.hashes
+local fontdata = hashes.identifiers
+local fontmarks = hashes.marks
+----- parameters = fonts.hashes.parameters -- not in generic
+----- resources = fonts.hashes.resources -- not in generic
+
+nodes.injections = nodes.injections or { }
+local injections = nodes.injections
+
+local tracers = nodes.tracers
+local setcolor = tracers and tracers.colors.set
+local resetcolor = tracers and tracers.colors.reset
+
+local nodecodes = nodes.nodecodes
+local glyph_code = nodecodes.glyph
+local disc_code = nodecodes.disc
+local kern_code = nodecodes.kern
+local glue_code = nodecodes.glue
+
+local nuts = nodes.nuts
+local nodepool = nuts.pool
+
+local tonode = nuts.tonode
+local tonut = nuts.tonut
+
+local setfield = nuts.setfield
+local getnext = nuts.getnext
+local getprev = nuts.getprev
+local getid = nuts.getid
+local getfont = nuts.getfont
+local getchar = nuts.getchar
+local getoffsets = nuts.getoffsets
+local getboth = nuts.getboth
+local getdisc = nuts.getdisc
+local setdisc = nuts.setdisc
+local setoffsets = nuts.setoffsets
+local ischar = nuts.ischar
+local getkern = nuts.getkern
+local setkern = nuts.setkern
+local setlink = nuts.setlink
+local setwidth = nuts.setwidth
+local getwidth = nuts.getwidth
+
+----- traverse_id = nuts.traverse_id
+----- traverse_char = nuts.traverse_char
+local nextchar = nuts.traversers.char
+local nextglue = nuts.traversers.glue
+
+local insert_node_before = nuts.insert_before
+local insert_node_after = nuts.insert_after
+
+local properties = nodes.properties.data
+
+local fontkern = nuts.pool and nuts.pool.fontkern -- context
+local italickern = nuts.pool and nuts.pool.italickern -- context
+
+local useitalickerns = false
+
+directives.register("fonts.injections.useitalics", function(v)
+ if v then
+ report_injections("using italics for space kerns (tracing only)")
+ end
+ useitalickerns = v
+end)
+
+do if not fontkern then -- generic
+
+ local thekern = nuts.new("kern",0) -- fontkern
+ local setkern = nuts.setkern
+ local copy_node = nuts.copy_node
+
+ fontkern = function(k)
+ local n = copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+
+end end
+
+do if not italickern then -- generic
+
+ local thekern = nuts.new("kern",3) -- italiccorrection
+ local setkern = nuts.setkern
+ local copy_node = nuts.copy_node
+
+ italickern = function(k)
+ local n = copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+
+end end
+
+function injections.installnewkern() end -- obsolete
+
+local nofregisteredkerns = 0
+local nofregisteredpositions = 0
+local nofregisteredmarks = 0
+local nofregisteredcursives = 0
+local keepregisteredcounts = false
+
+function injections.keepcounts()
+ keepregisteredcounts = true
+end
+
+function injections.resetcounts()
+ nofregisteredkerns = 0
+ nofregisteredpositions = 0
+ nofregisteredmarks = 0
+ nofregisteredcursives = 0
+ keepregisteredcounts = false
+end
+
+-- We need to make sure that a possible metatable will not kick in unexpectedly.
+
+function injections.reset(n)
+ local p = rawget(properties,n)
+ if p then
+ p.injections = false -- { } -- nil should work too as we use rawget
+ else
+ properties[n] = false -- { injections = { } } -- nil should work too as we use rawget
+ end
+end
+
+function injections.copy(target,source)
+ local sp = rawget(properties,source)
+ if sp then
+ local tp = rawget(properties,target)
+ local si = sp.injections
+ if si then
+ si = fastcopy(si)
+ if tp then
+ tp.injections = si
+ else
+ properties[target] = {
+ injections = si,
+ }
+ end
+ elseif tp then
+ tp.injections = false -- { }
+ else
+ properties[target] = { injections = { } }
+ end
+ else
+ local tp = rawget(properties,target)
+ if tp then
+ tp.injections = false -- { }
+ else
+ properties[target] = false -- { injections = { } }
+ end
+ end
+end
+
+function injections.setligaindex(n,index) -- todo: don't set when 0
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections
+ if i then
+ i.ligaindex = index
+ else
+ p.injections = {
+ ligaindex = index
+ }
+ end
+ else
+ properties[n] = {
+ injections = {
+ ligaindex = index
+ }
+ }
+ end
+end
+
+function injections.getligaindex(n,default)
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections
+ if i then
+ return i.ligaindex or default
+ end
+ end
+ return default
+end
+
+function injections.setcursive(start,nxt,factor,rlmode,exit,entry,tfmstart,tfmnext,r2lflag)
+
+ -- The standard says something about the r2lflag related to the first in a series:
+ --
+ -- When this bit is set, the last glyph in a given sequence to which the cursive
+ -- attachment lookup is applied, will be positioned on the baseline.
+ --
+ -- But it looks like we don't need to consider it.
+
+ local dx = factor*(exit[1]-entry[1])
+ local dy = -factor*(exit[2]-entry[2])
+ local ws = tfmstart.width
+ local wn = tfmnext.width
+ nofregisteredcursives = nofregisteredcursives + 1
+ if rlmode < 0 then
+ dx = -(dx + wn)
+ else
+ dx = dx - ws
+ end
+ if dx == 0 then
+ -- get rid of funny -0
+ dx = 0
+ end
+ --
+ local p = rawget(properties,start)
+ if p then
+ local i = p.injections
+ if i then
+ i.cursiveanchor = true
+ else
+ p.injections = {
+ cursiveanchor = true,
+ }
+ end
+ else
+ properties[start] = {
+ injections = {
+ cursiveanchor = true,
+ },
+ }
+ end
+ local p = rawget(properties,nxt)
+ if p then
+ local i = p.injections
+ if i then
+ i.cursivex = dx
+ i.cursivey = dy
+ else
+ p.injections = {
+ cursivex = dx,
+ cursivey = dy,
+ }
+ end
+ else
+ properties[nxt] = {
+ injections = {
+ cursivex = dx,
+ cursivey = dy,
+ },
+ }
+ end
+ return dx, dy, nofregisteredcursives
+end
+
+-- kind: 0=single 1=first of pair, 2=second of pair
+
+function injections.setposition(kind,current,factor,rlmode,spec,injection)
+ local x = factor * (spec[1] or 0)
+ local y = factor * (spec[2] or 0)
+ local w = factor * (spec[3] or 0)
+ local h = factor * (spec[4] or 0)
+ if x ~= 0 or w ~= 0 or y ~= 0 or h ~= 0 then -- okay?
+ local yoffset = y - h
+ local leftkern = x -- both kerns are set in a pair kern compared
+ local rightkern = w - x -- to normal kerns where we set only leftkern
+ if leftkern ~= 0 or rightkern ~= 0 or yoffset ~= 0 then
+ nofregisteredpositions = nofregisteredpositions + 1
+ if rlmode and rlmode < 0 then
+ leftkern, rightkern = rightkern, leftkern
+ end
+ if not injection then
+ injection = "injections"
+ end
+ local p = rawget(properties,current)
+ if p then
+ local i = p[injection]
+ if i then
+ if leftkern ~= 0 then
+ i.leftkern = (i.leftkern or 0) + leftkern
+ end
+ if rightkern ~= 0 then
+ i.rightkern = (i.rightkern or 0) + rightkern
+ end
+ if yoffset ~= 0 then
+ i.yoffset = (i.yoffset or 0) + yoffset
+ end
+ elseif leftkern ~= 0 or rightkern ~= 0 then
+ p[injection] = {
+ leftkern = leftkern,
+ rightkern = rightkern,
+ yoffset = yoffset,
+ }
+ else
+ p[injection] = {
+ yoffset = yoffset,
+ }
+ end
+ elseif leftkern ~= 0 or rightkern ~= 0 then
+ properties[current] = {
+ [injection] = {
+ leftkern = leftkern,
+ rightkern = rightkern,
+ yoffset = yoffset,
+ },
+ }
+ else
+ properties[current] = {
+ [injection] = {
+ yoffset = yoffset,
+ },
+ }
+ end
+ return x, y, w, h, nofregisteredpositions
+ end
+ end
+ return x, y, w, h -- no bound
+end
+
+-- The next one is used for simple kerns coming from a truetype kern table. The r2l
+-- variant variant needs checking but it is unlikely that a r2l script uses thsi
+-- feature.
+
+function injections.setkern(current,factor,rlmode,x,injection)
+ local dx = factor * x
+ if dx ~= 0 then
+ nofregisteredkerns = nofregisteredkerns + 1
+ local p = rawget(properties,current)
+ if not injection then
+ injection = "injections"
+ end
+ if p then
+ local i = p[injection]
+ if i then
+ i.leftkern = dx + (i.leftkern or 0)
+ else
+ p[injection] = {
+ leftkern = dx,
+ }
+ end
+ else
+ properties[current] = {
+ [injection] = {
+ leftkern = dx,
+ },
+ }
+ end
+ return dx, nofregisteredkerns
+ else
+ return 0, 0
+ end
+end
+
+-- This one is an optimization of pairs where we have only a "w" entry. This one is
+-- potentially different from the previous one wrt r2l. It needs checking. The
+-- optimization relates to smaller tma files.
+
+function injections.setmove(current,factor,rlmode,x,injection)
+ local dx = factor * x
+ if dx ~= 0 then
+ nofregisteredkerns = nofregisteredkerns + 1
+ local p = rawget(properties,current)
+ if not injection then
+ injection = "injections"
+ end
+ if rlmode and rlmode < 0 then
+ -- we need to swap with a single so then we also need to to it here
+ -- as move is just a simple single
+ if p then
+ local i = p[injection]
+ if i then
+ i.rightkern = dx + (i.rightkern or 0)
+ else
+ p[injection] = {
+ rightkern = dx,
+ }
+ end
+ else
+ properties[current] = {
+ [injection] = {
+ rightkern = dx,
+ },
+ }
+ end
+ else
+ if p then
+ local i = p[injection]
+ if i then
+ i.leftkern = dx + (i.leftkern or 0)
+ else
+ p[injection] = {
+ leftkern = dx,
+ }
+ end
+ else
+ properties[current] = {
+ [injection] = {
+ leftkern = dx,
+ },
+ }
+ end
+ end
+ return dx, nofregisteredkerns
+ else
+ return 0, 0
+ end
+end
+
+function injections.setmark(start,base,factor,rlmode,ba,ma,tfmbase,mkmk,checkmark) -- ba=baseanchor, ma=markanchor
+ local dx = factor*(ba[1]-ma[1])
+ local dy = factor*(ba[2]-ma[2])
+ nofregisteredmarks = nofregisteredmarks + 1
+ if rlmode >= 0 then
+ dx = tfmbase.width - dx -- see later commented ox
+ end
+ local p = rawget(properties,start)
+ -- hm, dejavu serif does a sloppy mark2mark before mark2base
+ if p then
+ local i = p.injections
+ if i then
+ if i.markmark then
+ -- out of order mkmk: yes or no or option
+ else
+ -- if dx ~= 0 then
+ -- i.markx = dx
+ -- end
+ -- if y ~= 0 then
+ -- i.marky = dy
+ -- end
+ -- if rlmode then
+ -- i.markdir = rlmode
+ -- end
+ i.markx = dx
+ i.marky = dy
+ i.markdir = rlmode or 0
+ i.markbase = nofregisteredmarks
+ i.markbasenode = base
+ i.markmark = mkmk
+ i.checkmark = checkmark
+ end
+ else
+ p.injections = {
+ markx = dx,
+ marky = dy,
+ markdir = rlmode or 0,
+ markbase = nofregisteredmarks,
+ markbasenode = base,
+ markmark = mkmk,
+ checkmark = checkmark,
+ }
+ end
+ else
+ properties[start] = {
+ injections = {
+ markx = dx,
+ marky = dy,
+ markdir = rlmode or 0,
+ markbase = nofregisteredmarks,
+ markbasenode = base,
+ markmark = mkmk,
+ checkmark = checkmark,
+ },
+ }
+ end
+ return dx, dy, nofregisteredmarks
+end
+
+local function dir(n)
+ return (n and n<0 and "r-to-l") or (n and n>0 and "l-to-r") or "unset"
+end
+
+local function showchar(n,nested)
+ local char = getchar(n)
+ report_injections("%wfont %s, char %U, glyph %c",nested and 2 or 0,getfont(n),char,char)
+end
+
+local function show(n,what,nested,symbol)
+ if n then
+ local p = rawget(properties,n)
+ if p then
+ local i = p[what]
+ if i then
+ local leftkern = i.leftkern or 0
+ local rightkern = i.rightkern or 0
+ local yoffset = i.yoffset or 0
+ local markx = i.markx or 0
+ local marky = i.marky or 0
+ local markdir = i.markdir or 0
+ local markbase = i.markbase or 0
+ local cursivex = i.cursivex or 0
+ local cursivey = i.cursivey or 0
+ local ligaindex = i.ligaindex or 0
+ local cursbase = i.cursiveanchor
+ local margin = nested and 4 or 2
+ --
+ if rightkern ~= 0 or yoffset ~= 0 then
+ report_injections("%w%s pair: lx %p, rx %p, dy %p",margin,symbol,leftkern,rightkern,yoffset)
+ elseif leftkern ~= 0 then
+ report_injections("%w%s kern: dx %p",margin,symbol,leftkern)
+ end
+ if markx ~= 0 or marky ~= 0 or markbase ~= 0 then
+ report_injections("%w%s mark: dx %p, dy %p, dir %s, base %s",margin,symbol,markx,marky,markdir,markbase ~= 0 and "yes" or "no")
+ end
+ if cursivex ~= 0 or cursivey ~= 0 then
+ if cursbase then
+ report_injections("%w%s curs: base dx %p, dy %p",margin,symbol,cursivex,cursivey)
+ else
+ report_injections("%w%s curs: dx %p, dy %p",margin,symbol,cursivex,cursivey)
+ end
+ elseif cursbase then
+ report_injections("%w%s curs: base",margin,symbol)
+ end
+ if ligaindex ~= 0 then
+ report_injections("%w%s liga: index %i",margin,symbol,ligaindex)
+ end
+ end
+ end
+ end
+end
+
+local function showsub(n,what,where)
+ report_injections("begin subrun: %s",where)
+ for n in nextchar, n do
+ showchar(n,where)
+ show(n,what,where," ")
+ end
+ report_injections("end subrun")
+end
+
+local function trace(head,where)
+ report_injections()
+ report_injections("begin run %s: %s kerns, %s positions, %s marks and %s cursives registered",
+ where or "",nofregisteredkerns,nofregisteredpositions,nofregisteredmarks,nofregisteredcursives)
+ local n = head
+ while n do
+ local id = getid(n)
+ if id == glyph_code then
+ showchar(n)
+ show(n,"injections",false," ")
+ show(n,"preinjections",false,"<")
+ show(n,"postinjections",false,">")
+ show(n,"replaceinjections",false,"=")
+ show(n,"emptyinjections",false,"*")
+ elseif id == disc_code then
+ local pre, post, replace = getdisc(n)
+ if pre then
+ showsub(pre,"preinjections","pre")
+ end
+ if post then
+ showsub(post,"postinjections","post")
+ end
+ if replace then
+ showsub(replace,"replaceinjections","replace")
+ end
+ show(n,"emptyinjections",false,"*")
+ end
+ n = getnext(n)
+ end
+ report_injections("end run")
+end
+
+local function show_result(head)
+ local current = head
+ local skipping = false
+ while current do
+ local id = getid(current)
+ if id == glyph_code then
+ local w = getwidth(current)
+ local x, y = getoffsets(current)
+ report_injections("char: %C, width %p, xoffset %p, yoffset %p",getchar(current),w,x,y)
+ skipping = false
+ elseif id == kern_code then
+ report_injections("kern: %p",getkern(current))
+ skipping = false
+ elseif not skipping then
+ report_injections()
+ skipping = true
+ end
+ current = getnext(current)
+ end
+ report_injections()
+end
+
+-- G +D-pre G
+-- D-post+
+-- +D-replace+
+--
+-- G +D-pre +D-pre
+-- D-post +D-post
+-- +D-replace +D-replace
+
+local function inject_kerns_only(head,where)
+ if trace_injections then
+ trace(head,"kerns")
+ end
+ local current = head
+ local prev = nil
+ local next = nil
+ local prevdisc = nil
+ -- local prevglyph = nil
+ local pre = nil -- saves a lookup
+ local post = nil -- saves a lookup
+ local replace = nil -- saves a lookup
+ local pretail = nil -- saves a lookup
+ local posttail = nil -- saves a lookup
+ local replacetail = nil -- saves a lookup
+ while current do
+ local next = getnext(current)
+ local char, id = ischar(current)
+ if char then
+ local p = rawget(properties,current)
+ if p then
+ local i = p.injections
+ if i then
+ -- left|glyph|right
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ head = insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if prevdisc then
+ local done = false
+ if post then
+ local i = p.postinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ setlink(posttail,fontkern(leftkern))
+ done = true
+ end
+ end
+ end
+ if replace then
+ local i = p.replaceinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ setlink(replacetail,fontkern(leftkern))
+ done = true
+ end
+ end
+ else
+ local i = p.emptyinjections
+ if i then
+ -- glyph|disc|glyph (special case)
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ replace = fontkern(leftkern)
+ done = true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ prevdisc = nil
+ -- prevglyph = current
+ elseif char == false then
+ -- other font
+ prevdisc = nil
+ -- prevglyph = current
+ elseif id == disc_code then
+ pre, post, replace, pretail, posttail, replacetail = getdisc(current,true)
+ local done = false
+ if pre then
+ -- left|pre glyphs|right
+ for n in nextchar, pre do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.preinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ pre = insert_node_before(pre,n,fontkern(leftkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if post then
+ -- left|post glyphs|right
+ for n in nextchar, post do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.postinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ post = insert_node_before(post,n,fontkern(leftkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ -- left|replace glyphs|right
+ for n in nextchar, replace do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.replaceinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ replace = insert_node_before(replace,n,fontkern(leftkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ -- prevglyph = nil
+ prevdisc = current
+ else
+ -- prevglyph = nil
+ prevdisc = nil
+ end
+ prev = current
+ current = next
+ end
+ --
+ if keepregisteredcounts then
+ keepregisteredcounts = false
+ else
+ nofregisteredkerns = 0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+
+local function inject_positions_only(head,where)
+ if trace_injections then
+ trace(head,"positions")
+ end
+ local current = head
+ local prev = nil
+ local next = nil
+ local prevdisc = nil
+ local prevglyph = nil
+ local pre = nil -- saves a lookup
+ local post = nil -- saves a lookup
+ local replace = nil -- saves a lookup
+ local pretail = nil -- saves a lookup
+ local posttail = nil -- saves a lookup
+ local replacetail = nil -- saves a lookup
+ while current do
+ local next = getnext(current)
+ local char, id = ischar(current)
+ if char then
+ local p = rawget(properties,current)
+ if p then
+ local i = p.injections
+ if i then
+ -- left|glyph|right
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(current,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ local rightkern = i.rightkern
+ if leftkern and leftkern ~= 0 then
+ if rightkern and leftkern == -rightkern then
+ setoffsets(current,leftkern,false)
+ rightkern = 0
+ else
+ head = insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(head,current,fontkern(rightkern))
+ end
+ else
+ local i = p.emptyinjections
+ if i then
+ -- glyph|disc|glyph (special case)
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ if next and getid(next) == disc_code then
+ if replace then
+ -- error, we expect an empty one
+ else
+ -- KE setfield(next,"replace",fontkern(rightkern)) -- maybe also leftkern
+ replace = fontkern(rightkern) -- maybe also leftkern
+ done = true --KE
+ end
+ end
+ end
+ end
+ end
+ if prevdisc then
+ local done = false
+ if post then
+ local i = p.postinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ setlink(posttail,fontkern(leftkern))
+ done = true
+ end
+ end
+ end
+ if replace then
+ local i = p.replaceinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ setlink(replacetail,fontkern(leftkern))
+ done = true
+ end
+ end
+ else
+ local i = p.emptyinjections
+ if i then
+ -- new .. okay?
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ replace = fontkern(leftkern)
+ done = true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ prevdisc = nil
+ prevglyph = current
+ elseif char == false then
+ prevdisc = nil
+ prevglyph = current
+ elseif id == disc_code then
+ pre, post, replace, pretail, posttail, replacetail = getdisc(current,true)
+ local done = false
+ if pre then
+ -- left|pre glyphs|right
+ for n in nextchar, pre do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.preinjections
+ if i then
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ pre = insert_node_before(pre,n,fontkern(leftkern))
+ done = true
+ end
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(pre,n,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if post then
+ -- left|post glyphs|right
+ for n in nextchar, post do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.postinjections
+ if i then
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ post = insert_node_before(post,n,fontkern(leftkern))
+ done = true
+ end
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(post,n,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ -- left|replace glyphs|right
+ for n in nextchar, replace do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.replaceinjections
+ if i then
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ replace = insert_node_before(replace,n,fontkern(leftkern))
+ done = true
+ end
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(replace,n,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if prevglyph then
+ if pre then
+ local p = rawget(properties,prevglyph)
+ if p then
+ local i = p.preinjections
+ if i then
+ -- glyph|pre glyphs
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ pre = insert_node_before(pre,pre,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ if replace then
+ local p = rawget(properties,prevglyph)
+ if p then
+ local i = p.replaceinjections
+ if i then
+ -- glyph|replace glyphs
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ replace = insert_node_before(replace,replace,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevglyph = nil
+ prevdisc = current
+ else
+ prevglyph = nil
+ prevdisc = nil
+ end
+ prev = current
+ current = next
+ end
+ --
+ if keepregisteredcounts then
+ keepregisteredcounts = false
+ else
+ nofregisteredpositions = 0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+
+local function showoffset(n,flag)
+ local x, y = getoffsets(n)
+ if x ~= 0 or y ~= 0 then
+ setcolor(n,"darkgray")
+ end
+end
+
+local function inject_everything(head,where)
+ if trace_injections then
+ trace(head,"everything")
+ end
+ local hascursives = nofregisteredcursives > 0
+ local hasmarks = nofregisteredmarks > 0
+ --
+ local current = head
+ local last = nil
+ local prev = nil
+ local next = nil
+ local prevdisc = nil
+ local prevglyph = nil
+ local pre = nil -- saves a lookup
+ local post = nil -- saves a lookup
+ local replace = nil -- saves a lookup
+ local pretail = nil -- saves a lookup
+ local posttail = nil -- saves a lookup
+ local replacetail = nil -- saves a lookup
+ --
+ local cursiveanchor = nil
+ local minc = 0
+ local maxc = 0
+ local glyphs = { }
+ local marks = { }
+ local nofmarks = 0
+ --
+ -- local applyfix = hascursives and fix_cursive_marks
+ --
+ -- move out
+ --
+ local function processmark(p,n,pn) -- p = basenode
+ local px, py = getoffsets(p)
+ local nx, ny = getoffsets(n)
+ local ox = 0
+ local rightkern = nil
+ local pp = rawget(properties,p)
+ if pp then
+ pp = pp.injections
+ if pp then
+ rightkern = pp.rightkern
+ end
+ end
+ local markdir = pn.markdir
+ if rightkern then -- x and w ~= 0
+ ox = px - (pn.markx or 0) - rightkern
+ if markdir and markdir < 0 then
+ -- kern(w-x) glyph(p) kern(x) mark(n)
+ if not pn.markmark then
+ ox = ox + (pn.leftkern or 0)
+ end
+ else
+ -- kern(x) glyph(p) kern(w-x) mark(n)
+ --
+ -- According to Kai we don't need to handle leftkern here but I'm
+ -- pretty sure I've run into a case where it was needed so maybe
+ -- some day we need something more clever here.
+ --
+ -- maybe we need to apply both then
+ --
+ if false then
+ -- a mark with kerning (maybe husayni needs it )
+ local leftkern = pp.leftkern
+ if leftkern then
+ ox = ox - leftkern
+ end
+ end
+ end
+ else
+ ox = px - (pn.markx or 0)
+ if markdir and markdir < 0 then
+ if not pn.markmark then
+ local leftkern = pn.leftkern
+ if leftkern then
+ ox = ox + leftkern -- husayni needs it
+ end
+ end
+ end
+ if pn.checkmark then
+ local wn = getwidth(n) -- in arial marks have widths
+ if wn and wn ~= 0 then
+ wn = wn/2
+ if trace_injections then
+ report_injections("correcting non zero width mark %C",getchar(n))
+ end
+ -- -- bad: we should center
+ --
+ -- pn.leftkern = -wn
+ -- pn.rightkern = -wn
+ --
+ -- -- we're too late anyway as kerns are already injected so we do it the
+ -- -- ugly way (no checking if the previous is already a kern) .. maybe we
+ -- -- should fix the font instead
+ --
+ -- todo: head and check for prev / next kern
+ --
+ insert_node_before(n,n,fontkern(-wn))
+ insert_node_after(n,n,fontkern(-wn))
+ end
+ end
+ end
+ local oy = ny + py + (pn.marky or 0)
+ if not pn.markmark then
+ local yoffset = pn.yoffset
+ if yoffset then
+ oy = oy + yoffset -- husayni needs it
+ end
+ end
+ setoffsets(n,ox,oy)
+ if trace_marks then
+ showoffset(n,true)
+ end
+ end
+ -- begin of temp fix --
+ -- local base = nil -- bah, some arabic fonts have no mark anchoring
+ -- end of temp fix --
+ while current do
+ local next = getnext(current)
+ local char, id = ischar(current)
+ if char then
+ local p = rawget(properties,current)
+ -- begin of temp fix --
+ -- if applyfix then
+ -- if not p then
+ -- local m = fontmarks[getfont(current)]
+ -- if m and m[char] then
+ -- if base then
+ -- p = { injections = { markbasenode = base } }
+ -- nofmarks = nofmarks + 1
+ -- marks[nofmarks] = current
+ -- properties[current] = p
+ -- hasmarks = true
+ -- end
+ -- else
+ -- base = current
+ -- end
+ -- end
+ -- end
+ -- end of temp fix
+ if p then
+ local i = p.injections
+ -- begin of temp fix --
+ -- if applyfix then
+ -- if not i then
+ -- local m = fontmarks[getfont(current)]
+ -- if m and m[char] then
+ -- if base then
+ -- i = { markbasenode = base }
+ -- nofmarks = nofmarks + 1
+ -- marks[nofmarks] = current
+ -- p.injections = i
+ -- hasmarks = true
+ -- end
+ -- else
+ -- base = current
+ -- end
+ -- end
+ -- end
+ -- end of temp fix --
+ if i then
+ local pm = i.markbasenode
+ -- begin of temp fix --
+ -- if applyfix then
+ -- if not pm then
+ -- local m = fontmarks[getfont(current)]
+ -- if m and m[char] then
+ -- if base then
+ -- pm = base
+ -- i.markbasenode = pm
+ -- hasmarks = true
+ -- end
+ -- else
+ -- base = current
+ -- end
+ -- else
+ -- base = current
+ -- end
+ -- end
+ -- end of temp fix --
+ if pm then
+ nofmarks = nofmarks + 1
+ marks[nofmarks] = current
+ else
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(current,false,yoffset)
+ end
+ if hascursives then
+ local cursivex = i.cursivex
+ if cursivex then
+ if cursiveanchor then
+ if cursivex ~= 0 then
+ i.leftkern = (i.leftkern or 0) + cursivex
+ end
+ if maxc == 0 then
+ minc = 1
+ maxc = 1
+ glyphs[1] = cursiveanchor
+ else
+ maxc = maxc + 1
+ glyphs[maxc] = cursiveanchor
+ end
+ properties[cursiveanchor].cursivedy = i.cursivey -- cursiveprops
+ last = current
+ else
+ maxc = 0
+ end
+ elseif maxc > 0 then
+ local nx, ny = getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti = glyphs[i]
+ ny = ny + properties[ti].cursivedy
+ setoffsets(ti,false,ny) -- why not add ?
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ maxc = 0
+ cursiveanchor = nil
+ end
+ if i.cursiveanchor then
+ cursiveanchor = current -- no need for both now
+ else
+ if maxc > 0 then
+ local nx, ny = getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti = glyphs[i]
+ ny = ny + properties[ti].cursivedy
+ setoffsets(ti,false,ny) -- why not add ?
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ maxc = 0
+ end
+ cursiveanchor = nil
+ end
+ end
+ -- left|glyph|right
+ local leftkern = i.leftkern
+ local rightkern = i.rightkern
+ if leftkern and leftkern ~= 0 then
+ if rightkern and leftkern == -rightkern then
+ setoffsets(current,leftkern,false)
+ rightkern = 0
+ else
+ head = insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(head,current,fontkern(rightkern))
+ end
+ end
+ else
+ local i = p.emptyinjections
+ if i then
+ -- glyph|disc|glyph (special case)
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ if next and getid(next) == disc_code then
+ if replace then
+ -- error, we expect an empty one
+ else
+ replace = fontkern(rightkern)
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if prevdisc then
+ if p then
+ local done = false
+ if post then
+ local i = p.postinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ setlink(posttail,fontkern(leftkern))
+ done = true
+ end
+ end
+ end
+ if replace then
+ local i = p.replaceinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ setlink(replacetail,fontkern(leftkern))
+ done = true
+ end
+ end
+ else
+ local i = p.emptyinjections
+ if i then
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ replace = fontkern(leftkern)
+ done = true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ else
+ -- cursive
+ if hascursives and maxc > 0 then
+ local nx, ny = getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti = glyphs[i]
+ ny = ny + properties[ti].cursivedy
+ local xi, yi = getoffsets(ti)
+ setoffsets(ti,xi,yi + ny) -- can be mark, we could use properties
+ end
+ maxc = 0
+ cursiveanchor = nil
+ end
+ end
+ prevdisc = nil
+ prevglyph = current
+ elseif char == false then
+ -- base = nil
+ prevdisc = nil
+ prevglyph = current
+ elseif id == disc_code then
+ -- base = nil
+ pre, post, replace, pretail, posttail, replacetail = getdisc(current,true)
+ local done = false
+ if pre then
+ -- left|pre glyphs|right
+ for n in nextchar, pre do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.preinjections
+ if i then
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ pre = insert_node_before(pre,n,fontkern(leftkern))
+ done = true
+ end
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(pre,n,fontkern(rightkern))
+ done = true
+ end
+ if hasmarks then
+ local pm = i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if post then
+ -- left|post glyphs|right
+ for n in nextchar, post do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.postinjections
+ if i then
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ post = insert_node_before(post,n,fontkern(leftkern))
+ done = true
+ end
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(post,n,fontkern(rightkern))
+ done = true
+ end
+ if hasmarks then
+ local pm = i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ -- left|replace glyphs|right
+ for n in nextchar, replace do
+ local p = rawget(properties,n)
+ if p then
+ local i = p.injections or p.replaceinjections
+ if i then
+ local yoffset = i.yoffset
+ if yoffset and yoffset ~= 0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern = i.leftkern
+ if leftkern and leftkern ~= 0 then
+ replace = insert_node_before(replace,n,fontkern(leftkern))
+ done = true
+ end
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ insert_node_after(replace,n,fontkern(rightkern))
+ done = true
+ end
+ if hasmarks then
+ local pm = i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if prevglyph then
+ if pre then
+ local p = rawget(properties,prevglyph)
+ if p then
+ local i = p.preinjections
+ if i then
+ -- glyph|pre glyphs
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ pre = insert_node_before(pre,pre,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ if replace then
+ local p = rawget(properties,prevglyph)
+ if p then
+ local i = p.replaceinjections
+ if i then
+ -- glyph|replace glyphs
+ local rightkern = i.rightkern
+ if rightkern and rightkern ~= 0 then
+ replace = insert_node_before(replace,replace,fontkern(rightkern))
+ done = true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevglyph = nil
+ prevdisc = current
+ else
+ -- base = nil
+ prevglyph = nil
+ prevdisc = nil
+ end
+ prev = current
+ current = next
+ end
+ -- cursive
+ if hascursives and maxc > 0 then
+ local nx, ny = getoffsets(last)
+ for i=maxc,minc,-1 do
+ local ti = glyphs[i]
+ ny = ny + properties[ti].cursivedy
+ setoffsets(ti,false,ny) -- why not add ?
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ end
+ --
+ if nofmarks > 0 then
+ for i=1,nofmarks do
+ local m = marks[i]
+ local p = rawget(properties,m)
+ local i = p.injections
+ local b = i.markbasenode
+ processmark(b,m,i)
+ end
+ elseif hasmarks then
+ -- sometyhing bad happened
+ end
+ --
+ if keepregisteredcounts then
+ keepregisteredcounts = false
+ else
+ nofregisteredkerns = 0
+ nofregisteredpositions = 0
+ nofregisteredmarks = 0
+ nofregisteredcursives = 0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+
+-- space triggers
+
+local triggers = false
+
+function nodes.injections.setspacekerns(font,sequence)
+ if triggers then
+ triggers[font] = sequence
+ else
+ triggers = { [font] = sequence }
+ end
+end
+
+local getthreshold
+
+if context then
+
+ local threshold = 1 -- todo: add a few methods for context
+ local parameters = fonts.hashes.parameters
+
+ directives.register("otf.threshold", function(v) threshold = tonumber(v) or 1 end)
+
+ getthreshold = function(font)
+ local p = parameters[font]
+ local f = p.factor
+ local s = p.spacing
+ local t = threshold * (s and s.width or p.space or 0) - 2
+ return t > 0 and t or 0, f
+ end
+
+else
+
+ injections.threshold = 0
+
+ getthreshold = function(font)
+ local p = fontdata[font].parameters
+ local f = p.factor
+ local s = p.spacing
+ local t = injections.threshold * (s and s.width or p.space or 0) - 2
+ return t > 0 and t or 0, f
+ end
+
+end
+
+injections.getthreshold = getthreshold
+
+function injections.isspace(n,threshold,id)
+ if (id or getid(n)) == glue_code then
+ local w = getwidth(n)
+ if threshold and w > threshold then -- was >=
+ return 32
+ end
+ end
+end
+
+-- We have a plugin so that Kai can use the next in plain. Such a plugin is rather application
+-- specific.
+--
+-- local getboth = nodes.direct.getboth
+-- local getid = nodes.direct.getid
+-- local getprev = nodes.direct.getprev
+-- local getnext = nodes.direct.getnext
+--
+-- local whatsit_code = nodes.nodecodes.whatsit
+-- local glyph_code = nodes.nodecodes.glyph
+--
+-- local function getspaceboth(n) -- fragile: what it prev/next has no width field
+-- local prev, next = getboth(n)
+-- while prev and (getid(prev) == whatsit_code or (getwidth(prev) == 0 and getid(prev) ~= glyph_code)) do
+-- prev = getprev(prev)
+-- end
+-- while next and (getid(next) == whatsit_code or (getwidth(next) == 0 and getid(next) ~= glyph_code)) do
+-- next = getnext(next)
+-- end
+-- end
+--
+-- injections.installgetspaceboth(getspaceboth)
+
+local getspaceboth = getboth
+
+function injections.installgetspaceboth(gb)
+ getspaceboth = gb or getboth
+end
+
+local function injectspaces(head)
+
+ if not triggers then
+ return head
+ end
+ local lastfont = nil
+ local spacekerns = nil
+ local leftkerns = nil
+ local rightkerns = nil
+ local factor = 0
+ local threshold = 0
+ local leftkern = false
+ local rightkern = false
+
+ local function updatefont(font,trig)
+ leftkerns = trig.left
+ rightkerns = trig.right
+ lastfont = font
+ threshold,
+ factor = getthreshold(font)
+ end
+
+ for n in nextglue, head do
+ local prev, next = getspaceboth(n)
+ local prevchar = prev and ischar(prev)
+ local nextchar = next and ischar(next)
+ if nextchar then
+ local font = getfont(next)
+ local trig = triggers[font]
+ if trig then
+ if lastfont ~= font then
+ updatefont(font,trig)
+ end
+ if rightkerns then
+ rightkern = rightkerns[nextchar]
+ end
+ end
+ end
+ if prevchar then
+ local font = getfont(prev)
+ local trig = triggers[font]
+ if trig then
+ if lastfont ~= font then
+ updatefont(font,trig)
+ end
+ if leftkerns then
+ leftkern = leftkerns[prevchar]
+ end
+ end
+ end
+ if leftkern then
+ local old = getwidth(n)
+ if old > threshold then
+ if rightkern then
+ if useitalickerns then
+ local lnew = leftkern * factor
+ local rnew = rightkern * factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p + %p] %C",prevchar,lnew,old,rnew,nextchar)
+ end
+ head = insert_node_before(head,n,italickern(lnew))
+ insert_node_after(head,n,italickern(rnew))
+ else
+ local new = old + (leftkern + rightkern) * factor
+ if trace_spaces then
+ report_spaces("%C [%p -> %p] %C",prevchar,old,new,nextchar)
+ end
+ setwidth(n,new)
+ end
+ rightkern = false
+ else
+ if useitalickerns then
+ local new = leftkern * factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p]",prevchar,old,new)
+ end
+ insert_node_after(head,n,italickern(new)) -- tricky with traverse but ok
+ else
+ local new = old + leftkern * factor
+ if trace_spaces then
+ report_spaces("%C [%p -> %p]",prevchar,old,new)
+ end
+ setwidth(n,new)
+ end
+ end
+ end
+ leftkern = false
+ elseif rightkern then
+ local old = getwidth(n)
+ if old > threshold then
+ if useitalickerns then
+ local new = rightkern * factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p]",nextchar,old,new)
+ end
+ insert_node_after(head,n,italickern(new))
+ else
+ local new = old + rightkern * factor
+ if trace_spaces then
+ report_spaces("[%p -> %p] %C",nextchar,old,new)
+ end
+ setwidth(n,new)
+ end
+ end
+ rightkern = false
+ end
+ end
+
+ triggers = false
+
+ return head
+end
+
+--
+
+function injections.handler(head,where)
+ if triggers then
+ head = injectspaces(head)
+ end
+ -- todo: marks only run too
+ if nofregisteredmarks > 0 or nofregisteredcursives > 0 then
+ if trace_injections then
+ report_injections("injection variant %a","everything")
+ end
+ return inject_everything(head,where)
+ elseif nofregisteredpositions > 0 then
+ if trace_injections then
+ report_injections("injection variant %a","positions")
+ end
+ return inject_positions_only(head,where)
+ elseif nofregisteredkerns > 0 then
+ if trace_injections then
+ report_injections("injection variant %a","kerns")
+ end
+ return inject_kerns_only(head,where)
+ else
+ return head
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-otl.lua b/macros/luatex/generic/luaotfload/fontloader-font-otl.lua
new file mode 100644
index 0000000000..f8cd8217cd
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-otl.lua
@@ -0,0 +1,857 @@
+if not modules then modules = { } end modules ['font-otl'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files",
+}
+
+-- After some experimenting with an alternative loader (one that is needed for
+-- getting outlines in mp) I decided not to be compatible with the old (built-in)
+-- one. The approach used in font-otn is as follows: we load the font in a compact
+-- format but still very compatible with the ff data structures. From there we
+-- create hashes to access the data efficiently. The implementation of feature
+-- processing is mostly based on looking at the data as organized in the glyphs and
+-- lookups as well as the specification. Keeping the lookup data in the glyphs is
+-- very instructive and handy for tracing. On the other hand hashing is what brings
+-- speed. So, the in the new approach (the old one will stay around too) we no
+-- longer keep data in the glyphs which saves us a (what in retrospect looks a bit
+-- like) a reconstruction step. It also means that the data format of the cached
+-- files changes. What method is used depends on that format. There is no fundamental
+-- change in processing, and not even in data organation. Most has to do with
+-- loading and storage.
+
+-- todo: less tounicodes
+
+local lower = string.lower
+local type, next, tonumber, tostring, unpack = type, next, tonumber, tostring, unpack
+local abs = math.abs
+local derivetable = table.derive
+local formatters = string.formatters
+
+local setmetatableindex = table.setmetatableindex
+local allocate = utilities.storage.allocate
+local registertracker = trackers.register
+local registerdirective = directives.register
+local starttiming = statistics.starttiming
+local stoptiming = statistics.stoptiming
+local elapsedtime = statistics.elapsedtime
+local findbinfile = resolvers.findbinfile
+
+----- trace_private = false registertracker("otf.private", function(v) trace_private = v end)
+----- trace_subfonts = false registertracker("otf.subfonts", function(v) trace_subfonts = v end)
+local trace_loading = false registertracker("otf.loading", function(v) trace_loading = v end)
+local trace_features = false registertracker("otf.features", function(v) trace_features = v end)
+----- trace_dynamics = false registertracker("otf.dynamics", function(v) trace_dynamics = v end)
+----- trace_sequences = false registertracker("otf.sequences", function(v) trace_sequences = v end)
+----- trace_markwidth = false registertracker("otf.markwidth", function(v) trace_markwidth = v end)
+local trace_defining = false registertracker("fonts.defining", function(v) trace_defining = v end)
+
+local report_otf = logs.reporter("fonts","otf loading")
+
+local fonts = fonts
+local otf = fonts.handlers.otf
+
+otf.version = 3.109 -- beware: also sync font-mis.lua and in mtx-fonts
+otf.cache = containers.define("fonts", "otl", otf.version, true)
+otf.svgcache = containers.define("fonts", "svg", otf.version, true)
+otf.pngcache = containers.define("fonts", "png", otf.version, true)
+otf.pdfcache = containers.define("fonts", "pdf", otf.version, true)
+
+otf.svgenabled = false
+otf.pngenabled = false
+
+local otfreaders = otf.readers
+
+local hashes = fonts.hashes
+local definers = fonts.definers
+local readers = fonts.readers
+local constructors = fonts.constructors
+
+local otffeatures = constructors.features.otf
+local registerotffeature = otffeatures.register
+
+local otfenhancers = constructors.enhancers.otf
+local registerotfenhancer = otfenhancers.register
+
+local forceload = false
+local cleanup = 0 -- mk: 0=885M 1=765M 2=735M (regular run 730M)
+local syncspace = true
+local forcenotdef = false
+
+local privateoffset = fonts.constructors and fonts.constructors.privateoffset or 0xF0000 -- 0x10FFFF
+
+local applyruntimefixes = fonts.treatments and fonts.treatments.applyfixes
+
+local wildcard = "*"
+local default = "dflt"
+
+local formats = fonts.formats
+
+formats.otf = "opentype"
+formats.ttf = "truetype"
+formats.ttc = "truetype"
+
+registerdirective("fonts.otf.loader.cleanup", function(v) cleanup = tonumber(v) or (v and 1) or 0 end)
+registerdirective("fonts.otf.loader.force", function(v) forceload = v end)
+registerdirective("fonts.otf.loader.syncspace", function(v) syncspace = v end)
+registerdirective("fonts.otf.loader.forcenotdef", function(v) forcenotdef = v end)
+
+-- otfenhancers.patch("before","migrate metadata","cambria",function() end)
+
+registerotfenhancer("check extra features", function() end) -- placeholder
+
+-- Kai has memory problems on osx so here is an experiment (I only tested on windows as
+-- my test mac is old and gets no updates and is therefore rather useless.):
+
+local checkmemory = utilities.lua and utilities.lua.checkmemory
+local threshold = 100 -- MB
+local tracememory = false
+
+registertracker("fonts.otf.loader.memory",function(v) tracememory = v end)
+
+if not checkmemory then -- we need a generic plug (this code might move):
+
+ local collectgarbage = collectgarbage
+
+ checkmemory = function(previous,threshold) -- threshold in MB
+ local current = collectgarbage("count")
+ if previous then
+ local checked = (threshold or 64)*1024
+ if current - previous > checked then
+ collectgarbage("collect")
+ current = collectgarbage("count")
+ end
+ end
+ return current
+ end
+
+end
+
+function otf.load(filename,sub,instance)
+ local base = file.basename(file.removesuffix(filename))
+ local name = file.removesuffix(base) -- already no suffix
+ local attr = lfs.attributes(filename)
+ local size = attr and attr.size or 0
+ local time = attr and attr.modification or 0
+ -- sub can be number of string
+ if sub == "" then
+ sub = false
+ end
+ local hash = name
+ if sub then
+ hash = hash .. "-" .. sub
+ end
+ if instance then
+ hash = hash .. "-" .. instance
+ end
+ hash = containers.cleanname(hash)
+ local data = containers.read(otf.cache,hash)
+ local reload = not data or data.size ~= size or data.time ~= time or data.tableversion ~= otfreaders.tableversion
+ if forceload then
+ report_otf("forced reload of %a due to hard coded flag",filename)
+ reload = true
+ end
+ if reload then
+ report_otf("loading %a, hash %a",filename,hash)
+ --
+ starttiming(otfreaders,true)
+ data = otfreaders.loadfont(filename,sub or 1,instance) -- we can pass the number instead (if it comes from a name search)
+ if data then
+ -- todo: make this a plugin
+ local used = checkmemory()
+ local resources = data.resources
+ local svgshapes = resources.svgshapes
+ local pngshapes = resources.pngshapes
+ if cleanup == 0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ if svgshapes then
+ resources.svgshapes = nil
+ if otf.svgenabled then
+ local timestamp = os.date()
+ -- work in progress ... a bit boring to do
+ containers.write(otf.svgcache,hash, {
+ svgshapes = svgshapes,
+ timestamp = timestamp,
+ })
+ data.properties.svg = {
+ hash = hash,
+ timestamp = timestamp,
+ }
+ end
+ if cleanup > 1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ end
+ if pngshapes then
+ resources.pngshapes = nil
+ if otf.pngenabled then
+ local timestamp = os.date()
+ -- work in progress ... a bit boring to do
+ containers.write(otf.pngcache,hash, {
+ pngshapes = pngshapes,
+ timestamp = timestamp,
+ })
+ data.properties.png = {
+ hash = hash,
+ timestamp = timestamp,
+ }
+ end
+ if cleanup > 1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ end
+ --
+ otfreaders.compact(data)
+ if cleanup == 0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ otfreaders.rehash(data,"unicodes")
+ otfreaders.addunicodetable(data)
+ otfreaders.extend(data)
+ if cleanup == 0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ otfreaders.pack(data)
+ report_otf("loading done")
+ report_otf("saving %a in cache",filename)
+ data = containers.write(otf.cache, hash, data)
+ if cleanup > 1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ stoptiming(otfreaders)
+ if elapsedtime then
+ report_otf("loading, optimizing, packing and caching time %s", elapsedtime(otfreaders))
+ end
+ if cleanup > 3 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ data = containers.read(otf.cache,hash) -- this frees the old table and load the sparse one
+ if cleanup > 2 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ else
+ stoptiming(otfreaders)
+ data = nil
+ report_otf("loading failed due to read error")
+ end
+ end
+ if data then
+ if trace_defining then
+ report_otf("loading from cache using hash %a",hash)
+ end
+ --
+ otfreaders.unpack(data)
+ otfreaders.expand(data) -- inline tables
+ otfreaders.addunicodetable(data) -- only when not done yet
+ --
+ otfenhancers.apply(data,filename,data) -- in context one can also use treatments
+ --
+ -- constructors.addcoreunicodes(data.resources.unicodes) -- still needed ?
+ --
+ if applyruntimefixes then
+ applyruntimefixes(filename,data) -- e.g. see treatments.lfg
+ end
+ --
+ data.metadata.math = data.resources.mathconstants
+ --
+ -- delayed tables (experiment)
+ --
+ local classes = data.resources.classes
+ if not classes then
+ local descriptions = data.descriptions
+ classes = setmetatableindex(function(t,k)
+ local d = descriptions[k]
+ local v = (d and d.class or "base") or false
+ t[k] = v
+ return v
+ end)
+ data.resources.classes = classes
+ end
+ --
+ end
+
+ return data
+end
+
+-- modes: node, base, none
+
+function otf.setfeatures(tfmdata,features)
+ local okay = constructors.initializefeatures("otf",tfmdata,features,trace_features,report_otf)
+ if okay then
+ return constructors.collectprocessors("otf",tfmdata,features,trace_features,report_otf)
+ else
+ return { } -- will become false
+ end
+end
+
+-- the first version made a top/mid/not extensible table, now we just
+-- pass on the variants data and deal with it in the tfm scaler (there
+-- is no longer an extensible table anyway)
+--
+-- we cannot share descriptions as virtual fonts might extend them (ok,
+-- we could use a cache with a hash
+--
+-- we already assign an empty table to characters as we can add for
+-- instance protruding info and loop over characters; one is not supposed
+-- to change descriptions and if one does so one should make a copy!
+
+local function copytotfm(data,cache_id)
+ if data then
+ local metadata = data.metadata
+ local properties = derivetable(data.properties)
+ local descriptions = derivetable(data.descriptions)
+ local goodies = derivetable(data.goodies)
+ local characters = { }
+ local parameters = { }
+ local mathparameters = { }
+ --
+ local resources = data.resources
+ local unicodes = resources.unicodes
+ local spaceunits = 500
+ local spacer = "space"
+ local designsize = metadata.designsize or 100
+ local minsize = metadata.minsize or designsize
+ local maxsize = metadata.maxsize or designsize
+ local mathspecs = metadata.math
+ --
+ if designsize == 0 then
+ designsize = 100
+ minsize = 100
+ maxsize = 100
+ end
+ if mathspecs then
+ for name, value in next, mathspecs do
+ mathparameters[name] = value
+ end
+ end
+ for unicode in next, data.descriptions do -- use parent table
+ characters[unicode] = { }
+ end
+ if mathspecs then
+ for unicode, character in next, characters do
+ local d = descriptions[unicode] -- we could use parent table here
+ local m = d.math
+ if m then
+ -- watch out: luatex uses horiz_variants for the parts
+ --
+ local italic = m.italic
+ local vitalic = m.vitalic
+ --
+ local variants = m.hvariants
+ local parts = m.hparts
+ if variants then
+ local c = character
+ for i=1,#variants do
+ -- local un = variants[i].glyph
+ local un = variants[i]
+ c.next = un
+ c = characters[un]
+ end -- c is now last in chain
+ c.horiz_variants = parts
+ elseif parts then
+ character.horiz_variants = parts
+ italic = m.hitalic
+ end
+ --
+ local variants = m.vvariants
+ local parts = m.vparts
+ if variants then
+ local c = character
+ for i=1,#variants do
+ -- local un = variants[i].glyph
+ local un = variants[i]
+ c.next = un
+ c = characters[un]
+ end -- c is now last in chain
+ c.vert_variants = parts
+ elseif parts then
+ character.vert_variants = parts
+ end
+ --
+ if italic and italic ~= 0 then
+ character.italic = italic
+ end
+ --
+ if vitalic and vitalic ~= 0 then
+ character.vert_italic = vitalic
+ end
+ --
+ local accent = m.accent -- taccent?
+ if accent then
+ character.accent = accent
+ end
+ --
+ local kerns = m.kerns
+ if kerns then
+ character.mathkerns = kerns
+ end
+ end
+ end
+ end
+ -- we need a runtime lookup because of running from cdrom or zip, brrr (shouldn't
+ -- we use the basename then?)
+ local filename = constructors.checkedfilename(resources)
+ local fontname = metadata.fontname
+ local fullname = metadata.fullname or fontname
+ local psname = fontname or fullname
+ local subfont = metadata.subfontindex
+ local units = metadata.units or 1000
+ --
+ if units == 0 then -- catch bugs in fonts
+ units = 1000 -- maybe 2000 when ttf
+ metadata.units = 1000
+ report_otf("changing %a units to %a",0,units)
+ end
+ --
+ local monospaced = metadata.monospaced
+ local charwidth = metadata.averagewidth -- or unset
+ local charxheight = metadata.xheight -- or unset
+ local italicangle = metadata.italicangle
+ local hasitalics = metadata.hasitalics
+ properties.monospaced = monospaced
+ properties.hasitalics = hasitalics
+ parameters.italicangle = italicangle
+ parameters.charwidth = charwidth
+ parameters.charxheight = charxheight
+ --
+ local space = 0x0020
+ local emdash = 0x2014
+ if monospaced then
+ if descriptions[space] then
+ spaceunits, spacer = descriptions[space].width, "space"
+ end
+ if not spaceunits and descriptions[emdash] then
+ spaceunits, spacer = descriptions[emdash].width, "emdash"
+ end
+ if not spaceunits and charwidth then
+ spaceunits, spacer = charwidth, "charwidth"
+ end
+ else
+ if descriptions[space] then
+ spaceunits, spacer = descriptions[space].width, "space"
+ end
+ if not spaceunits and descriptions[emdash] then
+ spaceunits, spacer = descriptions[emdash].width/2, "emdash/2"
+ end
+ if not spaceunits and charwidth then
+ spaceunits, spacer = charwidth, "charwidth"
+ end
+ end
+ spaceunits = tonumber(spaceunits) or units/2
+ --
+ parameters.slant = 0
+ parameters.space = spaceunits -- 3.333 (cmr10)
+ parameters.space_stretch = 1*units/2 -- 500 -- 1.666 (cmr10)
+ parameters.space_shrink = 1*units/3 -- 333 -- 1.111 (cmr10)
+ parameters.x_height = 2*units/5 -- 400
+ parameters.quad = units -- 1000
+ if spaceunits < 2*units/5 then
+ -- todo: warning
+ end
+ if italicangle and italicangle ~= 0 then
+ parameters.italicangle = italicangle
+ parameters.italicfactor = math.cos(math.rad(90+italicangle))
+ parameters.slant = - math.tan(italicangle*math.pi/180)
+ end
+ if monospaced then
+ parameters.space_stretch = 0
+ parameters.space_shrink = 0
+ elseif syncspace then --
+ parameters.space_stretch = spaceunits/2
+ parameters.space_shrink = spaceunits/3
+ end
+ parameters.extra_space = parameters.space_shrink -- 1.111 (cmr10)
+ if charxheight then
+ parameters.x_height = charxheight
+ else
+ local x = 0x0078
+ if x then
+ local x = descriptions[x]
+ if x then
+ parameters.x_height = x.height
+ end
+ end
+ end
+ --
+ parameters.designsize = (designsize/10)*65536
+ parameters.minsize = (minsize /10)*65536
+ parameters.maxsize = (maxsize /10)*65536
+ parameters.ascender = abs(metadata.ascender or 0)
+ parameters.descender = abs(metadata.descender or 0)
+ parameters.units = units
+ parameters.vheight = metadata.defaultvheight
+ --
+ properties.space = spacer
+ properties.encodingbytes = 2
+ properties.format = data.format or formats.otf
+ properties.filename = filename
+ properties.fontname = fontname
+ properties.fullname = fullname
+ properties.psname = psname
+ properties.name = filename or fullname
+ properties.subfont = subfont
+ --
+ -- properties.name = specification.name
+ -- properties.sub = specification.sub
+ --
+ properties.private = properties.private or data.private or privateoffset
+ --
+ return {
+ characters = characters,
+ descriptions = descriptions,
+ parameters = parameters,
+ mathparameters = mathparameters,
+ resources = resources,
+ properties = properties,
+ goodies = goodies,
+ }
+ end
+end
+
+-- These woff files are a kind of joke in a tex environment because one can simply convert
+-- them to ttf/otf and use them as such (after all, we cache them too). The successor format
+-- woff2 is more complex so there we can as well call an external converter which in the end
+-- makes this code kind of obsolete before it's even used. Although ... it might become a
+-- more general conversion plug in.
+
+local converters = {
+ woff = {
+ cachename = "webfonts",
+ action = otf.readers.woff2otf,
+ }
+}
+
+local function checkconversion(specification)
+ local filename = specification.filename
+ local converter = converters[lower(file.suffix(filename))]
+ if converter then
+ local base = file.basename(filename)
+ local name = file.removesuffix(base)
+ local attr = lfs.attributes(filename)
+ local size = attr and attr.size or 0
+ local time = attr and attr.modification or 0
+ if size > 0 then
+ local cleanname = containers.cleanname(name)
+ local cachename = caches.setfirstwritablefile(cleanname,converter.cachename)
+ if not io.exists(cachename) or (time ~= lfs.attributes(cachename).modification) then
+ report_otf("caching font %a in %a",filename,cachename)
+ converter.action(filename,cachename) -- todo infoonly
+ lfs.touch(cachename,time,time)
+ end
+ specification.filename = cachename
+ end
+ end
+end
+
+local function otftotfm(specification)
+ local cache_id = specification.hash
+ local tfmdata = containers.read(constructors.cache,cache_id)
+ if not tfmdata then
+
+ checkconversion(specification) -- for the moment here
+
+ local name = specification.name
+ local sub = specification.sub
+ local subindex = specification.subindex
+ local filename = specification.filename
+ local features = specification.features.normal
+ local instance = specification.instance or (features and features.axis)
+ local rawdata = otf.load(filename,sub,instance)
+ if rawdata and next(rawdata) then
+ local descriptions = rawdata.descriptions
+ rawdata.lookuphash = { } -- to be done
+ tfmdata = copytotfm(rawdata,cache_id)
+ if tfmdata and next(tfmdata) then
+ -- at this moment no characters are assigned yet, only empty slots
+ local features = constructors.checkedfeatures("otf",features)
+ local shared = tfmdata.shared
+ if not shared then
+ shared = { }
+ tfmdata.shared = shared
+ end
+ shared.rawdata = rawdata
+ -- shared.features = features -- default
+ shared.dynamics = { }
+ -- shared.processes = { }
+ tfmdata.changed = { }
+ shared.features = features
+ shared.processes = otf.setfeatures(tfmdata,features)
+ end
+ end
+ containers.write(constructors.cache,cache_id,tfmdata)
+ end
+ return tfmdata
+end
+
+local function read_from_otf(specification)
+ local tfmdata = otftotfm(specification)
+ if tfmdata then
+ -- this late ? .. needs checking
+ tfmdata.properties.name = specification.name
+ tfmdata.properties.sub = specification.sub
+ --
+ tfmdata = constructors.scale(tfmdata,specification)
+ local allfeatures = tfmdata.shared.features or specification.features.normal
+ constructors.applymanipulators("otf",tfmdata,allfeatures,trace_features,report_otf)
+ constructors.setname(tfmdata,specification) -- only otf?
+ fonts.loggers.register(tfmdata,file.suffix(specification.filename),specification)
+ end
+ return tfmdata
+end
+
+local function checkmathsize(tfmdata,mathsize)
+ local mathdata = tfmdata.shared.rawdata.metadata.math
+ local mathsize = tonumber(mathsize)
+ if mathdata then -- we cannot use mathparameters as luatex will complain
+ local parameters = tfmdata.parameters
+ parameters.scriptpercentage = mathdata.ScriptPercentScaleDown
+ parameters.scriptscriptpercentage = mathdata.ScriptScriptPercentScaleDown
+ parameters.mathsize = mathsize -- only when a number !
+ end
+end
+
+registerotffeature {
+ name = "mathsize",
+ description = "apply mathsize specified in the font",
+ initializers = {
+ base = checkmathsize,
+ node = checkmathsize,
+ }
+}
+
+-- readers
+
+function otf.collectlookups(rawdata,kind,script,language)
+ if not kind then
+ return
+ end
+ if not script then
+ script = default
+ end
+ if not language then
+ language = default
+ end
+ local lookupcache = rawdata.lookupcache
+ if not lookupcache then
+ lookupcache = { }
+ rawdata.lookupcache = lookupcache
+ end
+ local kindlookup = lookupcache[kind]
+ if not kindlookup then
+ kindlookup = { }
+ lookupcache[kind] = kindlookup
+ end
+ local scriptlookup = kindlookup[script]
+ if not scriptlookup then
+ scriptlookup = { }
+ kindlookup[script] = scriptlookup
+ end
+ local languagelookup = scriptlookup[language]
+ if not languagelookup then
+ local sequences = rawdata.resources.sequences
+ local featuremap = { }
+ local featurelist = { }
+ if sequences then
+ for s=1,#sequences do
+ local sequence = sequences[s]
+ local features = sequence.features
+ if features then
+ features = features[kind]
+ if features then
+ -- features = features[script] or features[default] or features[wildcard]
+ features = features[script] or features[wildcard]
+ if features then
+ -- features = features[language] or features[default] or features[wildcard]
+ features = features[language] or features[wildcard]
+ if features then
+ if not featuremap[sequence] then
+ featuremap[sequence] = true
+ featurelist[#featurelist+1] = sequence
+ end
+ end
+ end
+ end
+ end
+ end
+ if #featurelist == 0 then
+ featuremap, featurelist = false, false
+ end
+ else
+ featuremap, featurelist = false, false
+ end
+ languagelookup = { featuremap, featurelist }
+ scriptlookup[language] = languagelookup
+ end
+ return unpack(languagelookup)
+end
+
+-- moved from font-oth.lua, todo: also afm
+
+local function getgsub(tfmdata,k,kind,value)
+ local shared = tfmdata.shared
+ local rawdata = shared and shared.rawdata
+ if rawdata then
+ local sequences = rawdata.resources.sequences
+ if sequences then
+ local properties = tfmdata.properties
+ local validlookups, lookuplist = otf.collectlookups(rawdata,kind,properties.script,properties.language)
+ if validlookups then
+ -- local choice = tonumber(value) or 1 -- no random here (yet)
+ for i=1,#lookuplist do
+ local lookup = lookuplist[i]
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ for i=1,nofsteps do
+ local coverage = steps[i].coverage
+ if coverage then
+ local found = coverage[k]
+ if found then
+ return found, lookup.type
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+end
+
+otf.getgsub = getgsub -- returns value, gsub_kind
+
+function otf.getsubstitution(tfmdata,k,kind,value)
+ local found, kind = getgsub(tfmdata,k,kind,value)
+ if not found then
+ --
+ elseif kind == "gsub_single" then
+ return found
+ elseif kind == "gsub_alternate" then
+ local choice = tonumber(value) or 1 -- no random here (yet)
+ return found[choice] or found[1] or k
+ end
+ return k
+end
+
+otf.getalternate = otf.getsubstitution
+
+function otf.getmultiple(tfmdata,k,kind)
+ local found, kind = getgsub(tfmdata,k,kind)
+ if found and kind == "gsub_multiple" then
+ return found
+ end
+ return { k }
+end
+
+function otf.getkern(tfmdata,left,right,kind)
+ local kerns = getgsub(tfmdata,left,kind or "kern",true) -- for now we use getsub
+ if kerns then
+ local found = kerns[right]
+ local kind = type(found)
+ if kind == "table" then
+ found = found[1][3] -- can be more clever
+ elseif kind ~= "number" then
+ found = false
+ end
+ if found then
+ return found * tfmdata.parameters.factor
+ end
+ end
+ return 0
+end
+
+local function check_otf(forced,specification,suffix)
+ local name = specification.name
+ if forced then
+ name = specification.forcedname -- messy
+ end
+ local fullname = findbinfile(name,suffix) or ""
+ if fullname == "" then
+ fullname = fonts.names.getfilename(name,suffix) or ""
+ end
+ if fullname ~= "" and not fonts.names.ignoredfile(fullname) then
+ specification.filename = fullname
+ return read_from_otf(specification)
+ end
+end
+
+local function opentypereader(specification,suffix)
+ local forced = specification.forced or ""
+ if formats[forced] then
+ return check_otf(true,specification,forced)
+ else
+ return check_otf(false,specification,suffix)
+ end
+end
+
+readers.opentype = opentypereader -- kind of useless and obsolete
+
+function readers.otf(specification) return opentypereader(specification,"otf") end
+function readers.ttf(specification) return opentypereader(specification,"ttf") end
+function readers.ttc(specification) return opentypereader(specification,"ttf") end
+
+function readers.woff(specification)
+ checkconversion(specification)
+ opentypereader(specification,"")
+end
+
+-- this will be overloaded
+
+function otf.scriptandlanguage(tfmdata,attr)
+ local properties = tfmdata.properties
+ return properties.script or "dflt", properties.language or "dflt"
+end
+
+-- a little bit of abstraction
+
+local function justset(coverage,unicode,replacement)
+ coverage[unicode] = replacement
+end
+
+otf.coverup = {
+ stepkey = "steps",
+ actions = {
+ chainsubstitution = justset,
+ chainposition = justset,
+ substitution = justset,
+ alternate = justset,
+ multiple = justset,
+ kern = justset,
+ pair = justset,
+ single = justset,
+ ligature = function(coverage,unicode,ligature)
+ local first = ligature[1]
+ local tree = coverage[first]
+ if not tree then
+ tree = { }
+ coverage[first] = tree
+ end
+ for i=2,#ligature do
+ local l = ligature[i]
+ local t = tree[l]
+ if not t then
+ t = { }
+ tree[l] = t
+ end
+ tree = t
+ end
+ tree.ligature = unicode
+ end,
+ },
+ register = function(coverage,featuretype,format)
+ return {
+ format = format,
+ coverage = coverage,
+ }
+ end
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-oto.lua b/macros/luatex/generic/luaotfload/fontloader-font-oto.lua
new file mode 100644
index 0000000000..4d112ac316
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-oto.lua
@@ -0,0 +1,542 @@
+if not modules then modules = { } end modules ['font-oto'] = { -- original tex
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local concat, unpack = table.concat, table.unpack
+local insert, remove = table.insert, table.remove
+local format, gmatch, gsub, find, match, lower, strip = string.format, string.gmatch, string.gsub, string.find, string.match, string.lower, string.strip
+local type, next, tonumber, tostring, rawget = type, next, tonumber, tostring, rawget
+
+local trace_baseinit = false trackers.register("otf.baseinit", function(v) trace_baseinit = v end)
+local trace_singles = false trackers.register("otf.singles", function(v) trace_singles = v end)
+local trace_multiples = false trackers.register("otf.multiples", function(v) trace_multiples = v end)
+local trace_alternatives = false trackers.register("otf.alternatives", function(v) trace_alternatives = v end)
+local trace_ligatures = false trackers.register("otf.ligatures", function(v) trace_ligatures = v end)
+local trace_kerns = false trackers.register("otf.kerns", function(v) trace_kerns = v end)
+local trace_preparing = false trackers.register("otf.preparing", function(v) trace_preparing = v end)
+
+local report_prepare = logs.reporter("fonts","otf prepare")
+
+local fonts = fonts
+local otf = fonts.handlers.otf
+
+local otffeatures = otf.features
+local registerotffeature = otffeatures.register
+
+otf.defaultbasealternate = "none" -- first last
+
+local getprivate = fonts.constructors.getprivate
+
+local wildcard = "*"
+local default = "dflt"
+
+local formatters = string.formatters
+local f_unicode = formatters["%U"]
+local f_uniname = formatters["%U (%s)"]
+local f_unilist = formatters["% t (% t)"]
+
+local function gref(descriptions,n)
+ if type(n) == "number" then
+ local name = descriptions[n].name
+ if name then
+ return f_uniname(n,name)
+ else
+ return f_unicode(n)
+ end
+ elseif n then
+ local num = { }
+ local nam = { }
+ local j = 0
+ for i=1,#n do
+ local ni = n[i]
+ if tonumber(ni) then -- first is likely a key
+ j = j + 1
+ local di = descriptions[ni]
+ num[j] = f_unicode(ni)
+ nam[j] = di and di.name or "-"
+ end
+ end
+ return f_unilist(num,nam)
+ else
+ return "<error in base mode tracing>"
+ end
+end
+
+local function cref(feature,sequence)
+ return formatters["feature %a, type %a, chain lookup %a"](feature,sequence.type,sequence.name)
+end
+
+local function report_substitution(feature,sequence,descriptions,unicode,substitution)
+ if unicode == substitution then
+ report_prepare("%s: base substitution %s maps onto itself",
+ cref(feature,sequence),
+ gref(descriptions,unicode))
+ else
+ report_prepare("%s: base substitution %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ gref(descriptions,substitution))
+ end
+end
+
+local function report_alternate(feature,sequence,descriptions,unicode,replacement,value,comment)
+ if unicode == replacement then
+ report_prepare("%s: base alternate %s maps onto itself",
+ cref(feature,sequence),
+ gref(descriptions,unicode))
+ else
+ report_prepare("%s: base alternate %s => %s (%S => %S)",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ replacement and gref(descriptions,replacement),
+ value,
+ comment)
+ end
+end
+
+local function report_ligature(feature,sequence,descriptions,unicode,ligature)
+ report_prepare("%s: base ligature %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,ligature),
+ gref(descriptions,unicode))
+end
+
+local function report_kern(feature,sequence,descriptions,unicode,otherunicode,value)
+ report_prepare("%s: base kern %s + %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ gref(descriptions,otherunicode),
+ value)
+end
+
+-- We need to make sure that luatex sees the difference between base fonts that have
+-- different glyphs in the same slots in fonts that have the same fullname (or filename).
+-- LuaTeX will merge fonts eventually (and subset later on). If needed we can use a more
+-- verbose name as long as we don't use <()<>[]{}/%> and the length is < 128.
+
+local basehash, basehashes, applied = { }, 1, { }
+
+local function registerbasehash(tfmdata)
+ local properties = tfmdata.properties
+ local hash = concat(applied," ")
+ local base = basehash[hash]
+ if not base then
+ basehashes = basehashes + 1
+ base = basehashes
+ basehash[hash] = base
+ end
+ properties.basehash = base
+ properties.fullname = (properties.fullname or properties.name) .. "-" .. base
+ -- report_prepare("fullname base hash '%a, featureset %a",tfmdata.properties.fullname,hash)
+ applied = { }
+end
+
+local function registerbasefeature(feature,value)
+ applied[#applied+1] = feature .. "=" .. tostring(value)
+end
+
+-- The original basemode ligature builder used the names of components and did some expression
+-- juggling to get the chain right. The current variant starts with unicodes but still uses
+-- names to make the chain. This is needed because we have to create intermediates when needed
+-- but use predefined snippets when available. To some extend the current builder is more stupid
+-- but I don't worry that much about it as ligatures are rather predicatable.
+--
+-- Personally I think that an ff + i == ffi rule as used in for instance latin modern is pretty
+-- weird as no sane person will key that in and expect a glyph for that ligature plus the following
+-- character. Anyhow, as we need to deal with this, we do, but no guarantes are given.
+--
+-- latin modern dejavu
+--
+-- f+f 102 102 102 102
+-- f+i 102 105 102 105
+-- f+l 102 108 102 108
+-- f+f+i 102 102 105
+-- f+f+l 102 102 108 102 102 108
+-- ff+i 64256 105 64256 105
+-- ff+l 64256 108
+--
+-- As you can see here, latin modern is less complete than dejavu but
+-- in practice one will not notice it.
+--
+-- The while loop is needed because we need to resolve for instance pseudo names like
+-- hyphen_hyphen to endash so in practice we end up with a bit too many definitions but the
+-- overhead is neglectable. We can have changed[first] or changed[second] but it quickly becomes
+-- messy if we need to take that into account.
+
+local function makefake(tfmdata,name,present)
+ local private = getprivate(tfmdata)
+ local character = { intermediate = true, ligatures = { } }
+ resources.unicodes[name] = private
+ tfmdata.characters[private] = character
+ tfmdata.descriptions[private] = { name = name }
+ present[name] = private
+ return character
+end
+
+local function make_1(present,tree,name)
+ for k, v in next, tree do
+ if k == "ligature" then
+ present[name] = v
+ else
+ make_1(present,v,name .. "_" .. k)
+ end
+ end
+end
+
+local function make_2(present,tfmdata,characters,tree,name,preceding,unicode,done)
+ for k, v in next, tree do
+ if k == "ligature" then
+ local character = characters[preceding]
+ if not character then
+ if trace_baseinit then
+ report_prepare("weird ligature in lookup %a, current %C, preceding %C",sequence.name,v,preceding)
+ end
+ character = makefake(tfmdata,name,present)
+ end
+ local ligatures = character.ligatures
+ if ligatures then
+ ligatures[unicode] = { char = v }
+ else
+ character.ligatures = { [unicode] = { char = v } }
+ end
+ if done then
+ local d = done[name]
+ if not d then
+ done[name] = { "dummy", v }
+ else
+ d[#d+1] = v
+ end
+ end
+ else
+ local code = present[name] or unicode
+ local name = name .. "_" .. k
+ make_2(present,tfmdata,characters,v,name,code,k,done)
+ end
+ end
+end
+
+local function preparesubstitutions(tfmdata,feature,value,validlookups,lookuplist)
+ local characters = tfmdata.characters
+ local descriptions = tfmdata.descriptions
+ local resources = tfmdata.resources
+ local changed = tfmdata.changed
+
+ local ligatures = { }
+ local alternate = tonumber(value) or true and 1
+ local defaultalt = otf.defaultbasealternate
+
+ local trace_singles = trace_baseinit and trace_singles
+ local trace_alternatives = trace_baseinit and trace_alternatives
+ local trace_ligatures = trace_baseinit and trace_ligatures
+
+ -- A chain of changes is handled in font-con which is clesner because
+ -- we can have shared changes and such.
+
+ if not changed then
+ changed = { }
+ tfmdata.changed = changed
+ end
+
+ for i=1,#lookuplist do
+ local sequence = lookuplist[i]
+ local steps = sequence.steps
+ local kind = sequence.type
+ if kind == "gsub_single" then
+ for i=1,#steps do
+ for unicode, data in next, steps[i].coverage do
+ if unicode ~= data then
+ changed[unicode] = data
+ end
+ if trace_singles then
+ report_substitution(feature,sequence,descriptions,unicode,data)
+ end
+ end
+ end
+ elseif kind == "gsub_alternate" then
+ for i=1,#steps do
+ for unicode, data in next, steps[i].coverage do
+ local replacement = data[alternate]
+ if replacement then
+ if unicode ~= replacement then
+ changed[unicode] = replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,"normal")
+ end
+ elseif defaultalt == "first" then
+ replacement = data[1]
+ if unicode ~= replacement then
+ changed[unicode] = replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,defaultalt)
+ end
+ elseif defaultalt == "last" then
+ replacement = data[#data]
+ if unicode ~= replacement then
+ changed[unicode] = replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,defaultalt)
+ end
+ else
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,"unknown")
+ end
+ end
+ end
+ end
+ elseif kind == "gsub_ligature" then
+ for i=1,#steps do
+ for unicode, data in next, steps[i].coverage do
+ ligatures[#ligatures+1] = { unicode, data, "" } -- lookupname }
+ if trace_ligatures then
+ report_ligature(feature,sequence,descriptions,unicode,data)
+ end
+ end
+ end
+ end
+ end
+
+ local nofligatures = #ligatures
+
+ if nofligatures > 0 then
+ local characters = tfmdata.characters
+ local present = { }
+ local done = trace_baseinit and trace_ligatures and { }
+
+ for i=1,nofligatures do
+ local ligature = ligatures[i]
+ local unicode = ligature[1]
+ local tree = ligature[2]
+ make_1(present,tree,"ctx_"..unicode)
+ end
+
+ for i=1,nofligatures do
+ local ligature = ligatures[i]
+ local unicode = ligature[1]
+ local tree = ligature[2]
+ local lookupname = ligature[3]
+ make_2(present,tfmdata,characters,tree,"ctx_"..unicode,unicode,unicode,done,sequence)
+ end
+
+ end
+
+end
+
+local function preparepositionings(tfmdata,feature,value,validlookups,lookuplist)
+ local characters = tfmdata.characters
+ local descriptions = tfmdata.descriptions
+ local resources = tfmdata.resources
+ local properties = tfmdata.properties
+ local traceindeed = trace_baseinit and trace_kerns
+ -- check out this sharedkerns trickery
+ for i=1,#lookuplist do
+ local sequence = lookuplist[i]
+ local steps = sequence.steps
+ local kind = sequence.type
+ local format = sequence.format
+ if kind == "gpos_pair" then
+ for i=1,#steps do
+ local step = steps[i]
+ local format = step.format
+ if format == "kern" or format == "move" then
+ for unicode, data in next, steps[i].coverage do
+ local character = characters[unicode]
+ local kerns = character.kerns
+ if not kerns then
+ kerns = { }
+ character.kerns = kerns
+ end
+ if traceindeed then
+ for otherunicode, kern in next, data do
+ if not kerns[otherunicode] and kern ~= 0 then
+ kerns[otherunicode] = kern
+ report_kern(feature,sequence,descriptions,unicode,otherunicode,kern)
+ end
+ end
+ else
+ for otherunicode, kern in next, data do
+ if not kerns[otherunicode] and kern ~= 0 then
+ kerns[otherunicode] = kern
+ end
+ end
+ end
+ end
+ else
+ for unicode, data in next, steps[i].coverage do
+ local character = characters[unicode]
+ local kerns = character.kerns
+ for otherunicode, kern in next, data do
+ -- kern[2] is true (all zero) or a table
+ local other = kern[2]
+ if other == true or (not other and not (kerns and kerns[otherunicode])) then
+ local kern = kern[1]
+ if kern == true then
+ -- all zero
+ elseif kern[1] ~= 0 or kern[2] ~= 0 or kern[4] ~= 0 then
+ -- a complex pair not suitable for basemode
+ else
+ kern = kern[3]
+ if kern ~= 0 then
+ if kerns then
+ kerns[otherunicode] = kern
+ else
+ kerns = { [otherunicode] = kern }
+ character.kerns = kerns
+ end
+ if traceindeed then
+ report_kern(feature,sequence,descriptions,unicode,otherunicode,kern)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+
+end
+
+local function initializehashes(tfmdata)
+ -- already done
+end
+
+local function checkmathreplacements(tfmdata,fullname,fixitalics)
+ if tfmdata.mathparameters then
+ local characters = tfmdata.characters
+ local changed = tfmdata.changed
+ if next(changed) then
+ if trace_preparing or trace_baseinit then
+ report_prepare("checking math replacements for %a",fullname)
+ end
+ for unicode, replacement in next, changed do
+ local u = characters[unicode]
+ local r = characters[replacement]
+ if u and r then
+ local n = u.next
+ local v = u.vert_variants
+ local h = u.horiz_variants
+ if fixitalics then
+ -- quite some warnings on stix ...
+ local ui = u.italic
+ if ui and not r.italic then
+ if trace_preparing then
+ report_prepare("using %i units of italic correction from %C for %U",ui,unicode,replacement)
+ end
+ r.italic = ui -- print(ui,ri)
+ end
+ end
+ if n and not r.next then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","incremental step",unicode,replacement)
+ end
+ r.next = n
+ end
+ if v and not r.vert_variants then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","vertical variants",unicode,replacement)
+ end
+ r.vert_variants = v
+ end
+ if h and not r.horiz_variants then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","horizontal variants",unicode,replacement)
+ end
+ r.horiz_variants = h
+ end
+ else
+ if trace_preparing then
+ report_prepare("error replacing %C by %U",unicode,replacement)
+ end
+ end
+ end
+ end
+ end
+end
+
+local function featuresinitializer(tfmdata,value)
+ if true then -- value then
+ local starttime = trace_preparing and os.clock()
+ local features = tfmdata.shared.features
+ local fullname = tfmdata.properties.fullname or "?"
+ if features then
+ initializehashes(tfmdata)
+ local collectlookups = otf.collectlookups
+ local rawdata = tfmdata.shared.rawdata
+ local properties = tfmdata.properties
+ local script = properties.script
+ local language = properties.language
+ local rawresources = rawdata.resources
+ local rawfeatures = rawresources and rawresources.features
+ local basesubstitutions = rawfeatures and rawfeatures.gsub
+ local basepositionings = rawfeatures and rawfeatures.gpos
+ local substitutionsdone = false
+ local positioningsdone = false
+ --
+ if basesubstitutions or basepositionings then
+ local sequences = tfmdata.resources.sequences
+ for s=1,#sequences do
+ local sequence = sequences[s]
+ local sfeatures = sequence.features
+ if sfeatures then
+ local order = sequence.order
+ if order then
+ for i=1,#order do --
+ local feature = order[i]
+ local value = features[feature]
+ if value then
+ local validlookups, lookuplist = collectlookups(rawdata,feature,script,language)
+ if not validlookups then
+ -- skip
+ elseif basesubstitutions and basesubstitutions[feature] then
+ if trace_preparing then
+ report_prepare("filtering base %s feature %a for %a with value %a","sub",feature,fullname,value)
+ end
+ preparesubstitutions(tfmdata,feature,value,validlookups,lookuplist)
+ registerbasefeature(feature,value)
+ substitutionsdone = true
+ elseif basepositionings and basepositionings[feature] then
+ if trace_preparing then
+ report_prepare("filtering base %a feature %a for %a with value %a","pos",feature,fullname,value)
+ end
+ preparepositionings(tfmdata,feature,value,validlookups,lookuplist)
+ registerbasefeature(feature,value)
+ positioningsdone = true
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ --
+ if substitutionsdone then
+ checkmathreplacements(tfmdata,fullname,features.fixitalics)
+ end
+ --
+ registerbasehash(tfmdata)
+ end
+ if trace_preparing then
+ report_prepare("preparation time is %0.3f seconds for %a",os.clock()-starttime,fullname)
+ end
+ end
+end
+
+registerotffeature {
+ name = "features",
+ description = "features",
+ default = true,
+ initializers = {
+ -- position = 1, -- after setscript (temp hack ... we need to force script / language to 1
+ base = featuresinitializer,
+ }
+}
+
+otf.basemodeinitializer = featuresinitializer
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-otr.lua b/macros/luatex/generic/luaotfload/fontloader-font-otr.lua
new file mode 100644
index 0000000000..4fe0a6a976
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-otr.lua
@@ -0,0 +1,2553 @@
+if not modules then modules = { } end modules ['font-otr'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- When looking into a cid font relates issue in the ff library I wondered if
+-- it made sense to use Lua to filter the information from the otf and ttf
+-- files. Quite some ff code relates to special fonts and in practice we only
+-- use rather normal opentype fonts.
+--
+-- The code here is based on the documentation (and examples) at the microsoft
+-- website. The code will be extended and improved stepwise. After some experiments
+-- I decided to convert to a format more suitable for the context font handler
+-- because it makes no sense to rehash all those lookups again.
+--
+-- Currently we can use this code for getting basic info about the font, loading
+-- shapes and loading the extensive table. I'm not sure if I will provide a ff
+-- compatible output as well (We're not that far from it as currently I can load
+-- all data reasonable fast.)
+
+-- We can omit redundant glyphs names i.e. ones that match the agl or
+-- are just a unicode string but it doesn't save that much. It will be an option
+-- some day.
+
+-- Optimizing the widths will be done anyway as it save quite some on a cjk font
+-- and the existing (old) code if okay.
+
+-- todo: more messages (only if really needed)
+--
+-- considered, in math:
+--
+-- start -> first (so we can skip the first same-size one)
+-- end -> last
+--
+-- Widths and weights are kind of messy: for instance lmmonolt has a pfmweight of
+-- 400 while it should be 300. So, for now we mostly stick to the old compromis.
+
+-- We don't really need all those language tables so they might be dropped some
+-- day.
+
+-- The new reader is faster on some aspects and slower on other. The memory footprint
+-- is lower. The string reader is a bit faster than the file reader. The new reader
+-- gives more efficient tables and has bit more analysis. In practice these times are
+-- not that relevant because we cache. The otf files take a it more time because we
+-- need to calculate the boundingboxes. In theory the processing of text should be
+-- somewhat faster especially for complex fonts with many lookups.
+--
+-- old new str reader
+-- lmroman12-regular.otf 0.103 0.203 0.195
+-- latinmodern-math.otf 0.454 0.768 0.712
+-- husayni.ttf 1.142 1.526 1.259
+--
+-- If there is demand I will consider making a ff compatible table dumper but it's
+-- probably more fun to provide a way to show features applied.
+
+-- I experimented a bit with f:readbyte(n) and f:readshort() and so and it is indeed
+-- faster but it might not be the real bottleneck as we still need to juggle data. It
+-- is probably more memory efficient as no intermediate strings are involved.
+
+-- if not characters then
+-- require("char-def")
+-- require("char-ini")
+-- end
+
+local next, type, tonumber = next, type, tonumber
+local byte, lower, char, gsub = string.byte, string.lower, string.char, string.gsub
+local fullstrip = string.fullstrip
+local floor, round = math.floor, math.round
+local P, R, S, C, Cs, Cc, Ct, Carg, Cmt = lpeg.P, lpeg.R, lpeg.S, lpeg.C, lpeg.Cs, lpeg.Cc, lpeg.Ct, lpeg.Carg, lpeg.Cmt
+local lpegmatch = lpeg.match
+local rshift = bit32.rshift
+
+local setmetatableindex = table.setmetatableindex
+local sortedkeys = table.sortedkeys
+local sortedhash = table.sortedhash
+local stripstring = string.nospaces
+local utf16_to_utf8_be = utf.utf16_to_utf8_be
+
+local report = logs.reporter("otf reader")
+local report_cmap = logs.reporter("otf reader","cmap")
+
+local trace_cmap = false trackers.register("otf.cmap", function(v) trace_cmap = v end)
+local trace_cmap_details = false trackers.register("otf.cmap.details", function(v) trace_cmap_details = v end)
+
+fonts = fonts or { }
+local handlers = fonts.handlers or { }
+fonts.handlers = handlers
+local otf = handlers.otf or { }
+handlers.otf = otf
+local readers = otf.readers or { }
+otf.readers = readers
+
+----- streamreader = utilities.streams -- faster on big files (not true any longer)
+local streamreader = utilities.files -- faster on identify (also uses less memory)
+local streamwriter = utilities.files
+
+readers.streamreader = streamreader
+readers.streamwriter = streamwriter
+
+local openfile = streamreader.open
+local closefile = streamreader.close
+----- skipbytes = streamreader.skip
+local setposition = streamreader.setposition
+local skipshort = streamreader.skipshort
+local readbytes = streamreader.readbytes
+local readstring = streamreader.readstring
+local readbyte = streamreader.readcardinal1 -- 8-bit unsigned integer
+local readushort = streamreader.readcardinal2 -- 16-bit unsigned integer
+local readuint = streamreader.readcardinal3 -- 24-bit unsigned integer
+local readulong = streamreader.readcardinal4 -- 32-bit unsigned integer
+----- readchar = streamreader.readinteger1 -- 8-bit signed integer
+local readshort = streamreader.readinteger2 -- 16-bit signed integer
+local readlong = streamreader.readinteger4 -- 32-bit unsigned integer
+local readfixed = streamreader.readfixed4
+local read2dot14 = streamreader.read2dot14 -- 16-bit signed fixed number with the low 14 bits of fraction (2.14) (F2DOT14)
+local readfword = readshort -- 16-bit signed integer that describes a quantity in FUnits
+local readufword = readushort -- 16-bit unsigned integer that describes a quantity in FUnits
+local readoffset = readushort
+local readcardinaltable = streamreader.readcardinaltable
+local readintegertable = streamreader.readintegertable
+
+function streamreader.readtag(f)
+ return lower(stripstring(readstring(f,4)))
+end
+
+local short = 2
+local ushort = 2
+local ulong = 4
+
+directives.register("fonts.streamreader",function()
+
+ streamreader = utilities.streams
+
+ openfile = streamreader.open
+ closefile = streamreader.close
+ setposition = streamreader.setposition
+ skipshort = streamreader.skipshort
+ readbytes = streamreader.readbytes
+ readstring = streamreader.readstring
+ readbyte = streamreader.readcardinal1
+ readushort = streamreader.readcardinal2
+ readuint = streamreader.readcardinal3
+ readulong = streamreader.readcardinal4
+ readshort = streamreader.readinteger2
+ readlong = streamreader.readinteger4
+ readfixed = streamreader.readfixed4
+ read2dot14 = streamreader.read2dot14
+ readfword = readshort
+ readufword = readushort
+ readoffset = readushort
+ readcardinaltable = streamreader.readcardinaltable
+ readintegertable = streamreader.readintegertable
+
+ function streamreader.readtag(f)
+ return lower(stripstring(readstring(f,4)))
+ end
+
+end)
+
+-- date represented in number of seconds since 12:00 midnight, January 1, 1904. The value is represented as a
+-- signed 64-bit integer
+
+local function readlongdatetime(f)
+ local a, b, c, d, e, f, g, h = readbytes(f,8)
+ return 0x100000000 * d + 0x1000000 * e + 0x10000 * f + 0x100 * g + h
+end
+
+local tableversion = 0.004
+readers.tableversion = tableversion
+local privateoffset = fonts.constructors and fonts.constructors.privateoffset or 0xF0000 -- 0x10FFFF
+
+-- We have quite some data tables. We are somewhat ff compatible with names but as I used
+-- the information from the microsoft site there can be differences. Eventually I might end
+-- up with a different ordering and naming.
+
+local reservednames = { [0] =
+ "copyright",
+ "family",
+ "subfamily",
+ "uniqueid",
+ "fullname",
+ "version",
+ "postscriptname",
+ "trademark",
+ "manufacturer",
+ "designer",
+ "description", -- descriptor in ff
+ "vendorurl",
+ "designerurl",
+ "license",
+ "licenseurl",
+ "reserved",
+ "typographicfamily", -- preffamilyname
+ "typographicsubfamily", -- prefmodifiers
+ "compatiblefullname", -- for mac
+ "sampletext",
+ "cidfindfontname",
+ "wwsfamily",
+ "wwssubfamily",
+ "lightbackgroundpalette",
+ "darkbackgroundpalette",
+ "variationspostscriptnameprefix",
+}
+
+-- more at: https://www.microsoft.com/typography/otspec/name.htm
+
+-- setmetatableindex(reservednames,function(t,k)
+-- local v = "name_" .. k
+-- t[k] = v
+-- return v
+-- end)
+
+local platforms = { [0] =
+ "unicode",
+ "macintosh",
+ "iso",
+ "windows",
+ "custom",
+}
+
+local encodings = {
+ -- these stay:
+ unicode = { [0] =
+ "unicode 1.0 semantics",
+ "unicode 1.1 semantics",
+ "iso/iec 10646",
+ "unicode 2.0 bmp", -- cmap subtable formats 0, 4, 6
+ "unicode 2.0 full", -- cmap subtable formats 0, 4, 6, 10, 12
+ "unicode variation sequences", -- cmap subtable format 14).
+ "unicode full repertoire", -- cmap subtable formats 0, 4, 6, 10, 12, 13
+ },
+ -- these can go:
+ macintosh = { [0] =
+ "roman", "japanese", "chinese (traditional)", "korean", "arabic", "hebrew", "greek", "russian",
+ "rsymbol", "devanagari", "gurmukhi", "gujarati", "oriya", "bengali", "tamil", "telugu", "kannada",
+ "malayalam", "sinhalese", "burmese", "khmer", "thai", "laotian", "georgian", "armenian",
+ "chinese (simplified)", "tibetan", "mongolian", "geez", "slavic", "vietnamese", "sindhi",
+ "uninterpreted",
+ },
+ -- these stay:
+ iso = { [0] =
+ "7-bit ascii",
+ "iso 10646",
+ "iso 8859-1",
+ },
+ -- these stay:
+ windows = { [0] =
+ "symbol",
+ "unicode bmp", -- this is utf16
+ "shiftjis",
+ "prc",
+ "big5",
+ "wansung",
+ "johab",
+ "reserved 7",
+ "reserved 8",
+ "reserved 9",
+ "unicode ucs-4",
+ },
+ custom = {
+ --custom: 0-255 : otf windows nt compatibility mapping
+ }
+}
+
+local decoders = {
+ unicode = { },
+ macintosh = { },
+ iso = { },
+ windows = {
+ -- maybe always utf16
+ ["unicode semantics"] = utf16_to_utf8_be,
+ ["unicode bmp"] = utf16_to_utf8_be,
+ ["unicode full"] = utf16_to_utf8_be,
+ ["unicode 1.0 semantics"] = utf16_to_utf8_be,
+ ["unicode 1.1 semantics"] = utf16_to_utf8_be,
+ ["unicode 2.0 bmp"] = utf16_to_utf8_be,
+ ["unicode 2.0 full"] = utf16_to_utf8_be,
+ ["unicode variation sequences"] = utf16_to_utf8_be,
+ ["unicode full repertoire"] = utf16_to_utf8_be,
+ },
+ custom = { },
+}
+
+-- This is bit over the top as we can just look for either windows, unicode or macintosh
+-- names (in that order). A font with no english name is probably a weird one anyway.
+
+local languages = {
+ -- these stay:
+ unicode = {
+ [ 0] = "english",
+ },
+ -- english can stay:
+ macintosh = {
+ [ 0] = "english",
+ -- [ 1] = "french",
+ -- [ 2] = "german",
+ -- [ 3] = "italian",
+ -- [ 4] = "dutch",
+ -- [ 5] = "swedish",
+ -- [ 6] = "spanish",
+ -- [ 7] = "danish",
+ -- [ 8] = "portuguese",
+ -- [ 9] = "norwegian",
+ -- [ 10] = "hebrew",
+ -- [ 11] = "japanese",
+ -- [ 12] = "arabic",
+ -- [ 13] = "finnish",
+ -- [ 14] = "greek",
+ -- [ 15] = "icelandic",
+ -- [ 16] = "maltese",
+ -- [ 17] = "turkish",
+ -- [ 18] = "croatian",
+ -- [ 19] = "chinese (traditional)",
+ -- [ 20] = "urdu",
+ -- [ 21] = "hindi",
+ -- [ 22] = "thai",
+ -- [ 23] = "korean",
+ -- [ 24] = "lithuanian",
+ -- [ 25] = "polish",
+ -- [ 26] = "hungarian",
+ -- [ 27] = "estonian",
+ -- [ 28] = "latvian",
+ -- [ 29] = "sami",
+ -- [ 30] = "faroese",
+ -- [ 31] = "farsi/persian",
+ -- [ 32] = "russian",
+ -- [ 33] = "chinese (simplified)",
+ -- [ 34] = "flemish",
+ -- [ 35] = "irish gaelic",
+ -- [ 36] = "albanian",
+ -- [ 37] = "romanian",
+ -- [ 38] = "czech",
+ -- [ 39] = "slovak",
+ -- [ 40] = "slovenian",
+ -- [ 41] = "yiddish",
+ -- [ 42] = "serbian",
+ -- [ 43] = "macedonian",
+ -- [ 44] = "bulgarian",
+ -- [ 45] = "ukrainian",
+ -- [ 46] = "byelorussian",
+ -- [ 47] = "uzbek",
+ -- [ 48] = "kazakh",
+ -- [ 49] = "azerbaijani (cyrillic script)",
+ -- [ 50] = "azerbaijani (arabic script)",
+ -- [ 51] = "armenian",
+ -- [ 52] = "georgian",
+ -- [ 53] = "moldavian",
+ -- [ 54] = "kirghiz",
+ -- [ 55] = "tajiki",
+ -- [ 56] = "turkmen",
+ -- [ 57] = "mongolian (mongolian script)",
+ -- [ 58] = "mongolian (cyrillic script)",
+ -- [ 59] = "pashto",
+ -- [ 60] = "kurdish",
+ -- [ 61] = "kashmiri",
+ -- [ 62] = "sindhi",
+ -- [ 63] = "tibetan",
+ -- [ 64] = "nepali",
+ -- [ 65] = "sanskrit",
+ -- [ 66] = "marathi",
+ -- [ 67] = "bengali",
+ -- [ 68] = "assamese",
+ -- [ 69] = "gujarati",
+ -- [ 70] = "punjabi",
+ -- [ 71] = "oriya",
+ -- [ 72] = "malayalam",
+ -- [ 73] = "kannada",
+ -- [ 74] = "tamil",
+ -- [ 75] = "telugu",
+ -- [ 76] = "sinhalese",
+ -- [ 77] = "burmese",
+ -- [ 78] = "khmer",
+ -- [ 79] = "lao",
+ -- [ 80] = "vietnamese",
+ -- [ 81] = "indonesian",
+ -- [ 82] = "tagalong",
+ -- [ 83] = "malay (roman script)",
+ -- [ 84] = "malay (arabic script)",
+ -- [ 85] = "amharic",
+ -- [ 86] = "tigrinya",
+ -- [ 87] = "galla",
+ -- [ 88] = "somali",
+ -- [ 89] = "swahili",
+ -- [ 90] = "kinyarwanda/ruanda",
+ -- [ 91] = "rundi",
+ -- [ 92] = "nyanja/chewa",
+ -- [ 93] = "malagasy",
+ -- [ 94] = "esperanto",
+ -- [128] = "welsh",
+ -- [129] = "basque",
+ -- [130] = "catalan",
+ -- [131] = "latin",
+ -- [132] = "quenchua",
+ -- [133] = "guarani",
+ -- [134] = "aymara",
+ -- [135] = "tatar",
+ -- [136] = "uighur",
+ -- [137] = "dzongkha",
+ -- [138] = "javanese (roman script)",
+ -- [139] = "sundanese (roman script)",
+ -- [140] = "galician",
+ -- [141] = "afrikaans",
+ -- [142] = "breton",
+ -- [143] = "inuktitut",
+ -- [144] = "scottish gaelic",
+ -- [145] = "manx gaelic",
+ -- [146] = "irish gaelic (with dot above)",
+ -- [147] = "tongan",
+ -- [148] = "greek (polytonic)",
+ -- [149] = "greenlandic",
+ -- [150] = "azerbaijani (roman script)",
+ },
+ -- these can stay:
+ iso = {
+ },
+ -- english can stay:
+ windows = {
+ -- [0x0436] = "afrikaans - south africa",
+ -- [0x041c] = "albanian - albania",
+ -- [0x0484] = "alsatian - france",
+ -- [0x045e] = "amharic - ethiopia",
+ -- [0x1401] = "arabic - algeria",
+ -- [0x3c01] = "arabic - bahrain",
+ -- [0x0c01] = "arabic - egypt",
+ -- [0x0801] = "arabic - iraq",
+ -- [0x2c01] = "arabic - jordan",
+ -- [0x3401] = "arabic - kuwait",
+ -- [0x3001] = "arabic - lebanon",
+ -- [0x1001] = "arabic - libya",
+ -- [0x1801] = "arabic - morocco",
+ -- [0x2001] = "arabic - oman",
+ -- [0x4001] = "arabic - qatar",
+ -- [0x0401] = "arabic - saudi arabia",
+ -- [0x2801] = "arabic - syria",
+ -- [0x1c01] = "arabic - tunisia",
+ -- [0x3801] = "arabic - u.a.e.",
+ -- [0x2401] = "arabic - yemen",
+ -- [0x042b] = "armenian - armenia",
+ -- [0x044d] = "assamese - india",
+ -- [0x082c] = "azeri (cyrillic) - azerbaijan",
+ -- [0x042c] = "azeri (latin) - azerbaijan",
+ -- [0x046d] = "bashkir - russia",
+ -- [0x042d] = "basque - basque",
+ -- [0x0423] = "belarusian - belarus",
+ -- [0x0845] = "bengali - bangladesh",
+ -- [0x0445] = "bengali - india",
+ -- [0x201a] = "bosnian (cyrillic) - bosnia and herzegovina",
+ -- [0x141a] = "bosnian (latin) - bosnia and herzegovina",
+ -- [0x047e] = "breton - france",
+ -- [0x0402] = "bulgarian - bulgaria",
+ -- [0x0403] = "catalan - catalan",
+ -- [0x0c04] = "chinese - hong kong s.a.r.",
+ -- [0x1404] = "chinese - macao s.a.r.",
+ -- [0x0804] = "chinese - people's republic of china",
+ -- [0x1004] = "chinese - singapore",
+ -- [0x0404] = "chinese - taiwan",
+ -- [0x0483] = "corsican - france",
+ -- [0x041a] = "croatian - croatia",
+ -- [0x101a] = "croatian (latin) - bosnia and herzegovina",
+ -- [0x0405] = "czech - czech republic",
+ -- [0x0406] = "danish - denmark",
+ -- [0x048c] = "dari - afghanistan",
+ -- [0x0465] = "divehi - maldives",
+ -- [0x0813] = "dutch - belgium",
+ -- [0x0413] = "dutch - netherlands",
+ -- [0x0c09] = "english - australia",
+ -- [0x2809] = "english - belize",
+ -- [0x1009] = "english - canada",
+ -- [0x2409] = "english - caribbean",
+ -- [0x4009] = "english - india",
+ -- [0x1809] = "english - ireland",
+ -- [0x2009] = "english - jamaica",
+ -- [0x4409] = "english - malaysia",
+ -- [0x1409] = "english - new zealand",
+ -- [0x3409] = "english - republic of the philippines",
+ -- [0x4809] = "english - singapore",
+ -- [0x1c09] = "english - south africa",
+ -- [0x2c09] = "english - trinidad and tobago",
+ -- [0x0809] = "english - united kingdom",
+ [0x0409] = "english - united states",
+ -- [0x3009] = "english - zimbabwe",
+ -- [0x0425] = "estonian - estonia",
+ -- [0x0438] = "faroese - faroe islands",
+ -- [0x0464] = "filipino - philippines",
+ -- [0x040b] = "finnish - finland",
+ -- [0x080c] = "french - belgium",
+ -- [0x0c0c] = "french - canada",
+ -- [0x040c] = "french - france",
+ -- [0x140c] = "french - luxembourg",
+ -- [0x180c] = "french - principality of monoco",
+ -- [0x100c] = "french - switzerland",
+ -- [0x0462] = "frisian - netherlands",
+ -- [0x0456] = "galician - galician",
+ -- [0x0437] = "georgian -georgia",
+ -- [0x0c07] = "german - austria",
+ -- [0x0407] = "german - germany",
+ -- [0x1407] = "german - liechtenstein",
+ -- [0x1007] = "german - luxembourg",
+ -- [0x0807] = "german - switzerland",
+ -- [0x0408] = "greek - greece",
+ -- [0x046f] = "greenlandic - greenland",
+ -- [0x0447] = "gujarati - india",
+ -- [0x0468] = "hausa (latin) - nigeria",
+ -- [0x040d] = "hebrew - israel",
+ -- [0x0439] = "hindi - india",
+ -- [0x040e] = "hungarian - hungary",
+ -- [0x040f] = "icelandic - iceland",
+ -- [0x0470] = "igbo - nigeria",
+ -- [0x0421] = "indonesian - indonesia",
+ -- [0x045d] = "inuktitut - canada",
+ -- [0x085d] = "inuktitut (latin) - canada",
+ -- [0x083c] = "irish - ireland",
+ -- [0x0434] = "isixhosa - south africa",
+ -- [0x0435] = "isizulu - south africa",
+ -- [0x0410] = "italian - italy",
+ -- [0x0810] = "italian - switzerland",
+ -- [0x0411] = "japanese - japan",
+ -- [0x044b] = "kannada - india",
+ -- [0x043f] = "kazakh - kazakhstan",
+ -- [0x0453] = "khmer - cambodia",
+ -- [0x0486] = "k'iche - guatemala",
+ -- [0x0487] = "kinyarwanda - rwanda",
+ -- [0x0441] = "kiswahili - kenya",
+ -- [0x0457] = "konkani - india",
+ -- [0x0412] = "korean - korea",
+ -- [0x0440] = "kyrgyz - kyrgyzstan",
+ -- [0x0454] = "lao - lao p.d.r.",
+ -- [0x0426] = "latvian - latvia",
+ -- [0x0427] = "lithuanian - lithuania",
+ -- [0x082e] = "lower sorbian - germany",
+ -- [0x046e] = "luxembourgish - luxembourg",
+ -- [0x042f] = "macedonian (fyrom) - former yugoslav republic of macedonia",
+ -- [0x083e] = "malay - brunei darussalam",
+ -- [0x043e] = "malay - malaysia",
+ -- [0x044c] = "malayalam - india",
+ -- [0x043a] = "maltese - malta",
+ -- [0x0481] = "maori - new zealand",
+ -- [0x047a] = "mapudungun - chile",
+ -- [0x044e] = "marathi - india",
+ -- [0x047c] = "mohawk - mohawk",
+ -- [0x0450] = "mongolian (cyrillic) - mongolia",
+ -- [0x0850] = "mongolian (traditional) - people's republic of china",
+ -- [0x0461] = "nepali - nepal",
+ -- [0x0414] = "norwegian (bokmal) - norway",
+ -- [0x0814] = "norwegian (nynorsk) - norway",
+ -- [0x0482] = "occitan - france",
+ -- [0x0448] = "odia (formerly oriya) - india",
+ -- [0x0463] = "pashto - afghanistan",
+ -- [0x0415] = "polish - poland",
+ -- [0x0416] = "portuguese - brazil",
+ -- [0x0816] = "portuguese - portugal",
+ -- [0x0446] = "punjabi - india",
+ -- [0x046b] = "quechua - bolivia",
+ -- [0x086b] = "quechua - ecuador",
+ -- [0x0c6b] = "quechua - peru",
+ -- [0x0418] = "romanian - romania",
+ -- [0x0417] = "romansh - switzerland",
+ -- [0x0419] = "russian - russia",
+ -- [0x243b] = "sami (inari) - finland",
+ -- [0x103b] = "sami (lule) - norway",
+ -- [0x143b] = "sami (lule) - sweden",
+ -- [0x0c3b] = "sami (northern) - finland",
+ -- [0x043b] = "sami (northern) - norway",
+ -- [0x083b] = "sami (northern) - sweden",
+ -- [0x203b] = "sami (skolt) - finland",
+ -- [0x183b] = "sami (southern) - norway",
+ -- [0x1c3b] = "sami (southern) - sweden",
+ -- [0x044f] = "sanskrit - india",
+ -- [0x1c1a] = "serbian (cyrillic) - bosnia and herzegovina",
+ -- [0x0c1a] = "serbian (cyrillic) - serbia",
+ -- [0x181a] = "serbian (latin) - bosnia and herzegovina",
+ -- [0x081a] = "serbian (latin) - serbia",
+ -- [0x046c] = "sesotho sa leboa - south africa",
+ -- [0x0432] = "setswana - south africa",
+ -- [0x045b] = "sinhala - sri lanka",
+ -- [0x041b] = "slovak - slovakia",
+ -- [0x0424] = "slovenian - slovenia",
+ -- [0x2c0a] = "spanish - argentina",
+ -- [0x400a] = "spanish - bolivia",
+ -- [0x340a] = "spanish - chile",
+ -- [0x240a] = "spanish - colombia",
+ -- [0x140a] = "spanish - costa rica",
+ -- [0x1c0a] = "spanish - dominican republic",
+ -- [0x300a] = "spanish - ecuador",
+ -- [0x440a] = "spanish - el salvador",
+ -- [0x100a] = "spanish - guatemala",
+ -- [0x480a] = "spanish - honduras",
+ -- [0x080a] = "spanish - mexico",
+ -- [0x4c0a] = "spanish - nicaragua",
+ -- [0x180a] = "spanish - panama",
+ -- [0x3c0a] = "spanish - paraguay",
+ -- [0x280a] = "spanish - peru",
+ -- [0x500a] = "spanish - puerto rico",
+ -- [0x0c0a] = "spanish (modern sort) - spain",
+ -- [0x040a] = "spanish (traditional sort) - spain",
+ -- [0x540a] = "spanish - united states",
+ -- [0x380a] = "spanish - uruguay",
+ -- [0x200a] = "spanish - venezuela",
+ -- [0x081d] = "sweden - finland",
+ -- [0x041d] = "swedish - sweden",
+ -- [0x045a] = "syriac - syria",
+ -- [0x0428] = "tajik (cyrillic) - tajikistan",
+ -- [0x085f] = "tamazight (latin) - algeria",
+ -- [0x0449] = "tamil - india",
+ -- [0x0444] = "tatar - russia",
+ -- [0x044a] = "telugu - india",
+ -- [0x041e] = "thai - thailand",
+ -- [0x0451] = "tibetan - prc",
+ -- [0x041f] = "turkish - turkey",
+ -- [0x0442] = "turkmen - turkmenistan",
+ -- [0x0480] = "uighur - prc",
+ -- [0x0422] = "ukrainian - ukraine",
+ -- [0x042e] = "upper sorbian - germany",
+ -- [0x0420] = "urdu - islamic republic of pakistan",
+ -- [0x0843] = "uzbek (cyrillic) - uzbekistan",
+ -- [0x0443] = "uzbek (latin) - uzbekistan",
+ -- [0x042a] = "vietnamese - vietnam",
+ -- [0x0452] = "welsh - united kingdom",
+ -- [0x0488] = "wolof - senegal",
+ -- [0x0485] = "yakut - russia",
+ -- [0x0478] = "yi - prc",
+ -- [0x046a] = "yoruba - nigeria",
+ },
+ custom = {
+ },
+}
+
+local standardromanencoding = { [0] = -- taken from wikipedia
+ "notdef", ".null", "nonmarkingreturn", "space", "exclam", "quotedbl",
+ "numbersign", "dollar", "percent", "ampersand", "quotesingle", "parenleft",
+ "parenright", "asterisk", "plus", "comma", "hyphen", "period", "slash",
+ "zero", "one", "two", "three", "four", "five", "six", "seven", "eight",
+ "nine", "colon", "semicolon", "less", "equal", "greater", "question", "at",
+ "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O",
+ "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", "bracketleft",
+ "backslash", "bracketright", "asciicircum", "underscore", "grave", "a", "b",
+ "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q",
+ "r", "s", "t", "u", "v", "w", "x", "y", "z", "braceleft", "bar",
+ "braceright", "asciitilde", "Adieresis", "Aring", "Ccedilla", "Eacute",
+ "Ntilde", "Odieresis", "Udieresis", "aacute", "agrave", "acircumflex",
+ "adieresis", "atilde", "aring", "ccedilla", "eacute", "egrave",
+ "ecircumflex", "edieresis", "iacute", "igrave", "icircumflex", "idieresis",
+ "ntilde", "oacute", "ograve", "ocircumflex", "odieresis", "otilde", "uacute",
+ "ugrave", "ucircumflex", "udieresis", "dagger", "degree", "cent", "sterling",
+ "section", "bullet", "paragraph", "germandbls", "registered", "copyright",
+ "trademark", "acute", "dieresis", "notequal", "AE", "Oslash", "infinity",
+ "plusminus", "lessequal", "greaterequal", "yen", "mu", "partialdiff",
+ "summation", "product", "pi", "integral", "ordfeminine", "ordmasculine",
+ "Omega", "ae", "oslash", "questiondown", "exclamdown", "logicalnot",
+ "radical", "florin", "approxequal", "Delta", "guillemotleft",
+ "guillemotright", "ellipsis", "nonbreakingspace", "Agrave", "Atilde",
+ "Otilde", "OE", "oe", "endash", "emdash", "quotedblleft", "quotedblright",
+ "quoteleft", "quoteright", "divide", "lozenge", "ydieresis", "Ydieresis",
+ "fraction", "currency", "guilsinglleft", "guilsinglright", "fi", "fl",
+ "daggerdbl", "periodcentered", "quotesinglbase", "quotedblbase",
+ "perthousand", "Acircumflex", "Ecircumflex", "Aacute", "Edieresis", "Egrave",
+ "Iacute", "Icircumflex", "Idieresis", "Igrave", "Oacute", "Ocircumflex",
+ "apple", "Ograve", "Uacute", "Ucircumflex", "Ugrave", "dotlessi",
+ "circumflex", "tilde", "macron", "breve", "dotaccent", "ring", "cedilla",
+ "hungarumlaut", "ogonek", "caron", "Lslash", "lslash", "Scaron", "scaron",
+ "Zcaron", "zcaron", "brokenbar", "Eth", "eth", "Yacute", "yacute", "Thorn",
+ "thorn", "minus", "multiply", "onesuperior", "twosuperior", "threesuperior",
+ "onehalf", "onequarter", "threequarters", "franc", "Gbreve", "gbreve",
+ "Idotaccent", "Scedilla", "scedilla", "Cacute", "cacute", "Ccaron", "ccaron",
+ "dcroat",
+}
+
+local weights = {
+ [100] = "thin",
+ [200] = "extralight",
+ [300] = "light",
+ [400] = "normal",
+ [500] = "medium",
+ [600] = "semibold", -- demi demibold
+ [700] = "bold",
+ [800] = "extrabold",
+ [900] = "black",
+}
+
+local widths = {
+ [1] = "ultracondensed",
+ [2] = "extracondensed",
+ [3] = "condensed",
+ [4] = "semicondensed",
+ [5] = "normal",
+ [6] = "semiexpanded",
+ [7] = "expanded",
+ [8] = "extraexpanded",
+ [9] = "ultraexpanded",
+}
+
+setmetatableindex(weights, function(t,k)
+ local r = floor((k + 50) / 100) * 100
+ local v = (r > 900 and "black") or rawget(t,r) or "normal"
+ return v
+end)
+
+setmetatableindex(widths,function(t,k)
+ return "normal"
+end)
+
+local panoseweights = {
+ [ 0] = "normal",
+ [ 1] = "normal",
+ [ 2] = "verylight",
+ [ 3] = "light",
+ [ 4] = "thin",
+ [ 5] = "book",
+ [ 6] = "medium",
+ [ 7] = "demi",
+ [ 8] = "bold",
+ [ 9] = "heavy",
+ [10] = "black",
+}
+
+local panosewidths = {
+ [ 0] = "normal",
+ [ 1] = "normal",
+ [ 2] = "normal",
+ [ 3] = "normal",
+ [ 4] = "normal",
+ [ 5] = "expanded",
+ [ 6] = "condensed",
+ [ 7] = "veryexpanded",
+ [ 8] = "verycondensed",
+ [ 9] = "monospaced",
+}
+
+-- We implement a reader per table.
+
+-- helper
+
+local helpers = { }
+readers.helpers = helpers
+
+local function gotodatatable(f,fontdata,tag,criterium)
+ if criterium and f then
+ local tables = fontdata.tables
+ if tables then
+ local datatable = tables[tag]
+ if datatable then
+ local tableoffset = datatable.offset
+ setposition(f,tableoffset)
+ return tableoffset
+ end
+ else
+ report("no tables")
+ end
+ end
+end
+
+local function reportskippedtable(f,fontdata,tag,criterium)
+ if criterium and f then
+ local tables = fontdata.tables
+ if tables then
+ local datatable = tables[tag]
+ if datatable then
+ report("loading of table %a skipped",tag)
+ end
+ else
+ report("no tables")
+ end
+ end
+end
+
+local function setvariabledata(fontdata,tag,data)
+ local variabledata = fontdata.variabledata
+ if variabledata then
+ variabledata[tag] = data
+ else
+ fontdata.variabledata = { [tag] = data }
+ end
+end
+
+helpers.gotodatatable = gotodatatable
+helpers.setvariabledata = setvariabledata
+helpers.reportskippedtable = reportskippedtable
+
+-- The name table is probably the first one to load. After all this one provides
+-- useful information about what we deal with. The complication is that we need
+-- to filter the best one available.
+
+local platformnames = {
+ postscriptname = true,
+ fullname = true,
+ family = true,
+ subfamily = true,
+ typographicfamily = true,
+ typographicsubfamily = true,
+ compatiblefullname = true,
+}
+
+local platformextras = {
+ uniqueid = true,
+ version = true,
+ copyright = true,
+ license = true,
+ licenseurl = true,
+ manufacturer = true,
+ vendorurl = true,
+}
+
+function readers.name(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"name",true)
+ if tableoffset then
+ local format = readushort(f)
+ local nofnames = readushort(f)
+ local offset = readushort(f)
+ -- we can also provide a raw list as extra, todo as option
+ local start = tableoffset + offset
+ local namelists = {
+ unicode = { },
+ windows = { },
+ macintosh = { },
+ -- iso = { },
+ -- windows = { },
+ }
+ for i=1,nofnames do
+ local platform = platforms[readushort(f)]
+ if platform then
+ local namelist = namelists[platform]
+ if namelist then
+ local encoding = readushort(f)
+ local language = readushort(f)
+ local encodings = encodings[platform]
+ local languages = languages[platform]
+ if encodings and languages then
+ local encoding = encodings[encoding]
+ local language = languages[language]
+ if encoding and language then
+ local index = readushort(f)
+ local name = reservednames[index]
+ namelist[#namelist+1] = {
+ platform = platform,
+ encoding = encoding,
+ language = language,
+ name = name,
+ index = index,
+ length = readushort(f),
+ offset = start + readushort(f),
+ }
+ else
+ skipshort(f,3)
+ end
+ else
+ skipshort(f,3)
+ end
+ else
+ skipshort(f,5)
+ end
+ else
+ skipshort(f,5)
+ end
+ end
+ -- if format == 1 then
+ -- local noftags = readushort(f)
+ -- for i=1,noftags do
+ -- local length = readushort(f)
+ -- local offset = readushort(f)
+ -- end
+ -- end
+ --
+ -- we need to choose one we like, for instance an unicode one
+ --
+ local names = { }
+ local done = { }
+ local extras = { }
+ --
+ -- there is quite some logic in ff ... hard to follow so we start simple
+ -- and extend when we run into it (todo: proper reverse hash) .. we're only
+ -- interested in english anyway
+ --
+ local function decoded(platform,encoding,content)
+ local decoder = decoders[platform]
+ if decoder then
+ decoder = decoder[encoding]
+ end
+ if decoder then
+ return decoder(content)
+ else
+ return content
+ end
+ end
+ --
+ local function filter(platform,e,l)
+ local namelist = namelists[platform]
+ for i=1,#namelist do
+ local name = namelist[i]
+ local nametag = name.name
+ local index = name.index
+ if not done[nametag or i] then
+ local encoding = name.encoding
+ local language = name.language
+ if (not e or encoding == e) and (not l or language == l) then
+ setposition(f,name.offset)
+ local content = decoded(platform,encoding,readstring(f,name.length))
+ if nametag then
+ names[nametag] = {
+ content = content,
+ platform = platform,
+ encoding = encoding,
+ language = language,
+ }
+ end
+ extras[index] = content
+ done[nametag or i] = true
+ end
+ end
+ end
+ end
+ --
+ filter("windows","unicode bmp","english - united states")
+ -- filter("unicode") -- which one ?
+ filter("macintosh","roman","english")
+ filter("windows")
+ filter("macintosh")
+ filter("unicode")
+ --
+ fontdata.names = names
+ fontdata.extras = extras
+ --
+ if specification.platformnames then
+ local collected = { }
+ local platformextras = specification.platformextras and platformextras
+ for platform, namelist in next, namelists do
+ local filtered = false
+ for i=1,#namelist do
+ local entry = namelist[i]
+ local name = entry.name
+ if platformnames[name] or (platformextras and platformextras[name]) then
+ setposition(f,entry.offset)
+ local content = decoded(platform,entry.encoding,readstring(f,entry.length))
+ if filtered then
+ filtered[name] = content
+ else
+ filtered = { [name] = content }
+ end
+ end
+ end
+ if filtered then
+ collected[platform] = filtered
+ end
+ end
+ fontdata.platformnames = collected
+ end
+ else
+ fontdata.names = { }
+ end
+end
+
+----- validutf = lpeg.patterns.utf8character^0 * P(-1)
+local validutf = lpeg.patterns.validutf8
+
+local function getname(fontdata,key)
+ local names = fontdata.names
+ if names then
+ local value = names[key]
+ if value then
+ local content = value.content
+ return lpegmatch(validutf,content) and content or nil
+ end
+ end
+end
+
+-- This table is an original windows (with its precursor os/2) table. In ff this one is
+-- part of the pfminfo table but here we keep it separate (for now). We will create a
+-- properties table afterwards.
+
+readers["os/2"] = function(f,fontdata)
+ local tableoffset = gotodatatable(f,fontdata,"os/2",true)
+ if tableoffset then
+ local version = readushort(f)
+ local windowsmetrics = {
+ version = version,
+ averagewidth = readshort(f), -- ushort?
+ weightclass = readushort(f),
+ widthclass = readushort(f),
+ fstype = readushort(f),
+ subscriptxsize = readshort(f),
+ subscriptysize = readshort(f),
+ subscriptxoffset = readshort(f),
+ subscriptyoffset = readshort(f),
+ superscriptxsize = readshort(f),
+ superscriptysize = readshort(f),
+ superscriptxoffset = readshort(f),
+ superscriptyoffset = readshort(f),
+ strikeoutsize = readshort(f),
+ strikeoutpos = readshort(f),
+ familyclass = readshort(f),
+ panose = { readbytes(f,10) },
+ unicoderanges = { readulong(f), readulong(f), readulong(f), readulong(f) },
+ vendor = readstring(f,4),
+ fsselection = readushort(f),
+ firstcharindex = readushort(f),
+ lastcharindex = readushort(f),
+ typoascender = readshort(f),
+ typodescender = readshort(f),
+ typolinegap = readshort(f),
+ winascent = readushort(f),
+ windescent = readushort(f),
+ }
+ if version >= 1 then
+ windowsmetrics.codepageranges = { readulong(f), readulong(f) }
+ end
+ if version >= 2 then
+ windowsmetrics.xheight = readshort(f)
+ windowsmetrics.capheight = readshort(f)
+ windowsmetrics.defaultchar = readushort(f)
+ windowsmetrics.breakchar = readushort(f)
+ -- windowsmetrics.maxcontexts = readushort(f)
+ -- windowsmetrics.loweropticalpointsize = readushort(f)
+ -- windowsmetrics.upperopticalpointsize = readushort(f)
+ end
+ --
+ -- todo: unicoderanges
+ --
+ windowsmetrics.weight = windowsmetrics.weightclass and weights[windowsmetrics.weightclass]
+ windowsmetrics.width = windowsmetrics.widthclass and widths [windowsmetrics.widthclass]
+ --
+ windowsmetrics.panoseweight = panoseweights[windowsmetrics.panose[3]]
+ windowsmetrics.panosewidth = panosewidths [windowsmetrics.panose[4]]
+ --
+ fontdata.windowsmetrics = windowsmetrics
+ else
+ fontdata.windowsmetrics = { }
+ end
+end
+
+readers.head = function(f,fontdata)
+ local tableoffset = gotodatatable(f,fontdata,"head",true)
+ if tableoffset then
+ local version = readulong(f)
+ local fontversion = readulong(f)
+ local fontheader = {
+ version = version,
+ fontversion = number.to16dot16(fontversion),
+ fontversionnumber = fontversion,
+ -- checksum = readulong(f),
+ checksum = readushort(f) * 0x10000 + readushort(f),
+ magic = readulong(f),
+ flags = readushort(f),
+ units = readushort(f),
+ created = readlongdatetime(f),
+ modified = readlongdatetime(f),
+ xmin = readshort(f),
+ ymin = readshort(f),
+ xmax = readshort(f),
+ ymax = readshort(f),
+ macstyle = readushort(f),
+ smallpixels = readushort(f),
+ directionhint = readshort(f),
+ indextolocformat = readshort(f),
+ glyphformat = readshort(f),
+ }
+ fontdata.fontheader = fontheader
+ else
+ fontdata.fontheader = { }
+ end
+ fontdata.nofglyphs = 0
+end
+
+-- This table is a rather simple one. No treatment of values is needed here. Most
+-- variables are not used but nofmetrics is quite important.
+
+readers.hhea = function(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"hhea",specification.details)
+ if tableoffset then
+ fontdata.horizontalheader = {
+ version = readulong(f),
+ ascender = readfword(f),
+ descender = readfword(f),
+ linegap = readfword(f),
+ maxadvancewidth = readufword(f),
+ minleftsidebearing = readfword(f),
+ minrightsidebearing = readfword(f),
+ maxextent = readfword(f),
+ caretsloperise = readshort(f),
+ caretsloperun = readshort(f),
+ caretoffset = readshort(f),
+ reserved_1 = readshort(f),
+ reserved_2 = readshort(f),
+ reserved_3 = readshort(f),
+ reserved_4 = readshort(f),
+ metricdataformat = readshort(f),
+ nofmetrics = readushort(f),
+ }
+ else
+ fontdata.horizontalheader = {
+ nofmetrics = 0,
+ }
+ end
+end
+
+readers.vhea = function(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"vhea",specification.details)
+ if tableoffset then
+ fontdata.verticalheader = {
+ version = readulong(f),
+ ascender = readfword(f),
+ descender = readfword(f),
+ linegap = readfword(f),
+ maxadvanceheight = readufword(f),
+ mintopsidebearing = readfword(f),
+ minbottomsidebearing = readfword(f),
+ maxextent = readfword(f),
+ caretsloperise = readshort(f),
+ caretsloperun = readshort(f),
+ caretoffset = readshort(f),
+ reserved_1 = readshort(f),
+ reserved_2 = readshort(f),
+ reserved_3 = readshort(f),
+ reserved_4 = readshort(f),
+ metricdataformat = readshort(f),
+ nofmetrics = readushort(f),
+ }
+ else
+ fontdata.verticalheader = {
+ nofmetrics = 0,
+ }
+ end
+end
+
+-- We probably never need all these variables, but we do need the nofglyphs when loading other
+-- tables. Again we use the microsoft names but see no reason to have "max" in each name.
+
+-- fontdata.maximumprofile can be bad
+
+readers.maxp = function(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"maxp",specification.details)
+ if tableoffset then
+ local version = readulong(f)
+ local nofglyphs = readushort(f)
+ fontdata.nofglyphs = nofglyphs
+ if version == 0x00005000 then
+ fontdata.maximumprofile = {
+ version = version,
+ nofglyphs = nofglyphs,
+ }
+ elseif version == 0x00010000 then
+ fontdata.maximumprofile = {
+ version = version,
+ nofglyphs = nofglyphs,
+ points = readushort(f),
+ contours = readushort(f),
+ compositepoints = readushort(f),
+ compositecontours = readushort(f),
+ zones = readushort(f),
+ twilightpoints = readushort(f),
+ storage = readushort(f),
+ functiondefs = readushort(f),
+ instructiondefs = readushort(f),
+ stackelements = readushort(f),
+ sizeofinstructions = readushort(f),
+ componentelements = readushort(f),
+ componentdepth = readushort(f),
+ }
+ else
+ fontdata.maximumprofile = {
+ version = version,
+ nofglyphs = 0,
+ }
+ end
+ end
+end
+
+-- Here we filter the (advance) widths (that can be different from the boundingbox width of
+-- course).
+
+readers.hmtx = function(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"hmtx",specification.glyphs)
+ if tableoffset then
+ local horizontalheader = fontdata.horizontalheader
+ local nofmetrics = horizontalheader.nofmetrics
+ local glyphs = fontdata.glyphs
+ local nofglyphs = fontdata.nofglyphs
+ local width = 0 -- advance
+ local leftsidebearing = 0
+ for i=0,nofmetrics-1 do
+ local glyph = glyphs[i]
+ width = readshort(f) -- readushort
+ leftsidebearing = readshort(f)
+ if width ~= 0 then
+ glyph.width = width
+ end
+ -- if leftsidebearing ~= 0 then
+ -- glyph.lsb = leftsidebearing
+ -- end
+ end
+ -- The next can happen in for instance a monospace font or in a cjk font
+ -- with fixed widths.
+ for i=nofmetrics,nofglyphs-1 do
+ local glyph = glyphs[i]
+ if width ~= 0 then
+ glyph.width = width
+ end
+ -- if leftsidebearing ~= 0 then
+ -- glyph.lsb = leftsidebearing
+ -- end
+ end
+ end
+end
+
+readers.vmtx = function(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"vmtx",specification.glyphs)
+ if tableoffset then
+ local verticalheader = fontdata.verticalheader
+ local nofmetrics = verticalheader.nofmetrics
+ local glyphs = fontdata.glyphs
+ local nofglyphs = fontdata.nofglyphs
+ local vheight = 0
+ local vdefault = verticalheader.ascender - verticalheader.descender
+ local topsidebearing = 0
+ for i=0,nofmetrics-1 do
+ local glyph = glyphs[i]
+ vheight = readushort(f)
+ topsidebearing = readshort(f)
+ if vheight ~= 0 and vheight ~= vdefault then
+ glyph.vheight = vheight
+ end
+ if topsidebearing ~= 0 then
+ glyph.tsb = topsidebearing
+ end
+ end
+ -- The next can happen in for instance a monospace font or in a cjk font
+ -- with fixed heights.
+ for i=nofmetrics,nofglyphs-1 do
+ local glyph = glyphs[i]
+ if vheight ~= 0 and vheight ~= vdefault then
+ glyph.vheight = vheight
+ end
+ end
+ end
+end
+
+readers.vorg = function(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"vorg",specification.glyphs)
+end
+
+-- The post table relates to postscript (printing) but has some relevant properties for other
+-- usage as well. We just use the names from the microsoft specification. The version 2.0
+-- description is somewhat fuzzy but it is a hybrid with overloads.
+
+readers.post = function(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"post",true)
+ if tableoffset then
+ local version = readulong(f)
+ fontdata.postscript = {
+ version = version,
+ italicangle = round(1000*readfixed(f))/1000,
+ underlineposition = readfword(f),
+ underlinethickness = readfword(f),
+ monospaced = readulong(f),
+ minmemtype42 = readulong(f),
+ maxmemtype42 = readulong(f),
+ minmemtype1 = readulong(f),
+ maxmemtype1 = readulong(f),
+ }
+ if not specification.glyphs then
+ -- enough done
+ elseif version == 0x00010000 then
+ -- mac encoding (258 glyphs)
+ for index=0,#standardromanencoding do
+ glyphs[index].name = standardromanencoding[index]
+ end
+ elseif version == 0x00020000 then
+ local glyphs = fontdata.glyphs
+ local nofglyphs = readushort(f)
+ local indices = { }
+ local names = { }
+ local maxnames = 0
+ for i=0,nofglyphs-1 do
+ local nameindex = readushort(f)
+ if nameindex >= 258 then
+ maxnames = maxnames + 1
+ nameindex = nameindex - 257
+ indices[nameindex] = i
+ else
+ glyphs[i].name = standardromanencoding[nameindex]
+ end
+ end
+ for i=1,maxnames do
+ local mapping = indices[i]
+ if not mapping then
+ report("quit post name fetching at %a of %a: %s",i,maxnames,"no index")
+ break
+ else
+ local length = readbyte(f)
+ if length > 0 then
+ glyphs[mapping].name = readstring(f,length)
+ else
+ report("quit post name fetching at %a of %a: %s",i,maxnames,"overflow")
+ break
+ end
+ end
+ end
+ end
+ else
+ fontdata.postscript = { }
+ end
+end
+
+readers.cff = function(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cff",specification.glyphs)
+end
+
+-- Not all cmaps make sense .. e.g. dfont is obsolete and probably more are not relevant. Let's see
+-- what we run into. There is some weird calculation going on here because we offset in a table
+-- being a blob of memory or file. Anyway, I can't stand lunatic formats like this esp when there
+-- is no real gain.
+
+local formatreaders = { }
+local duplicatestoo = true
+
+local sequence = {
+ -- these is some provision against redundant loading
+ { 3, 1, 4 },
+ { 3, 10, 12 },
+ { 0, 3, 4 },
+ { 0, 3, 12 },
+ { 0, 1, 4 },
+ { 0, 1, 12 }, -- for some old mac fonts
+ { 0, 0, 6 },
+ { 3, 0, 6 },
+ { 3, 0, 4 }, -- for (likely) old crap
+ -- variants
+ { 0, 5, 14 },
+ -- last resort ranges
+ { 0, 4, 12 },
+ { 3, 10, 13 },
+}
+
+local supported = { }
+
+for i=1,#sequence do
+ local si = sequence[i]
+ local sp, se, sf = si[1], si[2], si[3]
+ local p = supported[sp]
+ if not p then
+ p = { }
+ supported[sp] = p
+ end
+ local e = p[se]
+ if not e then
+ e = { }
+ p[se] = e
+ end
+ e[sf] = true
+end
+
+formatreaders[4] = function(f,fontdata,offset)
+ setposition(f,offset+2) -- skip format
+ --
+ local length = readushort(f) -- in bytes of subtable
+ local language = readushort(f)
+ local nofsegments = readushort(f) / 2
+ --
+ skipshort(f,3) -- searchrange entryselector rangeshift
+ --
+ local mapping = fontdata.mapping
+ local glyphs = fontdata.glyphs
+ local duplicates = fontdata.duplicates
+ local nofdone = 0
+ local endchars = readcardinaltable(f,nofsegments,ushort)
+ local reserved = readushort(f) -- 0
+ local startchars = readcardinaltable(f,nofsegments,ushort)
+ local deltas = readcardinaltable(f,nofsegments,ushort)
+ local offsets = readcardinaltable(f,nofsegments,ushort)
+ -- format length language nofsegments searchrange entryselector rangeshift 4-tables
+ local size = (length - 2 * 2 - 5 * 2 - 4 * 2 * nofsegments) / 2
+ local indices = readcardinaltable(f,size-1,ushort)
+ --
+ for segment=1,nofsegments do
+ local startchar = startchars[segment]
+ local endchar = endchars[segment]
+ local offset = offsets[segment]
+ local delta = deltas[segment]
+ if startchar == 0xFFFF and endchar == 0xFFFF then
+ -- break
+ elseif startchar == 0xFFFF and offset == 0 then
+ -- break
+ elseif offset == 0xFFFF then
+ -- bad encoding
+ elseif offset == 0 then
+ if trace_cmap_details then
+ report("format 4.%i segment %2i from %C upto %C at index %H",1,segment,startchar,endchar,(startchar + delta) % 65536)
+ end
+ for unicode=startchar,endchar do
+ local index = (unicode + delta) % 65536
+ if index and index > 0 then
+ local glyph = glyphs[index]
+ if glyph then
+ local gu = glyph.unicode
+ if not gu then
+ glyph.unicode = unicode
+ nofdone = nofdone + 1
+ elseif gu ~= unicode then
+ if duplicatestoo then
+ local d = duplicates[gu]
+ if d then
+ d[unicode] = true
+ else
+ duplicates[gu] = { [unicode] = true }
+ end
+ else
+ -- no duplicates ... weird side effects in lm
+ report("duplicate case 1: %C %04i %s",unicode,index,glyphs[index].name)
+ end
+ end
+ if not mapping[index] then
+ mapping[index] = unicode
+ end
+ end
+ end
+ end
+ else
+ local shift = (segment-nofsegments+offset/2) - startchar
+ if trace_cmap_details then
+ report_cmap("format 4.%i segment %2i from %C upto %C at index %H",0,segment,startchar,endchar,(startchar + delta) % 65536)
+ end
+ for unicode=startchar,endchar do
+ local slot = shift + unicode
+ local index = indices[slot]
+ if index and index > 0 then
+ index = (index + delta) % 65536
+ local glyph = glyphs[index]
+ if glyph then
+ local gu = glyph.unicode
+ if not gu then
+ glyph.unicode = unicode
+ nofdone = nofdone + 1
+ elseif gu ~= unicode then
+ if duplicatestoo then
+ local d = duplicates[gu]
+ if d then
+ d[unicode] = true
+ else
+ duplicates[gu] = { [unicode] = true }
+ end
+ else
+ -- no duplicates ... weird side effects in lm
+ report("duplicate case 2: %C %04i %s",unicode,index,glyphs[index].name)
+ end
+ end
+ if not mapping[index] then
+ mapping[index] = unicode
+ end
+ end
+ end
+ end
+ end
+ end
+ return nofdone
+end
+
+formatreaders[6] = function(f,fontdata,offset)
+ setposition(f,offset) -- + 2 + 2 + 2 -- skip format length language
+ local format = readushort(f)
+ local length = readushort(f)
+ local language = readushort(f)
+ local mapping = fontdata.mapping
+ local glyphs = fontdata.glyphs
+ local duplicates = fontdata.duplicates
+ local start = readushort(f)
+ local count = readushort(f)
+ local stop = start+count-1
+ local nofdone = 0
+ if trace_cmap_details then
+ report_cmap("format 6 from %C to %C",2,start,stop)
+ end
+ for unicode=start,stop do
+ local index = readushort(f)
+ if index > 0 then
+ local glyph = glyphs[index]
+ if glyph then
+ local gu = glyph.unicode
+ if not gu then
+ glyph.unicode = unicode
+ nofdone = nofdone + 1
+ elseif gu ~= unicode then
+ -- report("format 6 overloading %C to %C",gu,unicode)
+ -- glyph.unicode = unicode
+ -- no duplicates ... weird side effects in lm
+ end
+ if not mapping[index] then
+ mapping[index] = unicode
+ end
+ end
+ end
+ end
+ return nofdone
+end
+
+formatreaders[12] = function(f,fontdata,offset)
+ setposition(f,offset+2+2+4+4) -- skip format reserved length language
+ local mapping = fontdata.mapping
+ local glyphs = fontdata.glyphs
+ local duplicates = fontdata.duplicates
+ local nofgroups = readulong(f)
+ local nofdone = 0
+ for i=1,nofgroups do
+ local first = readulong(f)
+ local last = readulong(f)
+ local index = readulong(f)
+ if trace_cmap_details then
+ report_cmap("format 12 from %C to %C starts at index %i",first,last,index)
+ end
+ for unicode=first,last do
+ local glyph = glyphs[index]
+ if glyph then
+ local gu = glyph.unicode
+ if not gu then
+ glyph.unicode = unicode
+ nofdone = nofdone + 1
+ elseif gu ~= unicode then
+ -- e.g. sourcehan fonts need this
+ local d = duplicates[gu]
+ if d then
+ d[unicode] = true
+ else
+ duplicates[gu] = { [unicode] = true }
+ end
+ end
+ if not mapping[index] then
+ mapping[index] = unicode
+ end
+ end
+ index = index + 1
+ end
+ end
+ return nofdone
+end
+
+formatreaders[13] = function(f,fontdata,offset)
+ --
+ -- this vector is only used for simple fallback fonts
+ --
+ setposition(f,offset+2+2+4+4) -- skip format reserved length language
+ local mapping = fontdata.mapping
+ local glyphs = fontdata.glyphs
+ local duplicates = fontdata.duplicates
+ local nofgroups = readulong(f)
+ local nofdone = 0
+ for i=1,nofgroups do
+ local first = readulong(f)
+ local last = readulong(f)
+ local index = readulong(f)
+ if first < privateoffset then
+ if trace_cmap_details then
+ report_cmap("format 13 from %C to %C get index %i",first,last,index)
+ end
+ local glyph = glyphs[index]
+ local unicode = glyph.unicode
+ if not unicode then
+ unicode = first
+ glyph.unicode = unicode
+ first = first + 1
+ end
+ local list = duplicates[unicode]
+ mapping[index] = unicode
+ if not list then
+ list = { }
+ duplicates[unicode] = list
+ end
+ if last >= privateoffset then
+ local limit = privateoffset - 1
+ report("format 13 from %C to %C pruned to %C",first,last,limit)
+ last = limit
+ end
+ for unicode=first,last do
+ list[unicode] = true
+ end
+ nofdone = nofdone + last - first + 1
+ else
+ report("format 13 from %C to %C ignored",first,last)
+ end
+ end
+ return nofdone
+end
+
+formatreaders[14] = function(f,fontdata,offset)
+ if offset and offset ~= 0 then
+ setposition(f,offset)
+ local format = readushort(f)
+ local length = readulong(f)
+ local nofrecords = readulong(f)
+ local records = { }
+ local variants = { }
+ local nofdone = 0
+ fontdata.variants = variants
+ for i=1,nofrecords do
+ records[i] = {
+ selector = readuint(f),
+ default = readulong(f), -- default offset
+ other = readulong(f), -- non-default offset
+ }
+ end
+ for i=1,nofrecords do
+ local record = records[i]
+ local selector = record.selector
+ local default = record.default
+ local other = record.other
+ --
+ -- there is no need to map the defaults to themselves
+ --
+ -- if default ~= 0 then
+ -- setposition(f,offset+default)
+ -- local nofranges = readulong(f)
+ -- for i=1,nofranges do
+ -- local start = readuint(f)
+ -- local extra = readbyte(f)
+ -- for i=start,start+extra do
+ -- mapping[i] = i
+ -- end
+ -- end
+ -- end
+ local other = record.other
+ if other ~= 0 then
+ setposition(f,offset+other)
+ local mapping = { }
+ local count = readulong(f)
+ for i=1,count do
+ mapping[readuint(f)] = readushort(f)
+ end
+ nofdone = nofdone + count
+ variants[selector] = mapping
+ end
+ end
+ return nofdone
+ else
+ return 0
+ end
+end
+
+local function checkcmap(f,fontdata,records,platform,encoding,format)
+ local pdata = records[platform]
+ if not pdata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no platform",platform,encoding,format)
+ end
+ return 0
+ end
+ local edata = pdata[encoding]
+ if not edata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no encoding",platform,encoding,format)
+ end
+ return 0
+ end
+ local fdata = edata[format]
+ if not fdata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no format",platform,encoding,format)
+ end
+ return 0
+ elseif type(fdata) ~= "number" then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","already done",platform,encoding,format)
+ end
+ return 0
+ end
+ edata[format] = true -- done
+ local reader = formatreaders[format]
+ if not reader then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","unsupported format",platform,encoding,format)
+ end
+ return 0
+ end
+ local n = reader(f,fontdata,fdata) or 0
+ if trace_cmap_details or trace_cmap then
+ local p = platforms[platform]
+ local e = encodings[p]
+ report_cmap("checked, platform %i (%s), encoding %i (%s), format %i, new unicodes %i",
+ platform,p,encoding,e and e[encoding] or "?",format,n)
+ end
+ return n
+end
+
+function readers.cmap(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"cmap",specification.glyphs)
+ if tableoffset then
+ local version = readushort(f)
+ local noftables = readushort(f)
+ local records = { }
+ local unicodecid = false
+ local variantcid = false
+ local variants = { }
+ local duplicates = fontdata.duplicates or { }
+ fontdata.duplicates = duplicates
+ for i=1,noftables do
+ local platform = readushort(f)
+ local encoding = readushort(f)
+ local offset = readulong(f)
+ local record = records[platform]
+ if not record then
+ records[platform] = {
+ [encoding] = {
+ offsets = { offset },
+ formats = { },
+ }
+ }
+ else
+ local subtables = record[encoding]
+ if not subtables then
+ record[encoding] = {
+ offsets = { offset },
+ formats = { },
+ }
+ else
+ local offsets = subtables.offsets
+ offsets[#offsets+1] = offset
+ end
+ end
+ end
+ if trace_cmap then
+ report("found cmaps:")
+ end
+ for platform, record in sortedhash(records) do
+ local p = platforms[platform]
+ local e = encodings[p]
+ local sp = supported[platform]
+ local ps = p or "?"
+ if trace_cmap then
+ if sp then
+ report(" platform %i: %s",platform,ps)
+ else
+ report(" platform %i: %s (unsupported)",platform,ps)
+ end
+ end
+ for encoding, subtables in sortedhash(record) do
+ local se = sp and sp[encoding]
+ local es = e and e[encoding] or "?"
+ if trace_cmap then
+ if se then
+ report(" encoding %i: %s",encoding,es)
+ else
+ report(" encoding %i: %s (unsupported)",encoding,es)
+ end
+ end
+ local offsets = subtables.offsets
+ local formats = subtables.formats
+ for i=1,#offsets do
+ local offset = tableoffset + offsets[i]
+ setposition(f,offset)
+ formats[readushort(f)] = offset
+ end
+ record[encoding] = formats
+ if trace_cmap then
+ local list = sortedkeys(formats)
+ for i=1,#list do
+ if not (se and se[list[i]]) then
+ list[i] = list[i] .. " (unsupported)"
+ end
+ end
+ report(" formats: % t",list)
+ end
+ end
+ end
+ --
+ local ok = false
+ for i=1,#sequence do
+ local si = sequence[i]
+ local sp, se, sf = si[1], si[2], si[3]
+ if checkcmap(f,fontdata,records,sp,se,sf) > 0 then
+ ok = true
+ end
+ end
+ if not ok then
+ report("no useable unicode cmap found")
+ end
+ --
+ fontdata.cidmaps = {
+ version = version,
+ noftables = noftables,
+ records = records,
+ }
+ else
+ fontdata.cidmaps = { }
+ end
+end
+
+-- The glyf table depends on the loca table. We have one entry to much in the locations table (the
+-- last one is a dummy) because we need to calculate the size of a glyph blob from the delta,
+-- although we not need it in our usage (yet). We can remove the locations table when we're done.
+
+function readers.loca(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"loca",specification.glyphs)
+end
+
+function readers.glyf(f,fontdata,specification) -- part goes to cff module
+ reportskippedtable(f,fontdata,"glyf",specification.glyphs)
+end
+
+-- The MicroSoft variant is pretty clean and is supported (implemented elsewhere)
+-- just because I wanted to see how such a font looks like.
+
+function readers.colr(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"colr",specification.glyphs)
+end
+function readers.cpal(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cpal",specification.glyphs)
+end
+
+-- This one is also supported, if only because I could locate a proper font for
+-- testing.
+
+function readers.svg(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"svg",specification.glyphs)
+end
+
+-- There is a font from apple to test the next one. Will there be more? Anyhow,
+-- it's relatively easy to support, so I did it.
+
+function readers.sbix(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"sbix",specification.glyphs)
+end
+
+-- I'm only willing to look into the next variant if I see a decent and complete (!)
+-- font and more can show up. It makes no sense to waste time on ideas. Okay, the
+-- apple font also has these tables.
+
+function readers.cbdt(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cbdt",specification.glyphs)
+end
+function readers.cblc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cblc",specification.glyphs)
+end
+function readers.ebdt(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"ebdt",specification.glyphs)
+end
+function readers.ebsc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"ebsc",specification.glyphs)
+end
+function readers.eblc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"eblc",specification.glyphs)
+end
+
+-- Here we have a table that we really need for later processing although a more advanced gpos table
+-- can also be available. Todo: we need a 'fake' lookup for this (analogue to ff).
+
+function readers.kern(f,fontdata,specification)
+ local tableoffset = gotodatatable(f,fontdata,"kern",specification.kerns)
+ if tableoffset then
+ local version = readushort(f)
+ local noftables = readushort(f)
+ for i=1,noftables do
+ local version = readushort(f)
+ local length = readushort(f)
+ local coverage = readushort(f)
+ -- bit 8-15 of coverage: format 0 or 2
+ local format = rshift(coverage,8) -- is this ok?
+ if format == 0 then
+ local nofpairs = readushort(f)
+ local searchrange = readushort(f)
+ local entryselector = readushort(f)
+ local rangeshift = readushort(f)
+ local kerns = { }
+ local glyphs = fontdata.glyphs
+ for i=1,nofpairs do
+ local left = readushort(f)
+ local right = readushort(f)
+ local kern = readfword(f)
+ local glyph = glyphs[left]
+ local kerns = glyph.kerns
+ if kerns then
+ kerns[right] = kern
+ else
+ glyph.kerns = { [right] = kern }
+ end
+ end
+ elseif format == 2 then
+ report("todo: kern classes")
+ else
+ report("todo: kerns")
+ end
+ end
+ end
+end
+
+function readers.gdef(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gdef",specification.details)
+end
+
+function readers.gsub(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gsub",specification.details)
+end
+
+function readers.gpos(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gpos",specification.details)
+end
+
+function readers.math(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"math",specification.details)
+end
+
+-- Now comes the loader. The order of reading these matters as we need to know
+-- some properties in order to read following tables. When details is true we also
+-- initialize the glyphs data.
+
+local function getinfo(maindata,sub,platformnames,rawfamilynames,metricstoo,instancenames)
+ local fontdata = sub and maindata.subfonts and maindata.subfonts[sub] or maindata
+ local names = fontdata.names
+ local info = nil
+ if names then
+ local metrics = fontdata.windowsmetrics or { }
+ local postscript = fontdata.postscript or { }
+ local fontheader = fontdata.fontheader or { }
+ local cffinfo = fontdata.cffinfo or { }
+ local verticalheader = fontdata.verticalheader or { }
+ local filename = fontdata.filename
+ local weight = getname(fontdata,"weight") or (cffinfo and cffinfo.weight) or (metrics and metrics.weight)
+ local width = getname(fontdata,"width") or (cffinfo and cffinfo.width ) or (metrics and metrics.width )
+ local fontname = getname(fontdata,"postscriptname")
+ local fullname = getname(fontdata,"fullname")
+ local family = getname(fontdata,"family")
+ local subfamily = getname(fontdata,"subfamily")
+ local familyname = getname(fontdata,"typographicfamily")
+ local subfamilyname = getname(fontdata,"typographicsubfamily")
+ local compatiblename = getname(fontdata,"compatiblefullname") -- kind of useless
+ if rawfamilynames then
+ -- for PG (for now, as i need to check / adapt context to catch a no-fallback case)
+ else
+ if not familyname then familyname = family end
+ if not subfamilyname then subfamilyname = subfamily end
+ end
+ if platformnames then
+ platformnames = fontdata.platformnames
+ end
+ if instancenames then
+ local variabledata = fontdata.variabledata
+ if variabledata then
+ local instances = variabledata and variabledata.instances
+ if instances then
+ instancenames = { }
+ for i=1,#instances do
+ instancenames[i] = lower(stripstring(instances[i].subfamily))
+ end
+ else
+ instancenames = nil
+ end
+ else
+ instancenames = nil
+ end
+ end
+ info = { -- we inherit some inconsistencies/choices from ff
+ subfontindex = fontdata.subfontindex or sub or 0,
+ -- filename = filename,
+ version = getname(fontdata,"version"),
+ -- format = fontdata.format,
+ fontname = fontname,
+ fullname = fullname,
+ -- cfffullname = cff.fullname,
+ family = family,
+ subfamily = subfamily,
+ familyname = familyname,
+ subfamilyname = subfamilyname,
+ compatiblename = compatiblename,
+ weight = weight and lower(weight),
+ width = width and lower(width),
+ pfmweight = metrics.weightclass or 400, -- will become weightclass
+ pfmwidth = metrics.widthclass or 5, -- will become widthclass
+ panosewidth = metrics.panosewidth,
+ panoseweight = metrics.panoseweight,
+ italicangle = postscript.italicangle or 0,
+ units = fontheader.units or 0,
+ designsize = fontdata.designsize,
+ minsize = fontdata.minsize,
+ maxsize = fontdata.maxsize,
+ boundingbox = fontheader and { fontheader.xmin or 0, fontheader.ymin or 0, fontheader.xmax or 0, fontheader.ymax or 0 } or nil,
+ monospaced = (tonumber(postscript.monospaced or 0) > 0) or metrics.panosewidth == "monospaced",
+ averagewidth = metrics.averagewidth,
+ xheight = metrics.xheight, -- can be missing
+ capheight = metrics.capheight or fontdata.maxy, -- can be missing
+ ascender = metrics.typoascender,
+ descender = metrics.typodescender,
+ platformnames = platformnames or nil,
+ instancenames = instancenames or nil,
+ tableoffsets = fontdata.tableoffsets,
+ defaultvheight = (verticalheader.ascender or 0) - (verticalheader.descender or 0)
+ }
+ if metricstoo then
+ local keys = {
+ "version",
+ "ascender", "descender", "linegap",
+ -- "caretoffset", "caretsloperise", "caretsloperun",
+ "maxadvancewidth", "maxadvanceheight", "maxextent",
+ -- "metricdataformat",
+ "minbottomsidebearing", "mintopsidebearing",
+ }
+ local h = fontdata.horizontalheader or { }
+ local v = fontdata.verticalheader or { }
+ if h then
+ local th = { }
+ local tv = { }
+ for i=1,#keys do
+ local key = keys[i]
+ th[key] = h[key] or 0
+ tv[key] = v[key] or 0
+ end
+ info.horizontalmetrics = th
+ info.verticalmetrics = tv
+ end
+ end
+ elseif n then
+ info = {
+ filename = fontdata.filename,
+ comment = "there is no info for subfont " .. n,
+ }
+ else
+ info = {
+ filename = fontdata.filename,
+ comment = "there is no info",
+ }
+ end
+ -- inspect(info)
+ return info
+end
+
+local function loadtables(f,specification,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ local tables = { }
+ local basename = file.basename(specification.filename)
+ local filesize = specification.filesize
+ local filetime = specification.filetime
+ local fontdata = { -- some can/will go
+ filename = basename,
+ filesize = filesize,
+ filetime = filetime,
+ version = readstring(f,4),
+ noftables = readushort(f),
+ searchrange = readushort(f), -- not needed
+ entryselector = readushort(f), -- not needed
+ rangeshift = readushort(f), -- not needed
+ tables = tables,
+ foundtables = false,
+ }
+ for i=1,fontdata.noftables do
+ local tag = lower(stripstring(readstring(f,4)))
+ -- local checksum = readulong(f) -- not used
+ local checksum = readushort(f) * 0x10000 + readushort(f)
+ local offset = readulong(f)
+ local length = readulong(f)
+ if offset + length > filesize then
+ report("bad %a table in file %a",tag,basename)
+ end
+ tables[tag] = {
+ checksum = checksum,
+ offset = offset,
+ length = length,
+ }
+ end
+-- inspect(tables)
+ fontdata.foundtables = sortedkeys(tables)
+ if tables.cff or tables.cff2 then
+ fontdata.format = "opentype"
+ else
+ fontdata.format = "truetype"
+ end
+ return fontdata, tables
+end
+
+local function prepareglyps(fontdata)
+ local glyphs = setmetatableindex(function(t,k)
+ local v = {
+ -- maybe more defaults
+ index = k,
+ }
+ t[k] = v
+ return v
+ end)
+ fontdata.glyphs = glyphs
+ fontdata.mapping = { }
+end
+
+local function readtable(tag,f,fontdata,specification,...)
+ local reader = readers[tag]
+ if reader then
+ reader(f,fontdata,specification,...)
+ end
+end
+
+local variablefonts_supported = (context and true) or (logs and logs.application and true) or false
+
+local function readdata(f,offset,specification)
+
+ local fontdata, tables = loadtables(f,specification,offset)
+
+ if specification.glyphs then
+ prepareglyps(fontdata)
+ end
+
+ if not variablefonts_supported then
+ specification.instance = nil
+ specification.variable = nil
+ specification.factors = nil
+ end
+
+ fontdata.temporary = { }
+
+ readtable("name",f,fontdata,specification)
+
+ local askedname = specification.askedname
+ if askedname then
+ local fullname = getname(fontdata,"fullname") or ""
+ local cleanname = gsub(askedname,"[^a-zA-Z0-9]","")
+ local foundname = gsub(fullname,"[^a-zA-Z0-9]","")
+ if lower(cleanname) ~= lower(foundname) then
+ return -- keep searching
+ end
+ end
+
+ readtable("stat",f,fontdata,specification)
+ readtable("avar",f,fontdata,specification)
+ readtable("fvar",f,fontdata,specification)
+
+ if variablefonts_supported then
+
+ local variabledata = fontdata.variabledata
+
+ if variabledata then
+ local instances = variabledata.instances
+ local axis = variabledata.axis
+ if axis and (not instances or #instances == 0) then
+ instances = { }
+ variabledata.instances = instances
+ local function add(n,subfamily,value)
+ local values = { }
+ for i=1,#axis do
+ local a = axis[i]
+ values[i] = {
+ axis = a.tag,
+ value = i == n and value or a.default,
+ }
+ end
+ instances[#instances+1] = {
+ subfamily = subfamily,
+ values = values,
+ }
+ end
+ for i=1,#axis do
+ local a = axis[i]
+ local tag = a.tag
+ add(i,"default"..tag,a.default)
+ add(i,"minimum"..tag,a.minimum)
+ add(i,"maximum"..tag,a.maximum)
+ end
+ -- report("%i fake instances added",#instances)
+ end
+ end
+
+ if not specification.factors then
+ local instance = specification.instance
+ if type(instance) == "string" then
+ local factors = helpers.getfactors(fontdata,instance)
+ if factors then
+ specification.factors = factors
+ fontdata.factors = factors
+ fontdata.instance = instance
+ report("user instance: %s, factors: % t",instance,factors)
+ else
+ report("user instance: %s, bad factors",instance)
+ end
+ end
+ end
+
+ if not fontdata.factors then
+ if fontdata.variabledata then
+ local factors = helpers.getfactors(fontdata,true)
+ if factors then
+ specification.factors = factors
+ fontdata.factors = factors
+ -- report("factors: % t",factors)
+ -- else
+ -- report("bad factors")
+ end
+ else
+ -- report("unknown instance")
+ end
+ end
+
+ end
+
+ readtable("os/2",f,fontdata,specification)
+ readtable("head",f,fontdata,specification)
+ readtable("maxp",f,fontdata,specification)
+ readtable("hhea",f,fontdata,specification)
+ readtable("vhea",f,fontdata,specification)
+ readtable("hmtx",f,fontdata,specification)
+ readtable("vmtx",f,fontdata,specification)
+ readtable("vorg",f,fontdata,specification)
+ readtable("post",f,fontdata,specification)
+
+ readtable("mvar",f,fontdata,specification)
+ readtable("hvar",f,fontdata,specification)
+ readtable("vvar",f,fontdata,specification)
+
+ readtable("gdef",f,fontdata,specification)
+
+ readtable("cff" ,f,fontdata,specification)
+ readtable("cff2",f,fontdata,specification)
+
+ readtable("cmap",f,fontdata,specification)
+ readtable("loca",f,fontdata,specification) -- maybe load it in glyf
+ readtable("glyf",f,fontdata,specification) -- loads gvar
+
+ readtable("colr",f,fontdata,specification)
+ readtable("cpal",f,fontdata,specification)
+
+ readtable("svg" ,f,fontdata,specification)
+
+ readtable("sbix",f,fontdata,specification)
+
+ readtable("cbdt",f,fontdata,specification)
+ readtable("cblc",f,fontdata,specification)
+ readtable("ebdt",f,fontdata,specification)
+ readtable("eblc",f,fontdata,specification)
+
+ readtable("kern",f,fontdata,specification)
+ readtable("gsub",f,fontdata,specification)
+ readtable("gpos",f,fontdata,specification)
+
+ readtable("math",f,fontdata,specification)
+
+ fontdata.locations = nil
+ fontdata.cidmaps = nil
+ fontdata.dictionaries = nil
+ -- fontdata.cff = nil
+
+ if specification.tableoffsets then
+ fontdata.tableoffsets = tables
+ setmetatableindex(tables, {
+ version = fontdata.version,
+ noftables = fontdata.noftables,
+ searchrange = fontdata.searchrange,
+ entryselector = fontdata.entryselector,
+ rangeshift = fontdata.rangeshift,
+ })
+ end
+ return fontdata
+end
+
+local function loadfontdata(specification)
+ local filename = specification.filename
+ local fileattr = lfs.attributes(filename)
+ local filesize = fileattr and fileattr.size or 0
+ local filetime = fileattr and fileattr.modification or 0
+ local f = openfile(filename,true) -- zero based
+ if not f then
+ report("unable to open %a",filename)
+ elseif filesize == 0 then
+ report("empty file %a",filename)
+ closefile(f)
+ else
+ specification.filesize = filesize
+ specification.filetime = filetime
+ local version = readstring(f,4)
+ local fontdata = nil
+ if version == "OTTO" or version == "true" or version == "\0\1\0\0" then
+ fontdata = readdata(f,0,specification)
+ elseif version == "ttcf" then
+ local subfont = tonumber(specification.subfont)
+ local ttcversion = readulong(f)
+ local nofsubfonts = readulong(f)
+ local offsets = readcardinaltable(f,nofsubfonts,ulong)
+ if subfont then -- a number of not
+ if subfont >= 1 and subfont <= nofsubfonts then
+ fontdata = readdata(f,offsets[subfont],specification)
+ else
+ report("no subfont %a in file %a",subfont,filename)
+ end
+ else
+ subfont = specification.subfont
+ if type(subfont) == "string" and subfont ~= "" then
+ specification.askedname = subfont
+ for i=1,nofsubfonts do
+ fontdata = readdata(f,offsets[i],specification)
+ if fontdata then
+ fontdata.subfontindex = i
+ report("subfont named %a has index %a",subfont,i)
+ break
+ end
+ end
+ if not fontdata then
+ report("no subfont named %a",subfont)
+ end
+ else
+ local subfonts = { }
+ fontdata = {
+ filename = filename,
+ filesize = filesize,
+ filetime = filetime,
+ version = version,
+ subfonts = subfonts,
+ ttcversion = ttcversion,
+ nofsubfonts = nofsubfonts,
+ }
+ for i=1,nofsubfonts do
+ subfonts[i] = readdata(f,offsets[i],specification)
+ end
+ end
+ end
+ else
+ report("unknown version %a in file %a",version,filename)
+ end
+ closefile(f)
+ return fontdata or { }
+ end
+end
+
+local function loadfont(specification,n,instance)
+ if type(specification) == "string" then
+ specification = {
+ filename = specification,
+ info = true, -- always true (for now)
+ details = true,
+ glyphs = true,
+ shapes = true,
+ kerns = true,
+ variable = true,
+ globalkerns = true,
+ lookups = true,
+ -- true or number:
+ subfont = n or true,
+ tounicode = false,
+ instance = instance
+ }
+ end
+ -- if shapes only then
+ if specification.shapes or specification.lookups or specification.kerns then
+ specification.glyphs = true
+ end
+ if specification.glyphs then
+ specification.details = true
+ end
+ if specification.details then
+ specification.info = true -- not really used any more
+ end
+ if specification.platformnames then
+ specification.platformnames = true -- not really used any more
+ end
+ if specification.instance or instance then
+ specification.variable = true
+ specification.instance = specification.instance or instance
+ end
+ local function message(str)
+ report("fatal error in file %a: %s\n%s",specification.filename,str,debug and debug.traceback())
+ end
+ local ok, result = xpcall(loadfontdata,message,specification)
+ if ok then
+ return result
+ end
+-- return loadfontdata(specification)
+end
+
+-- we need even less, but we can have a 'detail' variant
+
+function readers.loadshapes(filename,n,instance,streams)
+ local fontdata = loadfont {
+ filename = filename,
+ shapes = true,
+ streams = streams,
+ variable = true,
+ subfont = n,
+ instance = instance,
+ }
+ if fontdata then
+ -- easier on luajit but still we can hit the 64 K stack constants issue
+ for k, v in next, fontdata.glyphs do
+ v.class = nil
+ v.index = nil
+ v.math = nil
+ -- v.name = nil
+ end
+ local names = fontdata.names
+ if names then
+ for k, v in next, names do
+ names[k] = fullstrip(v.content)
+ end
+ end
+ end
+ return fontdata and {
+ -- version = 0.123 -- todo
+ filename = filename,
+ format = fontdata.format,
+ glyphs = fontdata.glyphs,
+ units = fontdata.fontheader.units,
+ cffinfo = fontdata.cffinfo,
+ fontheader = fontdata.fontheader,
+ horizontalheader = fontdata.horizontalheader,
+ verticalheader = fontdata.verticalheader,
+ maximumprofile = fontdata.maximumprofile,
+ names = fontdata.names,
+ postscript = fontdata.postscript,
+ } or {
+ filename = filename,
+ format = "unknown",
+ glyphs = { },
+ units = 0,
+ }
+end
+
+function readers.loadfont(filename,n,instance)
+ local fontdata = loadfont {
+ filename = filename,
+ glyphs = true,
+ shapes = false,
+ lookups = true,
+ variable = true,
+ -- kerns = true,
+ -- globalkerns = true, -- only for testing, e.g. cambria has different gpos and kern
+ subfont = n,
+ instance = instance,
+ }
+ if fontdata then
+ return {
+ tableversion = tableversion,
+ creator = "context mkiv",
+ size = fontdata.filesize,
+ time = fontdata.filetime,
+ glyphs = fontdata.glyphs,
+ descriptions = fontdata.descriptions,
+ format = fontdata.format,
+ goodies = { },
+ metadata = getinfo(fontdata,n,false,false,true,true), -- no platformnames here !
+ properties = {
+ hasitalics = fontdata.hasitalics or false,
+ maxcolorclass = fontdata.maxcolorclass,
+ hascolor = fontdata.hascolor or false,
+ instance = fontdata.instance,
+ factors = fontdata.factors,
+ },
+ resources = {
+ -- filename = fontdata.filename,
+ filename = filename,
+ private = privateoffset,
+ duplicates = fontdata.duplicates or { },
+ features = fontdata.features or { }, -- we need to add these in the loader
+ sublookups = fontdata.sublookups or { }, -- we need to add these in the loader
+ marks = fontdata.marks or { }, -- we need to add these in the loader
+ markclasses = fontdata.markclasses or { }, -- we need to add these in the loader
+ marksets = fontdata.marksets or { }, -- we need to add these in the loader
+ sequences = fontdata.sequences or { }, -- we need to add these in the loader
+ variants = fontdata.variants, -- variant -> unicode -> glyph
+ version = getname(fontdata,"version"),
+ cidinfo = fontdata.cidinfo,
+ mathconstants = fontdata.mathconstants,
+ colorpalettes = fontdata.colorpalettes,
+ svgshapes = fontdata.svgshapes,
+ pngshapes = fontdata.pngshapes,
+ variabledata = fontdata.variabledata,
+ foundtables = fontdata.foundtables,
+ },
+ }
+ end
+end
+
+function readers.getinfo(filename,specification) -- string, nil|number|table
+ -- platformnames is optional and not used by context (a too unpredictable mess
+ -- that only add to the confusion) .. so it's only for checking things
+ local subfont = nil
+ local platformnames = false
+ local rawfamilynames = false
+ local instancenames = true
+ local tableoffsets = false
+ if type(specification) == "table" then
+ subfont = tonumber(specification.subfont)
+ platformnames = specification.platformnames
+ rawfamilynames = specification.rawfamilynames
+ tableoffsets = specification.tableoffsets
+ else
+ subfont = tonumber(specification)
+ end
+ local fontdata = loadfont {
+ filename = filename,
+ details = true,
+ platformnames = platformnames,
+ instancenames = true,
+ tableoffsets = tableoffsets,
+ -- rawfamilynames = rawfamilynames,
+ }
+ if fontdata then
+ local subfonts = fontdata.subfonts
+ if not subfonts then
+ return getinfo(fontdata,nil,platformnames,rawfamilynames,false,instancenames)
+ elseif not subfont then
+ local info = { }
+ for i=1,#subfonts do
+ info[i] = getinfo(fontdata,i,platformnames,rawfamilynames,false,instancenames)
+ end
+ return info
+ elseif subfont >= 1 and subfont <= #subfonts then
+ return getinfo(fontdata,subfont,platformnames,rawfamilynames,false,instancenames)
+ else
+ return {
+ filename = filename,
+ comment = "there is no subfont " .. subfont .. " in this file"
+ }
+ end
+ else
+ return {
+ filename = filename,
+ comment = "the file cannot be opened for reading",
+ }
+ end
+end
+
+function readers.rehash(fontdata,hashmethod)
+ report("the %a helper is not yet implemented","rehash")
+end
+
+function readers.checkhash(fontdata)
+ report("the %a helper is not yet implemented","checkhash")
+end
+
+function readers.pack(fontdata,hashmethod)
+ report("the %a helper is not yet implemented","pack")
+end
+
+function readers.unpack(fontdata)
+ report("the %a helper is not yet implemented","unpack")
+end
+
+function readers.expand(fontdata)
+ report("the %a helper is not yet implemented","unpack")
+end
+
+function readers.compact(fontdata)
+ report("the %a helper is not yet implemented","compact")
+end
+
+-- plug in
+
+local extenders = { }
+
+function readers.registerextender(extender)
+ extenders[#extenders+1] = extender
+end
+
+function readers.extend(fontdata)
+ for i=1,#extenders do
+ local extender = extenders[i]
+ local name = extender.name or "unknown"
+ local action = extender.action
+ if action then
+ action(fontdata)
+ end
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-ots.lua b/macros/luatex/generic/luaotfload/fontloader-font-ots.lua
new file mode 100644
index 0000000000..6313022006
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-ots.lua
@@ -0,0 +1,4492 @@
+if not modules then modules = { } end modules ['font-ots'] = { -- sequences
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files",
+}
+
+--[[ldx--
+<p>This module is a bit more split up that I'd like but since we also want to test
+with plain <l n='tex'/> it has to be so. This module is part of <l n='context'/>
+and discussion about improvements and functionality mostly happens on the
+<l n='context'/> mailing list.</p>
+
+<p>The specification of OpenType is (or at least a decade ago was) kind of vague.
+Apart from a lack of a proper free specifications there's also the problem that
+Microsoft and Adobe may have their own interpretation of how and in what order to
+apply features. In general the Microsoft website has more detailed specifications
+and is a better reference. There is also some information in the FontForge help
+files. In the end we rely most on the Microsoft specification.</p>
+
+<p>Because there is so much possible, fonts might contain bugs and/or be made to
+work with certain rederers. These may evolve over time which may have the side
+effect that suddenly fonts behave differently. We don't want to catch all font
+issues.</p>
+
+<p>After a lot of experiments (mostly by Taco, me and Idris) the first implementation
+becaus quite useful. When it did most of what we wanted, a more optimized version
+evolved. Of course all errors are mine and of course the code can be improved. There
+are quite some optimizations going on here and processing speed is currently quite
+acceptable and has been improved over time. Many complex scripts are not yet supported
+yet, but I will look into them as soon as <l n='context'/> users ask for it.</p>
+
+<p>The specification leaves room for interpretation. In case of doubt the Microsoft
+implementation is the reference as it is the most complete one. As they deal with
+lots of scripts and fonts, Kai and Ivo did a lot of testing of the generic code and
+their suggestions help improve the code. I'm aware that not all border cases can be
+taken care of, unless we accept excessive runtime, and even then the interference
+with other mechanisms (like hyphenation) are not trivial.</p>
+
+<p>Especially discretionary handling has been improved much by Kai Eigner who uses complex
+(latin) fonts. The current implementation is a compromis between his patches and my code
+and in the meantime performance is quite ok. We cannot check all border cases without
+compromising speed but so far we're okay. Given good test cases we can probably improve
+it here and there. Especially chain lookups are non trivial with discretionaries but
+things got much better over time thanks to Kai.</p>
+
+<p>Glyphs are indexed not by unicode but in their own way. This is because there is no
+relationship with unicode at all, apart from the fact that a font might cover certain
+ranges of characters. One character can have multiple shapes. However, at the
+<l n='tex'/> end we use unicode so and all extra glyphs are mapped into a private
+space. This is needed because we need to access them and <l n='tex'/> has to include
+then in the output eventually.</p>
+
+<p>The initial data table is rather close to the open type specification and also not
+that different from the one produced by <l n='fontforge'/> but we uses hashes instead.
+In <l n='context'/> that table is packed (similar tables are shared) and cached on disk
+so that successive runs can use the optimized table (after loading the table is
+unpacked).</p>
+
+<p>This module is sparsely documented because it is has been a moving target. The
+table format of the reader changed a bit over time and we experiment a lot with
+different methods for supporting features. By now the structures are quite stable</p>
+
+<p>Incrementing the version number will force a re-cache. We jump the number by one
+when there's a fix in the reader or processing code that can result in different
+results.</p>
+
+<p>This code is also used outside context but in context it has to work with other
+mechanisms. Both put some constraints on the code here.</p>
+
+--ldx]]--
+
+-- Remark: We assume that cursives don't cross discretionaries which is okay because it
+-- is only used in semitic scripts.
+--
+-- Remark: We assume that marks precede base characters.
+--
+-- Remark: When complex ligatures extend into discs nodes we can get side effects. Normally
+-- this doesn't happen; ff\d{l}{l}{l} in lm works but ff\d{f}{f}{f}.
+--
+-- Todo: check if we copy attributes to disc nodes if needed.
+--
+-- Todo: it would be nice if we could get rid of components. In other places we can use
+-- the unicode properties. We can just keep a lua table.
+--
+-- Remark: We do some disc juggling where we need to keep in mind that the pre, post and
+-- replace fields can have prev pointers to a nesting node ... I wonder if that is still
+-- needed.
+--
+-- Remark: This is not possible:
+--
+-- \discretionary {alpha-} {betagammadelta}
+-- {\discretionary {alphabeta-} {gammadelta}
+-- {\discretionary {alphabetagamma-} {delta}
+-- {alphabetagammadelta}}}
+--
+-- Remark: Something is messed up: we have two mark / ligature indices, one at the
+-- injection end and one here ... this is based on KE's patches but there is something
+-- fishy there as I'm pretty sure that for husayni we need some connection (as it's much
+-- more complex than an average font) but I need proper examples of all cases, not of
+-- only some.
+--
+-- Remark: I wonder if indexed would be faster than unicoded. It would be a major
+-- rewrite to have char being unicode + an index field in glyph nodes. Also more
+-- assignments have to be made in order to keep things in sync. So, it's a no-go.
+--
+-- Remark: We can provide a fast loop when there are no disc nodes (tests show a 1%
+-- gain). Smaller functions might perform better cache-wise. But ... memory becomes
+-- faster anyway, so ...
+--
+-- Remark: Some optimizations made sense for 5.2 but seem less important for 5.3 but
+-- anyway served their purpose.
+--
+-- Todo: just (0=l2r and 1=r2l) or maybe (r2l = true)
+
+local type, next, tonumber = type, next, tonumber
+local random = math.random
+local formatters = string.formatters
+local insert = table.insert
+
+local registertracker = trackers.register
+
+local logs = logs
+local trackers = trackers
+local nodes = nodes
+local attributes = attributes
+local fonts = fonts
+
+local otf = fonts.handlers.otf
+local tracers = nodes.tracers
+
+local trace_singles = false registertracker("otf.singles", function(v) trace_singles = v end)
+local trace_multiples = false registertracker("otf.multiples", function(v) trace_multiples = v end)
+local trace_alternatives = false registertracker("otf.alternatives", function(v) trace_alternatives = v end)
+local trace_ligatures = false registertracker("otf.ligatures", function(v) trace_ligatures = v end)
+local trace_contexts = false registertracker("otf.contexts", function(v) trace_contexts = v end)
+local trace_marks = false registertracker("otf.marks", function(v) trace_marks = v end)
+local trace_kerns = false registertracker("otf.kerns", function(v) trace_kerns = v end)
+local trace_cursive = false registertracker("otf.cursive", function(v) trace_cursive = v end)
+local trace_preparing = false registertracker("otf.preparing", function(v) trace_preparing = v end)
+local trace_bugs = false registertracker("otf.bugs", function(v) trace_bugs = v end)
+local trace_details = false registertracker("otf.details", function(v) trace_details = v end)
+local trace_steps = false registertracker("otf.steps", function(v) trace_steps = v end)
+local trace_skips = false registertracker("otf.skips", function(v) trace_skips = v end)
+local trace_plugins = false registertracker("otf.plugins", function(v) trace_plugins = v end)
+local trace_chains = false registertracker("otf.chains", function(v) trace_chains = v end)
+
+local trace_kernruns = false registertracker("otf.kernruns", function(v) trace_kernruns = v end)
+----- trace_discruns = false registertracker("otf.discruns", function(v) trace_discruns = v end)
+local trace_compruns = false registertracker("otf.compruns", function(v) trace_compruns = v end)
+local trace_testruns = false registertracker("otf.testruns", function(v) trace_testruns = v end)
+
+local forcediscretionaries = false
+local forcepairadvance = false -- for testing
+
+directives.register("otf.forcediscretionaries",function(v)
+ forcediscretionaries = v
+end)
+
+directives.register("otf.forcepairadvance",function(v)
+ forcepairadvance = v
+end)
+
+local report_direct = logs.reporter("fonts","otf direct")
+local report_subchain = logs.reporter("fonts","otf subchain")
+local report_chain = logs.reporter("fonts","otf chain")
+local report_process = logs.reporter("fonts","otf process")
+local report_warning = logs.reporter("fonts","otf warning")
+local report_run = logs.reporter("fonts","otf run")
+
+registertracker("otf.substitutions", "otf.singles","otf.multiples","otf.alternatives","otf.ligatures")
+registertracker("otf.positions", "otf.marks","otf.kerns","otf.cursive")
+registertracker("otf.actions", "otf.substitutions","otf.positions")
+registertracker("otf.sample", "otf.steps","otf.substitutions","otf.positions","otf.analyzing")
+registertracker("otf.sample.silent", "otf.steps=silent","otf.substitutions","otf.positions","otf.analyzing")
+
+local nuts = nodes.nuts
+
+local getfield = nuts.getfield
+local getnext = nuts.getnext
+local setnext = nuts.setnext
+local getprev = nuts.getprev
+local setprev = nuts.setprev
+local getboth = nuts.getboth
+local setboth = nuts.setboth
+local getid = nuts.getid
+local getprop = nuts.getprop
+local setprop = nuts.setprop
+local getsubtype = nuts.getsubtype
+local setsubtype = nuts.setsubtype
+local getchar = nuts.getchar
+local setchar = nuts.setchar
+local getdisc = nuts.getdisc
+local setdisc = nuts.setdisc
+local setlink = nuts.setlink
+local getcomponents = nuts.getcomponents -- the original one, not yet node-aux
+local setcomponents = nuts.setcomponents -- the original one, not yet node-aux
+local getwidth = nuts.getwidth
+local getattr = nuts.getattr
+
+local getglyphdata = nuts.getglyphdata
+
+local ischar = nuts.ischar
+local isglyph = nuts.isglyph
+local usesfont = nuts.uses_font
+
+local insert_node_after = nuts.insert_after
+local copy_node = nuts.copy
+local copy_node_list = nuts.copy_list
+local remove_node = nuts.remove
+local find_node_tail = nuts.tail
+local flush_node_list = nuts.flush_list
+local flush_node = nuts.flush_node
+local end_of_math = nuts.end_of_math
+
+local setmetatable = setmetatable
+local setmetatableindex = table.setmetatableindex
+
+local nextnode = nuts.traversers.node
+
+----- zwnj = 0x200C
+----- zwj = 0x200D
+
+local nodecodes = nodes.nodecodes
+local glyphcodes = nodes.glyphcodes
+local disccodes = nodes.disccodes
+
+local glyph_code = nodecodes.glyph
+local glue_code = nodecodes.glue
+local disc_code = nodecodes.disc
+local math_code = nodecodes.math
+local dir_code = nodecodes.dir
+local localpar_code = nodecodes.localpar
+
+local discretionarydisc_code = disccodes.discretionary
+local ligatureglyph_code = glyphcodes.ligature
+
+local a_state = attributes.private('state')
+local a_noligature = attributes.private("noligature")
+
+local injections = nodes.injections
+local setmark = injections.setmark
+local setcursive = injections.setcursive
+local setkern = injections.setkern
+local setmove = injections.setmove
+local setposition = injections.setposition
+local resetinjection = injections.reset
+local copyinjection = injections.copy
+local setligaindex = injections.setligaindex
+local getligaindex = injections.getligaindex
+
+local fontdata = fonts.hashes.identifiers
+local fontfeatures = fonts.hashes.features
+
+local otffeatures = fonts.constructors.features.otf
+local registerotffeature = otffeatures.register
+
+local onetimemessage = fonts.loggers.onetimemessage or function() end
+
+local getrandom = utilities and utilities.randomizer and utilities.randomizer.get
+
+otf.defaultnodealternate = "none" -- first last
+
+-- We use a few semi-global variables. The handler can be called nested but this assumes
+-- that the same font is used.
+
+local tfmdata = false
+local characters = false
+local descriptions = false
+local marks = false
+local classes = false
+local currentfont = false
+local factor = 0
+local threshold = 0
+local checkmarks = false
+
+local discs = false
+local spaces = false
+
+local sweepnode = nil
+local sweephead = { } -- we don't nil entries but false them (no collection and such)
+
+local notmatchpre = { } -- to be checked: can we use false instead of nil / what if a == b tests
+local notmatchpost = { } -- to be checked: can we use false instead of nil / what if a == b tests
+local notmatchreplace = { } -- to be checked: can we use false instead of nil / what if a == b tests
+
+local handlers = { }
+
+local isspace = injections.isspace
+local getthreshold = injections.getthreshold
+
+local checkstep = (tracers and tracers.steppers.check) or function() end
+local registerstep = (tracers and tracers.steppers.register) or function() end
+local registermessage = (tracers and tracers.steppers.message) or function() end
+
+-- local function checkdisccontent(d)
+-- local pre, post, replace = getdisc(d)
+-- if pre then for n in traverse_id(glue_code,pre) do report("pre: %s",nodes.idstostring(pre)) break end end
+-- if post then for n in traverse_id(glue_code,post) do report("pos: %s",nodes.idstostring(post)) break end end
+-- if replace then for n in traverse_id(glue_code,replace) do report("rep: %s",nodes.idstostring(replace)) break end end
+-- end
+
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps == "silent" then
+ return
+ end
+ end
+ report_direct(...)
+end
+
+local function logwarning(...)
+ report_direct(...)
+end
+
+local gref do
+
+ local f_unicode = formatters["U+%X"] -- was ["%U"]
+ local f_uniname = formatters["U+%X (%s)"] -- was ["%U (%s)"]
+ local f_unilist = formatters["% t"]
+
+ gref = function(n) -- currently the same as in font-otb
+ if type(n) == "number" then
+ local description = descriptions[n]
+ local name = description and description.name
+ if name then
+ return f_uniname(n,name)
+ else
+ return f_unicode(n)
+ end
+ elseif n then
+ local t = { }
+ for i=1,#n do
+ local ni = n[i]
+ if tonumber(ni) then -- later we will start at 2
+ local di = descriptions[ni]
+ local nn = di and di.name
+ if nn then
+ t[#t+1] = f_uniname(ni,nn)
+ else
+ t[#t+1] = f_unicode(ni)
+ end
+ end
+ end
+ return f_unilist(t)
+ else
+ return "<error in node mode tracing>"
+ end
+ end
+
+end
+
+local function cref(dataset,sequence,index)
+ if not dataset then
+ return "no valid dataset"
+ end
+ local merged = sequence.merged and "merged " or ""
+ if index then
+ return formatters["feature %a, type %a, %schain lookup %a, index %a"](
+ dataset[4],sequence.type,merged,sequence.name,index)
+ else
+ return formatters["feature %a, type %a, %schain lookup %a"](
+ dataset[4],sequence.type,merged,sequence.name)
+ end
+end
+
+local function pref(dataset,sequence)
+ return formatters["feature %a, type %a, %slookup %a"](
+ dataset[4],sequence.type,sequence.merged and "merged " or "",sequence.name)
+end
+
+local function mref(rlmode)
+ if not rlmode or rlmode >= 0 then
+ return "l2r"
+ else
+ return "r2l"
+ end
+end
+
+-- The next code is somewhat complicated by the fact that some fonts can have ligatures made
+-- from ligatures that themselves have marks. This was identified by Kai in for instance
+-- arabtype: KAF LAM SHADDA ALEF FATHA (0x0643 0x0644 0x0651 0x0627 0x064E). This becomes
+-- KAF LAM-ALEF with a SHADDA on the first and a FATHA op de second component. In a next
+-- iteration this becomes a KAF-LAM-ALEF with a SHADDA on the second and a FATHA on the
+-- third component.
+
+-- We can assume that languages that use marks are not hyphenated. We can also assume
+-- that at most one discretionary is present.
+
+-- We do need components in funny kerning mode but maybe I can better reconstruct then
+-- as we do have the font components info available; removing components makes the
+-- previous code much simpler. Also, later on copying and freeing becomes easier.
+-- However, for arabic we need to keep them around for the sake of mark placement
+-- and indices.
+
+local function flattendisk(head,disc)
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(disc,true)
+ local prev, next = getboth(disc)
+ local ishead = head == disc
+ setdisc(disc)
+ flush_node(disc)
+ if pre then
+ flush_node_list(pre)
+ end
+ if post then
+ flush_node_list(post)
+ end
+ if ishead then
+ if replace then
+ if next then
+ setlink(replacetail,next)
+ end
+ return replace, replace
+ elseif next then
+ return next, next
+ else
+ -- return -- maybe warning
+ end
+ else
+ if replace then
+ if next then
+ setlink(replacetail,next)
+ end
+ setlink(prev,replace)
+ return head, replace
+ else
+ setlink(prev,next) -- checks for next anyway
+ return head, next
+ end
+ end
+end
+
+local function appenddisc(disc,list)
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(disc,true)
+ local posthead = list
+ local replacehead = copy_node_list(list)
+ if post then
+ setlink(posttail,posthead)
+ else
+ post = posthead
+ end
+ if replace then
+ setlink(replacetail,replacehead)
+ else
+ replace = replacehead
+ end
+ setdisc(disc,pre,post,replace)
+end
+
+-- start is a mark and we need to keep that one
+
+local copy_no_components = nuts.copy_no_components
+local copy_only_glyphs = nuts.copy_only_glyphs
+
+local set_components = setcomponents
+local take_components = getcomponents
+
+local function count_components(start,marks)
+ local char = isglyph(start)
+ if char then
+ if getsubtype(start) == ligatureglyph_code then
+ local i = 0
+ local components = getcomponents(start)
+ while components do
+ i = i + count_components(components,marks)
+ components = getnext(components)
+ end
+ return i
+ elseif not marks[char] then
+ return 1
+ end
+ end
+ return 0
+end
+
+local function markstoligature(head,start,stop,char)
+ if start == stop and getchar(start) == char then
+ return head, start
+ else
+ local prev = getprev(start)
+ local next = getnext(stop)
+ setprev(start)
+ setnext(stop)
+ local base = copy_no_components(start,copyinjection)
+ if head == start then
+ head = base
+ end
+ resetinjection(base)
+ setchar(base,char)
+ setsubtype(base,ligatureglyph_code)
+ set_components(base,start)
+ setlink(prev,base,next)
+ return head, base
+ end
+end
+
+-- Remark for Kai: (some arabic fonts do mark + mark = other mark and such)
+--
+-- The hasmarks is needed for ligatures of marks that are part of a ligature in
+-- which case we assume that we can delete the marks anyway (we can always become
+-- more clever if needed) .. in fact the whole logic here should be redone. We're
+-- in the not discfound branch then. We now have skiphash too so we can be more
+-- selective if needed (todo).
+
+local function toligature(head,start,stop,char,dataset,sequence,skiphash,discfound,hasmarks) -- brr head
+ if getattr(start,a_noligature) == 1 then
+ -- so we can do: e\noligature{ff}e e\noligature{f}fie (we only look at the first)
+ return head, start
+ end
+ if start == stop and getchar(start) == char then
+ resetinjection(start)
+ setchar(start,char)
+ return head, start
+ end
+ local prev = getprev(start)
+ local next = getnext(stop)
+ local comp = start
+ setprev(start)
+ setnext(stop)
+ local base = copy_no_components(start,copyinjection)
+ if start == head then
+ head = base
+ end
+ resetinjection(base)
+ setchar(base,char)
+ setsubtype(base,ligatureglyph_code)
+ set_components(base,comp)
+ setlink(prev,base,next)
+ if not discfound then
+ local deletemarks = not skiphash or hasmarks
+ local components = start
+ local baseindex = 0
+ local componentindex = 0
+ local head = base
+ local current = base
+ -- first we loop over the glyphs in start ... stop
+ while start do
+ local char = getchar(start)
+ if not marks[char] then
+ baseindex = baseindex + componentindex
+ componentindex = count_components(start,marks)
+ -- we can be more clever here: "not deletemarks or (skiphash and not skiphash[char])"
+ -- and such:
+ elseif not deletemarks then
+ -- we can get a loop when the font expects otherwise (i.e. unexpected deletemarks)
+ setligaindex(start,baseindex + getligaindex(start,componentindex))
+ if trace_marks then
+ logwarning("%s: keep mark %s, gets index %s",pref(dataset,sequence),gref(char),getligaindex(start))
+ end
+ local n = copy_node(start)
+ copyinjection(n,start) -- is this ok ? we position later anyway
+ head, current = insert_node_after(head,current,n) -- unlikely that mark has components
+ elseif trace_marks then
+ logwarning("%s: delete mark %s",pref(dataset,sequence),gref(char))
+ end
+ start = getnext(start)
+ end
+ -- we can have one accent as part of a lookup and another following
+ local start = getnext(current)
+ while start do
+ local char = ischar(start)
+ if char then
+ -- also something skiphash here?
+ if marks[char] then
+ setligaindex(start,baseindex + getligaindex(start,componentindex))
+ if trace_marks then
+ logwarning("%s: set mark %s, gets index %s",pref(dataset,sequence),gref(char),getligaindex(start))
+ end
+ start = getnext(start)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ else
+ -- discfound ... forget about marks .. probably no scripts that hyphenate and have marks
+ local discprev, discnext = getboth(discfound)
+ if discprev and discnext then
+ -- we assume normalization in context, and don't care about generic ... especially
+ -- \- can give problems as there we can have a negative char but that won't match
+ -- anyway
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(discfound,true)
+ if not replace then
+ local prev = getprev(base)
+ local comp = take_components(base)
+ local copied = copy_only_glyphs(comp)
+ if pre then
+ setlink(discprev,pre)
+ else
+ setnext(discprev) -- also blocks funny assignments
+ end
+ pre = comp
+ if post then
+ setlink(posttail,discnext)
+ setprev(post)
+ else
+ post = discnext
+ setprev(discnext) -- also blocks funny assignments
+ end
+ setlink(prev,discfound,next)
+ setboth(base)
+ -- here components have a pointer so we can't free it!
+ set_components(base,copied)
+ replace = base
+ if forcediscretionaries then
+ setdisc(discfound,pre,post,replace,discretionarydisc_code)
+ else
+ setdisc(discfound,pre,post,replace)
+ end
+ base = prev
+ end
+ end
+ end
+ return head, base
+end
+
+local function multiple_glyphs(head,start,multiple,skiphash,what,stop) -- what to do with skiphash matches here
+ local nofmultiples = #multiple
+ if nofmultiples > 0 then
+ resetinjection(start)
+ setchar(start,multiple[1])
+ if nofmultiples > 1 then
+ local sn = getnext(start)
+ for k=2,nofmultiples do
+ -- untested:
+ --
+ -- while ignoremarks and marks[getchar(sn)] then
+ -- local sn = getnext(sn)
+ -- end
+ local n = copy_node(start) -- ignore components
+ resetinjection(n)
+ setchar(n,multiple[k])
+ insert_node_after(head,start,n)
+ start = n
+ end
+ if what == true then
+ -- we're ok
+ elseif what > 1 then
+ local m = multiple[nofmultiples]
+ for i=2,what do
+ local n = copy_node(start) -- ignore components
+ resetinjection(n)
+ setchar(n,m)
+ insert_node_after(head,start,n)
+ start = n
+ end
+ end
+ end
+ return head, start, true
+ else
+ if trace_multiples then
+ logprocess("no multiple for %s",gref(getchar(start)))
+ end
+ return head, start, false
+ end
+end
+
+local function get_alternative_glyph(start,alternatives,value)
+ local n = #alternatives
+ if n == 1 then
+ -- we could actually change that into a gsub and save some memory in the
+ -- font loader but it makes tracing more messy
+ return alternatives[1], trace_alternatives and "1 (only one present)"
+ elseif value == "random" then
+ local r = getrandom and getrandom("glyph",1,n) or random(1,n)
+ return alternatives[r], trace_alternatives and formatters["value %a, taking %a"](value,r)
+ elseif value == "first" then
+ return alternatives[1], trace_alternatives and formatters["value %a, taking %a"](value,1)
+ elseif value == "last" then
+ return alternatives[n], trace_alternatives and formatters["value %a, taking %a"](value,n)
+ end
+ value = value == true and 1 or tonumber(value)
+ if type(value) ~= "number" then
+ return alternatives[1], trace_alternatives and formatters["invalid value %s, taking %a"](value,1)
+ end
+ -- local a = alternatives[value]
+ -- if a then
+ -- -- some kind of hash
+ -- return a, trace_alternatives and formatters["value %a, taking %a"](value,a)
+ -- end
+ if value > n then
+ local defaultalt = otf.defaultnodealternate
+ if defaultalt == "first" then
+ return alternatives[n], trace_alternatives and formatters["invalid value %s, taking %a"](value,1)
+ elseif defaultalt == "last" then
+ return alternatives[1], trace_alternatives and formatters["invalid value %s, taking %a"](value,n)
+ else
+ return false, trace_alternatives and formatters["invalid value %a, %s"](value,"out of range")
+ end
+ elseif value == 0 then
+ return getchar(start), trace_alternatives and formatters["invalid value %a, %s"](value,"no change")
+ elseif value < 1 then
+ return alternatives[1], trace_alternatives and formatters["invalid value %a, taking %a"](value,1)
+ else
+ return alternatives[value], trace_alternatives and formatters["value %a, taking %a"](value,value)
+ end
+end
+
+-- handlers
+
+function handlers.gsub_single(head,start,dataset,sequence,replacement)
+ if trace_singles then
+ logprocess("%s: replacing %s by single %s",pref(dataset,sequence),gref(getchar(start)),gref(replacement))
+ end
+ resetinjection(start)
+ setchar(start,replacement)
+ return head, start, true
+end
+
+function handlers.gsub_alternate(head,start,dataset,sequence,alternative)
+ local kind = dataset[4]
+ local what = dataset[1]
+ local value = what == true and tfmdata.shared.features[kind] or what
+ local choice, comment = get_alternative_glyph(start,alternative,value)
+ if choice then
+ if trace_alternatives then
+ logprocess("%s: replacing %s by alternative %a to %s, %s",pref(dataset,sequence),gref(getchar(start)),gref(choice),comment)
+ end
+ resetinjection(start)
+ setchar(start,choice)
+ else
+ if trace_alternatives then
+ logwarning("%s: no variant %a for %s, %s",pref(dataset,sequence),value,gref(getchar(start)),comment)
+ end
+ end
+ return head, start, true
+end
+
+function handlers.gsub_multiple(head,start,dataset,sequence,multiple,rlmode,skiphash)
+ if trace_multiples then
+ logprocess("%s: replacing %s by multiple %s",pref(dataset,sequence),gref(getchar(start)),gref(multiple))
+ end
+ return multiple_glyphs(head,start,multiple,skiphash,dataset[1])
+end
+
+-- Don't we deal with disc otherwise now? I need to check if the next one can be
+-- simplified. Anyway, it can be way messier: marks that get removed as well as
+-- marks that are kept.
+
+function handlers.gsub_ligature(head,start,dataset,sequence,ligature,rlmode,skiphash)
+ local current = getnext(start)
+ if not current then
+ return head, start, false, nil
+ end
+ local stop = nil
+ local startchar = getchar(start)
+ if skiphash and skiphash[startchar] then
+ while current do
+ local char = ischar(current,currentfont)
+ if char then
+ local lg = ligature[char]
+ if lg then
+ stop = current
+ ligature = lg
+ current = getnext(current)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if stop then
+ local lig = ligature.ligature
+ if lig then
+ if trace_ligatures then
+ local stopchar = getchar(stop)
+ head, start = markstoligature(head,start,stop,lig)
+ logprocess("%s: replacing %s upto %s by ligature %s case 1",pref(dataset,sequence),gref(startchar),gref(stopchar),gref(getchar(start)))
+ else
+ head, start = markstoligature(head,start,stop,lig)
+ end
+ return head, start, true, false
+ else
+ -- ok, goto next lookup
+ end
+ end
+ else
+ local discfound = false
+ local hasmarks = marks[startchar]
+ while current do
+ local char, id = ischar(current,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ current = getnext(current)
+ else
+ local lg = ligature[char]
+ if lg then
+ if marks[char] then
+ hasmarks = true
+ end
+ stop = current -- needed for fake so outside then
+ ligature = lg
+ current = getnext(current)
+ else
+ break
+ end
+ end
+ elseif char == false then
+ -- kind of weird
+ break
+ elseif id == disc_code then
+ discfound = current
+ break
+ else
+ break
+ end
+ end
+ -- of{f-}{}{f}e o{f-}{}{f}fe o{-}{}{ff}e (oe and ff ligature)
+ -- we can end up here when we have a start run .. testruns start at a disc but
+ -- so here we have the other case: char + disc
+ if discfound then
+ -- don't assume marks in a disc and we don't run over a disc (for now)
+ local pre, post, replace = getdisc(discfound)
+ local match
+ if replace then
+ local char = ischar(replace,currentfont)
+ if char and ligature[char] then
+ match = true
+ end
+ end
+ if not match and pre then
+ local char = ischar(pre,currentfont)
+ if char and ligature[char] then
+ match = true
+ end
+ end
+ if not match and not pre or not replace then
+ local n = getnext(discfound)
+ local char = ischar(n,currentfont)
+ if char and ligature[char] then
+ match = true
+ end
+ end
+ if match then
+ -- we force a restart
+ local ishead = head == start
+ local prev = getprev(start)
+ if stop then
+ setnext(stop)
+ local copy = copy_node_list(start)
+ local tail = stop -- was: getprev(stop) -- Kai: needs checking on your samples
+ local liat = find_node_tail(copy)
+ if pre then
+ setlink(liat,pre)
+ end
+ if replace then
+ setlink(tail,replace)
+ end
+ pre = copy
+ replace = start
+ else
+ setnext(start)
+ local copy = copy_node(start)
+ if pre then
+ setlink(copy,pre)
+ end
+ if replace then
+ setlink(start,replace)
+ end
+ pre = copy
+ replace = start
+ end
+ setdisc(discfound,pre,post,replace)
+ if prev then
+ setlink(prev,discfound)
+ else
+ setprev(discfound)
+ head = discfound
+ end
+ start = discfound
+ return head, start, true, true
+ end
+ end
+ local lig = ligature.ligature
+ if lig then
+ if stop then
+ if trace_ligatures then
+ local stopchar = getchar(stop)
+ -- head, start = toligature(head,start,stop,lig,dataset,sequence,skiphash,discfound,hasmarks)
+ head, start = toligature(head,start,stop,lig,dataset,sequence,skiphash,false,hasmarks)
+ logprocess("%s: replacing %s upto %s by ligature %s case 2",pref(dataset,sequence),gref(startchar),gref(stopchar),gref(lig))
+ else
+ -- head, start = toligature(head,start,stop,lig,dataset,sequence,skiphash,discfound,hasmarks)
+ head, start = toligature(head,start,stop,lig,dataset,sequence,skiphash,false,hasmarks)
+ end
+ else
+ -- weird but happens (in some arabic font)
+ resetinjection(start)
+ setchar(start,lig)
+ if trace_ligatures then
+ logprocess("%s: replacing %s by (no real) ligature %s case 3",pref(dataset,sequence),gref(startchar),gref(lig))
+ end
+ end
+ return head, start, true, false
+ else
+ -- weird but happens, pseudo ligatures ... just the components
+ end
+ end
+ return head, start, false, false
+end
+
+function handlers.gpos_single(head,start,dataset,sequence,kerns,rlmode,skiphash,step,injection)
+ local startchar = getchar(start)
+ local format = step.format
+ if format == "single" or type(kerns) == "table" then -- the table check can go
+ local dx, dy, w, h = setposition(0,start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s xy (%p,%p) and wh (%p,%p)",pref(dataset,sequence),gref(startchar),format,dx,dy,w,h)
+ end
+ else
+ local k = (format == "move" and setmove or setkern)(start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s %p",pref(dataset,sequence),gref(startchar),format,k)
+ end
+ end
+ return head, start, true
+end
+
+function handlers.gpos_pair(head,start,dataset,sequence,kerns,rlmode,skiphash,step,injection)
+ local snext = getnext(start)
+ if not snext then
+ return head, start, false
+ else
+ local prev = start
+ while snext do
+ local nextchar = ischar(snext,currentfont)
+ if nextchar then
+ if skiphash and skiphash[nextchar] then -- includes marks too when flag
+ prev = snext
+ snext = getnext(snext)
+ else
+ local krn = kerns[nextchar]
+ if not krn then
+ break
+ end
+ local format = step.format
+ if format == "pair" then
+ local a = krn[1]
+ local b = krn[2]
+ if a == true then
+ -- zero
+ elseif a then -- #a > 0
+ local x, y, w, h = setposition(1,start,factor,rlmode,a,injection)
+ if trace_kerns then
+ local startchar = getchar(start)
+ logprocess("%s: shifting first of pair %s and %s by xy (%p,%p) and wh (%p,%p) as %s",pref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h,injection or "injections")
+ end
+ end
+ if b == true then
+ -- zero
+ start = snext -- cf spec
+ elseif b then -- #b > 0
+ local x, y, w, h = setposition(2,snext,factor,rlmode,b,injection)
+ if trace_kerns then
+ local startchar = getchar(start)
+ logprocess("%s: shifting second of pair %s and %s by xy (%p,%p) and wh (%p,%p) as %s",pref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h,injection or "injections")
+ end
+ start = snext -- cf spec
+ elseif forcepairadvance then
+ start = snext -- for testing, not cf spec
+ end
+ return head, start, true
+ elseif krn ~= 0 then
+ local k = (format == "move" and setmove or setkern)(snext,factor,rlmode,krn,injection)
+ if trace_kerns then
+ logprocess("%s: inserting %s %p between %s and %s as %s",pref(dataset,sequence),format,k,gref(getchar(prev)),gref(nextchar),injection or "injections")
+ end
+ return head, start, true
+ else -- can't happen
+ break
+ end
+ end
+ else
+ break
+ end
+ end
+ return head, start, false
+ end
+end
+
+--[[ldx--
+<p>We get hits on a mark, but we're not sure if the it has to be applied so
+we need to explicitly test for basechar, baselig and basemark entries.</p>
+--ldx]]--
+
+function handlers.gpos_mark2base(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar = getchar(start)
+ if marks[markchar] then
+ local base = getprev(start) -- [glyph] [start=mark]
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base = getprev(base)
+ if base then
+ basechar = ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head, start, false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head, start, false
+ end
+ end
+ end
+ local ba = markanchors[1][basechar]
+ if ba then
+ local ma = markanchors[2]
+ local dx, dy, bound = setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basechar %s => (%p,%p)",
+ pref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head, start, true
+ elseif trace_bugs then
+ -- onetimemessage(currentfont,basechar,"no base anchors",report_fonts)
+ logwarning("%s: mark %s is not anchored to %s",pref(dataset,sequence),gref(markchar),gref(basechar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: nothing preceding, case %i",pref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: nothing preceding, case %i",pref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head, start, false
+end
+
+function handlers.gpos_mark2ligature(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar = getchar(start)
+ if marks[markchar] then
+ local base = getprev(start) -- [glyph] [optional marks] [start=mark]
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base = getprev(base)
+ if base then
+ basechar = ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head, start, false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head, start, false
+ end
+ end
+ end
+ local ba = markanchors[1][basechar]
+ if ba then
+ local ma = markanchors[2]
+ if ma then
+ local index = getligaindex(start)
+ ba = ba[index]
+ if ba then
+ local dx, dy, bound = setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, index %s, bound %s, anchoring mark %s to baselig %s at index %s => (%p,%p)",
+ pref(dataset,sequence),index,bound,gref(markchar),gref(basechar),index,dx,dy)
+ end
+ return head, start, true
+ else
+ if trace_bugs then
+ logwarning("%s: no matching anchors for mark %s and baselig %s with index %a",pref(dataset,sequence),gref(markchar),gref(basechar),index)
+ end
+ end
+ end
+ elseif trace_bugs then
+ -- logwarning("%s: char %s is missing in font",pref(dataset,sequence),gref(basechar))
+ onetimemessage(currentfont,basechar,"no base anchors",report_fonts)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",pref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",pref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head, start, false
+end
+
+function handlers.gpos_mark2mark(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar = getchar(start)
+ if marks[markchar] then
+ local base = getprev(start) -- [glyph] [basemark] [start=mark]
+ local slc = getligaindex(start)
+ if slc then -- a rather messy loop ... needs checking with husayni
+ while base do
+ local blc = getligaindex(base)
+ if blc and blc ~= slc then
+ base = getprev(base)
+ else
+ break
+ end
+ end
+ end
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then -- subtype test can go
+ local ba = markanchors[1][basechar] -- slot 1 has been made copy of the class hash
+ if ba then
+ local ma = markanchors[2]
+ local dx, dy, bound = setmark(start,base,factor,rlmode,ba,ma,characters[basechar],true,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basemark %s => (%p,%p)",
+ pref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head, start, true
+ end
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head, start, false
+end
+
+function handlers.gpos_cursive(head,start,dataset,sequence,exitanchors,rlmode,skiphash,step) -- to be checked
+ local startchar = getchar(start)
+ if marks[startchar] then
+ if trace_cursive then
+ logprocess("%s: ignoring cursive for mark %s",pref(dataset,sequence),gref(startchar))
+ end
+ else
+ local nxt = getnext(start)
+ while nxt do
+ local nextchar = ischar(nxt,currentfont)
+ if not nextchar then
+ break
+ elseif marks[nextchar] then -- always sequence.flags[1]
+ nxt = getnext(nxt)
+ else
+ local exit = exitanchors[3]
+ if exit then
+ local entry = exitanchors[1][nextchar]
+ if entry then
+ entry = entry[2]
+ if entry then
+ local r2lflag = sequence.flags[4] -- mentioned in the standard
+ local dx, dy, bound = setcursive(start,nxt,factor,rlmode,exit,entry,characters[startchar],characters[nextchar],r2lflag)
+ if trace_cursive then
+ logprocess("%s: moving %s to %s cursive (%p,%p) using bound %s in %s mode",pref(dataset,sequence),gref(startchar),gref(nextchar),dx,dy,bound,mref(rlmode))
+ end
+ return head, start, true
+ end
+ end
+ end
+ break
+ end
+ end
+ end
+ return head, start, false
+end
+
+--[[ldx--
+<p>I will implement multiple chain replacements once I run into a font that uses
+it. It's not that complex to handle.</p>
+--ldx]]--
+
+local chainprocs = { }
+
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps == "silent" then
+ return
+ end
+ end
+ report_subchain(...)
+end
+
+local logwarning = report_subchain
+
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps == "silent" then
+ return
+ end
+ end
+ report_chain(...)
+end
+
+local logwarning = report_chain
+
+-- We could share functions but that would lead to extra function calls with many
+-- arguments, redundant tests and confusing messages.
+
+-- The reversesub is a special case, which is why we need to store the replacements
+-- in a bit weird way. There is no lookup and the replacement comes from the lookup
+-- itself. It is meant mostly for dealing with Urdu.
+
+local function reversesub(head,start,stop,dataset,sequence,replacements,rlmode,skiphash)
+ local char = getchar(start)
+ local replacement = replacements[char]
+ if replacement then
+ if trace_singles then
+ logprocess("%s: single reverse replacement of %s by %s",cref(dataset,sequence),gref(char),gref(replacement))
+ end
+ resetinjection(start)
+ setchar(start,replacement)
+ return head, start, true
+ else
+ return head, start, false
+ end
+end
+
+
+chainprocs.reversesub = reversesub
+
+--[[ldx--
+<p>This chain stuff is somewhat tricky since we can have a sequence of actions to be
+applied: single, alternate, multiple or ligature where ligature can be an invalid
+one in the sense that it will replace multiple by one but not neccessary one that
+looks like the combination (i.e. it is the counterpart of multiple then). For
+example, the following is valid:</p>
+
+<typing>
+<line>xxxabcdexxx [single a->A][multiple b->BCD][ligature cde->E] xxxABCDExxx</line>
+</typing>
+
+<p>Therefore we we don't really do the replacement here already unless we have the
+single lookup case. The efficiency of the replacements can be improved by deleting
+as less as needed but that would also make the code even more messy.</p>
+--ldx]]--
+
+--[[ldx--
+<p>Here we replace start by a single variant.</p>
+--ldx]]--
+
+-- To be done (example needed): what if > 1 steps
+
+-- this is messy: do we need this disc checking also in alternaties?
+
+local function reportzerosteps(dataset,sequence)
+ logwarning("%s: no steps",cref(dataset,sequence))
+end
+
+local function reportmoresteps(dataset,sequence)
+ logwarning("%s: more than 1 step",cref(dataset,sequence))
+end
+
+-- local function reportbadsteps(dataset,sequence)
+-- logwarning("%s: bad step, no proper return values",cref(dataset,sequence))
+-- end
+
+local function getmapping(dataset,sequence,currentlookup)
+ local steps = currentlookup.steps
+ local nofsteps = currentlookup.nofsteps
+ if nofsteps == 0 then
+ reportzerosteps(dataset,sequence)
+ currentlookup.mapping = false
+ return false
+ else
+ if nofsteps > 1 then
+ reportmoresteps(dataset,sequence)
+ end
+ local mapping = steps[1].coverage
+ currentlookup.mapping = mapping
+ currentlookup.format = steps[1].format
+ return mapping
+ end
+end
+
+function chainprocs.gsub_remove(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ if trace_chains then
+ logprocess("%s: removing character %s",cref(dataset,sequence,chainindex),gref(getchar(start)))
+ end
+ head, start = remove_node(head,start,true)
+ return head, getprev(start), true
+end
+
+function chainprocs.gsub_single(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local current = start
+ while current do
+ local currentchar = ischar(current)
+ if currentchar then
+ local replacement = mapping[currentchar]
+ if not replacement or replacement == "" then
+ if trace_bugs then
+ logwarning("%s: no single for %s",cref(dataset,sequence,chainindex),gref(currentchar))
+ end
+ else
+ if trace_singles then
+ logprocess("%s: replacing single %s by %s",cref(dataset,sequence,chainindex),gref(currentchar),gref(replacement))
+ end
+ resetinjection(current)
+ setchar(current,replacement)
+ end
+ return head, start, true
+ elseif currentchar == false then
+ -- can't happen
+ break
+ elseif current == stop then
+ break
+ else
+ current = getnext(current)
+ end
+ end
+ end
+ return head, start, false
+end
+
+--[[ldx--
+<p>Here we replace start by new glyph. First we delete the rest of the match.</p>
+--ldx]]--
+
+-- char_1 mark_1 -> char_x mark_1 (ignore marks)
+-- char_1 mark_1 -> char_x
+
+-- to be checked: do we always have just one glyph?
+-- we can also have alternates for marks
+-- marks come last anyway
+-- are there cases where we need to delete the mark
+
+function chainprocs.gsub_alternate(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local kind = dataset[4]
+ local what = dataset[1]
+ local value = what == true and tfmdata.shared.features[kind] or what -- todo: optimize in ctx
+ local current = start
+ while current do
+ local currentchar = ischar(current)
+ if currentchar then
+ local alternatives = mapping[currentchar]
+ if alternatives then
+ local choice, comment = get_alternative_glyph(current,alternatives,value)
+ if choice then
+ if trace_alternatives then
+ logprocess("%s: replacing %s by alternative %a to %s, %s",cref(dataset,sequence),gref(currentchar),choice,gref(choice),comment)
+ end
+ resetinjection(start)
+ setchar(start,choice)
+ else
+ if trace_alternatives then
+ logwarning("%s: no variant %a for %s, %s",cref(dataset,sequence),value,gref(currentchar),comment)
+ end
+ end
+ end
+ return head, start, true
+ elseif currentchar == false then
+ -- can't happen
+ break
+ elseif current == stop then
+ break
+ else
+ current = getnext(current)
+ end
+ end
+ end
+ return head, start, false
+end
+
+--[[ldx--
+<p>Here we replace start by a sequence of new glyphs.</p>
+--ldx]]--
+
+function chainprocs.gsub_multiple(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar = getchar(start)
+ local replacement = mapping[startchar]
+ if not replacement or replacement == "" then
+ if trace_bugs then
+ logwarning("%s: no multiple for %s",cref(dataset,sequence),gref(startchar))
+ end
+ else
+ if trace_multiples then
+ logprocess("%s: replacing %s by multiple characters %s",cref(dataset,sequence),gref(startchar),gref(replacement))
+ end
+ return multiple_glyphs(head,start,replacement,skiphash,dataset[1],stop)
+ end
+ end
+ return head, start, false
+end
+
+--[[ldx--
+<p>When we replace ligatures we use a helper that handles the marks. I might change
+this function (move code inline and handle the marks by a separate function). We
+assume rather stupid ligatures (no complex disc nodes).</p>
+--ldx]]--
+
+-- compare to handlers.gsub_ligature which is more complex ... why
+
+function chainprocs.gsub_ligature(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar = getchar(start)
+ local ligatures = mapping[startchar]
+ if not ligatures then
+ if trace_bugs then
+ logwarning("%s: no ligatures starting with %s",cref(dataset,sequence,chainindex),gref(startchar))
+ end
+ else
+ local hasmarks = marks[startchar]
+ local current = getnext(start)
+ local discfound = false
+ local last = stop
+ local nofreplacements = 1
+ while current do
+ -- todo: ischar ... can there really be disc nodes here?
+ local id = getid(current)
+ if id == disc_code then
+ if not discfound then
+ discfound = current
+ end
+ if current == stop then
+ break -- okay? or before the disc
+ else
+ current = getnext(current)
+ end
+ else
+ local schar = getchar(current)
+ if skiphash and skiphash[schar] then -- marks
+ -- if current == stop then -- maybe add this
+ -- break
+ -- else
+ current = getnext(current)
+ -- end
+ else
+ local lg = ligatures[schar]
+ if lg then
+ ligatures = lg
+ last = current
+ nofreplacements = nofreplacements + 1
+ if marks[char] then
+ hasmarks = true
+ end
+ if current == stop then
+ break
+ else
+ current = getnext(current)
+ end
+ else
+ break
+ end
+ end
+ end
+ end
+ local ligature = ligatures.ligature
+ if ligature then
+ if chainindex then
+ stop = last
+ end
+ if trace_ligatures then
+ if start == stop then
+ logprocess("%s: replacing character %s by ligature %s case 3",cref(dataset,sequence,chainindex),gref(startchar),gref(ligature))
+ else
+ logprocess("%s: replacing character %s upto %s by ligature %s case 4",cref(dataset,sequence,chainindex),gref(startchar),gref(getchar(stop)),gref(ligature))
+ end
+ end
+ head, start = toligature(head,start,stop,ligature,dataset,sequence,skiphash,discfound,hasmarks)
+ return head, start, true, nofreplacements, discfound
+ elseif trace_bugs then
+ if start == stop then
+ logwarning("%s: replacing character %s by ligature fails",cref(dataset,sequence,chainindex),gref(startchar))
+ else
+ logwarning("%s: replacing character %s upto %s by ligature fails",cref(dataset,sequence,chainindex),gref(startchar),gref(getchar(stop)))
+ end
+ end
+ end
+ end
+ return head, start, false, 0, false
+end
+
+function chainprocs.gpos_single(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar = getchar(start)
+ local kerns = mapping[startchar]
+ if kerns then
+ local format = currentlookup.format
+ if format == "single" then
+ local dx, dy, w, h = setposition(0,start,factor,rlmode,kerns) -- currentlookup.flags ?
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),format,dx,dy,w,h)
+ end
+ else -- needs checking .. maybe no kerns format for single
+ local k = (format == "move" and setmove or setkern)(start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s %p",cref(dataset,sequence),gref(startchar),format,k)
+ end
+ end
+ return head, start, true
+ end
+ end
+ return head, start, false
+end
+
+function chainprocs.gpos_pair(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex) -- todo: injections ?
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local snext = getnext(start)
+ if snext then
+ local startchar = getchar(start)
+ local kerns = mapping[startchar] -- always 1 step
+ if kerns then
+ local prev = start
+ while snext do
+ local nextchar = ischar(snext,currentfont)
+ if not nextchar then
+ break
+ end
+ if skiphash and skiphash[nextchar] then
+ prev = snext
+ snext = getnext(snext)
+ else
+ local krn = kerns[nextchar]
+ if not krn then
+ break
+ end
+ local format = currentlookup.format
+ if format == "pair" then
+ local a = krn[1]
+ local b = krn[2]
+ if a == true then
+ -- zero
+ elseif a then
+ local x, y, w, h = setposition(1,start,factor,rlmode,a,"injections") -- currentlookups flags?
+ if trace_kerns then
+ local startchar = getchar(start)
+ logprocess("%s: shifting first of pair %s and %s by (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h)
+ end
+ end
+ if b == true then
+ -- zero
+ start = snext -- cf spec
+ elseif b then -- #b > 0
+ local x, y, w, h = setposition(2,snext,factor,rlmode,b,"injections")
+ if trace_kerns then
+ local startchar = getchar(start)
+ logprocess("%s: shifting second of pair %s and %s by (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h)
+ end
+ start = snext -- cf spec
+ elseif forcepairadvance then
+ start = snext -- for testing, not cf spec
+ end
+ return head, start, true
+ elseif krn ~= 0 then
+ local k = (format == "move" and setmove or setkern)(snext,factor,rlmode,krn)
+ if trace_kerns then
+ logprocess("%s: inserting %s %p between %s and %s",cref(dataset,sequence),format,k,gref(getchar(prev)),gref(nextchar))
+ end
+ return head, start, true
+ else
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ return head, start, false
+end
+
+function chainprocs.gpos_mark2base(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar = getchar(start)
+ if marks[markchar] then
+ local markanchors = mapping[markchar] -- always 1 step
+ if markanchors then
+ local base = getprev(start) -- [glyph] [start=mark]
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base = getprev(base)
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head, start, false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head, start, false
+ end
+ end
+ end
+ local ba = markanchors[1][basechar]
+ if ba then
+ local ma = markanchors[2]
+ if ma then
+ local dx, dy, bound = setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basechar %s => (%p,%p)",
+ cref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head, start, true
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head, start, false
+end
+
+function chainprocs.gpos_mark2ligature(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar = getchar(start)
+ if marks[markchar] then
+ local markanchors = mapping[markchar] -- always 1 step
+ if markanchors then
+ local base = getprev(start) -- [glyph] [optional marks] [start=mark]
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base = getprev(base)
+ if base then
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",cref(dataset,sequence),markchar,1)
+ end
+ return head, start, false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",cref(dataset,sequence),markchar,2)
+ end
+ return head, start, false
+ end
+ end
+ end
+ local ba = markanchors[1][basechar]
+ if ba then
+ local ma = markanchors[2]
+ if ma then
+ local index = getligaindex(start)
+ ba = ba[index]
+ if ba then
+ local dx, dy, bound = setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to baselig %s at index %s => (%p,%p)",
+ cref(dataset,sequence),a or bound,gref(markchar),gref(basechar),index,dx,dy)
+ end
+ return head, start, true
+ end
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s, prev node is no char, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s, prev node is no char, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s, mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s, mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head, start, false
+end
+
+function chainprocs.gpos_mark2mark(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar = getchar(start)
+ if marks[markchar] then
+ local markanchors = mapping[markchar] -- always 1 step
+ if markanchors then
+ local base = getprev(start) -- [glyph] [basemark] [start=mark]
+ local slc = getligaindex(start)
+ if slc then -- a rather messy loop ... needs checking with husayni
+ while base do
+ local blc = getligaindex(base)
+ if blc and blc ~= slc then
+ base = getprev(base)
+ else
+ break
+ end
+ end
+ end
+ if base then -- subtype test can go
+ local basechar = ischar(base,currentfont)
+ if basechar then
+ local ba = markanchors[1][basechar]
+ if ba then
+ local ma = markanchors[2]
+ if ma then
+ local dx, dy, bound = setmark(start,base,factor,rlmode,ba,ma,characters[basechar],true,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basemark %s => (%p,%p)",
+ cref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head, start, true
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no mark, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no mark, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head, start, false
+end
+
+function chainprocs.gpos_cursive(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping = currentlookup.mapping
+ if mapping == nil then
+ mapping = getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar = getchar(start)
+ local exitanchors = mapping[startchar] -- always 1 step
+ if exitanchors then
+ if marks[startchar] then
+ if trace_cursive then
+ logprocess("%s: ignoring cursive for mark %s",pref(dataset,sequence),gref(startchar))
+ end
+ else
+ local nxt = getnext(start)
+ while nxt do
+ local nextchar = ischar(nxt,currentfont)
+ if not nextchar then
+ break
+ elseif marks[nextchar] then
+ -- should not happen (maybe warning)
+ nxt = getnext(nxt)
+ else
+ local exit = exitanchors[3]
+ if exit then
+ local entry = exitanchors[1][nextchar]
+ if entry then
+ entry = entry[2]
+ if entry then
+ local r2lflag = sequence.flags[4] -- mentioned in the standard
+ local dx, dy, bound = setcursive(start,nxt,factor,rlmode,exit,entry,characters[startchar],characters[nextchar],r2lflag)
+ if trace_cursive then
+ logprocess("%s: moving %s to %s cursive (%p,%p) using bound %s in %s mode",pref(dataset,sequence),gref(startchar),gref(nextchar),dx,dy,bound,mref(rlmode))
+ end
+ return head, start, true
+ end
+ end
+ elseif trace_bugs then
+ onetimemessage(currentfont,startchar,"no entry anchors",report_fonts)
+ end
+ break
+ end
+ end
+ end
+ elseif trace_cursive and trace_details then
+ logprocess("%s, cursive %s is already done",pref(dataset,sequence),gref(getchar(start)),alreadydone)
+ end
+ end
+ return head, start, false
+end
+
+-- what pointer to return, spec says stop
+-- to be discussed ... is bidi changer a space?
+-- elseif char == zwnj and sequence[n][32] then -- brrr
+
+local function show_skip(dataset,sequence,char,ck,class)
+ logwarning("%s: skipping char %s, class %a, rule %a, lookuptype %a",cref(dataset,sequence),gref(char),class,ck[1],ck[8] or ck[2])
+end
+
+-- A previous version had disc collapsing code in the (single sub) handler plus some
+-- checking in the main loop, but that left the pre/post sequences undone. The best
+-- solution is to add some checking there and backtrack when a replace/post matches
+-- but it takes a bit of work to figure out an efficient way (this is what the
+-- sweep* names refer to). I might look into that variant one day again as it can
+-- replace some other code too. In that approach we can have a special version for
+-- gub and pos which gains some speed. This method does the test and passes info to
+-- the handlers. Here collapsing is handled in the main loop which also makes code
+-- elsewhere simpler (i.e. no need for the other special runners and disc code in
+-- ligature building). I also experimented with pushing preceding glyphs sequences
+-- in the replace/pre fields beforehand which saves checking afterwards but at the
+-- cost of duplicate glyphs (memory) but it's too much overhead (runtime).
+--
+-- In the meantime Kai had moved the code from the single chain into a more general
+-- handler and this one (renamed to chaindisk) is used now. I optimized the code a
+-- bit and brought it in sycn with the other code. Hopefully I didn't introduce
+-- errors. Note: this somewhat complex approach is meant for fonts that implement
+-- (for instance) ligatures by character replacement which to some extend is not
+-- that suitable for hyphenation. I also use some helpers. This method passes some
+-- states but reparses the list. There is room for a bit of speed up but that will
+-- be done in the context version. (In fact a partial rewrite of all code can bring
+-- some more efficiency.)
+--
+-- I didn't test it with extremes but successive disc nodes still can give issues
+-- but in order to handle that we need more complex code which also slows down even
+-- more. The main loop variant could deal with that: test, collapse, backtrack.
+
+local userkern = nuts.pool and nuts.pool.newkern -- context
+
+do if not userkern then -- generic
+
+ local thekern = nuts.new("kern",1) -- userkern
+ local setkern = nuts.setkern -- not injections.setkern
+
+ userkern = function(k)
+ local n = copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+
+end end
+
+local function checked(head)
+ local current = head
+ while current do
+ if getid(current) == glue_code then
+ local kern = userkern(getwidth(current))
+ if head == current then
+ local next = getnext(current)
+ if next then
+ setlink(kern,next)
+ end
+ flush_node(current)
+ head = kern
+ current = next
+ else
+ local prev, next = getboth(current)
+ setlink(prev,kern,next)
+ flush_node(current)
+ current = next
+ end
+ else
+ current = getnext(current)
+ end
+ end
+ return head
+end
+
+local function setdiscchecked(d,pre,post,replace)
+ if pre then pre = checked(pre) end
+ if post then post = checked(post) end
+ if replace then replace = checked(replace) end
+ setdisc(d,pre,post,replace)
+end
+
+local noflags = { false, false, false, false }
+
+local function chainrun(head,start,last,dataset,sequence,rlmode,skiphash,ck)
+
+ local size = ck[5] - ck[4] + 1
+ local chainlookups = ck[6]
+ local done = false
+
+ -- current match
+ if chainlookups then
+ -- Lookups can be like { 1, false, 3 } or { false, 2 } or basically anything and
+ -- #lookups can be less than #current
+
+ if size == 1 then
+
+ -- if nofchainlookups > size then
+ -- -- bad rules
+ -- end
+
+ local chainlookup = chainlookups[1]
+ for j=1,#chainlookup do
+ local chainstep = chainlookup[j]
+ local chainkind = chainstep.type
+ local chainproc = chainprocs[chainkind]
+ if chainproc then
+ local ok
+ head, start, ok = chainproc(head,start,last,dataset,sequence,chainstep,rlmode,skiphash)
+ if ok then
+ done = true
+ end
+ else
+ logprocess("%s: %s is not yet supported (1)",cref(dataset,sequence),chainkind)
+ end
+ end
+
+ else
+
+ -- See LookupType 5: Contextual Substitution Subtable. Now it becomes messy. The
+ -- easiest case is where #current maps on #lookups i.e. one-to-one. But what if
+ -- we have a ligature. Cf the spec we then need to advance one character but we
+ -- really need to test it as there are fonts out there that are fuzzy and have
+ -- too many lookups:
+ --
+ -- U+1105 U+119E U+1105 U+119E : sourcehansansklight: script=hang ccmp=yes
+ --
+ -- Even worse are these family emoji shapes as they can have multiple lookups
+ -- per slot (probably only for gpos).
+
+ -- It's very unlikely that we will have skip classes here but still ... we seldom
+ -- enter this branch anyway.
+
+ local i = 1
+ local laststart = start
+ local nofchainlookups = #chainlookups -- useful?
+ while start do
+ if skiphash then -- hm, so we know we skip some
+ while start do
+ local char = ischar(start,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ start = getnext(start)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ end
+ local chainlookup = chainlookups[i]
+ if chainlookup then
+ for j=1,#chainlookup do
+ local chainstep = chainlookup[j]
+ local chainkind = chainstep.type
+ local chainproc = chainprocs[chainkind]
+ if chainproc then
+ local ok, n
+ head, start, ok, n = chainproc(head,start,last,dataset,sequence,chainstep,rlmode,skiphash,i)
+ -- messy since last can be changed !
+ if ok then
+ done = true
+ if n and n > 1 and i + n > nofchainlookups then
+ -- this is a safeguard, we just ignore the rest of the lookups
+ i = size -- prevents an advance
+ break
+ end
+ end
+ else
+ -- actually an error
+ logprocess("%s: %s is not yet supported (2)",cref(dataset,sequence),chainkind)
+ end
+ end
+ else
+ -- we skip but we could also delete as option .. what does an empty lookup actually mean
+ -- in opentype ... anyway, we could map it onto gsub_remove if needed
+ end
+ i = i + 1
+ if i > size or not start then
+ break
+ elseif start then
+ laststart = start
+ start = getnext(start)
+ end
+ end
+ if not start then
+ start = laststart
+ end
+
+ end
+ else
+ -- todo: needs checking for holes in the replacements
+ local replacements = ck[7]
+ if replacements then
+ head, start, done = reversesub(head,start,last,dataset,sequence,replacements,rlmode,skiphash)
+ else
+ done = true
+ if trace_contexts then
+ logprocess("%s: skipping match",cref(dataset,sequence))
+ end
+ end
+ end
+ return head, start, done
+end
+
+local function chaindisk(head,start,dataset,sequence,rlmode,skiphash,ck)
+
+ if not start then
+ return head, start, false
+ end
+
+ local startishead = start == head
+ local seq = ck[3]
+ local f = ck[4]
+ local l = ck[5]
+ local s = #seq
+ local done = false
+ local sweepnode = sweepnode
+ local sweeptype = sweeptype
+ local sweepoverflow = false
+ local keepdisc = not sweepnode
+ local lookaheaddisc = nil
+ local backtrackdisc = nil
+ local current = start
+ local last = start
+ local prev = getprev(start)
+ local hasglue = false
+
+ -- fishy: so we can overflow and then go on in the sweep?
+ -- todo : id can also be glue_code as we checked spaces
+
+ local i = f
+ while i <= l do
+ local id = getid(current)
+ if id == glyph_code then
+ i = i + 1
+ last = current
+ current = getnext(current)
+ elseif id == glue_code then
+ i = i + 1
+ last = current
+ current = getnext(current)
+ hasglue = true
+ elseif id == disc_code then
+ if keepdisc then
+ keepdisc = false
+ lookaheaddisc = current
+ local replace = getfield(current,"replace")
+ if not replace then
+ sweepoverflow = true
+ sweepnode = current
+ current = getnext(current)
+ else
+ while replace and i <= l do
+ if getid(replace) == glyph_code then
+ i = i + 1
+ end
+ replace = getnext(replace)
+ end
+ current = getnext(replace)
+ end
+ last = current
+ else
+ head, current = flattendisk(head,current)
+ end
+ else
+ last = current
+ current = getnext(current)
+ end
+ if current then
+ -- go on
+ elseif sweepoverflow then
+ -- we already are following up on sweepnode
+ break
+ elseif sweeptype == "post" or sweeptype == "replace" then
+ current = getnext(sweepnode)
+ if current then
+ sweeptype = nil
+ sweepoverflow = true
+ else
+ break
+ end
+ else
+ break -- added
+ end
+ end
+
+ if sweepoverflow then
+ local prev = current and getprev(current)
+ if not current or prev ~= sweepnode then
+ local head = getnext(sweepnode)
+ local tail = nil
+ if prev then
+ tail = prev
+ setprev(current,sweepnode)
+ else
+ tail = find_node_tail(head)
+ end
+ setnext(sweepnode,current)
+ setprev(head)
+ setnext(tail)
+ appenddisc(sweepnode,head)
+ end
+ end
+
+ if l < s then
+ local i = l
+ local t = sweeptype == "post" or sweeptype == "replace"
+ while current and i < s do
+ local id = getid(current)
+ if id == glyph_code then
+ i = i + 1
+ current = getnext(current)
+ elseif id == glue_code then
+ i = i + 1
+ current = getnext(current)
+ hasglue = true
+ elseif id == disc_code then
+ if keepdisc then
+ keepdisc = false
+ if notmatchpre[current] ~= notmatchreplace[current] then
+ lookaheaddisc = current
+ end
+ -- we assume a simple text only replace (we could use nuts.count)
+ local replace = getfield(current,"replace")
+ while replace and i < s do
+ if getid(replace) == glyph_code then
+ i = i + 1
+ end
+ replace = getnext(replace)
+ end
+ current = getnext(current)
+ elseif notmatchpre[current] ~= notmatchreplace[current] then
+ head, current = flattendisk(head,current)
+ else
+ current = getnext(current) -- HH
+ end
+ else
+ current = getnext(current)
+ end
+ if not current and t then
+ current = getnext(sweepnode)
+ if current then
+ sweeptype = nil
+ end
+ end
+ end
+ end
+
+ if f > 1 then
+ local current = prev
+ local i = f
+ local t = sweeptype == "pre" or sweeptype == "replace"
+ if not current and t and current == checkdisk then
+ current = getprev(sweepnode)
+ end
+ while current and i > 1 do -- missing getprev added / moved outside
+ local id = getid(current)
+ if id == glyph_code then
+ i = i - 1
+ elseif id == glue_code then
+ i = i - 1
+ hasglue = true
+ elseif id == disc_code then
+ if keepdisc then
+ keepdisc = false
+ if notmatchpost[current] ~= notmatchreplace[current] then
+ backtrackdisc = current
+ end
+ -- we assume a simple text only replace (we could use nuts.count)
+ local replace = getfield(current,"replace")
+ while replace and i > 1 do
+ if getid(replace) == glyph_code then
+ i = i - 1
+ end
+ replace = getnext(replace)
+ end
+ elseif notmatchpost[current] ~= notmatchreplace[current] then
+ head, current = flattendisk(head,current)
+ end
+ end
+ current = getprev(current)
+ if t and current == checkdisk then
+ current = getprev(sweepnode)
+ end
+ end
+ end
+ local done = false
+
+ if lookaheaddisc then
+
+ local cf = start
+ local cl = getprev(lookaheaddisc)
+ local cprev = getprev(start)
+ local insertedmarks = 0
+
+ while cprev do
+ local char = ischar(cf,currentfont)
+ if char and marks[char] then
+ insertedmarks = insertedmarks + 1
+ cf = cprev
+ startishead = cf == head
+ cprev = getprev(cprev)
+ else
+ break
+ end
+ end
+ setlink(cprev,lookaheaddisc)
+ setprev(cf)
+ setnext(cl)
+ if startishead then
+ head = lookaheaddisc
+ end
+ local pre, post, replace = getdisc(lookaheaddisc)
+ local new = copy_node_list(cf) -- br, how often does that happen
+ local cnew = new
+ if pre then
+ setlink(find_node_tail(cf),pre)
+ end
+ if replace then
+ local tail = find_node_tail(new)
+ setlink(tail,replace)
+ end
+ for i=1,insertedmarks do
+ cnew = getnext(cnew)
+ end
+ cl = start
+ local clast = cnew
+ for i=f,l do
+ cl = getnext(cl)
+ clast = getnext(clast)
+ end
+ if not notmatchpre[lookaheaddisc] then
+ local ok = false
+ cf, start, ok = chainrun(cf,start,cl,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done = true
+ end
+ end
+ if not notmatchreplace[lookaheaddisc] then
+ local ok = false
+ new, cnew, ok = chainrun(new,cnew,clast,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done = true
+ end
+ end
+ if hasglue then
+ setdiscchecked(lookaheaddisc,cf,post,new)
+ else
+ setdisc(lookaheaddisc,cf,post,new)
+ end
+ start = getprev(lookaheaddisc)
+ sweephead[cf] = getnext(clast) or false
+ sweephead[new] = getnext(cl) or false
+
+ elseif backtrackdisc then
+
+ local cf = getnext(backtrackdisc)
+ local cl = start
+ local cnext = getnext(start)
+ local insertedmarks = 0
+
+ while cnext do
+ local char = ischar(cnext,currentfont)
+ if char and marks[char] then
+ insertedmarks = insertedmarks + 1
+ cl = cnext
+ cnext = getnext(cnext)
+ else
+ break
+ end
+ end
+ setlink(backtrackdisc,cnext)
+ setprev(cf)
+ setnext(cl)
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(backtrackdisc,true)
+ local new = copy_node_list(cf)
+ local cnew = find_node_tail(new)
+ for i=1,insertedmarks do
+ cnew = getprev(cnew)
+ end
+ local clast = cnew
+ for i=f,l do
+ clast = getnext(clast)
+ end
+ if not notmatchpost[backtrackdisc] then
+ local ok = false
+ cf, start, ok = chainrun(cf,start,last,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done = true
+ end
+ end
+ if not notmatchreplace[backtrackdisc] then
+ local ok = false
+ new, cnew, ok = chainrun(new,cnew,clast,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done = true
+ end
+ end
+ if post then
+ setlink(posttail,cf)
+ else
+ post = cf
+ end
+ if replace then
+ setlink(replacetail,new)
+ else
+ replace = new
+ end
+ if hasglue then
+ setdiscchecked(backtrackdisc,pre,post,replace)
+ else
+ setdisc(backtrackdisc,pre,post,replace)
+ end
+ start = getprev(backtrackdisc)
+ sweephead[post] = getnext(clast) or false
+ sweephead[replace] = getnext(last) or false
+
+ else
+
+ local ok = false
+ head, start, ok = chainrun(head,start,last,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done = true
+ end
+
+ end
+
+ return head, start, done
+end
+
+local function chaintrac(head,start,dataset,sequence,rlmode,skiphash,ck,match,discseen,sweepnode)
+ local rule = ck[1]
+ local lookuptype = ck[8] or ck[2]
+ local nofseq = #ck[3]
+ local first = ck[4]
+ local last = ck[5]
+ local char = getchar(start)
+ logwarning("%s: rule %s %s at char %s for (%s,%s,%s) chars, lookuptype %a, %sdisc seen, %ssweeping",
+ cref(dataset,sequence),rule,match and "matches" or "nomatch",
+ gref(char),first-1,last-first+1,nofseq-last,lookuptype,
+ discseen and "" or "no ", sweepnode and "" or "not ")
+end
+
+-- The next one is quite optimized but still somewhat slow, fonts like ebgaramond
+-- are real torture tests because they have many steps with one context (having
+-- multiple contexts makes more sense) also because we (can) reduce them. Instead of
+-- a match boolean variable and check for that I decided to use a goto with labels
+-- instead. This is one of the cases where it makes the code more readable and we
+-- might even gain a bit performance.
+
+-- when we have less replacements (lookups) then current matches we can push too much into
+-- the previous disc .. such be it (<before><disc><current=fl><after> with only f done)
+
+local function handle_contextchain(head,start,dataset,sequence,contexts,rlmode,skiphash)
+ -- optimizing for rlmode gains nothing
+ local sweepnode = sweepnode
+ local sweeptype = sweeptype
+ local postreplace
+ local prereplace
+ local checkdisc
+ local discseen -- = false
+ if sweeptype then
+ if sweeptype == "replace" then
+ postreplace = true
+ prereplace = true
+ else
+ postreplace = sweeptype == "post"
+ prereplace = sweeptype == "pre"
+ end
+ checkdisc = getprev(head)
+ end
+ local currentfont = currentfont
+
+ local skipped -- = false
+
+ local startprev,
+ startnext = getboth(start)
+ local done -- = false
+
+ -- we can have multiple hits and as we scan (currently) all we need to check
+ -- if we have a match ... contextchains have no real coverage table (with
+ -- unique entries)
+
+ -- fonts can have many steps (each doing one check) or many contexts
+
+ -- todo: make a per-char cache so that we have small contexts (when we have a context
+ -- n == 1 and otherwise it can be more so we can even distingish n == 1 or more)
+
+ local nofcontexts = contexts.n -- #contexts
+
+ local startchar = nofcontext == 1 or ischar(start,currentfont) -- only needed in a chain
+
+ for k=1,nofcontexts do -- does this disc mess work well with n > 1
+
+ local ck = contexts[k]
+ local seq = ck[3]
+ local f = ck[4] -- first current
+ if not startchar or not seq[f][startchar] then
+ -- report("no hit in %a at %i of %i contexts",sequence.type,k,nofcontexts)
+ goto next
+ end
+ local s = seq.n -- or #seq
+ local l = ck[5] -- last current
+ local current = start
+ local last = start
+
+ -- current match
+
+ if l > f then
+ -- before/current/after | before/current | current/after
+ local discfound -- = nil
+ local n = f + 1
+ last = startnext -- the second in current (first already matched)
+ while n <= l do
+ if postreplace and not last then
+ last = getnext(sweepnode)
+ sweeptype = nil
+ end
+ if last then
+ local char, id = ischar(last,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped = true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ last = getnext(last)
+ elseif seq[n][char] then
+ if n < l then
+ last = getnext(last)
+ end
+ n = n + 1
+ elseif discfound then
+ notmatchreplace[discfound] = true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char == false then
+ if discfound then
+ notmatchreplace[discfound] = true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif id == disc_code then
+ -- elseif id == disc_code and (not discs or discs[last]) then
+ discseen = true
+ discfound = last
+ notmatchpre[last] = nil
+ notmatchpost[last] = true
+ notmatchreplace[last] = nil
+ local pre, post, replace = getdisc(last)
+ if pre then
+ local n = n
+ while pre do
+ if seq[n][getchar(pre)] then
+ n = n + 1
+ if n > l then
+ break
+ end
+ pre = getnext(pre)
+ else
+ notmatchpre[last] = true
+ break
+ end
+ end
+ -- commented, for Kai to check
+ -- if n <= l then
+ -- notmatchpre[last] = true
+ -- end
+ else
+ notmatchpre[last] = true
+ end
+ if replace then
+ -- so far we never entered this branch
+ while replace do
+ if seq[n][getchar(replace)] then
+ n = n + 1
+ if n > l then
+ break
+ end
+ replace = getnext(replace)
+ else
+ notmatchreplace[last] = true
+ if notmatchpre[last] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ -- why here again
+ if notmatchpre[last] then
+ goto next
+ end
+ end
+ -- maybe only if match
+ last = getnext(last)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ end
+
+ -- before
+
+ if f > 1 then
+ if startprev then
+ local prev = startprev
+ if prereplace and prev == checkdisc then
+ prev = getprev(sweepnode)
+ end
+ if prev then
+ local discfound -- = nil
+ local n = f - 1
+ while n >= 1 do
+ if prev then
+ local char, id = ischar(prev,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped = true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ prev = getprev(prev)
+ elseif seq[n][char] then
+ if n > 1 then
+ prev = getprev(prev)
+ end
+ n = n - 1
+ elseif discfound then
+ notmatchreplace[discfound] = true
+ if notmatchpost[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char == false then
+ if discfound then
+ notmatchreplace[discfound] = true
+ if notmatchpost[discfound] then
+ goto next
+ end
+ else
+ goto next
+ end
+ break
+ elseif id == disc_code then
+ -- elseif id == disc_code and (not discs or discs[prev]) then
+ -- the special case: f i where i becomes dottless i ..
+ discseen = true
+ discfound = prev
+ notmatchpre[prev] = true
+ notmatchpost[prev] = nil
+ notmatchreplace[prev] = nil
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(prev,true)
+ -- weird test: needs checking
+ if pre ~= start and post ~= start and replace ~= start then
+ if post then
+ local n = n
+ while posttail do
+ if seq[n][getchar(posttail)] then
+ n = n - 1
+ if posttail == post or n < 1 then
+ break
+ else
+ posttail = getprev(posttail)
+ end
+ else
+ notmatchpost[prev] = true
+ break
+ end
+ end
+ if n >= 1 then
+ notmatchpost[prev] = true
+ end
+ else
+ notmatchpost[prev] = true
+ end
+ if replace then
+ -- we seldom enter this branch (e.g. on brill efficient)
+ while replacetail do
+ if seq[n][getchar(replacetail)] then
+ n = n - 1
+ if replacetail == replace or n < 1 then
+ break
+ else
+ replacetail = getprev(replacetail)
+ end
+ else
+ notmatchreplace[prev] = true
+ if notmatchpost[prev] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ else
+ -- notmatchreplace[prev] = true -- not according to Kai
+ end
+ end
+ prev = getprev(prev)
+ -- elseif id == glue_code and seq[n][32] and isspace(prev,threshold,id) then
+ -- elseif seq[n][32] and spaces[prev] then
+ -- n = n - 1
+ -- prev = getprev(prev)
+ elseif id == glue_code then
+ local sn = seq[n]
+ if (sn[32] and spaces[prev]) or sn[0xFFFC] then
+ n = n - 1
+ prev = getprev(prev)
+ else
+ goto next
+ end
+ elseif seq[n][0xFFFC] then
+ n = n - 1
+ prev = getprev(prev)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+
+ -- after
+
+ if s > l then
+ local current = last and getnext(last)
+ if not current and postreplace then
+ current = getnext(sweepnode)
+ end
+ if current then
+ local discfound -- = nil
+ local n = l + 1
+ while n <= s do
+ if current then
+ local char, id = ischar(current,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped = true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ current = getnext(current) -- was absent
+ elseif seq[n][char] then
+ if n < s then -- new test
+ current = getnext(current) -- was absent
+ end
+ n = n + 1
+ elseif discfound then
+ notmatchreplace[discfound] = true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char == false then
+ if discfound then
+ notmatchreplace[discfound] = true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif id == disc_code then
+ -- elseif id == disc_code and (not discs or discs[current]) then
+ discseen = true
+ discfound = current
+ notmatchpre[current] = nil
+ notmatchpost[current] = true
+ notmatchreplace[current] = nil
+ local pre, post, replace = getdisc(current)
+ if pre then
+ local n = n
+ while pre do
+ if seq[n][getchar(pre)] then
+ n = n + 1
+ if n > s then
+ break
+ else
+ pre = getnext(pre)
+ end
+ else
+ notmatchpre[current] = true
+ break
+ end
+ end
+ if n <= s then
+ notmatchpre[current] = true
+ end
+ else
+ notmatchpre[current] = true
+ end
+ if replace then
+ -- so far we never entered this branch
+ while replace do
+ if seq[n][getchar(replace)] then
+ n = n + 1
+ if n > s then
+ break
+ else
+ replace = getnext(replace)
+ end
+ else
+ notmatchreplace[current] = true
+ if notmatchpre[current] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ else
+ -- notmatchreplace[current] = true -- not according to Kai
+ end
+ current = getnext(current)
+ elseif id == glue_code then
+ local sn = seq[n]
+ if (sn[32] and spaces[current]) or sn[0xFFFC] then
+ n = n + 1
+ current = getnext(current)
+ else
+ goto next
+ end
+ elseif seq[n][0xFFFC] then
+ n = n + 1
+ current = getnext(current)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ else
+ goto next
+ end
+ end
+
+ if trace_contexts then
+ chaintrac(head,start,dataset,sequence,rlmode,skipped and skiphash,ck,true,discseen,sweepnode)
+ end
+ if discseen or sweepnode then
+ head, start, done = chaindisk(head,start,dataset,sequence,rlmode,skipped and skiphash,ck)
+ else
+ head, start, done = chainrun(head,start,last,dataset,sequence,rlmode,skipped and skiphash,ck)
+ end
+ if done then
+ break
+ -- else
+ -- next context
+ end
+ ::next::
+ -- if trace_chains then
+ -- chaintrac(head,start,dataset,sequence,rlmode,skipped and skiphash,ck,false,discseen,sweepnode)
+ -- end
+ end
+ if discseen then
+ notmatchpre = { }
+ notmatchpost = { }
+ notmatchreplace = { }
+ -- notmatchpre = { a = 1, b = 1 } notmatchpre .a = nil notmatchpre .b = nil
+ -- notmatchpost = { a = 1, b = 1 } notmatchpost .a = nil notmatchpost .b = nil
+ -- notmatchreplace = { a = 1, b = 1 } notmatchreplace.a = nil notmatchreplace.b = nil
+ end
+ return head, start, done
+end
+
+handlers.gsub_context = handle_contextchain
+handlers.gsub_contextchain = handle_contextchain
+handlers.gsub_reversecontextchain = handle_contextchain
+handlers.gpos_contextchain = handle_contextchain
+handlers.gpos_context = handle_contextchain
+
+-- this needs testing
+
+local function chained_contextchain(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash)
+ local steps = currentlookup.steps
+ local nofsteps = currentlookup.nofsteps
+ if nofsteps > 1 then
+ reportmoresteps(dataset,sequence)
+ end
+ -- probably wrong
+ local l = steps[1].coverage[getchar(start)]
+ if l then
+ return handle_contextchain(head,start,dataset,sequence,l,rlmode,skiphash)
+ else
+ return head, start, false
+ end
+end
+
+chainprocs.gsub_context = chained_contextchain
+chainprocs.gsub_contextchain = chained_contextchain
+chainprocs.gsub_reversecontextchain = chained_contextchain
+chainprocs.gpos_contextchain = chained_contextchain
+chainprocs.gpos_context = chained_contextchain
+
+------------------------------
+
+-- experiment (needs no handler in font-otc so not now):
+--
+-- function otf.registerchainproc(name,f)
+-- -- chainprocs[name] = f
+-- chainprocs[name] = function(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash)
+-- local done = currentlookup.nofsteps > 0
+-- if not done then
+-- reportzerosteps(dataset,sequence)
+-- else
+-- head, start, done = f(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash)
+-- if not head or not start then
+-- reportbadsteps(dataset,sequence)
+-- end
+-- end
+-- return head, start, done
+-- end
+-- end
+
+local missing = setmetatableindex("table")
+local logwarning = report_process
+local resolved = { } -- we only resolve a font,script,language pair once
+
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps == "silent" then
+ return
+ end
+ end
+ report_process(...)
+end
+
+-- todo: pass all these 'locals' in a table
+
+local sequencelists = setmetatableindex(function(t,font)
+ local sequences = fontdata[font].resources.sequences
+ if not sequences or not next(sequences) then
+ sequences = false
+ end
+ t[font] = sequences
+ return sequences
+end)
+
+-- fonts.hashes.sequences = sequencelists
+
+do -- overcome local limit
+
+ local autofeatures = fonts.analyzers.features
+ local featuretypes = otf.tables.featuretypes
+ local defaultscript = otf.features.checkeddefaultscript
+ local defaultlanguage = otf.features.checkeddefaultlanguage
+
+ local wildcard = "*"
+ local default = "dflt"
+
+ local function initialize(sequence,script,language,enabled,autoscript,autolanguage)
+ local features = sequence.features
+ if features then
+ local order = sequence.order
+ if order then
+ local featuretype = featuretypes[sequence.type or "unknown"]
+ for i=1,#order do
+ local kind = order[i]
+ local valid = enabled[kind]
+ if valid then
+ local scripts = features[kind]
+ local languages = scripts and (
+ scripts[script] or
+ scripts[wildcard] or
+ (autoscript and defaultscript(featuretype,autoscript,scripts))
+ )
+ local enabled = languages and (
+ languages[language] or
+ languages[wildcard] or
+ (autolanguage and defaultlanguage(featuretype,autolanguage,languages))
+ )
+ if enabled then
+ return { valid, autofeatures[kind] or false, sequence, kind }
+ end
+ end
+ end
+ else
+ -- can't happen
+ end
+ end
+ return false
+ end
+
+ function otf.dataset(tfmdata,font) -- generic variant, overloaded in context
+ local shared = tfmdata.shared
+ local properties = tfmdata.properties
+ local language = properties.language or "dflt"
+ local script = properties.script or "dflt"
+ local enabled = shared.features
+ local autoscript = enabled and enabled.autoscript
+ local autolanguage = enabled and enabled.autolanguage
+ local res = resolved[font]
+ if not res then
+ res = { }
+ resolved[font] = res
+ end
+ local rs = res[script]
+ if not rs then
+ rs = { }
+ res[script] = rs
+ end
+ local rl = rs[language]
+ if not rl then
+ rl = {
+ -- indexed but we can also add specific data by key
+ }
+ rs[language] = rl
+ local sequences = tfmdata.resources.sequences
+ if sequences then
+ for s=1,#sequences do
+ local v = enabled and initialize(sequences[s],script,language,enabled,autoscript,autolanguage)
+ if v then
+ rl[#rl+1] = v
+ end
+ end
+ end
+ end
+ return rl
+ end
+
+end
+
+-- Functions like kernrun, comprun etc evolved over time and in the end look rather
+-- complex. It's a bit of a compromis between extensive copying and creating subruns.
+-- The logic has been improved a lot by Kai and Ivo who use complex fonts which
+-- really helped to identify border cases on the one hand and get insight in the diverse
+-- ways fonts implement features (not always that consistent and efficient). At the same
+-- time I tried to keep the code relatively efficient so that the overhead in runtime
+-- stays acceptable.
+
+local function report_disc(what,n)
+ report_run("%s: %s > %s",what,n,languages.serializediscretionary(n))
+end
+
+local function kernrun(disc,k_run,font,attr,...)
+ --
+ -- we catch <font 1><disc font 2>
+ --
+ if trace_kernruns then
+ report_disc("kern",disc)
+ end
+ --
+ local prev, next = getboth(disc)
+ --
+ local nextstart = next
+ local done = false
+ --
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(disc,true)
+ --
+ local prevmarks = prev
+ --
+ -- can be optional, because why on earth do we get a disc after a mark (okay, maybe when a ccmp
+ -- has happened but then it should be in the disc so basically this test indicates an error)
+ --
+ while prevmarks do
+ local char = ischar(prevmarks,font)
+ if char and marks[char] then
+ prevmarks = getprev(prevmarks)
+ else
+ break
+ end
+ end
+ --
+ if prev and not ischar(prev,font) then -- and (pre or replace)
+ prev = false
+ end
+ if next and not ischar(next,font) then -- and (post or replace)
+ next = false
+ end
+ --
+ -- we need to get rid of this nest mess some day .. has to be done otherwise
+ --
+ if pre then
+ if k_run(pre,"injections",nil,font,attr,...) then
+ done = true
+ end
+ if prev then
+ setlink(prev,pre)
+ if k_run(prevmarks,"preinjections",pre,font,attr,...) then -- or prev?
+ done = true
+ end
+ setprev(pre)
+ setlink(prev,disc)
+ end
+ end
+ --
+ if post then
+ if k_run(post,"injections",nil,font,attr,...) then
+ done = true
+ end
+ if next then
+ setlink(posttail,next)
+ if k_run(posttail,"postinjections",next,font,attr,...) then
+ done = true
+ end
+ setnext(posttail)
+ setlink(disc,next)
+ end
+ end
+ --
+ if replace then
+ if k_run(replace,"injections",nil,font,attr,...) then
+ done = true
+ end
+ if prev then
+ setlink(prev,replace)
+ if k_run(prevmarks,"replaceinjections",replace,font,attr,...) then -- getnext(replace))
+ done = true
+ end
+ setprev(replace)
+ setlink(prev,disc)
+ end
+ if next then
+ setlink(replacetail,next)
+ if k_run(replacetail,"replaceinjections",next,font,attr,...) then
+ done = true
+ end
+ setnext(replacetail)
+ setlink(disc,next)
+ end
+ elseif prev and next then
+ setlink(prev,next)
+ if k_run(prevmarks,"emptyinjections",next,font,attr,...) then
+ done = true
+ end
+ setlink(prev,disc,next)
+ end
+ if done and trace_testruns then
+ report_disc("done",disc)
+ end
+ return nextstart, done
+end
+
+-- fonts like ebgaramond do ligatures this way (less efficient than e.g. dejavu which
+-- will do the testrun variant)
+
+local function comprun(disc,c_run,...) -- vararg faster than the whole list
+ if trace_compruns then
+ report_disc("comp",disc)
+ end
+ --
+ local pre, post, replace = getdisc(disc)
+ local renewed = false
+ --
+ if pre then
+ sweepnode = disc
+ sweeptype = "pre" -- in alternative code preinjections is used (also used then for properties, saves a variable)
+ local new, done = c_run(pre,...)
+ if done then
+ pre = new
+ renewed = true
+ end
+ end
+ --
+ if post then
+ sweepnode = disc
+ sweeptype = "post"
+ local new, done = c_run(post,...)
+ if done then
+ post = new
+ renewed = true
+ end
+ end
+ --
+ if replace then
+ sweepnode = disc
+ sweeptype = "replace"
+ local new, done = c_run(replace,...)
+ if done then
+ replace = new
+ renewed = true
+ end
+ end
+ --
+ sweepnode = nil
+ sweeptype = nil
+ if renewed then
+ if trace_testruns then
+ report_disc("done",disc)
+ end
+ setdisc(disc,pre,post,replace)
+ end
+ --
+ return getnext(disc), renewed
+end
+
+-- if we can hyphenate in a lig then unlikely a lig so we
+-- could have a option here to ignore lig
+
+local function testrun(disc,t_run,c_run,...)
+ if trace_testruns then
+ report_disc("test",disc)
+ end
+ local prev, next = getboth(disc)
+ if not next then
+ -- weird discretionary
+ return
+ end
+ local pre, post, replace, pretail, posttail, replacetail = getdisc(disc,true)
+ local renewed = false
+ if (post or replace) then -- and prev then -- hm, we can start with a disc
+ if post then
+ setlink(posttail,next)
+ else
+ post = next
+ end
+ if replace then
+ setlink(replacetail,next)
+ else
+ replace = next
+ end
+ local d_post = t_run(post,next,...)
+ local d_replace = t_run(replace,next,...)
+ if d_post > 0 or d_replace > 0 then
+ local d = d_replace > d_post and d_replace or d_post
+ local head = getnext(disc) -- is: next
+ local tail = head
+ for i=2,d do -- must start at 2 according to Kai
+ local nx = getnext(tail)
+ local id = getid(nx)
+ if id == disc_code then
+ head, tail = flattendisk(head,nx)
+ elseif id == glyph_code then
+ tail = nx
+ else
+ -- we can have overrun into a glue
+ break
+ end
+ end
+ next = getnext(tail)
+ setnext(tail)
+ setprev(head)
+ local new = copy_node_list(head)
+ if posttail then
+ setlink(posttail,head)
+ else
+ post = head
+ end
+ if replacetail then
+ setlink(replacetail,new)
+ else
+ replace = new
+ end
+ else
+ -- we stay inside the disc
+ if posttail then
+ setnext(posttail)
+ else
+ post = nil
+ end
+ if replacetail then
+ setnext(replacetail)
+ else
+ replace = nil
+ end
+ end
+ setlink(disc,next)
+ -- pre, post, replace, pretail, posttail, replacetail = getdisc(disc,true)
+ end
+ --
+ -- like comprun
+ --
+ if trace_testruns then
+ report_disc("more",disc)
+ end
+ --
+ if pre then
+ sweepnode = disc
+ sweeptype = "pre"
+ local new, ok = c_run(pre,...)
+ if ok then
+ pre = new
+ renewed = true
+ end
+ end
+ --
+ if post then
+ sweepnode = disc
+ sweeptype = "post"
+ local new, ok = c_run(post,...)
+ if ok then
+ post = new
+ renewed = true
+ end
+ end
+ --
+ if replace then
+ sweepnode = disc
+ sweeptype = "replace"
+ local new, ok = c_run(replace,...)
+ if ok then
+ replace = new
+ renewed = true
+ end
+ end
+ --
+ sweepnode = nil
+ sweeptype = nil
+ if renewed then
+ setdisc(disc,pre,post,replace)
+ if trace_testruns then
+ report_disc("done",disc)
+ end
+ end
+ -- next can have changed (copied list)
+ return getnext(disc), renewed
+end
+
+-- We can make some assumptions with respect to discretionaries. First of all it is very
+-- unlikely that some of the analysis related attributes applies. Then we can also assume
+-- that the ConTeXt specific dynamic attribute is different, although we do use explicit
+-- discretionaries (maybe we need to tag those some day). So, at least for now, we don't
+-- have the following test in the sub runs:
+--
+-- -- local a = getglyhpdata(start)
+-- -- if a then
+-- -- a = (a == attr) and (not attribute or getprop(start,a_state) == attribute)
+-- -- else
+-- -- a = not attribute or getprop(start,a_state) == attribute
+-- -- end
+-- -- if a then
+--
+-- but use this instead:
+--
+-- -- local a = getglyphdata(start)
+-- -- if not a or (a == attr) then
+--
+-- and even that one is probably not needed. However, we can handle interesting
+-- cases now:
+--
+-- 1{2{\oldstyle\discretionary{3}{4}{5}}6}7\par
+-- 1{2\discretionary{3{\oldstyle3}}{{\oldstyle4}4}{5{\oldstyle5}5}6}7\par
+
+local nesting = 0
+
+local function c_run_single(head,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ local done = false
+ local sweep = sweephead[head]
+ if sweep then
+ start = sweep
+ -- sweephead[head] = nil
+ sweephead[head] = false
+ else
+ start = head
+ end
+ while start do
+ local char, id = ischar(start,font)
+ if char then
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(start)
+ end
+ if not a or (a == attr) then
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ local ok
+ head, start, ok = handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ done = true
+ end
+ end
+ if start then
+ start = getnext(start)
+ end
+ else
+ -- go on can be a mixed one
+ start = getnext(start)
+ end
+ elseif char == false then
+ return head, done
+ elseif sweep then
+ -- else we loose the rest
+ return head, done
+ else
+ -- in disc component
+ start = getnext(start)
+ end
+ end
+ return head, done
+end
+
+-- only replace?
+
+local function t_run_single(start,stop,font,attr,lookupcache)
+ local lastd = nil
+ while start ~= stop do
+ local char = ischar(start,font)
+ if char then
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(start)
+ end
+ local startnext = getnext(start)
+ if not a or (a == attr) then
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then -- hm, hyphens can match (tlig) so we need to really check
+ -- if we need more than ligatures we can outline the code and use functions
+ local s = startnext
+ local ss = nil
+ local sstop = s == stop
+ if not s then
+ s = ss
+ ss = nil
+ end
+ -- a bit weird: why multiple ... anyway we can't have a disc in a disc
+ -- how about post ... we can probably merge this into the while
+ while getid(s) == disc_code do
+ ss = getnext(s)
+ s = getfield(s,"replace")
+ if not s then
+ s = ss
+ ss = nil
+ end
+ end
+ local l = nil
+ local d = 0
+ while s do
+ local char = ischar(s,font)
+ if char then
+ local lg = lookupmatch[char]
+ if lg then
+ if sstop then
+ d = 1
+ elseif d > 0 then
+ d = d + 1
+ end
+ l = lg
+ s = getnext(s)
+ sstop = s == stop
+ if not s then
+ s = ss
+ ss = nil
+ end
+ while getid(s) == disc_code do
+ ss = getnext(s)
+ s = getfield(s,"replace")
+ if not s then
+ s = ss
+ ss = nil
+ end
+ end
+lookupmatch = lg
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if l and l.ligature then -- so we test for ligature
+ lastd = d
+ end
+-- why not: if not l then break elseif l.ligature then return d end
+ else
+-- why not: break
+ -- no match (yet)
+ end
+ else
+ -- go on can be a mixed one
+-- why not: break
+ end
+ if lastd then
+ return lastd
+ end
+ start = startnext
+ else
+ break
+ end
+ end
+ return 0
+end
+
+local function k_run_single(sub,injection,last,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(sub)
+ end
+ if not a or (a == attr) then
+ for n in nextnode, sub do -- only gpos
+ if n == last then
+ break
+ end
+ local char = ischar(n)
+ if char then
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ local h, d, ok = handler(sub,n,dataset,sequence,lookupmatch,rlmode,skiphash,step,injection)
+ if ok then
+ return true
+ end
+ end
+ end
+ end
+ end
+end
+
+local function c_run_multiple(head,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ local done = false
+ local sweep = sweephead[head]
+ if sweep then
+ start = sweep
+ -- sweephead[head] = nil
+ sweephead[head] = false
+ else
+ start = head
+ end
+ while start do
+ local char = ischar(start,font)
+ if char then
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(start)
+ end
+ if not a or (a == attr) then
+ for i=1,nofsteps do
+ local step = steps[i]
+ local lookupcache = step.coverage
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ -- we could move all code inline but that makes things even more unreadable
+ local ok
+ head, start, ok = handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ done = true
+ break
+ elseif not start then
+ -- don't ask why ... shouldn't happen
+ break
+ end
+ end
+ end
+ if start then
+ start = getnext(start)
+ end
+ else
+ -- go on can be a mixed one
+ start = getnext(start)
+ end
+ elseif char == false then
+ -- whatever glyph
+ return head, done
+ elseif sweep then
+ -- else we loose the rest
+ return head, done
+ else
+ -- in disc component
+ start = getnext(start)
+ end
+ end
+ return head, done
+end
+
+local function t_run_multiple(start,stop,font,attr,steps,nofsteps)
+ local lastd = nil
+ while start ~= stop do
+ local char = ischar(start,font)
+ if char then
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(start)
+ end
+ local startnext = getnext(start)
+ if not a or (a == attr) then
+ for i=1,nofsteps do
+ local step = steps[i]
+ local lookupcache = step.coverage
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ -- if we need more than ligatures we can outline the code and use functions
+ local s = startnext
+ local ss = nil
+ local sstop = s == stop
+ if not s then
+ s = ss
+ ss = nil
+ end
+ while getid(s) == disc_code do
+ ss = getnext(s)
+ s = getfield(s,"replace")
+ if not s then
+ s = ss
+ ss = nil
+ end
+ end
+ local l = nil
+ local d = 0
+ while s do
+ local char = ischar(s)
+ if char then
+ local lg = lookupmatch[char]
+ if lg then
+ if sstop then
+ d = 1
+ elseif d > 0 then
+ d = d + 1
+ end
+ l = lg
+ s = getnext(s)
+ sstop = s == stop
+ if not s then
+ s = ss
+ ss = nil
+ end
+ while getid(s) == disc_code do
+ ss = getnext(s)
+ s = getfield(s,"replace")
+ if not s then
+ s = ss
+ ss = nil
+ end
+ end
+lookupmatch = lg
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if l and l.ligature then
+ lastd = d
+ end
+ end
+ end
+ else
+ -- go on can be a mixed one
+ end
+ if lastd then
+ return lastd
+ end
+ start = startnext
+ else
+ break
+ end
+ end
+ return 0
+end
+
+local function k_run_multiple(sub,injection,last,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(sub)
+ end
+ if not a or (a == attr) then
+ for n in nextnode, sub do -- only gpos
+ if n == last then
+ break
+ end
+ local char = ischar(n)
+ if char then
+ for i=1,nofsteps do
+ local step = steps[i]
+ local lookupcache = step.coverage
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ local h, d, ok = handler(sub,n,dataset,sequence,lookupmatch,rlmode,skiphash,step,injection) -- sub was head
+ if ok then
+ return true
+ end
+ end
+ end
+ end
+ end
+ end
+end
+
+local txtdirstate, pardirstate do -- this might change (no need for nxt in pardirstate)
+
+ local getdirection = nuts.getdirection
+ local lefttoright = 0
+ local righttoleft = 1
+
+ txtdirstate = function(start,stack,top,rlparmode)
+ local dir, pop = getdirection(start)
+ if pop then
+ if top == 1 then
+ return 0, rlparmode
+ else
+ top = top - 1
+ if stack[top] == righttoleft then
+ return top, -1
+ else
+ return top, 1
+ end
+ end
+ elseif dir == lefttoright then
+ top = top + 1
+ stack[top] = lefttoright
+ return top, 1
+ elseif dir == righttoleft then
+ top = top + 1
+ stack[top] = righttoleft
+ return top, -1
+ else
+ return top, rlparmode
+ end
+ end
+
+ pardirstate = function(start)
+ local dir = getdirection(start)
+ if dir == lefttoright then
+ return 1, 1
+ elseif dir == righttoleft then
+ return -1, -1
+ -- for old times sake we we handle strings too
+ elseif dir == "TLT" then
+ return 1, 1
+ elseif dir == "TRT" then
+ return -1, -1
+ else
+ return 0, 0
+ end
+ end
+
+end
+
+-- These are non public helpers that can change without notice!
+
+otf.helpers = otf.helpers or { }
+otf.helpers.txtdirstate = txtdirstate
+otf.helpers.pardirstate = pardirstate
+
+-- This is the main loop. We run over the node list dealing with a specific font. The
+-- attribute is a context specific thing. We could work on sub start-stop ranges instead
+-- but I wonder if there is that much speed gain (experiments showed that it made not
+-- much sense) and we need to keep track of directions anyway. Also at some point I
+-- want to play with font interactions and then we do need the full sweeps. Apart from
+-- optimizations the principles of processing the features hasn't changed much since
+-- the beginning.
+
+do
+
+ -- reference:
+ --
+ -- local a = attr and getglyphdata(start)
+ -- if a then
+ -- a = (a == attr) and (not attribute or getprop(start,a_state) == attribute)
+ -- else
+ -- a = not attribute or getprop(start,a_state) == attribute
+ -- end
+ --
+ -- used:
+ --
+ -- local a -- happens often so no assignment is faster
+ -- if attr then
+ -- if getglyphdata(start) == attr and (not attribute or getprop(start,a_state) == attribute) then
+ -- a = true
+ -- end
+ -- elseif not attribute or getprop(start,a_state) == attribute then
+ -- a = true
+ -- end
+
+ -- This is a measurable experimental speedup (only with hyphenated text and multiple
+ -- fonts per processor call), especially for fonts with lots of contextual lookups.
+
+ local fastdisc = true
+ local testdics = false
+
+ directives.register("otf.fastdisc",function(v) fastdisc = v end) -- normally enabled
+
+ -- using a merged combined hash as first test saves some 30% on ebgaramond and
+ -- about 15% on arabtype .. then moving the a test also saves a bit (even when
+ -- often a is not set at all so that one is a bit debatable
+
+ local otfdataset = nil -- todo: make an installer
+
+ local getfastdisc = { __index = function(t,k)
+ local v = usesfont(k,currentfont)
+ t[k] = v
+ return v
+ end }
+
+ local getfastspace = { __index = function(t,k)
+ -- we don't pass the id so that one can overload isspace
+ local v = isspace(k,threshold) or false
+ t[k] = v
+ return v
+ end }
+
+ function otf.featuresprocessor(head,font,attr,direction,n)
+
+ local sequences = sequencelists[font] -- temp hack
+
+ nesting = nesting + 1
+
+ if nesting == 1 then
+ currentfont = font
+ tfmdata = fontdata[font]
+ descriptions = tfmdata.descriptions -- only needed in gref so we could pass node there instead
+ characters = tfmdata.characters -- but this branch is not entered that often anyway
+ local resources = tfmdata.resources
+ marks = resources.marks
+ classes = resources.classes
+ threshold,
+ factor = getthreshold(font)
+ checkmarks = tfmdata.properties.checkmarks
+
+ if not otfdataset then
+ otfdataset = otf.dataset
+ end
+
+ discs = fastdisc and n and n > 1 and setmetatable({},getfastdisc) -- maybe inline
+ spaces = setmetatable({},getfastspace)
+
+ elseif currentfont ~= font then
+
+ report_warning("nested call with a different font, level %s, quitting",nesting)
+ nesting = nesting - 1
+ return head, false
+
+ end
+
+ -- some 10% faster when no dynamics but hardly measureable on real runs .. but: it only
+ -- works when we have no other dynamics as otherwise the zero run will be applied to the
+ -- whole stream for which we then need to pass another variable which we won't
+
+ -- if attr == 0 then
+ -- attr = false
+ -- end
+
+ if trace_steps then
+ checkstep(head)
+ end
+
+ local initialrl = 0
+
+ if getid(head) == localpar_code and getsubtype(head) == 0 then
+ initialrl = pardirstate(head)
+ elseif direction == 1 or direction == "TRT" then
+ initialrl = -1
+ end
+
+ -- local done = false
+ local datasets = otfdataset(tfmdata,font,attr)
+ local dirstack = { nil } -- could move outside function but we can have local runs
+ sweephead = { }
+ -- sweephead = { a = 1, b = 1 } sweephead.a = nil sweephead.b = nil
+
+ -- Keeping track of the headnode is needed for devanagari. (I generalized it a bit
+ -- so that multiple cases are also covered.) We could prepend a temp node.
+
+ -- We don't goto the next node when a disc node is created so that we can then treat
+ -- the pre, post and replace. It's a bit of a hack but works out ok for most cases.
+
+ for s=1,#datasets do
+ local dataset = datasets[s]
+ local attribute = dataset[2]
+ local sequence = dataset[3] -- sequences[s] -- also dataset[5]
+ local rlparmode = initialrl
+ local topstack = 0
+ local typ = sequence.type
+ local gpossing = typ == "gpos_single" or typ == "gpos_pair" -- store in dataset
+ local forcetestrun = typ == "gsub_ligature" -- testrun is only for ligatures
+ local handler = handlers[typ] -- store in dataset
+ local steps = sequence.steps
+ local nofsteps = sequence.nofsteps
+ local skiphash = sequence.skiphash
+
+ if not steps then
+ -- This permits injection, watch the different arguments. Watch out, the arguments passed
+ -- are not frozen as we might extend or change this. Is this used at all apart from some
+ -- experiments?
+ local h, ok = handler(head,dataset,sequence,initialrl,font,attr) -- less arguments now
+ -- if ok then
+ -- done = true
+ -- end
+ if h and h ~= head then
+ head = h
+ end
+ elseif typ == "gsub_reversecontextchain" then
+ --
+ -- This might need a check: if we have #before or #after > 0 then we might need to reverse
+ -- the before and after lists in the loader. But first I need to see a font that uses multiple
+ -- matches.
+ --
+ local start = find_node_tail(head)
+ local rlmode = 0 -- how important is this .. do we need to check for dir?
+ local merged = steps.merged
+ while start do
+ local char = ischar(start,font)
+ if char then
+ local m = merged[char]
+ if m then
+ local a -- happens often so no assignment is faster
+ if attr then
+ a = getglyphdata(start)
+ end
+ if not a or (a == attr) then
+ for i=m[1],m[2] do
+ local step = steps[i]
+ -- for i=1,#m do
+ -- local step = m[i]
+ local lookupcache = step.coverage
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ local ok
+ head, start, ok = handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ -- done = true
+ break
+ end
+ end
+ end
+ if start then
+ start = getprev(start)
+ end
+ else
+ start = getprev(start)
+ end
+ else
+ start = getprev(start)
+ end
+ else
+ start = getprev(start)
+ end
+ end
+ else
+ local start = head
+ local rlmode = initialrl
+ if nofsteps == 1 then -- happens often
+ local step = steps[1]
+ local lookupcache = step.coverage
+ while start do
+ local char, id = ischar(start,font)
+ if char then
+ if skiphash and skiphash[char] then -- we never needed it here but let's try
+ start = getnext(start)
+ else
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ local a -- happens often so no assignment is faster
+ if attr then
+ if getglyphdata(start) == attr and (not attribute or getprop(start,a_state) == attribute) then
+ a = true
+ end
+ elseif not attribute or getprop(start,a_state) == attribute then
+ a = true
+ end
+ if a then
+ local ok, df
+ head, start, ok, df = handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ -- if ok then
+ -- done = true
+ -- end
+ if df then
+-- print("restart 1",typ)
+ elseif start then
+ start = getnext(start)
+ end
+ else
+ start = getnext(start)
+ end
+ else
+ start = getnext(start)
+ end
+ end
+ elseif char == false or id == glue_code then
+ -- a different font|state or glue (happens often)
+ start = getnext(start)
+ elseif id == disc_code then
+ if not discs or discs[start] == true then
+ local ok
+ if gpossing then
+ start, ok = kernrun(start,k_run_single, font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ elseif forcetestrun then
+ start, ok = testrun(start,t_run_single,c_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ else
+ start, ok = comprun(start,c_run_single, font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ end
+ -- if ok then
+ -- done = true
+ -- end
+ else
+ start = getnext(start)
+ end
+ elseif id == math_code then
+ start = getnext(end_of_math(start))
+ elseif id == dir_code then
+ topstack, rlmode = txtdirstate(start,dirstack,topstack,rlparmode)
+ start = getnext(start)
+ -- elseif id == localpar_code then
+ -- rlparmode, rlmode = pardirstate(start)
+ -- start = getnext(start)
+ else
+ start = getnext(start)
+ end
+ end
+ else
+ local merged = steps.merged
+ while start do
+ local char, id = ischar(start,font)
+ if char then
+ if skiphash and skiphash[char] then -- we never needed it here but let's try
+ start = getnext(start)
+ else
+ local m = merged[char]
+ if m then
+ local a -- happens often so no assignment is faster
+ if attr then
+ if getglyphdata(start) == attr and (not attribute or getprop(start,a_state) == attribute) then
+ a = true
+ end
+ elseif not attribute or getprop(start,a_state) == attribute then
+ a = true
+ end
+ if a then
+ local ok, df
+ for i=m[1],m[2] do
+ local step = steps[i]
+ -- for i=1,#m do
+ -- local step = m[i]
+ local lookupcache = step.coverage
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ -- we could move all code inline but that makes things even more unreadable
+-- local ok, df
+ head, start, ok, df = handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if df then
+ break
+ elseif ok then
+ -- done = true
+ break
+ elseif not start then
+ -- don't ask why ... shouldn't happen
+ break
+ end
+ end
+ end
+ if df then
+-- print("restart 2",typ)
+ elseif start then
+ start = getnext(start)
+ end
+ else
+ start = getnext(start)
+ end
+ else
+ start = getnext(start)
+ end
+ end
+ elseif char == false or id == glue_code then
+ -- a different font|state or glue (happens often)
+ start = getnext(start)
+ elseif id == disc_code then
+ if not discs or discs[start] == true then
+ local ok
+ if gpossing then
+ start, ok = kernrun(start,k_run_multiple, font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ elseif forcetestrun then
+ start, ok = testrun(start,t_run_multiple,c_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ else
+ start, ok = comprun(start,c_run_multiple, font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ end
+ -- if ok then
+ -- done = true
+ -- end
+ else
+ start = getnext(start)
+ end
+ elseif id == math_code then
+ start = getnext(end_of_math(start))
+ elseif id == dir_code then
+ topstack, rlmode = txtdirstate(start,dirstack,topstack,rlparmode)
+ start = getnext(start)
+ -- elseif id == localpar_code then
+ -- rlparmode, rlmode = pardirstate(start)
+ -- start = getnext(start)
+ else
+ start = getnext(start)
+ end
+ end
+ end
+ end
+
+ if trace_steps then -- ?
+ registerstep(head)
+ end
+
+ end
+
+ nesting = nesting - 1
+
+ -- return head, done
+ return head
+ end
+
+ -- This is not an official helper and used for tracing experiments. It can be changed as I like
+ -- at any moment. At some point it might be used in a module that can help font development.
+
+ function otf.datasetpositionprocessor(head,font,direction,dataset)
+
+ currentfont = font
+ tfmdata = fontdata[font]
+ descriptions = tfmdata.descriptions -- only needed in gref so we could pass node there instead
+ characters = tfmdata.characters -- but this branch is not entered that often anyway
+ local resources = tfmdata.resources
+ marks = resources.marks
+ classes = resources.classes
+ threshold,
+ factor = getthreshold(font)
+ checkmarks = tfmdata.properties.checkmarks
+
+ if type(dataset) == "number" then
+ dataset = otfdataset(tfmdata,font,0)[dataset]
+ end
+
+ local sequence = dataset[3] -- sequences[s] -- also dataset[5]
+ local typ = sequence.type
+ -- local gpossing = typ == "gpos_single" or typ == "gpos_pair" -- store in dataset
+
+ -- gpos_contextchain gpos_context
+
+ -- if not gpossing then
+ -- return head, false
+ -- end
+
+ local handler = handlers[typ] -- store in dataset
+ local steps = sequence.steps
+ local nofsteps = sequence.nofsteps
+
+ local done = false
+ local dirstack = { nil } -- could move outside function but we can have local runs (maybe a few more nils)
+ local start = head
+ local initialrl = (direction == 1 or direction == "TRT") and -1 or 0
+ local rlmode = initialrl
+ local rlparmode = initialrl
+ local topstack = 0
+ local merged = steps.merged
+
+ -- local matches = false
+ local position = 0
+
+ while start do
+ local char, id = ischar(start,font)
+ if char then
+ position = position + 1
+ local m = merged[char]
+ if m then
+ if skiphash and skiphash[char] then -- we never needed it here but let's try
+ start = getnext(start)
+ else
+ for i=m[1],m[2] do
+ local step = steps[i]
+ local lookupcache = step.coverage
+ local lookupmatch = lookupcache[char]
+ if lookupmatch then
+ local ok
+ head, start, ok = handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ -- if matches then
+ -- matches[position] = i
+ -- else
+ -- matches = { [position] = i }
+ -- end
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if start then
+ start = getnext(start)
+ end
+ end
+ else
+ start = getnext(start)
+ end
+ elseif char == false or id == glue_code then
+ -- a different font|state or glue (happens often)
+ start = getnext(start)
+ elseif id == math_code then
+ start = getnext(end_of_math(start))
+ elseif id == dir_code then
+ topstack, rlmode = txtdirstate(start,dirstack,topstack,rlparmode)
+ start = getnext(start)
+ -- elseif id == localpar_code then
+ -- rlparmode, rlmode = pardirstate(start)
+ -- start = getnext(start)
+ else
+ start = getnext(start)
+ end
+ end
+
+ return head
+ end
+
+ -- end of experiment
+
+end
+
+-- so far
+
+local plugins = { }
+otf.plugins = plugins
+
+local report = logs.reporter("fonts")
+
+function otf.registerplugin(name,f)
+ if type(name) == "string" and type(f) == "function" then
+ plugins[name] = { name, f }
+ report()
+ report("plugin %a has been loaded, please be aware of possible side effects",name)
+ report()
+ if logs.pushtarget then
+ logs.pushtarget("log")
+ end
+ report("Plugins are not officially supported unless stated otherwise. This is because")
+ report("they bypass the regular font handling and therefore some features in ConTeXt")
+ report("(especially those related to fonts) might not work as expected or might not work")
+ report("at all. Some plugins are for testing and development only and might change")
+ report("whenever we feel the need for it.")
+ report()
+ if logs.poptarget then
+ logs.poptarget()
+ end
+ end
+end
+
+function otf.plugininitializer(tfmdata,value)
+ if type(value) == "string" then
+ tfmdata.shared.plugin = plugins[value]
+ end
+end
+
+function otf.pluginprocessor(head,font,attr,direction) -- n
+ local s = fontdata[font].shared
+ local p = s and s.plugin
+ if p then
+ if trace_plugins then
+ report_process("applying plugin %a",p[1])
+ end
+ return p[2](head,font,attr,direction)
+ else
+ return head, false
+ end
+end
+
+function otf.featuresinitializer(tfmdata,value)
+ -- nothing done here any more
+end
+
+registerotffeature {
+ name = "features",
+ description = "features",
+ default = true,
+ initializers = {
+ position = 1,
+ node = otf.featuresinitializer,
+ plug = otf.plugininitializer,
+ },
+ processors = {
+ node = otf.featuresprocessor,
+ plug = otf.pluginprocessor,
+ }
+}
+
+-- This can be used for extra handlers, but should be used with care! We implement one
+-- here but some more can be found in the osd (script devanagary) file. Now watch out:
+-- when a handlers has steps, it is called as the other ones, but when we have no steps,
+-- we use a different call:
+--
+-- function(head,dataset,sequence,initialrl,font,attr)
+-- return head, done
+-- end
+--
+-- Also see (!!).
+
+otf.handlers = handlers
+
+local setspacekerns = nodes.injections.setspacekerns if not setspacekerns then os.exit() end
+
+local tag = "kern" -- maybe some day a merge
+
+if fontfeatures then
+
+ function handlers.trigger_space_kerns(head,dataset,sequence,initialrl,font,attr)
+ local features = fontfeatures[font]
+ local enabled = features and features.spacekern and features[tag]
+ if enabled then
+ setspacekerns(font,sequence)
+ end
+ return head, enabled
+ end
+
+else -- generic (no hashes)
+
+ function handlers.trigger_space_kerns(head,dataset,sequence,initialrl,font,attr)
+ local shared = fontdata[font].shared
+ local features = shared and shared.features
+ local enabled = features and features.spacekern and features[tag]
+ if enabled then
+ setspacekerns(font,sequence)
+ end
+ return head, enabled
+ end
+
+end
+
+-- There are fonts out there that change the space but we don't do that kind of
+-- things in TeX.
+
+local function hasspacekerns(data)
+ local resources = data.resources
+ local sequences = resources.sequences
+ local validgpos = resources.features.gpos
+ if validgpos and sequences then
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local steps = sequence.steps
+ if steps and sequence.features[tag] then
+ local kind = sequence.type
+ if kind == "gpos_pair" or kind == "gpos_single" then
+ for i=1,#steps do
+ local step = steps[i]
+ local coverage = step.coverage
+ local rules = step.rules
+ if rules then
+ -- not now: analyze (simple) rules
+ elseif not coverage then
+ -- nothing to do
+ elseif kind == "gpos_single" then
+ -- maybe a message that we ignore
+ elseif kind == "gpos_pair" then
+ local format = step.format
+ if format == "move" or format == "kern" then
+ local kerns = coverage[32]
+ if kerns then
+ return true
+ end
+ for k, v in next, coverage do
+ if v[32] then
+ return true
+ end
+ end
+ elseif format == "pair" then
+ local kerns = coverage[32]
+ if kerns then
+ for k, v in next, kerns do
+ local one = v[1]
+ if one and one ~= true then
+ return true
+ end
+ end
+ end
+ for k, v in next, coverage do
+ local kern = v[32]
+ if kern then
+ local one = kern[1]
+ if one and one ~= true then
+ return true
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ return false
+end
+
+otf.readers.registerextender {
+ name = "spacekerns",
+ action = function(data)
+ data.properties.hasspacekerns = hasspacekerns(data)
+ end
+}
+
+local function spaceinitializer(tfmdata,value) -- attr
+ local resources = tfmdata.resources
+ local spacekerns = resources and resources.spacekerns
+ if value and spacekerns == nil then
+ local rawdata = tfmdata.shared and tfmdata.shared.rawdata
+ local properties = rawdata.properties
+ if properties and properties.hasspacekerns then
+ local sequences = resources.sequences
+ local validgpos = resources.features.gpos
+ if validgpos and sequences then
+ local left = { }
+ local right = { }
+ local last = 0
+ local feat = nil
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local steps = sequence.steps
+ if steps then
+ -- we don't support space kerns in other features
+ local kern = sequence.features[tag]
+ if kern then
+ local kind = sequence.type
+ if kind == "gpos_pair" or kind == "gpos_single" then
+ if feat then
+ for script, languages in next, kern do
+ local f = feat[script]
+ if f then
+ for l in next, languages do
+ f[l] = true
+ end
+ else
+ feat[script] = languages
+ end
+ end
+ else
+ feat = kern
+ end
+ for i=1,#steps do
+ local step = steps[i]
+ local coverage = step.coverage
+ local rules = step.rules
+ if rules then
+ -- not now: analyze (simple) rules
+ elseif not coverage then
+ -- nothng to do
+ elseif kind == "gpos_single" then
+ -- makes no sense in TeX
+ elseif kind == "gpos_pair" then
+ local format = step.format
+ if format == "move" or format == "kern" then
+ local kerns = coverage[32]
+ if kerns then
+ for k, v in next, kerns do
+ right[k] = v
+ end
+ end
+ for k, v in next, coverage do
+ local kern = v[32]
+ if kern then
+ left[k] = kern
+ end
+ end
+ elseif format == "pair" then
+ local kerns = coverage[32]
+ if kerns then
+ for k, v in next, kerns do
+ local one = v[1]
+ if one and one ~= true then
+ right[k] = one[3]
+ end
+ end
+ end
+ for k, v in next, coverage do
+ local kern = v[32]
+ if kern then
+ local one = kern[1]
+ if one and one ~= true then
+ left[k] = one[3]
+ end
+ end
+ end
+ end
+ end
+ end
+ last = i
+ end
+ else
+ -- no steps ... needed for old one ... we could use the basekerns
+ -- instead
+ end
+ end
+ end
+ left = next(left) and left or false
+ right = next(right) and right or false
+ if left or right then
+ spacekerns = {
+ left = left,
+ right = right,
+ }
+ if last > 0 then
+ local triggersequence = {
+ -- no steps, see (!!)
+ features = { [tag] = feat or { dflt = { dflt = true, } } },
+ flags = noflags,
+ name = "trigger_space_kerns",
+ order = { tag },
+ type = "trigger_space_kerns",
+ left = left,
+ right = right,
+ }
+ insert(sequences,last,triggersequence)
+ end
+ end
+ end
+ end
+ resources.spacekerns = spacekerns
+ end
+ return spacekerns
+end
+
+registerotffeature {
+ name = "spacekern",
+ description = "space kern injection",
+ default = true,
+ initializers = {
+ node = spaceinitializer,
+ },
+}
+
+local function markinitializer(tfmdata,value)
+ local properties = tfmdata.properties
+ properties.checkmarks = value
+end
+
+registerotffeature {
+ name = "checkmarks",
+ description = "check mark widths",
+ default = true,
+ initializers = {
+ node = markinitializer,
+ },
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-ott.lua b/macros/luatex/generic/luaotfload/fontloader-font-ott.lua
new file mode 100644
index 0000000000..c9e467f225
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-ott.lua
@@ -0,0 +1,1234 @@
+if not modules then modules = { } end modules ["font-ott"] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files",
+ -- dataonly = true,
+}
+
+local type, next, tonumber, tostring, rawget, rawset = type, next, tonumber, tostring, rawget, rawset
+local gsub, lower, format, match, gmatch, find = string.gsub, string.lower, string.format, string.match, string.gmatch, string.find
+local sequenced = table.sequenced
+local is_boolean = string.is_boolean
+
+local setmetatableindex = table.setmetatableindex
+local setmetatablenewindex = table.setmetatablenewindex
+local allocate = utilities.storage.allocate
+
+local fonts = fonts
+local otf = fonts.handlers.otf
+local otffeatures = otf.features
+
+local tables = otf.tables or { }
+otf.tables = tables
+
+local statistics = otf.statistics or { }
+otf.statistics = statistics
+
+local scripts = allocate {
+ ["adlm"] = "adlam",
+ ["aghb"] = "caucasian albanian",
+ ["ahom"] = "ahom",
+ ["arab"] = "arabic",
+ ["armi"] = "imperial aramaic",
+ ["armn"] = "armenian",
+ ["avst"] = "avestan",
+ ["bali"] = "balinese",
+ ["bamu"] = "bamum",
+ ["bass"] = "bassa vah",
+ ["batk"] = "batak",
+ ["beng"] = "bengali",
+ ["bhks"] = "bhaiksuki",
+ ["bng2"] = "bengali variant 2",
+ ["bopo"] = "bopomofo",
+ ["brah"] = "brahmi",
+ ["brai"] = "braille",
+ ["bugi"] = "buginese",
+ ["buhd"] = "buhid",
+ ["byzm"] = "byzantine music",
+ ["cakm"] = "chakma",
+ ["cans"] = "canadian syllabics",
+ ["cari"] = "carian",
+ ["cham"] = "cham",
+ ["cher"] = "cherokee",
+ ["copt"] = "coptic",
+ ["cprt"] = "cypriot syllabary",
+ ["cyrl"] = "cyrillic",
+ ["dev2"] = "devanagari variant 2",
+ ["deva"] = "devanagari",
+ ["dogr"] = "dogra",
+ ["dsrt"] = "deseret",
+ ["dupl"] = "duployan",
+ ["egyp"] = "egyptian heiroglyphs",
+ ["elba"] = "elbasan",
+ ["ethi"] = "ethiopic",
+ ["geor"] = "georgian",
+ ["gjr2"] = "gujarati variant 2",
+ ["glag"] = "glagolitic",
+ ["gong"] = "gunjala gondi",
+ ["gonm"] = "masaram gondi",
+ ["goth"] = "gothic",
+ ["gran"] = "grantha",
+ ["grek"] = "greek",
+ ["gujr"] = "gujarati",
+ ["gur2"] = "gurmukhi variant 2",
+ ["guru"] = "gurmukhi",
+ ["hang"] = "hangul",
+ ["hani"] = "cjk ideographic",
+ ["hano"] = "hanunoo",
+ ["hatr"] = "hatran",
+ ["hebr"] = "hebrew",
+ ["hluw"] = "anatolian hieroglyphs",
+ ["hmng"] = "pahawh hmong",
+ ["hung"] = "old hungarian",
+ ["ital"] = "old italic",
+ ["jamo"] = "hangul jamo",
+ ["java"] = "javanese",
+ ["kali"] = "kayah li",
+ ["kana"] = "hiragana and katakana",
+ ["khar"] = "kharosthi",
+ ["khmr"] = "khmer",
+ ["khoj"] = "khojki",
+ ["knd2"] = "kannada variant 2",
+ ["knda"] = "kannada",
+ ["kthi"] = "kaithi",
+ ["lana"] = "tai tham",
+ ["lao" ] = "lao",
+ ["latn"] = "latin",
+ ["lepc"] = "lepcha",
+ ["limb"] = "limbu",
+ ["lina"] = "linear a",
+ ["linb"] = "linear b",
+ ["lisu"] = "lisu",
+ ["lyci"] = "lycian",
+ ["lydi"] = "lydian",
+ ["mahj"] = "mahajani",
+ ["maka"] = "makasar",
+ ["mand"] = "mandaic and mandaean",
+ ["mani"] = "manichaean",
+ ["marc"] = "marchen",
+ ["math"] = "mathematical alphanumeric symbols",
+ ["medf"] = "medefaidrin",
+ ["mend"] = "mende kikakui",
+ ["merc"] = "meroitic cursive",
+ ["mero"] = "meroitic hieroglyphs",
+ ["mlm2"] = "malayalam variant 2",
+ ["mlym"] = "malayalam",
+ ["modi"] = "modi",
+ ["mong"] = "mongolian",
+ ["mroo"] = "mro",
+ ["mtei"] = "meitei Mayek",
+ ["mult"] = "multani",
+ ["musc"] = "musical symbols",
+ ["mym2"] = "myanmar variant 2",
+ ["mymr"] = "myanmar",
+ ["narb"] = "old north arabian",
+ ["nbat"] = "nabataean",
+ ["newa"] = "newa",
+ ["nko" ] = 'n"ko',
+ ["nshu"] = "nüshu",
+ ["ogam"] = "ogham",
+ ["olck"] = "ol chiki",
+ ["orkh"] = "old turkic and orkhon runic",
+ ["ory2"] = "odia variant 2",
+ ["orya"] = "oriya",
+ ["osge"] = "osage",
+ ["osma"] = "osmanya",
+ ["palm"] = "palmyrene",
+ ["pauc"] = "pau cin hau",
+ ["perm"] = "old permic",
+ ["phag"] = "phags-pa",
+ ["phli"] = "inscriptional pahlavi",
+ ["phlp"] = "psalter pahlavi",
+ ["phnx"] = "phoenician",
+ ["plrd"] = "miao",
+ ["prti"] = "inscriptional parthian",
+ ["rjng"] = "rejang",
+ ["rohg"] = "hanifi rohingya",
+ ["runr"] = "runic",
+ ["samr"] = "samaritan",
+ ["sarb"] = "old south arabian",
+ ["saur"] = "saurashtra",
+ ["sgnw"] = "sign writing",
+ ["shaw"] = "shavian",
+ ["shrd"] = "sharada",
+ ["sidd"] = "siddham",
+ ["sind"] = "khudawadi",
+ ["sinh"] = "sinhala",
+ ["sogd"] = "sogdian",
+ ["sogo"] = "old sogdian",
+ ["sora"] = "sora sompeng",
+ ["soyo"] = "soyombo",
+ ["sund"] = "sundanese",
+ ["sylo"] = "syloti nagri",
+ ["syrc"] = "syriac",
+ ["tagb"] = "tagbanwa",
+ ["takr"] = "takri",
+ ["tale"] = "tai le",
+ ["talu"] = "tai lu",
+ ["taml"] = "tamil",
+ ["tang"] = "tangut",
+ ["tavt"] = "tai viet",
+ ["tel2"] = "telugu variant 2",
+ ["telu"] = "telugu",
+ ["tfng"] = "tifinagh",
+ ["tglg"] = "tagalog",
+ ["thaa"] = "thaana",
+ ["thai"] = "thai",
+ ["tibt"] = "tibetan",
+ ["tirh"] = "tirhuta",
+ ["tml2"] = "tamil variant 2",
+ ["ugar"] = "ugaritic cuneiform",
+ ["vai" ] = "vai",
+ ["wara"] = "warang citi",
+ ["xpeo"] = "old persian cuneiform",
+ ["xsux"] = "sumero-akkadian cuneiform",
+ ["yi" ] = "yi",
+ ["zanb"] = "zanabazar square",
+}
+
+local languages = allocate {
+ ["aba" ] = "abaza",
+ ["abk" ] = "abkhazian",
+ ["ach" ] = "acholi",
+ ["acr" ] = "achi",
+ ["ady" ] = "adyghe",
+ ["afk" ] = "afrikaans",
+ ["afr" ] = "afar",
+ ["agw" ] = "agaw",
+ ["aio" ] = "aiton",
+ ["aka" ] = "akan",
+ ["als" ] = "alsatian",
+ ["alt" ] = "altai",
+ ["amh" ] = "amharic",
+ ["ang" ] = "anglo-saxon",
+ ["apph"] = "phonetic transcription—americanist conventions",
+ ["ara" ] = "arabic",
+ ["arg" ] = "aragonese",
+ ["ari" ] = "aari",
+ ["ark" ] = "rakhine",
+ ["asm" ] = "assamese",
+ ["ast" ] = "asturian",
+ ["ath" ] = "athapaskan",
+ ["avr" ] = "avar",
+ ["awa" ] = "awadhi",
+ ["aym" ] = "aymara",
+ ["azb" ] = "torki",
+ ["aze" ] = "azerbaijani",
+ ["bad" ] = "badaga",
+ ["bad0"] = "banda",
+ ["bag" ] = "baghelkhandi",
+ ["bal" ] = "balkar",
+ ["ban" ] = "balinese",
+ ["bar" ] = "bavarian",
+ ["bau" ] = "baulé",
+ ["bbc" ] = "batak toba",
+ ["bbr" ] = "berber",
+ ["bch" ] = "bench",
+ ["bcr" ] = "bible cree",
+ ["bdy" ] = "bandjalang",
+ ["bel" ] = "belarussian",
+ ["bem" ] = "bemba",
+ ["ben" ] = "bengali",
+ ["bgc" ] = "haryanvi",
+ ["bgq" ] = "bagri",
+ ["bgr" ] = "bulgarian",
+ ["bhi" ] = "bhili",
+ ["bho" ] = "bhojpuri",
+ ["bik" ] = "bikol",
+ ["bil" ] = "bilen",
+ ["bis" ] = "bislama",
+ ["bjj" ] = "kanauji",
+ ["bkf" ] = "blackfoot",
+ ["bli" ] = "baluchi",
+ ["blk" ] = "pa'o karen",
+ ["bln" ] = "balante",
+ ["blt" ] = "balti",
+ ["bmb" ] = "bambara (bamanankan)",
+ ["bml" ] = "bamileke",
+ ["bos" ] = "bosnian",
+ ["bpy" ] = "bishnupriya manipuri",
+ ["bre" ] = "breton",
+ ["brh" ] = "brahui",
+ ["bri" ] = "braj bhasha",
+ ["brm" ] = "burmese",
+ ["brx" ] = "bodo",
+ ["bsh" ] = "bashkir",
+ ["bsk" ] = "burushaski",
+ ["bti" ] = "beti",
+ ["bts" ] = "batak simalungun",
+ ["bug" ] = "bugis",
+ ["byv" ] = "medumba",
+ ["cak" ] = "kaqchikel",
+ ["cat" ] = "catalan",
+ ["cbk" ] = "zamboanga chavacano",
+ ["cchn"] = "chinantec",
+ ["ceb" ] = "cebuano",
+ ["cgg" ] = "chiga",
+ ["cha" ] = "chamorro",
+ ["che" ] = "chechen",
+ ["chg" ] = "chaha gurage",
+ ["chh" ] = "chattisgarhi",
+ ["chi" ] = "chichewa (chewa, nyanja)",
+ ["chk" ] = "chukchi",
+ ["chk0"] = "chuukese",
+ ["cho" ] = "choctaw",
+ ["chp" ] = "chipewyan",
+ ["chr" ] = "cherokee",
+ ["chu" ] = "chuvash",
+ ["chy" ] = "cheyenne",
+ ["cja" ] = "western cham",
+ ["cjm" ] = "eastern cham",
+ ["cmr" ] = "comorian",
+ ["cop" ] = "coptic",
+ ["cor" ] = "cornish",
+ ["cos" ] = "corsican",
+ ["cpp" ] = "creoles",
+ ["cre" ] = "cree",
+ ["crr" ] = "carrier",
+ ["crt" ] = "crimean tatar",
+ ["csb" ] = "kashubian",
+ ["csl" ] = "church slavonic",
+ ["csy" ] = "czech",
+ ["ctg" ] = "chittagonian",
+ ["cuk" ] = "san blas kuna",
+ ["dan" ] = "danish",
+ ["dar" ] = "dargwa",
+ ["dax" ] = "dayi",
+ ["dcr" ] = "woods cree",
+ ["deu" ] = "german",
+ ["dgo" ] = "dogri",
+ ["dgr" ] = "dogri",
+ ["dhg" ] = "dhangu",
+ ["dhv" ] = "divehi (dhivehi, maldivian)",
+ ["diq" ] = "dimli",
+ ["div" ] = "divehi (dhivehi, maldivian)",
+ ["djr" ] = "zarma",
+ ["djr0"] = "djambarrpuyngu",
+ ["dng" ] = "dangme",
+ ["dnj" ] = "dan",
+ ["dnk" ] = "dinka",
+ ["dri" ] = "dari",
+ ["duj" ] = "dhuwal",
+ ["dun" ] = "dungan",
+ ["dzn" ] = "dzongkha",
+ ["ebi" ] = "ebira",
+ ["ecr" ] = "eastern cree",
+ ["edo" ] = "edo",
+ ["efi" ] = "efik",
+ ["ell" ] = "greek",
+ ["emk" ] = "eastern maninkakan",
+ ["eng" ] = "english",
+ ["erz" ] = "erzya",
+ ["esp" ] = "spanish",
+ ["esu" ] = "central yupik",
+ ["eti" ] = "estonian",
+ ["euq" ] = "basque",
+ ["evk" ] = "evenki",
+ ["evn" ] = "even",
+ ["ewe" ] = "ewe",
+ ["fan" ] = "french antillean",
+ ["fan0"] = " fang",
+ ["far" ] = "persian",
+ ["fat" ] = "fanti",
+ ["fin" ] = "finnish",
+ ["fji" ] = "fijian",
+ ["fle" ] = "dutch (flemish)",
+ ["fmp" ] = "fe’fe’",
+ ["fne" ] = "forest nenets",
+ ["fon" ] = "fon",
+ ["fos" ] = "faroese",
+ ["fra" ] = "french",
+ ["frc" ] = "cajun french",
+ ["fri" ] = "frisian",
+ ["frl" ] = "friulian",
+ ["frp" ] = "arpitan",
+ ["fta" ] = "futa",
+ ["ful" ] = "fulah",
+ ["fuv" ] = "nigerian fulfulde",
+ ["gad" ] = "ga",
+ ["gae" ] = "scottish gaelic (gaelic)",
+ ["gag" ] = "gagauz",
+ ["gal" ] = "galician",
+ ["gar" ] = "garshuni",
+ ["gaw" ] = "garhwali",
+ ["gez" ] = "ge'ez",
+ ["gih" ] = "githabul",
+ ["gil" ] = "gilyak",
+ ["gil0"] = "kiribati (gilbertese)",
+ ["gkp" ] = "kpelle (guinea)",
+ ["glk" ] = "gilaki",
+ ["gmz" ] = "gumuz",
+ ["gnn" ] = "gumatj",
+ ["gog" ] = "gogo",
+ ["gon" ] = "gondi",
+ ["grn" ] = "greenlandic",
+ ["gro" ] = "garo",
+ ["gua" ] = "guarani",
+ ["guc" ] = "wayuu",
+ ["guf" ] = "gupapuyngu",
+ ["guj" ] = "gujarati",
+ ["guz" ] = "gusii",
+ ["hai" ] = "haitian (haitian creole)",
+ ["hal" ] = "halam",
+ ["har" ] = "harauti",
+ ["hau" ] = "hausa",
+ ["haw" ] = "hawaiian",
+ ["hay" ] = "haya",
+ ["haz" ] = "hazaragi",
+ ["hbn" ] = "hammer-banna",
+ ["her" ] = "herero",
+ ["hil" ] = "hiligaynon",
+ ["hin" ] = "hindi",
+ ["hma" ] = "high mari",
+ ["hmn" ] = "hmong",
+ ["hmo" ] = "hiri motu",
+ ["hnd" ] = "hindko",
+ ["ho" ] = "ho",
+ ["hri" ] = "harari",
+ ["hrv" ] = "croatian",
+ ["hun" ] = "hungarian",
+ ["hye" ] = "armenian",
+ ["hye0"] = "armenian east",
+ ["iba" ] = "iban",
+ ["ibb" ] = "ibibio",
+ ["ibo" ] = "igbo",
+ ["ido" ] = "ido",
+ ["ijo" ] = "ijo languages",
+ ["ile" ] = "interlingue",
+ ["ilo" ] = "ilokano",
+ ["ina" ] = "interlingua",
+ ["ind" ] = "indonesian",
+ ["ing" ] = "ingush",
+ ["inu" ] = "inuktitut",
+ ["ipk" ] = "inupiat",
+ ["ipph"] = "phonetic transcription—ipa conventions",
+ ["iri" ] = "irish",
+ ["irt" ] = "irish traditional",
+ ["isl" ] = "icelandic",
+ ["ism" ] = "inari sami",
+ ["ita" ] = "italian",
+ ["iwr" ] = "hebrew",
+ ["jam" ] = "jamaican creole",
+ ["jan" ] = "japanese",
+ ["jav" ] = "javanese",
+ ["jbo" ] = "lojban",
+ ["jct" ] = "krymchak",
+ ["jii" ] = "yiddish",
+ ["jud" ] = "ladino",
+ ["jul" ] = "jula",
+ ["kab" ] = "kabardian",
+ ["kab0"] = "kabyle",
+ ["kac" ] = "kachchi",
+ ["kal" ] = "kalenjin",
+ ["kan" ] = "kannada",
+ ["kar" ] = "karachay",
+ ["kat" ] = "georgian",
+ ["kaz" ] = "kazakh",
+ ["kde" ] = "makonde",
+ ["kea" ] = "kabuverdianu (crioulo)",
+ ["keb" ] = "kebena",
+ ["kek" ] = "kekchi",
+ ["kge" ] = "khutsuri georgian",
+ ["kha" ] = "khakass",
+ ["khk" ] = "khanty-kazim",
+ ["khm" ] = "khmer",
+ ["khs" ] = "khanty-shurishkar",
+ ["kht" ] = "khamti shan",
+ ["khv" ] = "khanty-vakhi",
+ ["khw" ] = "khowar",
+ ["kik" ] = "kikuyu (gikuyu)",
+ ["kir" ] = "kirghiz (kyrgyz)",
+ ["kis" ] = "kisii",
+ ["kiu" ] = "kirmanjki",
+ ["kjd" ] = "southern kiwai",
+ ["kjp" ] = "eastern pwo karen",
+ ["kjz" ] = "bumthangkha",
+ ["kkn" ] = "kokni",
+ ["klm" ] = "kalmyk",
+ ["kmb" ] = "kamba",
+ ["kmn" ] = "kumaoni",
+ ["kmo" ] = "komo",
+ ["kms" ] = "komso",
+ ["kmz" ] = "khorasani turkic",
+ ["knr" ] = "kanuri",
+ ["kod" ] = "kodagu",
+ ["koh" ] = "korean old hangul",
+ ["kok" ] = "konkani",
+ ["kom" ] = "komi",
+ ["kon" ] = "kikongo",
+ ["kon0"] = "kongo",
+ ["kop" ] = "komi-permyak",
+ ["kor" ] = "korean",
+ ["kos" ] = "kosraean",
+ ["koz" ] = "komi-zyrian",
+ ["kpl" ] = "kpelle",
+ ["kri" ] = "krio",
+ ["krk" ] = "karakalpak",
+ ["krl" ] = "karelian",
+ ["krm" ] = "karaim",
+ ["krn" ] = "karen",
+ ["krt" ] = "koorete",
+ ["ksh" ] = "kashmiri",
+ ["ksh0"] = "ripuarian",
+ ["ksi" ] = "khasi",
+ ["ksm" ] = "kildin sami",
+ ["ksw" ] = "s’gaw karen",
+ ["kua" ] = "kuanyama",
+ ["kui" ] = "kui",
+ ["kul" ] = "kulvi",
+ ["kum" ] = "kumyk",
+ ["kur" ] = "kurdish",
+ ["kuu" ] = "kurukh",
+ ["kuy" ] = "kuy",
+ ["kyk" ] = "koryak",
+ ["kyu" ] = "western kayah",
+ ["lad" ] = "ladin",
+ ["lah" ] = "lahuli",
+ ["lak" ] = "lak",
+ ["lam" ] = "lambani",
+ ["lao" ] = "lao",
+ ["lat" ] = "latin",
+ ["laz" ] = "laz",
+ ["lcr" ] = "l-cree",
+ ["ldk" ] = "ladakhi",
+ ["lez" ] = "lezgi",
+ ["lij" ] = "ligurian",
+ ["lim" ] = "limburgish",
+ ["lin" ] = "lingala",
+ ["lis" ] = "lisu",
+ ["ljp" ] = "lampung",
+ ["lki" ] = "laki",
+ ["lma" ] = "low mari",
+ ["lmb" ] = "limbu",
+ ["lmo" ] = "lombard",
+ ["lmw" ] = "lomwe",
+ ["lom" ] = "loma",
+ ["lrc" ] = "luri",
+ ["lsb" ] = "lower sorbian",
+ ["lsm" ] = "lule sami",
+ ["lth" ] = "lithuanian",
+ ["ltz" ] = "luxembourgish",
+ ["lua" ] = "luba-lulua",
+ ["lub" ] = "luba-katanga",
+ ["lug" ] = "ganda",
+ ["luh" ] = "luyia",
+ ["luo" ] = "luo",
+ ["lvi" ] = "latvian",
+ ["mad" ] = "madura",
+ ["mag" ] = "magahi",
+ ["mah" ] = "marshallese",
+ ["maj" ] = "majang",
+ ["mak" ] = "makhuwa",
+ ["mal" ] = "malayalam reformed",
+ ["mam" ] = "mam",
+ ["man" ] = "mansi",
+ ["map" ] = "mapudungun",
+ ["mar" ] = "marathi",
+ ["maw" ] = "marwari",
+ ["mbn" ] = "mbundu",
+ ["mbo" ] = "mbo",
+ ["mch" ] = "manchu",
+ ["mcr" ] = "moose cree",
+ ["mde" ] = "mende",
+ ["mdr" ] = "mandar",
+ ["men" ] = "me'en",
+ ["mer" ] = "meru",
+ ["mfa" ] = "pattani malay",
+ ["mfe" ] = "morisyen",
+ ["min" ] = "minangkabau",
+ ["miz" ] = "mizo",
+ ["mkd" ] = "macedonian",
+ ["mkr" ] = "makasar",
+ ["mkw" ] = "kituba",
+ ["mle" ] = "male",
+ ["mlg" ] = "malagasy",
+ ["mln" ] = "malinke",
+ ["mlr" ] = "malayalam reformed",
+ ["mly" ] = "malay",
+ ["mnd" ] = "mandinka",
+ ["mng" ] = "mongolian",
+ ["mni" ] = "manipuri",
+ ["mnk" ] = "maninka",
+ ["mnx" ] = "manx",
+ ["moh" ] = "mohawk",
+ ["mok" ] = "moksha",
+ ["mol" ] = "moldavian",
+ ["mon" ] = "mon",
+ ["mor" ] = "moroccan",
+ ["mos" ] = "mossi",
+ ["mri" ] = "maori",
+ ["mth" ] = "maithili",
+ ["mts" ] = "maltese",
+ ["mun" ] = "mundari",
+ ["mus" ] = "muscogee",
+ ["mwl" ] = "mirandese",
+ ["mww" ] = "hmong daw",
+ ["myn" ] = "mayan",
+ ["mzn" ] = "mazanderani",
+ ["nag" ] = "naga-assamese",
+ ["nah" ] = "nahuatl",
+ ["nan" ] = "nanai",
+ ["nap" ] = "neapolitan",
+ ["nas" ] = "naskapi",
+ ["nau" ] = "nauruan",
+ ["nav" ] = "navajo",
+ ["ncr" ] = "n-cree",
+ ["ndb" ] = "ndebele",
+ ["ndc" ] = "ndau",
+ ["ndg" ] = "ndonga",
+ ["nds" ] = "low saxon",
+ ["nep" ] = "nepali",
+ ["new" ] = "newari",
+ ["nga" ] = "ngbaka",
+ ["ngr" ] = "nagari",
+ ["nhc" ] = "norway house cree",
+ ["nis" ] = "nisi",
+ ["niu" ] = "niuean",
+ ["nkl" ] = "nyankole",
+ ["nko" ] = "n'ko",
+ ["nld" ] = "dutch",
+ ["noe" ] = "nimadi",
+ ["nog" ] = "nogai",
+ ["nor" ] = "norwegian",
+ ["nov" ] = "novial",
+ ["nsm" ] = "northern sami",
+ ["nso" ] = "sotho, northern",
+ ["nta" ] = "northern tai",
+ ["nto" ] = "esperanto",
+ ["nym" ] = "nyamwezi",
+ ["nyn" ] = "norwegian nynorsk",
+ ["nza" ] = "mbembe tigon",
+ ["oci" ] = "occitan",
+ ["ocr" ] = "oji-cree",
+ ["ojb" ] = "ojibway",
+ ["ori" ] = "odia",
+ ["oro" ] = "oromo",
+ ["oss" ] = "ossetian",
+ ["paa" ] = "palestinian aramaic",
+ ["pag" ] = "pangasinan",
+ ["pal" ] = "pali",
+ ["pam" ] = "pampangan",
+ ["pan" ] = "punjabi",
+ ["pap" ] = "palpa",
+ ["pap0"] = "papiamentu",
+ ["pas" ] = "pashto",
+ ["pau" ] = "palauan",
+ ["pcc" ] = "bouyei",
+ ["pcd" ] = "picard",
+ ["pdc" ] = "pennsylvania german",
+ ["pgr" ] = "polytonic greek",
+ ["phk" ] = "phake",
+ ["pih" ] = "norfolk",
+ ["pil" ] = "filipino",
+ ["plg" ] = "palaung",
+ ["plk" ] = "polish",
+ ["pms" ] = "piemontese",
+ ["pnb" ] = "western panjabi",
+ ["poh" ] = "pocomchi",
+ ["pon" ] = "pohnpeian",
+ ["pro" ] = "provencal",
+ ["ptg" ] = "portuguese",
+ ["pwo" ] = "western pwo karen",
+ ["qin" ] = "chin",
+ ["quc" ] = "k’iche’",
+ ["quh" ] = "quechua (bolivia)",
+ ["quz" ] = "quechua",
+ ["qvi" ] = "quechua (ecuador)",
+ ["qwh" ] = "quechua (peru)",
+ ["raj" ] = "rajasthani",
+ ["rar" ] = "rarotongan",
+ ["rbu" ] = "russian buriat",
+ ["rcr" ] = "r-cree",
+ ["rej" ] = "rejang",
+ ["ria" ] = "riang",
+ ["rif" ] = "tarifit",
+ ["rit" ] = "ritarungo",
+ ["rkw" ] = "arakwal",
+ ["rms" ] = "romansh",
+ ["rmy" ] = "vlax romani",
+ ["rom" ] = "romanian",
+ ["roy" ] = "romany",
+ ["rsy" ] = "rusyn",
+ ["rtm" ] = "rotuman",
+ ["rua" ] = "kinyarwanda",
+ ["run" ] = "rundi",
+ ["rup" ] = "aromanian",
+ ["rus" ] = "russian",
+ ["sad" ] = "sadri",
+ ["san" ] = "sanskrit",
+ ["sas" ] = "sasak",
+ ["sat" ] = "santali",
+ ["say" ] = "sayisi",
+ ["scn" ] = "sicilian",
+ ["sco" ] = "scots",
+ ["scs" ] = "north slavey",
+ ["sek" ] = "sekota",
+ ["sel" ] = "selkup",
+ ["sga" ] = "old irish",
+ ["sgo" ] = "sango",
+ ["sgs" ] = "samogitian",
+ ["shi" ] = "tachelhit",
+ ["shn" ] = "shan",
+ ["sib" ] = "sibe",
+ ["sid" ] = "sidamo",
+ ["sig" ] = "silte gurage",
+ ["sks" ] = "skolt sami",
+ ["sky" ] = "slovak",
+ ["sla" ] = "slavey",
+ ["slv" ] = "slovenian",
+ ["sml" ] = "somali",
+ ["smo" ] = "samoan",
+ ["sna" ] = "sena",
+ ["sna0"] = "shona",
+ ["snd" ] = "sindhi",
+ ["snh" ] = "sinhala (sinhalese)",
+ ["snk" ] = "soninke",
+ ["sog" ] = "sodo gurage",
+ ["sop" ] = "songe",
+ ["sot" ] = "sotho, southern",
+ ["sqi" ] = "albanian",
+ ["srb" ] = "serbian",
+ ["srd" ] = "sardinian",
+ ["srk" ] = "saraiki",
+ ["srr" ] = "serer",
+ ["ssl" ] = "south slavey",
+ ["ssm" ] = "southern sami",
+ ["stq" ] = "saterland frisian",
+ ["suk" ] = "sukuma",
+ ["sun" ] = "sundanese",
+ ["sur" ] = "suri",
+ ["sva" ] = "svan",
+ ["sve" ] = "swedish",
+ ["swa" ] = "swadaya aramaic",
+ ["swk" ] = "swahili",
+ ["swz" ] = "swati",
+ ["sxt" ] = "sutu",
+ ["sxu" ] = "upper saxon",
+ ["syl" ] = "sylheti",
+ ["syr" ] = "syriac",
+ ["syre"] = "estrangela syriac",
+ ["syrj"] = "western syriac",
+ ["syrn"] = "eastern syriac",
+ ["szl" ] = "silesian",
+ ["tab" ] = "tabasaran",
+ ["taj" ] = "tajiki",
+ ["tam" ] = "tamil",
+ ["tat" ] = "tatar",
+ ["tcr" ] = "th-cree",
+ ["tdd" ] = "dehong dai",
+ ["tel" ] = "telugu",
+ ["tet" ] = "tetum",
+ ["tgl" ] = "tagalog",
+ ["tgn" ] = "tongan",
+ ["tgr" ] = "tigre",
+ ["tgy" ] = "tigrinya",
+ ["tha" ] = "thai",
+ ["tht" ] = "tahitian",
+ ["tib" ] = "tibetan",
+ ["tiv" ] = "tiv",
+ ["tkm" ] = "turkmen",
+ ["tmh" ] = "tamashek",
+ ["tmn" ] = "temne",
+ ["tna" ] = "tswana",
+ ["tne" ] = "tundra nenets",
+ ["tng" ] = "tonga",
+ ["tod" ] = "todo",
+ ["tod0"] = "toma",
+ ["tpi" ] = "tok pisin",
+ ["trk" ] = "turkish",
+ ["tsg" ] = "tsonga",
+ ["tsj" ] = "tshangla",
+ ["tua" ] = "turoyo aramaic",
+ ["tul" ] = "tulu",
+ ["tum" ] = "tulu",
+ ["tuv" ] = "tuvin",
+ ["tvl" ] = "tuvalu",
+ ["twi" ] = "twi",
+ ["tyz" ] = "tày",
+ ["tzm" ] = "tamazight",
+ ["tzo" ] = "tzotzil",
+ ["udm" ] = "udmurt",
+ ["ukr" ] = "ukrainian",
+ ["umb" ] = "umbundu",
+ ["urd" ] = "urdu",
+ ["usb" ] = "upper sorbian",
+ ["uyg" ] = "uyghur",
+ ["uzb" ] = "uzbek",
+ ["vec" ] = "venetian",
+ ["ven" ] = "venda",
+ ["vit" ] = "vietnamese",
+ ["vol" ] = "volapük",
+ ["vro" ] = "võro",
+ ["wa" ] = "wa",
+ ["wag" ] = "wagdi",
+ ["war" ] = "waray-waray",
+ ["wcr" ] = "west-cree",
+ ["wel" ] = "welsh",
+ ["wlf" ] = "wolof",
+ ["wln" ] = "walloon",
+ ["wtm" ] = "mewati",
+ ["xbd" ] = "lü",
+ ["xhs" ] = "xhosa",
+ ["xjb" ] = "minjangbal",
+ ["xkf" ] = "khengkha",
+ ["xog" ] = "soga",
+ ["xpe" ] = "kpelle (liberia)",
+ ["yak" ] = "sakha",
+ ["yao" ] = "yao",
+ ["yap" ] = "yapese",
+ ["yba" ] = "yoruba",
+ ["ycr" ] = "y-cree",
+ ["yic" ] = "yi classic",
+ ["yim" ] = "yi modern",
+ ["zea" ] = "zealandic",
+ ["zgh" ] = "standard morrocan tamazigh",
+ ["zha" ] = "zhuang",
+ ["zhh" ] = "chinese, hong kong sar",
+ ["zhp" ] = "chinese phonetic",
+ ["zhs" ] = "chinese simplified",
+ ["zht" ] = "chinese traditional",
+ ["znd" ] = "zande",
+ ["zul" ] = "zulu",
+ ["zza" ] = "zazaki",
+}
+
+
+local features = allocate {
+ ["aalt"] = "access all alternates",
+ ["abvf"] = "above-base forms",
+ ["abvm"] = "above-base mark positioning",
+ ["abvs"] = "above-base substitutions",
+ ["afrc"] = "alternative fractions",
+ ["akhn"] = "akhands",
+ ["blwf"] = "below-base forms",
+ ["blwm"] = "below-base mark positioning",
+ ["blws"] = "below-base substitutions",
+ ["c2pc"] = "petite capitals from capitals",
+ ["c2sc"] = "small capitals from capitals",
+ ["calt"] = "contextual alternates",
+ ["case"] = "case-sensitive forms",
+ ["ccmp"] = "glyph composition/decomposition",
+ ["cfar"] = "conjunct form after ro",
+ ["cjct"] = "conjunct forms",
+ ["clig"] = "contextual ligatures",
+ ["cpct"] = "centered cjk punctuation",
+ ["cpsp"] = "capital spacing",
+ ["cswh"] = "contextual swash",
+ ["curs"] = "cursive positioning",
+ ["dflt"] = "default processing",
+ ["dist"] = "distances",
+ ["dlig"] = "discretionary ligatures",
+ ["dnom"] = "denominators",
+ ["dtls"] = "dotless forms", -- math
+ ["expt"] = "expert forms",
+ ["falt"] = "final glyph alternates",
+ ["fin2"] = "terminal forms #2",
+ ["fin3"] = "terminal forms #3",
+ ["fina"] = "terminal forms",
+ ["flac"] = "flattened accents over capitals", -- math
+ ["frac"] = "fractions",
+ ["fwid"] = "full width",
+ ["half"] = "half forms",
+ ["haln"] = "halant forms",
+ ["halt"] = "alternate half width",
+ ["hist"] = "historical forms",
+ ["hkna"] = "horizontal kana alternates",
+ ["hlig"] = "historical ligatures",
+ ["hngl"] = "hangul",
+ ["hojo"] = "hojo kanji forms",
+ ["hwid"] = "half width",
+ ["init"] = "initial forms",
+ ["isol"] = "isolated forms",
+ ["ital"] = "italics",
+ ["jalt"] = "justification alternatives",
+ ["jp04"] = "jis2004 forms",
+ ["jp78"] = "jis78 forms",
+ ["jp83"] = "jis83 forms",
+ ["jp90"] = "jis90 forms",
+ ["kern"] = "kerning",
+ ["lfbd"] = "left bounds",
+ ["liga"] = "standard ligatures",
+ ["ljmo"] = "leading jamo forms",
+ ["lnum"] = "lining figures",
+ ["locl"] = "localized forms",
+ ["ltra"] = "left-to-right alternates",
+ ["ltrm"] = "left-to-right mirrored forms",
+ ["mark"] = "mark positioning",
+ ["med2"] = "medial forms #2",
+ ["medi"] = "medial forms",
+ ["mgrk"] = "mathematical greek",
+ ["mkmk"] = "mark to mark positioning",
+ ["mset"] = "mark positioning via substitution",
+ ["nalt"] = "alternate annotation forms",
+ ["nlck"] = "nlc kanji forms",
+ ["nukt"] = "nukta forms",
+ ["numr"] = "numerators",
+ ["onum"] = "old style figures",
+ ["opbd"] = "optical bounds",
+ ["ordn"] = "ordinals",
+ ["ornm"] = "ornaments",
+ ["palt"] = "proportional alternate width",
+ ["pcap"] = "petite capitals",
+ ["pkna"] = "proportional kana",
+ ["pnum"] = "proportional figures",
+ ["pref"] = "pre-base forms",
+ ["pres"] = "pre-base substitutions",
+ ["pstf"] = "post-base forms",
+ ["psts"] = "post-base substitutions",
+ ["pwid"] = "proportional widths",
+ ["qwid"] = "quarter widths",
+ ["rand"] = "randomize",
+ ["rclt"] = "required contextual alternates",
+ ["rkrf"] = "rakar forms",
+ ["rlig"] = "required ligatures",
+ ["rphf"] = "reph form",
+ ["rtbd"] = "right bounds",
+ ["rtla"] = "right-to-left alternates",
+ ["rtlm"] = "right to left mirrored forms",
+ ["rvrn"] = "required variation alternates",
+ ["ruby"] = "ruby notation forms",
+ ["salt"] = "stylistic alternates",
+ ["sinf"] = "scientific inferiors",
+ ["size"] = "optical size", -- now stat table
+ ["smcp"] = "small capitals",
+ ["smpl"] = "simplified forms",
+ -- ["ss01"] = "stylistic set 1",
+ -- ["ss02"] = "stylistic set 2",
+ -- ["ss03"] = "stylistic set 3",
+ -- ["ss04"] = "stylistic set 4",
+ -- ["ss05"] = "stylistic set 5",
+ -- ["ss06"] = "stylistic set 6",
+ -- ["ss07"] = "stylistic set 7",
+ -- ["ss08"] = "stylistic set 8",
+ -- ["ss09"] = "stylistic set 9",
+ -- ["ss10"] = "stylistic set 10",
+ -- ["ss11"] = "stylistic set 11",
+ -- ["ss12"] = "stylistic set 12",
+ -- ["ss13"] = "stylistic set 13",
+ -- ["ss14"] = "stylistic set 14",
+ -- ["ss15"] = "stylistic set 15",
+ -- ["ss16"] = "stylistic set 16",
+ -- ["ss17"] = "stylistic set 17",
+ -- ["ss18"] = "stylistic set 18",
+ -- ["ss19"] = "stylistic set 19",
+ -- ["ss20"] = "stylistic set 20",
+ ["ssty"] = "script style", -- math
+ ["stch"] = "stretching glyph decomposition",
+ ["subs"] = "subscript",
+ ["sups"] = "superscript",
+ ["swsh"] = "swash",
+ ["titl"] = "titling",
+ ["tjmo"] = "trailing jamo forms",
+ ["tnam"] = "traditional name forms",
+ ["tnum"] = "tabular figures",
+ ["trad"] = "traditional forms",
+ ["twid"] = "third widths",
+ ["unic"] = "unicase",
+ ["valt"] = "alternate vertical metrics",
+ ["vatu"] = "vattu variants",
+ ["vert"] = "vertical writing",
+ ["vhal"] = "alternate vertical half metrics",
+ ["vjmo"] = "vowel jamo forms",
+ ["vkna"] = "vertical kana alternates",
+ ["vkrn"] = "vertical kerning",
+ ["vpal"] = "proportional alternate vertical metrics",
+ ["vrtr"] = "vertical alternates for rotation",
+ ["vrt2"] = "vertical rotation",
+ ["zero"] = "slashed zero",
+
+ ["trep"] = "traditional tex replacements",
+ ["tlig"] = "traditional tex ligatures",
+
+ ["ss.."] = "stylistic set ..",
+ ["cv.."] = "character variant ..",
+ ["js.."] = "justification ..",
+
+ ["dv.."] = "devanagari ..", -- for internal use
+ ["ml.."] = "malayalam ..", -- for internal use
+
+}
+
+local baselines = allocate {
+ ["hang"] = "hanging baseline",
+ ["icfb"] = "ideographic character face bottom edge baseline",
+ ["icft"] = "ideographic character face tope edige baseline",
+ ["ideo"] = "ideographic em-box bottom edge baseline",
+ ["idtp"] = "ideographic em-box top edge baseline",
+ ["math"] = "mathematical centered baseline",
+ ["romn"] = "roman baseline"
+}
+
+tables.scripts = scripts
+tables.languages = languages
+tables.features = features
+tables.baselines = baselines
+
+local acceptscripts = true directives.register("otf.acceptscripts", function(v) acceptscripts = v end)
+local acceptlanguages = true directives.register("otf.acceptlanguages", function(v) acceptlanguages = v end)
+
+local report_checks = logs.reporter("fonts","checks")
+
+-- hm, we overload the metatables
+
+if otffeatures.features then
+ for k, v in next, otffeatures.features do
+ features[k] = v
+ end
+ otffeatures.features = features
+end
+
+local function swapped(h)
+ local r = { }
+ for k, v in next, h do
+ r[gsub(v,"[^a-z0-9]","")] = k -- is already lower
+ end
+ return r
+end
+
+local verbosescripts = allocate(swapped(scripts ))
+local verboselanguages = allocate(swapped(languages))
+local verbosefeatures = allocate(swapped(features ))
+local verbosebaselines = allocate(swapped(baselines))
+
+-- lets forget about trailing spaces
+
+local function resolve(t,k)
+ if k then
+ k = gsub(lower(k),"[^a-z0-9]","")
+ local v = rawget(t,k)
+ if v then
+ return v
+ end
+ end
+end
+
+setmetatableindex(verbosescripts, resolve)
+setmetatableindex(verboselanguages, resolve)
+setmetatableindex(verbosefeatures, resolve)
+setmetatableindex(verbosebaselines, resolve)
+
+-- We could optimize the next lookups by using an extra metatable and storing
+-- already found values but in practice there are not that many lookups so
+-- it's never a bottleneck.
+
+setmetatableindex(scripts, function(t,k)
+ if k then
+ k = lower(k)
+ if k == "dflt" then
+ return k
+ end
+ local v = rawget(t,k)
+ if v then
+ return v
+ end
+ k = gsub(k," ","")
+ v = rawget(t,v)
+ if v then
+ return v
+ elseif acceptscripts then
+ report_checks("registering extra script %a",k)
+ rawset(t,k,k)
+ return k
+ end
+ end
+ return "dflt"
+end)
+
+setmetatableindex(languages, function(t,k)
+ if k then
+ k = lower(k)
+ if k == "dflt" then
+ return k
+ end
+ local v = rawget(t,k)
+ if v then
+ return v
+ end
+ k = gsub(k," ","")
+ v = rawget(t,v)
+ if v then
+ return v
+ elseif acceptlanguages then
+ report_checks("registering extra language %a",k)
+ rawset(t,k,k)
+ return k
+ end
+ end
+ return "dflt"
+end)
+
+if setmetatablenewindex then
+
+ setmetatablenewindex(languages, "ignore")
+ setmetatablenewindex(scripts, "ignore")
+ setmetatablenewindex(baselines, "ignore")
+
+end
+
+local function resolve(t,k)
+ if k then
+ k = lower(k)
+ local v = rawget(t,k)
+ if v then
+ return v
+ end
+ k = gsub(k," ","")
+ local v = rawget(t,k)
+ if v then
+ return v
+ end
+ local tag, dd = match(k,"(..)(%d+)")
+ if tag and dd then
+ local v = rawget(t,tag)
+ if v then
+ return v -- return format(v,tonumber(dd)) -- old way
+ else
+ local v = rawget(t,tag.."..") -- nicer in overview
+ if v then
+ return (gsub(v,"%.%.",tonumber(dd))) -- new way
+ end
+ end
+ end
+ end
+ return k -- "dflt"
+end
+
+setmetatableindex(features, resolve)
+
+local function assign(t,k,v)
+ if k and v then
+ v = lower(v)
+ rawset(t,k,v) -- rawset ?
+ -- rawset(features,gsub(v,"[^a-z0-9]",""),k) -- why ? old code
+ end
+end
+
+if setmetatablenewindex then
+
+ setmetatablenewindex(features, assign)
+
+end
+
+local checkers = {
+ rand = function(v)
+ return v == true and "random" or v
+ end
+}
+
+-- Keep this:
+--
+-- function otf.features.normalize(features)
+-- if features then
+-- local h = { }
+-- for k, v in next, features do
+-- k = lower(k)
+-- if k == "language" then
+-- v = gsub(lower(v),"[^a-z0-9]","")
+-- h.language = rawget(verboselanguages,v) or (languages[v] and v) or "dflt" -- auto adds
+-- elseif k == "script" then
+-- v = gsub(lower(v),"[^a-z0-9]","")
+-- h.script = rawget(verbosescripts,v) or (scripts[v] and v) or "dflt" -- auto adds
+-- else
+-- if type(v) == "string" then
+-- local b = is_boolean(v)
+-- if type(b) == "nil" then
+-- v = tonumber(v) or lower(v)
+-- else
+-- v = b
+-- end
+-- end
+-- if not rawget(features,k) then
+-- k = rawget(verbosefeatures,k) or k
+-- end
+-- local c = checkers[k]
+-- h[k] = c and c(v) or v
+-- end
+-- end
+-- return h
+-- end
+-- end
+
+-- inspect(fonts.handlers.otf.statistics.usedfeatures)
+
+if not storage then
+ return
+end
+
+local usedfeatures = statistics.usedfeatures or { }
+statistics.usedfeatures = usedfeatures
+
+table.setmetatableindex(usedfeatures, function(t,k) if k then local v = { } t[k] = v return v end end) -- table.autotable
+
+storage.register("fonts/otf/usedfeatures", usedfeatures, "fonts.handlers.otf.statistics.usedfeatures" )
+
+local normalizedaxis = otf.readers.helpers.normalizedaxis or function(s) return s end
+
+function otffeatures.normalize(features,wrap) -- wrap is for context
+ if features then
+ local h = { }
+ for key, value in next, features do
+ local k = lower(key)
+ if k == "language" then
+ local v = gsub(lower(value),"[^a-z0-9]","")
+ h.language = rawget(verboselanguages,v) or (languages[v] and v) or "dflt" -- auto adds
+ elseif k == "script" then
+ local v = gsub(lower(value),"[^a-z0-9]","")
+ h.script = rawget(verbosescripts,v) or (scripts[v] and v) or "dflt" -- auto adds
+ elseif k == "axis" then
+ h[k] = normalizedaxis(value)
+ if not callbacks.supported.glyph_stream_provider then
+ h.variableshapes = true -- for the moment
+ end
+ else
+ local uk = usedfeatures[key]
+ local uv = uk[value]
+ if uv then
+ -- report_checks("feature value %a first seen at %a",value,key)
+ else
+ uv = tonumber(value) -- before boolean as there we also handle 0/1
+ if uv then
+ -- we're okay
+ elseif type(value) == "string" then
+ local b = is_boolean(value)
+ if type(b) == "nil" then
+ -- we do this elsewhere
+ --
+ -- if find(value,"=") then
+ -- local t = { }
+ -- for k, v in gmatch(value,"([^%s,=]+)%s*=%s*([^%s,=]+)") do
+ -- t[k] = tonumber(v) or v
+ -- end
+ -- if next(t) then
+ -- value = sequenced(t,",")
+ -- end
+ -- end
+ if wrap and find(value,",") then
+ uv = "{"..lower(value).."}"
+ else
+ uv = lower(value)
+ end
+ else
+ uv = b
+ end
+ elseif type(value) == "table" then
+ uv = sequenced(t,",")
+ else
+ uv = value
+ end
+ if not rawget(features,k) then
+ k = rawget(verbosefeatures,k) or k
+ end
+ local c = checkers[k]
+ if c then
+ uv = c(uv) or vc
+ end
+ uk[value] = uv
+ end
+ h[k] = uv
+ end
+ end
+ return h
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-oup.lua b/macros/luatex/generic/luaotfload/fontloader-font-oup.lua
new file mode 100644
index 0000000000..51b1c248f8
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-oup.lua
@@ -0,0 +1,3067 @@
+if not modules then modules = { } end modules ['font-oup'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local next, type = next, type
+local P, R, S = lpeg.P, lpeg.R, lpeg.S
+local lpegmatch = lpeg.match
+local insert, remove, copy, unpack = table.insert, table.remove, table.copy, table.unpack
+
+local formatters = string.formatters
+local sortedkeys = table.sortedkeys
+local sortedhash = table.sortedhash
+local tohash = table.tohash
+local setmetatableindex = table.setmetatableindex
+
+local report_error = logs.reporter("otf reader","error")
+local report_markwidth = logs.reporter("otf reader","markwidth")
+local report_cleanup = logs.reporter("otf reader","cleanup")
+local report_optimizations = logs.reporter("otf reader","merges")
+local report_unicodes = logs.reporter("otf reader","unicodes")
+
+local trace_markwidth = false trackers.register("otf.markwidth", function(v) trace_markwidth = v end)
+local trace_cleanup = false trackers.register("otf.cleanups", function(v) trace_cleanups = v end)
+local trace_optimizations = false trackers.register("otf.optimizations", function(v) trace_optimizations = v end)
+local trace_unicodes = false trackers.register("otf.unicodes", function(v) trace_unicodes = v end)
+
+local readers = fonts.handlers.otf.readers
+local privateoffset = fonts.constructors and fonts.constructors.privateoffset or 0xF0000 -- 0x10FFFF
+
+local f_private = formatters["P%05X"]
+local f_unicode = formatters["U%05X"]
+local f_index = formatters["I%05X"]
+local f_character_y = formatters["%C"]
+local f_character_n = formatters["[ %C ]"]
+
+local check_duplicates = true -- can become an option (pseudo feature) / aways needed anyway
+local check_soft_hyphen = true -- can become an option (pseudo feature) / needed for tagging
+
+directives.register("otf.checksofthyphen",function(v)
+ check_soft_hyphen = v
+end)
+
+local function replaced(list,index,replacement)
+ if type(list) == "number" then
+ return replacement
+ elseif type(replacement) == "table" then
+ local t = { }
+ local n = index-1
+ for i=1,n do
+ t[i] = list[i]
+ end
+ for i=1,#replacement do
+ n = n + 1
+ t[n] = replacement[i]
+ end
+ for i=index+1,#list do
+ n = n + 1
+ t[n] = list[i]
+ end
+ else
+ list[index] = replacement
+ return list
+ end
+end
+
+local function unifyresources(fontdata,indices)
+ local descriptions = fontdata.descriptions
+ local resources = fontdata.resources
+ if not descriptions or not resources then
+ return
+ end
+ --
+ local nofindices = #indices
+ --
+ local variants = fontdata.resources.variants
+ if variants then
+ for selector, unicodes in next, variants do
+ for unicode, index in next, unicodes do
+ unicodes[unicode] = indices[index]
+ end
+ end
+ end
+ --
+ local function remark(marks)
+ if marks then
+ local newmarks = { }
+ for k, v in next, marks do
+ local u = indices[k]
+ if u then
+ newmarks[u] = v
+ elseif trace_optimizations then
+ report_optimizations("discarding mark %i",k)
+ end
+ end
+ return newmarks
+ end
+ end
+ --
+ local marks = resources.marks
+ if marks then
+ resources.marks = remark(marks)
+ end
+ --
+ local markclasses = resources.markclasses
+ if markclasses then
+ for class, marks in next, markclasses do
+ markclasses[class] = remark(marks)
+ end
+ end
+ --
+ local marksets = resources.marksets
+ if marksets then
+ for class, marks in next, marksets do
+ marksets[class] = remark(marks)
+ end
+ end
+ --
+ local done = { } -- we need to deal with shared !
+ --
+ local duplicates = check_duplicates and resources.duplicates
+ if duplicates and not next(duplicates) then
+ duplicates = false
+ end
+ --
+ local function recover(cover) -- can be packed
+ for i=1,#cover do
+ local c = cover[i]
+ if not done[c] then
+ local t = { }
+ for k, v in next, c do
+ local ug = indices[k]
+ if ug then
+ t[ug] = v
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,"coverage",k,nofindices)
+ end
+ end
+ cover[i] = t
+ done[c] = d
+ end
+ end
+ end
+ --
+ local function recursed(c,kind) -- ligs are not packed
+ local t = { }
+ for g, d in next, c do
+ if type(d) == "table" then
+ local ug = indices[g]
+ if ug then
+ t[ug] = recursed(d,kind)
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g,nofindices)
+ end
+ else
+ t[g] = indices[d] -- ligature
+ end
+ end
+ return t
+ end
+ --
+ -- the duplicates need checking (probably only in cjk fonts): currently we only check
+ -- gsub_single, gsub_alternate, gsub_multiple, gpos_single and gpos_cursive
+ --
+ local function unifythem(sequences)
+ if not sequences then
+ return
+ end
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local kind = sequence.type
+ local steps = sequence.steps
+ local features = sequence.features
+ if steps then
+ for i=1,#steps do
+ local step = steps[i]
+ if kind == "gsub_single" then
+ local c = step.coverage
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ t1 = { }
+ if duplicates then
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ local ud1 = indices[d1]
+ if ud1 then
+ t1[ug1] = ud1
+ local dg1 = duplicates[ug1]
+ if dg1 then
+ for u in next, dg1 do
+ t1[u] = ud1
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",3,kind,d1,nofindices)
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = indices[d1]
+ else
+ report_error("fuzzy case %i in unifying %s: %i",2,kind,g1)
+ end
+ end
+ end
+ done[c] = t1
+ end
+ step.coverage = t1
+ end
+ elseif kind == "gpos_pair" then
+ local c = step.coverage
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ t1 = { }
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ local t2 = done[d1]
+ if not t2 then
+ t2 = { }
+ for g2, d2 in next, d1 do
+ local ug2 = indices[g2]
+ if ug2 then
+ t2[ug2] = d2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g2,nofindices,nofindices)
+ end
+ end
+ done[d1] = t2
+ end
+ t1[ug1] = t2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ done[c] = t1
+ end
+ step.coverage = t1
+ end
+ elseif kind == "gsub_ligature" then
+ local c = step.coverage
+ if c then
+ step.coverage = recursed(c,kind)
+ end
+ elseif kind == "gsub_alternate" or kind == "gsub_multiple" then
+ local c = step.coverage
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ t1 = { }
+ if duplicates then
+ for g1, d1 in next, c do
+ for i=1,#d1 do
+ local d1i = d1[i]
+ local d1u = indices[d1i]
+ if d1u then
+ d1[i] = d1u
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,i,d1i,nofindices)
+ end
+ end
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = d1
+ local dg1 = duplicates[ug1]
+ if dg1 then
+ for u in next, dg1 do
+ t1[u] = copy(d1)
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1, d1 in next, c do
+ for i=1,#d1 do
+ local d1i = d1[i]
+ local d1u = indices[d1i]
+ if d1u then
+ d1[i] = d1u
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,d1i,nofindices)
+ end
+ end
+ t1[indices[g1]] = d1
+ end
+ end
+ done[c] = t1
+ end
+ step.coverage = t1
+ end
+ elseif kind == "gpos_single" then
+ local c = step.coverage
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ t1 = { }
+ if duplicates then
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = d1
+ local dg1 = duplicates[ug1]
+ if dg1 then
+ for u in next, dg1 do
+ t1[u] = d1
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ end
+ done[c] = t1
+ end
+ step.coverage = t1
+ end
+ elseif kind == "gpos_mark2base" or kind == "gpos_mark2mark" or kind == "gpos_mark2ligature" then
+ local c = step.coverage
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ t1 = { }
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ done[c] = t1
+ end
+ step.coverage = t1
+ end
+ local c = step.baseclasses
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ for g1, d1 in next, c do
+ local t2 = done[d1]
+ if not t2 then
+ t2 = { }
+ for g2, d2 in next, d1 do
+ local ug2 = indices[g2]
+ if ug2 then
+ t2[ug2] = d2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g2,nofindices)
+ end
+ end
+ done[d1] = t2
+ end
+ c[g1] = t2
+ end
+ done[c] = c
+ end
+ end
+ elseif kind == "gpos_cursive" then
+ local c = step.coverage
+ if c then
+ local t1 = done[c]
+ if not t1 then
+ t1 = { }
+ if duplicates then
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = d1
+ --
+ local dg1 = duplicates[ug1]
+ if dg1 then
+ -- probably needs a bit more
+ for u in next, dg1 do
+ t1[u] = copy(d1)
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1, d1 in next, c do
+ local ug1 = indices[g1]
+ if ug1 then
+ t1[ug1] = d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ end
+ done[c] = t1
+ end
+ step.coverage = t1
+ end
+ end
+ --
+ local rules = step.rules
+ if rules then
+ for i=1,#rules do
+ local rule = rules[i]
+ --
+ local before = rule.before if before then recover(before) end
+ local after = rule.after if after then recover(after) end
+ local current = rule.current if current then recover(current) end
+ --
+ local replacements = rule.replacements
+ if replacements then
+ if not done[replacements] then
+ local r = { }
+ for k, v in next, replacements do
+ r[indices[k]] = indices[v]
+ end
+ rule.replacements = r
+ done[replacements] = r
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ --
+ unifythem(resources.sequences)
+ unifythem(resources.sublookups)
+end
+
+local function copyduplicates(fontdata)
+ if check_duplicates then
+ local descriptions = fontdata.descriptions
+ local resources = fontdata.resources
+ local duplicates = resources.duplicates
+ if check_soft_hyphen then
+ -- ebgaramond has a zero width empty soft hyphen
+ -- antykwatorunsks lacks a soft hyphen
+ local ds = descriptions[0xAD]
+ if not ds or ds.width == 0 then
+ if ds then
+ descriptions[0xAD] = nil
+ if trace_unicodes then
+ report_unicodes("patching soft hyphen")
+ end
+ else
+ if trace_unicodes then
+ report_unicodes("adding soft hyphen")
+ end
+ end
+ if not duplicates then
+ duplicates = { }
+ resources.duplicates = duplicates
+ end
+ local dh = duplicates[0x2D]
+ if dh then
+ dh[#dh+1] = { [0xAD] = true }
+ else
+ duplicates[0x2D] = { [0xAD] = true }
+ end
+ end
+ end
+ if duplicates then
+ for u, d in next, duplicates do
+ local du = descriptions[u]
+ if du then
+ local t = { f_character_y(u), "@", f_index(du.index), "->" }
+ local n = 0
+ local m = 25
+ for u in next, d do
+ if descriptions[u] then
+ if n < m then
+ t[n+4] = f_character_n(u)
+ end
+ else
+ local c = copy(du)
+ c.unicode = u -- better this way
+ descriptions[u] = c
+ if n < m then
+ t[n+4] = f_character_y(u)
+ end
+ end
+ n = n + 1
+ end
+ if trace_unicodes then
+ if n <= m then
+ report_unicodes("%i : % t",n,t)
+ else
+ report_unicodes("%i : % t ...",n,t)
+ end
+ end
+ else
+ -- what a mess
+ end
+ end
+ end
+ end
+end
+
+local ignore = { -- should we fix them?
+ ["notdef"] = true,
+ [".notdef"] = true,
+ ["null"] = true,
+ [".null"] = true,
+ ["nonmarkingreturn"] = true,
+}
+
+
+local function checklookups(fontdata,missing,nofmissing)
+ local descriptions = fontdata.descriptions
+ local resources = fontdata.resources
+ if missing and nofmissing and nofmissing <= 0 then
+ return
+ end
+ --
+ local singles = { }
+ local alternates = { }
+ local ligatures = { }
+
+ if not missing then
+ missing = { }
+ nofmissing = 0
+ for u, d in next, descriptions do
+ if not d.unicode then
+ nofmissing = nofmissing + 1
+ missing[u] = true
+ end
+ end
+ end
+ local function collectthem(sequences)
+ if not sequences then
+ return
+ end
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local kind = sequence.type
+ local steps = sequence.steps
+ if steps then
+ for i=1,#steps do
+ local step = steps[i]
+ if kind == "gsub_single" then
+ local c = step.coverage
+ if c then
+ singles[#singles+1] = c
+ end
+ elseif kind == "gsub_alternate" then
+ local c = step.coverage
+ if c then
+ alternates[#alternates+1] = c
+ end
+ elseif kind == "gsub_ligature" then
+ local c = step.coverage
+ if c then
+ ligatures[#ligatures+1] = c
+ end
+ end
+ end
+ end
+ end
+ end
+
+ collectthem(resources.sequences)
+ collectthem(resources.sublookups)
+
+ local loops = 0
+ while true do
+ loops = loops + 1
+ local old = nofmissing
+ for i=1,#singles do
+ local c = singles[i]
+ for g1, g2 in next, c do
+ if missing[g1] then
+ local u2 = descriptions[g2].unicode
+ if u2 then
+ missing[g1] = false
+ descriptions[g1].unicode = u2
+ nofmissing = nofmissing - 1
+ end
+ end
+ if missing[g2] then
+ local u1 = descriptions[g1].unicode
+ if u1 then
+ missing[g2] = false
+ descriptions[g2].unicode = u1
+ nofmissing = nofmissing - 1
+ end
+ end
+ end
+ end
+ for i=1,#alternates do
+ local c = alternates[i]
+ -- maybe first a g1 loop and then a g2
+ for g1, d1 in next, c do
+ if missing[g1] then
+ for i=1,#d1 do
+ local g2 = d1[i]
+ local u2 = descriptions[g2].unicode
+ if u2 then
+ missing[g1] = false
+ descriptions[g1].unicode = u2
+ nofmissing = nofmissing - 1
+ end
+ end
+ end
+ if not missing[g1] then
+ for i=1,#d1 do
+ local g2 = d1[i]
+ if missing[g2] then
+ local u1 = descriptions[g1].unicode
+ if u1 then
+ missing[g2] = false
+ descriptions[g2].unicode = u1
+ nofmissing = nofmissing - 1
+ end
+ end
+ end
+ end
+ end
+ end
+ if nofmissing <= 0 then
+ if trace_unicodes then
+ report_unicodes("all missings done in %s loops",loops)
+ end
+ return
+ elseif old == nofmissing then
+ break
+ end
+ end
+
+ local t, n -- no need to insert/remove and allocate many times
+
+ local function recursed(c)
+ for g, d in next, c do
+ if g ~= "ligature" then
+ local u = descriptions[g].unicode
+ if u then
+ n = n + 1
+ t[n] = u
+ recursed(d)
+ n = n - 1
+ end
+ elseif missing[d] then
+ local l = { }
+ local m = 0
+ for i=1,n do
+ local u = t[i]
+ if type(u) == "table" then
+ for i=1,#u do
+ m = m + 1
+ l[m] = u[i]
+ end
+ else
+ m = m + 1
+ l[m] = u
+ end
+ end
+ missing[d] = false
+ descriptions[d].unicode = l
+ nofmissing = nofmissing - 1
+ end
+ end
+ end
+
+ if nofmissing > 0 then
+ t = { }
+ n = 0
+ local loops = 0
+ while true do
+ loops = loops + 1
+ local old = nofmissing
+ for i=1,#ligatures do
+ recursed(ligatures[i])
+ end
+ if nofmissing <= 0 then
+ if trace_unicodes then
+ report_unicodes("all missings done in %s loops",loops)
+ end
+ return
+ elseif old == nofmissing then
+ break
+ end
+ end
+ t = nil
+ n = 0
+ end
+
+ if trace_unicodes and nofmissing > 0 then
+ local done = { }
+ for i, r in next, missing do
+ if r then
+ local data = descriptions[i]
+ local name = data and data.name or f_index(i)
+ if not ignore[name] then
+ done[name] = true
+ end
+ end
+ end
+ if next(done) then
+ report_unicodes("not unicoded: % t",sortedkeys(done))
+ end
+ end
+end
+
+local function unifymissing(fontdata)
+ if not fonts.mappings then
+ require("font-map")
+ require("font-agl")
+ end
+ local unicodes = { }
+ local resources = fontdata.resources
+ resources.unicodes = unicodes
+ for unicode, d in next, fontdata.descriptions do
+ if unicode < privateoffset then
+ local name = d.name
+ if name then
+ unicodes[name] = unicode
+ end
+ end
+ end
+ fonts.mappings.addtounicode(fontdata,fontdata.filename,checklookups)
+ resources.unicodes = nil
+end
+
+local firstprivate = fonts.privateoffsets and fonts.privateoffsets.textbase or 0xF0000
+local puafirst = 0xE000
+local pualast = 0xF8FF
+
+local function unifyglyphs(fontdata,usenames)
+ local private = fontdata.private or privateoffset
+ local glyphs = fontdata.glyphs
+ local indices = { }
+ local descriptions = { }
+ local names = usenames and { }
+ local resources = fontdata.resources
+ local zero = glyphs[0]
+ local zerocode = zero.unicode
+ if not zerocode then
+ zerocode = private
+ zero.unicode = zerocode
+ private = private + 1
+ end
+ descriptions[zerocode] = zero
+ if names then
+ local name = glyphs[0].name or f_private(zerocode)
+ indices[0] = name
+ names[name] = zerocode
+ else
+ indices[0] = zerocode
+ end
+ --
+ if names then
+ -- seldom uses, we don't issue message ... this branch might even go away
+ for index=1,#glyphs do
+ local glyph = glyphs[index]
+ local unicode = glyph.unicode -- this is the primary one
+ if not unicode then
+ unicode = private
+ local name = glyph.name or f_private(unicode)
+ indices[index] = name
+ names[name] = unicode
+ private = private + 1
+ elseif unicode >= firstprivate then
+ unicode = private
+ local name = glyph.name or f_private(unicode)
+ indices[index] = name
+ names[name] = unicode
+ private = private + 1
+ elseif unicode >= puafirst and unicode <= pualast then
+ local name = glyph.name or f_private(unicode)
+ indices[index] = name
+ names[name] = unicode
+ elseif descriptions[unicode] then
+ unicode = private
+ local name = glyph.name or f_private(unicode)
+ indices[index] = name
+ names[name] = unicode
+ private = private + 1
+ else
+ local name = glyph.name or f_unicode(unicode)
+ indices[index] = name
+ names[name] = unicode
+ end
+ descriptions[unicode] = glyph
+ end
+ elseif trace_unicodes then
+ for index=1,#glyphs do
+ local glyph = glyphs[index]
+ local unicode = glyph.unicode -- this is the primary one
+ if not unicode then
+ unicode = private
+ indices[index] = unicode
+ private = private + 1
+ elseif unicode >= firstprivate then
+ local name = glyph.name
+ if name then
+ report_unicodes("moving glyph %a indexed %05X from private %U to %U ",name,index,unicode,private)
+ else
+ report_unicodes("moving glyph indexed %05X from private %U to %U ",index,unicode,private)
+ end
+ unicode = private
+ indices[index] = unicode
+ private = private + 1
+ elseif unicode >= puafirst and unicode <= pualast then
+ local name = glyph.name
+ if name then
+ report_unicodes("keeping private unicode %U for glyph %a indexed %05X",unicode,name,index)
+ else
+ report_unicodes("keeping private unicode %U for glyph indexed %05X",unicode,index)
+ end
+ indices[index] = unicode
+ elseif descriptions[unicode] then
+ local name = glyph.name
+ if name then
+ report_unicodes("assigning duplicate unicode %U to %U for glyph %a indexed %05X ",unicode,private,name,index)
+ else
+ report_unicodes("assigning duplicate unicode %U to %U for glyph indexed %05X ",unicode,private,index)
+ end
+ unicode = private
+ indices[index] = unicode
+ private = private + 1
+ else
+ indices[index] = unicode
+ end
+ descriptions[unicode] = glyph
+ end
+ else
+ for index=1,#glyphs do
+ local glyph = glyphs[index]
+ local unicode = glyph.unicode -- this is the primary one
+ if not unicode then
+ unicode = private
+ indices[index] = unicode
+ private = private + 1
+ elseif unicode >= firstprivate then
+ local name = glyph.name
+ unicode = private
+ indices[index] = unicode
+ private = private + 1
+ elseif unicode >= puafirst and unicode <= pualast then
+ local name = glyph.name
+ indices[index] = unicode
+ elseif descriptions[unicode] then
+ local name = glyph.name
+ unicode = private
+ indices[index] = unicode
+ private = private + 1
+ else
+ indices[index] = unicode
+ end
+ descriptions[unicode] = glyph
+ end
+ end
+ --
+ for index=1,#glyphs do
+ local math = glyphs[index].math
+ if math then
+ local list = math.vparts
+ if list then
+ for i=1,#list do local l = list[i] l.glyph = indices[l.glyph] end
+ end
+ local list = math.hparts
+ if list then
+ for i=1,#list do local l = list[i] l.glyph = indices[l.glyph] end
+ end
+ local list = math.vvariants
+ if list then
+ -- for i=1,#list do local l = list[i] l.glyph = indices[l.glyph] end
+ for i=1,#list do list[i] = indices[list[i]] end
+ end
+ local list = math.hvariants
+ if list then
+ -- for i=1,#list do local l = list[i] l.glyph = indices[l.glyph] end
+ for i=1,#list do list[i] = indices[list[i]] end
+ end
+ end
+ end
+ --
+ local colorpalettes = resources.colorpalettes
+ if colorpalettes then
+ for index=1,#glyphs do
+ local colors = glyphs[index].colors
+ if colors then
+ for i=1,#colors do
+ local c = colors[i]
+ c.slot = indices[c.slot]
+ end
+ end
+ end
+ end
+ --
+ fontdata.private = private
+ fontdata.glyphs = nil
+ fontdata.names = names
+ fontdata.descriptions = descriptions
+ fontdata.hashmethod = hashmethod
+ --
+ return indices, names
+end
+
+local p_crappyname do
+
+ local p_hex = R("af","AF","09")
+ local p_digit = R("09")
+ local p_done = S("._-")^0 + P(-1)
+ local p_alpha = R("az","AZ")
+ local p_ALPHA = R("AZ")
+
+ p_crappyname = (
+ -- (P("uni") + P("UNI") + P("Uni") + P("U") + P("u"))
+ lpeg.utfchartabletopattern({ "uni", "u" },true)
+ * S("Xx_")^0
+ * p_hex^1
+ -- + (P("identity") + P("Identity") + P("IDENTITY") + P("glyph") + P("jamo"))
+ + lpeg.utfchartabletopattern({ "identity", "glyph", "jamo" },true)
+ * p_hex^1
+ -- + (P("index") + P("Index") + P("INDEX")+ P("afii"))
+ + lpeg.utfchartabletopattern({ "index", "afii" }, true)
+ * p_digit^1
+ -- also happens l
+ + p_digit
+ * p_hex^3
+ + p_alpha
+ * p_digit^1
+ -- sort of special
+ + P("aj")
+ * p_digit^1
+ + P("eh_")
+ * (p_digit^1 + p_ALPHA * p_digit^1)
+ + (1-P("_"))^1
+ * P("_uni")
+ * p_hex^1
+ + P("_")
+ * P(1)^1
+ ) * p_done
+
+end
+
+-- In context we only keep glyph names because of tracing and access by name
+-- so weird names make no sense.
+
+local forcekeep = false -- only for testing something
+
+directives.register("otf.keepnames",function(v)
+ report_cleanup("keeping weird glyph names, expect larger files and more memory usage")
+ forcekeep = v
+end)
+
+local function stripredundant(fontdata)
+ local descriptions = fontdata.descriptions
+ if descriptions then
+ local n = 0
+ local c = 0
+ -- in context we always strip
+ if (not context and fonts.privateoffsets.keepnames) or forcekeep then
+ for unicode, d in next, descriptions do
+ if d.class == "base" then
+ d.class = nil
+ c = c + 1
+ end
+ end
+ else
+ for unicode, d in next, descriptions do
+ local name = d.name
+ if name and lpegmatch(p_crappyname,name) then
+ d.name = nil
+ n = n + 1
+ end
+ if d.class == "base" then
+ d.class = nil
+ c = c + 1
+ end
+ end
+ end
+ if trace_cleanup then
+ if n > 0 then
+ report_cleanup("%s bogus names removed (verbose unicode)",n)
+ end
+ if c > 0 then
+ report_cleanup("%s base class tags removed (default is base)",c)
+ end
+ end
+ end
+end
+
+readers.stripredundant = stripredundant
+
+function readers.getcomponents(fontdata) -- handy for resolving ligatures when names are missing
+ local resources = fontdata.resources
+ if resources then
+ local sequences = resources.sequences
+ if sequences then
+ local collected = { }
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ if sequence.type == "gsub_ligature" then
+ local steps = sequence.steps
+ if steps then
+ local l = { }
+ local function traverse(p,k,v)
+ if k == "ligature" then
+ collected[v] = { unpack(l) }
+ else
+ insert(l,k)
+ for k, vv in next, v do
+ traverse(p,k,vv)
+ end
+ remove(l)
+ end
+ end
+ for i=1,#steps do
+ -- we actually had/have this in base mode
+ local c = steps[i].coverage
+ if c then
+ for k, v in next, c do
+ traverse(k,k,v)
+ end
+ end
+ end
+ end
+ end
+ end
+ if next(collected) then
+ -- remove self referring
+ -- for k, v in next, collected do
+ -- for i=1,#v do
+ -- local vi = v[i]
+ -- if vi == k then
+ -- -- report("removing self referring ligature @ slot %5X from collected (1)",k)
+ -- collected[k] = nil
+ -- end
+ -- end
+ -- end
+ while true do
+ local done = false
+ for k, v in next, collected do
+ for i=1,#v do
+ local vi = v[i]
+ if vi == k then
+ -- report("removing self referring ligature @ slot %5X from collected (2)",k)
+ collected[k] = nil
+ break
+ else
+ local c = collected[vi]
+ if c then
+ done = true
+ local t = { }
+ local n = i - 1
+ for j=1,n do
+ t[j] = v[j]
+ end
+ for j=1,#c do
+ n = n + 1
+ t[n] = c[j]
+ end
+ for j=i+1,#v do
+ n = n + 1
+ t[n] = v[j]
+ end
+ collected[k] = t
+ break
+ end
+ end
+ end
+ end
+ if not done then
+ break
+ end
+ end
+ return collected
+ end
+ end
+ end
+end
+
+readers.unifymissing = unifymissing
+
+function readers.rehash(fontdata,hashmethod) -- TODO: combine loops in one
+ if not (fontdata and fontdata.glyphs) then
+ return
+ end
+ if hashmethod == "indices" then
+ fontdata.hashmethod = "indices"
+ elseif hashmethod == "names" then
+ fontdata.hashmethod = "names"
+ local indices = unifyglyphs(fontdata,true)
+ unifyresources(fontdata,indices)
+ copyduplicates(fontdata)
+ unifymissing(fontdata)
+ -- stripredundant(fontdata)
+ else
+ fontdata.hashmethod = "unicodes"
+ local indices = unifyglyphs(fontdata)
+ unifyresources(fontdata,indices)
+ copyduplicates(fontdata)
+ unifymissing(fontdata)
+ stripredundant(fontdata)
+ end
+ -- maybe here components
+end
+
+function readers.checkhash(fontdata)
+ local hashmethod = fontdata.hashmethod
+ if hashmethod == "unicodes" then
+ fontdata.names = nil -- just to be sure
+ elseif hashmethod == "names" and fontdata.names then
+ unifyresources(fontdata,fontdata.names)
+ copyduplicates(fontdata)
+ fontdata.hashmethod = "unicodes"
+ fontdata.names = nil -- no need for it
+ else
+ readers.rehash(fontdata,"unicodes")
+ end
+end
+
+function readers.addunicodetable(fontdata)
+ local resources = fontdata.resources
+ local unicodes = resources.unicodes
+ if not unicodes then
+ local descriptions = fontdata.descriptions
+ if descriptions then
+ unicodes = { }
+ resources.unicodes = unicodes
+ for u, d in next, descriptions do
+ local n = d.name
+ if n then
+ unicodes[n] = u
+ end
+ end
+ end
+ end
+end
+
+-- for the moment here:
+
+local concat, sort = table.concat, table.sort
+local next, type, tostring = next, type, tostring
+
+local criterium = 1
+local threshold = 0
+
+local trace_packing = false trackers.register("otf.packing", function(v) trace_packing = v end)
+local trace_loading = false trackers.register("otf.loading", function(v) trace_loading = v end)
+
+local report_otf = logs.reporter("fonts","otf loading")
+
+local function tabstr_normal(t)
+ local s = { }
+ local n = 0
+ for k, v in next, t do
+ n = n + 1
+ if type(v) == "table" then
+ s[n] = k .. ">" .. tabstr_normal(v)
+ elseif v == true then
+ s[n] = k .. "+" -- "=true"
+ elseif v then
+ s[n] = k .. "=" .. v
+ else
+ s[n] = k .. "-" -- "=false"
+ end
+ end
+ if n == 0 then
+ return ""
+ elseif n == 1 then
+ return s[1]
+ else
+ sort(s) -- costly but needed (occasional wrong hit otherwise)
+ return concat(s,",")
+ end
+end
+
+local function tabstr_flat(t)
+ local s = { }
+ local n = 0
+ for k, v in next, t do
+ n = n + 1
+ s[n] = k .. "=" .. v
+ end
+ if n == 0 then
+ return ""
+ elseif n == 1 then
+ return s[1]
+ else
+ sort(s) -- costly but needed (occasional wrong hit otherwise)
+ return concat(s,",")
+ end
+end
+
+local function tabstr_mixed(t) -- indexed
+ local s = { }
+ local n = #t
+ if n == 0 then
+ return ""
+ elseif n == 1 then
+ local k = t[1]
+ if k == true then
+ return "++" -- we need to distinguish from "true"
+ elseif k == false then
+ return "--" -- we need to distinguish from "false"
+ else
+ return tostring(k) -- number or string
+ end
+ else
+ for i=1,n do
+ local k = t[i]
+ if k == true then
+ s[i] = "++" -- we need to distinguish from "true"
+ elseif k == false then
+ s[i] = "--" -- we need to distinguish from "false"
+ else
+ s[i] = k -- number or string
+ end
+ end
+ return concat(s,",")
+ end
+end
+
+local function tabstr_boolean(t)
+ local s = { }
+ local n = 0
+ for k, v in next, t do
+ n = n + 1
+ if v then
+ s[n] = k .. "+"
+ else
+ s[n] = k .. "-"
+ end
+ end
+ if n == 0 then
+ return ""
+ elseif n == 1 then
+ return s[1]
+ else
+ sort(s) -- costly but needed (occasional wrong hit otherwise)
+ return concat(s,",")
+ end
+end
+
+-- beware: we cannot unpack and repack the same table because then sharing
+-- interferes (we could catch this if needed) .. so for now: save, reload
+-- and repack in such cases (never needed anyway) .. a tricky aspect is that
+-- we then need to sort more thanks to random hashing
+
+function readers.pack(data)
+
+ if data then
+
+ local h, t, c = { }, { }, { }
+ local hh, tt, cc = { }, { }, { }
+ local nt, ntt = 0, 0
+
+ local function pack_normal(v)
+ local tag = tabstr_normal(v)
+ local ht = h[tag]
+ if ht then
+ c[ht] = c[ht] + 1
+ return ht
+ else
+ nt = nt + 1
+ t[nt] = v
+ h[tag] = nt
+ c[nt] = 1
+ return nt
+ end
+ end
+
+ local function pack_normal_cc(v)
+ local tag = tabstr_normal(v)
+ local ht = h[tag]
+ if ht then
+ c[ht] = c[ht] + 1
+ return ht
+ else
+ v[1] = 0
+ nt = nt + 1
+ t[nt] = v
+ h[tag] = nt
+ c[nt] = 1
+ return nt
+ end
+ end
+
+ local function pack_flat(v)
+ local tag = tabstr_flat(v)
+ local ht = h[tag]
+ if ht then
+ c[ht] = c[ht] + 1
+ return ht
+ else
+ nt = nt + 1
+ t[nt] = v
+ h[tag] = nt
+ c[nt] = 1
+ return nt
+ end
+ end
+
+ local function pack_indexed(v)
+ local tag = concat(v," ")
+ local ht = h[tag]
+ if ht then
+ c[ht] = c[ht] + 1
+ return ht
+ else
+ nt = nt + 1
+ t[nt] = v
+ h[tag] = nt
+ c[nt] = 1
+ return nt
+ end
+ end
+
+ local function pack_mixed(v)
+ local tag = tabstr_mixed(v)
+ local ht = h[tag]
+ if ht then
+ c[ht] = c[ht] + 1
+ return ht
+ else
+ nt = nt + 1
+ t[nt] = v
+ h[tag] = nt
+ c[nt] = 1
+ return nt
+ end
+ end
+
+ -- saves a lot on noto sans
+
+ -- can be made more clever
+
+ local function pack_boolean(v)
+ local tag = tabstr_boolean(v)
+ local ht = h[tag]
+ if ht then
+ c[ht] = c[ht] + 1
+ return ht
+ else
+ nt = nt + 1
+ t[nt] = v
+ h[tag] = nt
+ c[nt] = 1
+ return nt
+ end
+ end
+
+ -- -- This was an experiment to see if we can bypass the luajit limits but loading is
+ -- -- still an issue due to other limits so we don't use this ... actually it can
+ -- -- prevent a luajittex crash but i don't care too much about that as we can't use
+ -- -- that engine anyway then.
+ --
+ -- local function check(t)
+ -- if type(t) == "table" then
+ -- local s = sortedkeys(t)
+ -- local n = #s
+ -- if n <= 10 then
+ -- return
+ -- end
+ -- local ranges = { }
+ -- local first, last
+ -- for i=1,#s do
+ -- local ti = s[i]
+ -- if not first then
+ -- first = ti
+ -- last = ti
+ -- elseif ti == last + 1 then
+ -- last = ti
+ -- elseif last - first < 10 then
+ -- -- we could permits a few exceptions
+ -- return
+ -- else
+ -- ranges[#ranges+1] = { first, last }
+ -- first, last = nil, nil
+ -- end
+ -- end
+ -- if #ranges > 0 then
+ -- return {
+ -- ranges = ranges
+ -- }
+ -- end
+ -- end
+ -- end
+ --
+ -- local function pack_boolean(v)
+ -- local tag
+ -- local r = check(v)
+ -- if r then
+ -- v = r
+ -- tag = tabstr_normal(v)
+ -- else
+ -- tag = tabstr_boolean(v)
+ -- end
+ -- local ht = h[tag]
+ -- if ht then
+ -- c[ht] = c[ht] + 1
+ -- return ht
+ -- else
+ -- nt = nt + 1
+ -- t[nt] = v
+ -- h[tag] = nt
+ -- c[nt] = 1
+ -- return nt
+ -- end
+ -- end
+
+ local function pack_final(v)
+ -- v == number
+ if c[v] <= criterium then
+ return t[v]
+ else
+ -- compact hash
+ local hv = hh[v]
+ if hv then
+ return hv
+ else
+ ntt = ntt + 1
+ tt[ntt] = t[v]
+ hh[v] = ntt
+ cc[ntt] = c[v]
+ return ntt
+ end
+ end
+ end
+
+ local function pack_final_cc(v)
+ -- v == number
+ if c[v] <= criterium then
+ return t[v]
+ else
+ -- compact hash
+ local hv = hh[v]
+ if hv then
+ return hv
+ else
+ ntt = ntt + 1
+ tt[ntt] = t[v]
+ hh[v] = ntt
+ cc[ntt] = c[v]
+ return ntt
+ end
+ end
+ end
+
+ local function success(stage,pass)
+ if nt == 0 then
+ if trace_loading or trace_packing then
+ report_otf("pack quality: nothing to pack")
+ end
+ return false
+ elseif nt >= threshold then
+ local one = 0
+ local two = 0
+ local rest = 0
+ if pass == 1 then
+ for k,v in next, c do
+ if v == 1 then
+ one = one + 1
+ elseif v == 2 then
+ two = two + 1
+ else
+ rest = rest + 1
+ end
+ end
+ else
+ for k,v in next, cc do
+ if v > 20 then
+ rest = rest + 1
+ elseif v > 10 then
+ two = two + 1
+ else
+ one = one + 1
+ end
+ end
+ data.tables = tt
+ end
+ if trace_loading or trace_packing then
+ report_otf("pack quality: stage %s, pass %s, %s packed, 1-10:%s, 11-20:%s, rest:%s (criterium: %s)",
+ stage, pass, one+two+rest, one, two, rest, criterium)
+ end
+ return true
+ else
+ if trace_loading or trace_packing then
+ report_otf("pack quality: stage %s, pass %s, %s packed, aborting pack (threshold: %s)",
+ stage, pass, nt, threshold)
+ end
+ return false
+ end
+ end
+
+ local function packers(pass)
+ if pass == 1 then
+ return pack_normal, pack_indexed, pack_flat, pack_boolean, pack_mixed, pack_normal_cc
+ else
+ return pack_final, pack_final, pack_final, pack_final, pack_final, pack_final_cc
+ end
+ end
+
+ local resources = data.resources
+ local sequences = resources.sequences
+ local sublookups = resources.sublookups
+ local features = resources.features
+ local palettes = resources.colorpalettes
+ local variable = resources.variabledata
+
+ local chardata = characters and characters.data
+ local descriptions = data.descriptions or data.glyphs
+
+ if not descriptions then
+ return
+ end
+
+ for pass=1,2 do
+
+ if trace_packing then
+ report_otf("start packing: stage 1, pass %s",pass)
+ end
+
+ local pack_normal, pack_indexed, pack_flat, pack_boolean, pack_mixed, pack_normal_cc = packers(pass)
+
+ for unicode, description in next, descriptions do
+ local boundingbox = description.boundingbox
+ if boundingbox then
+ description.boundingbox = pack_indexed(boundingbox)
+ end
+ local math = description.math
+ if math then
+ local kerns = math.kerns
+ if kerns then
+ for tag, kern in next, kerns do
+ kerns[tag] = pack_normal(kern)
+ end
+ end
+ end
+ -- if palettes then
+ -- local color = description.color
+ -- if color then
+ -- for i=1,#color do
+ -- color[i] = pack_normal(color[i])
+ -- end
+ -- end
+ -- end
+ end
+
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local kind = sequence.type
+ local steps = sequence.steps
+ local order = sequence.order
+ local features = sequence.features
+ local flags = sequence.flags
+ if steps then
+ for i=1,#steps do
+ local step = steps[i]
+ if kind == "gpos_pair" then
+ local c = step.coverage
+ if c then
+ if step.format ~= "pair" then
+ for g1, d1 in next, c do
+ c[g1] = pack_normal(d1)
+ end
+ elseif step.shared then
+ -- This branch results from classes. We already share at the reader end. Maybe
+ -- the sharing should be moved there altogether but it becomes kind of messy
+ -- then. Here we're still wasting time because in the second pass we serialize
+ -- and hash. So we compromise. We could merge the two passes ...
+ local shared = { }
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ if not shared[d2] then
+ local f = d2[1] if f and f ~= true then d2[1] = pack_indexed(f) end
+ local s = d2[2] if s and s ~= true then d2[2] = pack_indexed(s) end
+ shared[d2] = true
+ end
+ end
+ end
+ if pass == 2 then
+ step.shared = nil -- weird, so dups
+ end
+ else
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ local f = d2[1] if f and f ~= true then d2[1] = pack_indexed(f) end
+ local s = d2[2] if s and s ~= true then d2[2] = pack_indexed(s) end
+ end
+ end
+ end
+ end
+ elseif kind == "gpos_single" then
+ local c = step.coverage
+ if c then
+ if step.format == "single" then
+ for g1, d1 in next, c do
+ if d1 and d1 ~= true then
+ c[g1] = pack_indexed(d1)
+ end
+ end
+ else
+ step.coverage = pack_normal(c)
+ end
+ end
+ elseif kind == "gpos_cursive" then
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ local f = d1[2] if f then d1[2] = pack_indexed(f) end
+ local s = d1[3] if s then d1[3] = pack_indexed(s) end
+ end
+ end
+ elseif kind == "gpos_mark2base" or kind == "gpos_mark2mark" then
+ local c = step.baseclasses
+ if c then
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ d1[g2] = pack_indexed(d2)
+ end
+ end
+ end
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ d1[2] = pack_indexed(d1[2])
+ end
+ end
+ elseif kind == "gpos_mark2ligature" then
+ local c = step.baseclasses
+ if c then
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ for g3, d3 in next, d2 do
+ d2[g3] = pack_indexed(d3)
+ end
+ end
+ end
+ end
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ d1[2] = pack_indexed(d1[2])
+ end
+ end
+ end
+ -- if ... chain ...
+ local rules = step.rules
+ if rules then
+ for i=1,#rules do
+ local rule = rules[i]
+ local r = rule.before if r then for i=1,#r do r[i] = pack_boolean(r[i]) end end
+ local r = rule.after if r then for i=1,#r do r[i] = pack_boolean(r[i]) end end
+ local r = rule.current if r then for i=1,#r do r[i] = pack_boolean(r[i]) end end
+ -- local r = rule.lookups if r then rule.lookups = pack_mixed (r) end
+ local r = rule.replacements if r then rule.replacements = pack_flat (r) end
+ end
+ end
+ end
+ end
+ if order then
+ sequence.order = pack_indexed(order)
+ end
+ if features then
+ for script, feature in next, features do
+ features[script] = pack_normal(feature)
+ end
+ end
+ if flags then
+ sequence.flags = pack_normal(flags)
+ end
+ end
+ end
+
+ if sequences then
+ packthem(sequences)
+ end
+
+ if sublookups then
+ packthem(sublookups)
+ end
+
+ if features then
+ for k, list in next, features do
+ for feature, spec in next, list do
+ list[feature] = pack_normal(spec)
+ end
+ end
+ end
+
+ if palettes then
+ for i=1,#palettes do
+ local p = palettes[i]
+ for j=1,#p do
+ p[j] = pack_indexed(p[j])
+ end
+ end
+
+ end
+
+ if variable then
+
+ -- todo: segments
+
+ local instances = variable.instances
+ if instances then
+ for i=1,#instances do
+ local v = instances[i].values
+ for j=1,#v do
+ v[j] = pack_normal(v[j])
+ end
+ end
+ end
+
+ local function packdeltas(main)
+ if main then
+ local deltas = main.deltas
+ if deltas then
+ for i=1,#deltas do
+ local di = deltas[i]
+ local d = di.deltas
+ -- local r = di.regions
+ for j=1,#d do
+ d[j] = pack_indexed(d[j])
+ end
+ di.regions = pack_indexed(di.regions)
+ end
+ end
+ local regions = main.regions
+ if regions then
+ for i=1,#regions do
+ local r = regions[i]
+ for j=1,#r do
+ r[j] = pack_normal(r[j])
+ end
+ end
+ end
+ end
+ end
+
+ packdeltas(variable.global)
+ packdeltas(variable.horizontal)
+ packdeltas(variable.vertical)
+ packdeltas(variable.metrics)
+
+ end
+
+ if not success(1,pass) then
+ return
+ end
+
+ end
+
+ if nt > 0 then
+
+ for pass=1,2 do
+
+ if trace_packing then
+ report_otf("start packing: stage 2, pass %s",pass)
+ end
+
+ local pack_normal, pack_indexed, pack_flat, pack_boolean, pack_mixed, pack_normal_cc = packers(pass)
+
+ for unicode, description in next, descriptions do
+ local math = description.math
+ if math then
+ local kerns = math.kerns
+ if kerns then
+ math.kerns = pack_normal(kerns)
+ end
+ end
+ end
+
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local kind = sequence.type
+ local steps = sequence.steps
+ local features = sequence.features
+ if steps then
+ for i=1,#steps do
+ local step = steps[i]
+ if kind == "gpos_pair" then
+ local c = step.coverage
+ if c then
+ if step.format == "pair" then
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ d1[g2] = pack_normal(d2)
+ end
+ end
+ end
+ end
+ -- elseif kind == "gpos_cursive" then
+ -- local c = step.coverage -- new
+ -- if c then
+ -- for g1, d1 in next, c do
+ -- c[g1] = pack_normal_cc(d1)
+ -- end
+ -- end
+ elseif kind == "gpos_mark2ligature" then
+ local c = step.baseclasses -- new
+ if c then
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ d1[g2] = pack_normal(d2)
+ end
+ end
+ end
+ end
+ local rules = step.rules
+ if rules then
+ for i=1,#rules do
+ local rule = rules[i]
+ local r = rule.before if r then rule.before = pack_normal(r) end
+ local r = rule.after if r then rule.after = pack_normal(r) end
+ local r = rule.current if r then rule.current = pack_normal(r) end
+ end
+ end
+ end
+ end
+ if features then
+ sequence.features = pack_normal(features)
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ if variable then
+ local function unpackdeltas(main)
+ if main then
+ local regions = main.regions
+ if regions then
+ main.regions = pack_normal(regions)
+ end
+ end
+ end
+ unpackdeltas(variable.global)
+ unpackdeltas(variable.horizontal)
+ unpackdeltas(variable.vertical)
+ unpackdeltas(variable.metrics)
+ end
+ -- if not success(2,pass) then
+ -- -- return
+ -- end
+ end
+
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 3, pass %s",pass)
+ end
+
+ local pack_normal, pack_indexed, pack_flat, pack_boolean, pack_mixed, pack_normal_cc = packers(pass)
+
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local kind = sequence.type
+ local steps = sequence.steps
+ local features = sequence.features
+ if steps then
+ for i=1,#steps do
+ local step = steps[i]
+ if kind == "gpos_pair" then
+ local c = step.coverage
+ if c then
+ if step.format == "pair" then
+ for g1, d1 in next, c do
+ c[g1] = pack_normal(d1)
+ end
+ end
+ end
+ elseif kind == "gpos_cursive" then
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ c[g1] = pack_normal_cc(d1)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+
+ end
+
+ end
+
+ end
+end
+
+local unpacked_mt = {
+ __index =
+ function(t,k)
+ t[k] = false
+ return k -- next time true
+ end
+}
+
+function readers.unpack(data)
+
+ if data then
+ local tables = data.tables
+ if tables then
+ local resources = data.resources
+ local descriptions = data.descriptions or data.glyphs
+ local sequences = resources.sequences
+ local sublookups = resources.sublookups
+ local features = resources.features
+ local palettes = resources.colorpalettes
+ local variable = resources.variabledata
+ local unpacked = { }
+ setmetatable(unpacked,unpacked_mt)
+ for unicode, description in next, descriptions do
+ local tv = tables[description.boundingbox]
+ if tv then
+ description.boundingbox = tv
+ end
+ local math = description.math
+ if math then
+ local kerns = math.kerns
+ if kerns then
+ local tm = tables[kerns]
+ if tm then
+ math.kerns = tm
+ kerns = unpacked[tm]
+ end
+ if kerns then
+ for k, kern in next, kerns do
+ local tv = tables[kern]
+ if tv then
+ kerns[k] = tv
+ end
+ end
+ end
+ end
+ end
+ -- if palettes then
+ -- local color = description.color
+ -- if color then
+ -- for i=1,#color do
+ -- local tv = tables[color[i]]
+ -- if tv then
+ -- color[i] = tv
+ -- end
+ -- end
+ -- end
+ -- end
+ end
+
+ -- local function expandranges(t,ranges)
+ -- for i=1,#ranges do
+ -- local r = ranges[i]
+ -- for k=r[1],r[2] do
+ -- t[k] = true
+ -- end
+ -- end
+ -- end
+
+ local function unpackthem(sequences)
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local kind = sequence.type
+ local steps = sequence.steps
+ local order = sequence.order
+ local features = sequence.features
+ local flags = sequence.flags
+ local markclass = sequence.markclass
+ if features then
+ local tv = tables[features]
+ if tv then
+ sequence.features = tv
+ features = tv
+ end
+ for script, feature in next, features do
+ local tv = tables[feature]
+ if tv then
+ features[script] = tv
+ end
+ end
+ end
+ if steps then
+ for i=1,#steps do
+ local step = steps[i]
+ if kind == "gpos_pair" then
+ local c = step.coverage
+ if c then
+ if step.format == "pair" then
+ for g1, d1 in next, c do
+ local tv = tables[d1]
+ if tv then
+ c[g1] = tv
+ d1 = tv
+ end
+ for g2, d2 in next, d1 do
+ local tv = tables[d2]
+ if tv then
+ d1[g2] = tv
+ d2 = tv
+ end
+ local f = tables[d2[1]] if f then d2[1] = f end
+ local s = tables[d2[2]] if s then d2[2] = s end
+ end
+ end
+ else
+ for g1, d1 in next, c do
+ local tv = tables[d1]
+ if tv then
+ c[g1] = tv
+ end
+ end
+ end
+ end
+ elseif kind == "gpos_single" then
+ local c = step.coverage
+ if c then
+ if step.format == "single" then
+ for g1, d1 in next, c do
+ local tv = tables[d1]
+ if tv then
+ c[g1] = tv
+ end
+ end
+ else
+ local tv = tables[c]
+ if tv then
+ step.coverage = tv
+ end
+ end
+ end
+ elseif kind == "gpos_cursive" then
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ local tv = tables[d1]
+ if tv then
+ d1 = tv
+ c[g1] = d1
+ end
+ local f = tables[d1[2]] if f then d1[2] = f end
+ local s = tables[d1[3]] if s then d1[3] = s end
+ end
+ end
+ elseif kind == "gpos_mark2base" or kind == "gpos_mark2mark" then
+ local c = step.baseclasses
+ if c then
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ local tv = tables[d2]
+ if tv then
+ d1[g2] = tv
+ end
+ end
+ end
+ end
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ local tv = tables[d1[2]]
+ if tv then
+ d1[2] = tv
+ end
+ end
+ end
+ elseif kind == "gpos_mark2ligature" then
+ local c = step.baseclasses
+ if c then
+ for g1, d1 in next, c do
+ for g2, d2 in next, d1 do
+ local tv = tables[d2] -- new
+ if tv then
+ d2 = tv
+ d1[g2] = d2
+ end
+ for g3, d3 in next, d2 do
+ local tv = tables[d2[g3]]
+ if tv then
+ d2[g3] = tv
+ end
+ end
+ end
+ end
+ end
+ local c = step.coverage
+ if c then
+ for g1, d1 in next, c do
+ local tv = tables[d1[2]]
+ if tv then
+ d1[2] = tv
+ end
+ end
+ end
+ end
+ local rules = step.rules
+ if rules then
+ for i=1,#rules do
+ local rule = rules[i]
+ local before = rule.before
+ if before then
+ local tv = tables[before]
+ if tv then
+ rule.before = tv
+ before = tv
+ end
+ for i=1,#before do
+ local tv = tables[before[i]]
+ if tv then
+ before[i] = tv
+ end
+ end
+ -- for i=1,#before do
+ -- local bi = before[i]
+ -- local tv = tables[bi]
+ -- if tv then
+ -- bi = tv
+ -- before[i] = bi
+ -- end
+ -- local ranges = bi.ranges
+ -- if ranges then
+ -- expandranges(bi,ranges)
+ -- end
+ -- end
+ end
+ local after = rule.after
+ if after then
+ local tv = tables[after]
+ if tv then
+ rule.after = tv
+ after = tv
+ end
+ for i=1,#after do
+ local tv = tables[after[i]]
+ if tv then
+ after[i] = tv
+ end
+ end
+ -- for i=1,#after do
+ -- local ai = after[i]
+ -- local tv = tables[ai]
+ -- if tv then
+ -- ai = tv
+ -- after[i] = ai
+ -- end
+ -- local ranges = ai.ranges
+ -- if ranges then
+ -- expandranges(ai,ranges)
+ -- end
+ -- end
+ end
+ local current = rule.current
+ if current then
+ local tv = tables[current]
+ if tv then
+ rule.current = tv
+ current = tv
+ end
+ for i=1,#current do
+ local tv = tables[current[i]]
+ if tv then
+ current[i] = tv
+ end
+ end
+ -- for i=1,#current do
+ -- local ci = current[i]
+ -- local tv = tables[ci]
+ -- if tv then
+ -- ci = tv
+ -- current[i] = ci
+ -- end
+ -- local ranges = ci.ranges
+ -- if ranges then
+ -- expandranges(ci,ranges)
+ -- end
+ -- end
+ end
+ -- local lookups = rule.lookups
+ -- if lookups then
+ -- local tv = tables[lookups]
+ -- if tv then
+ -- rule.lookups = tv
+ -- end
+ -- end
+ local replacements = rule.replacements
+ if replacements then
+ local tv = tables[replacements]
+ if tv then
+ rule.replacements = tv
+ end
+ end
+ end
+ end
+ end
+ end
+ if order then
+ local tv = tables[order]
+ if tv then
+ sequence.order = tv
+ end
+ end
+ if flags then
+ local tv = tables[flags]
+ if tv then
+ sequence.flags = tv
+ end
+ end
+ end
+ end
+
+ if sequences then
+ unpackthem(sequences)
+ end
+
+ if sublookups then
+ unpackthem(sublookups)
+ end
+
+ if features then
+ for k, list in next, features do
+ for feature, spec in next, list do
+ local tv = tables[spec]
+ if tv then
+ list[feature] = tv
+ end
+ end
+ end
+ end
+
+ if palettes then
+ for i=1,#palettes do
+ local p = palettes[i]
+ for j=1,#p do
+ local tv = tables[p[j]]
+ if tv then
+ p[j] = tv
+ end
+ end
+ end
+ end
+
+ if variable then
+
+ -- todo: segments
+
+ local instances = variable.instances
+ if instances then
+ for i=1,#instances do
+ local v = instances[i].values
+ for j=1,#v do
+ local tv = tables[v[j]]
+ if tv then
+ v[j] = tv
+ end
+ end
+ end
+ end
+
+ local function unpackdeltas(main)
+ if main then
+ local deltas = main.deltas
+ if deltas then
+ for i=1,#deltas do
+ local di = deltas[i]
+ local d = di.deltas
+ local r = di.regions
+ for j=1,#d do
+ local tv = tables[d[j]]
+ if tv then
+ d[j] = tv
+ end
+ end
+ local tv = di.regions
+ if tv then
+ di.regions = tv
+ end
+ end
+ end
+ local regions = main.regions
+ if regions then
+ local tv = tables[regions]
+ if tv then
+ main.regions = tv
+ regions = tv
+ end
+ for i=1,#regions do
+ local r = regions[i]
+ for j=1,#r do
+ local tv = tables[r[j]]
+ if tv then
+ r[j] = tv
+ end
+ end
+ end
+ end
+ end
+ end
+
+ unpackdeltas(variable.global)
+ unpackdeltas(variable.horizontal)
+ unpackdeltas(variable.vertical)
+ unpackdeltas(variable.metrics)
+
+ end
+
+ data.tables = nil
+ end
+ end
+end
+
+local mt = {
+ __index = function(t,k) -- maybe set it
+ if k == "height" then
+ local ht = t.boundingbox[4]
+ return ht < 0 and 0 or ht
+ elseif k == "depth" then
+ local dp = -t.boundingbox[2]
+ return dp < 0 and 0 or dp
+ elseif k == "width" then
+ return 0
+ elseif k == "name" then -- or maybe uni*
+ return forcenotdef and ".notdef"
+ end
+ end
+}
+
+local function sameformat(sequence,steps,first,nofsteps,kind)
+ return true
+end
+
+local function mergesteps_1(lookup,strict)
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ local first = steps[1]
+ if strict then
+ local f = first.format
+ for i=2,nofsteps do
+ if steps[i].format ~= f then
+ if trace_optimizations then
+ report_optimizations("not merging %a steps of %a lookup %a, different formats",nofsteps,lookup.type,lookup.name)
+ end
+ return 0
+ end
+ end
+ end
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target = first.coverage
+ for i=2,nofsteps do
+ local c = steps[i].coverage
+ if c then
+ for k, v in next, c do
+ if not target[k] then
+ target[k] = v
+ end
+ end
+ end
+ end
+ lookup.nofsteps = 1
+ lookup.merged = true
+ lookup.steps = { first }
+ return nofsteps - 1
+end
+
+local function mergesteps_2(lookup) -- pairs
+ -- this can be tricky as we can have a match on a mark with no marks skip flag
+ -- in which case with multiple steps a hit can prevent a next step while in the
+ -- merged case we can hit differently (a messy font then anyway)
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ local first = steps[1]
+ if strict then
+ local f = first.format
+ for i=2,nofsteps do
+ if steps[i].format ~= f then
+ if trace_optimizations then
+ report_optimizations("not merging %a steps of %a lookup %a, different formats",nofsteps,lookup.type,lookup.name)
+ end
+ return 0
+ end
+ end
+ end
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target = first.coverage
+ for i=2,nofsteps do
+ local c = steps[i].coverage
+ if c then
+ for k, v in next, c do
+ local tk = target[k]
+ if tk then
+ for kk, vv in next, v do
+ if tk[kk] == nil then
+ tk[kk] = vv
+ end
+ end
+ else
+ target[k] = v
+ end
+ end
+ end
+ end
+ lookup.nofsteps = 1
+ lookup.merged = true
+ lookup.steps = { first }
+ return nofsteps - 1
+end
+
+-- we could have a coverage[first][second] = { } already here (because eventually
+-- we also have something like that after loading)
+
+local function mergesteps_3(lookup,strict) -- marks
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ -- check first
+ local coverage = { }
+ for i=1,nofsteps do
+ local c = steps[i].coverage
+ if c then
+ for k, v in next, c do
+ local tk = coverage[k] -- { class, { x, y } }
+ if tk then
+ if trace_optimizations then
+ report_optimizations("quitting merge due to multiple checks")
+ end
+ return nofsteps
+ else
+ coverage[k] = v
+ end
+ end
+ end
+ end
+ -- merge indeed
+ local first = steps[1]
+ local baseclasses = { } -- let's assume sparse step.baseclasses
+ for i=1,nofsteps do
+ local offset = i*10 -- we assume max 10 classes per step
+ local step = steps[i]
+ for k, v in sortedhash(step.baseclasses) do
+ baseclasses[offset+k] = v
+ end
+ for k, v in next, step.coverage do
+ v[1] = offset + v[1]
+ end
+ end
+ first.baseclasses = baseclasses
+ first.coverage = coverage
+ lookup.nofsteps = 1
+ lookup.merged = true
+ lookup.steps = { first }
+ return nofsteps - 1
+end
+
+local function nested(old,new)
+ for k, v in next, old do
+ if k == "ligature" then
+ if not new.ligature then
+ new.ligature = v
+ end
+ else
+ local n = new[k]
+ if n then
+ nested(v,n)
+ else
+ new[k] = v
+ end
+ end
+ end
+end
+
+local function mergesteps_4(lookup) -- ligatures
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ local first = steps[1]
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target = first.coverage
+ for i=2,nofsteps do
+ local c = steps[i].coverage
+ if c then
+ for k, v in next, c do
+ local tk = target[k]
+ if tk then
+ nested(v,tk)
+ else
+ target[k] = v
+ end
+ end
+ end
+ end
+ lookup.nofsteps = 1
+ lookup.steps = { first }
+ return nofsteps - 1
+end
+
+-- so we assume only one cursive entry and exit and even then the first one seems
+-- to win anyway: no exit or entry quite the lookup match and then we take the
+-- next step; this means that we can as well merge them
+
+local function mergesteps_5(lookup) -- cursive
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ local first = steps[1]
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target = first.coverage
+ local hash = nil
+ for k, v in next, target do
+ hash = v[1]
+ break
+ end
+ for i=2,nofsteps do
+ local c = steps[i].coverage
+ if c then
+ for k, v in next, c do
+ local tk = target[k]
+ if tk then
+ if not tk[2] then
+ tk[2] = v[2]
+ end
+ if not tk[3] then
+ tk[3] = v[3]
+ end
+ else
+ target[k] = v
+ v[1] = hash
+ end
+ end
+ end
+ end
+ lookup.nofsteps = 1
+ lookup.merged = true
+ lookup.steps = { first }
+ return nofsteps - 1
+end
+
+local function checkkerns(lookup)
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ local kerned = 0
+ for i=1,nofsteps do
+ local step = steps[i]
+ if step.format == "pair" then
+ local coverage = step.coverage
+ local kerns = true
+ for g1, d1 in next, coverage do
+ if d1 == true then
+ -- all zero
+ elseif not d1 then
+ -- null
+ elseif d1[1] ~= 0 or d1[2] ~= 0 or d1[4] ~= 0 then
+ kerns = false
+ break
+ end
+ end
+ if kerns then
+ if trace_optimizations then
+ report_optimizations("turning pairs of step %a of %a lookup %a into kerns",i,lookup.type,lookup.name)
+ end
+ local c = { }
+ for g1, d1 in next, coverage do
+ if d1 and d1 ~= true then
+ c[g1] = d1[3]
+ end
+ end
+ step.coverage = c
+ step.format = "move"
+ kerned = kerned + 1
+ end
+ end
+ end
+ return kerned
+end
+
+-- There are several options to optimize but we have this somewhat fuzzy aspect of
+-- advancing (depending on the second of a pair) so we need to retain that information.
+--
+-- We can have:
+--
+-- true, nil|false
+--
+-- which effectively means: nothing to be done and advance to next (so not next of
+-- next) and because coverage should be not overlapping we can wipe these. However,
+-- checking for (true,nil) (false,nil) and omitting them doesn't gain much.
+
+-- Because we pack we cannot mix tables and numbers so we can only turn a whole set in
+-- format kern instead of pair.
+
+local function checkpairs(lookup)
+ local steps = lookup.steps
+ local nofsteps = lookup.nofsteps
+ local kerned = 0
+
+ local function onlykerns(step)
+ local coverage = step.coverage
+ for g1, d1 in next, coverage do
+ for g2, d2 in next, d1 do
+ if d2[2] then
+ --- true or { a, b, c, d }
+ return false
+ else
+ local v = d2[1]
+ if v == true then
+ -- all zero
+ elseif v and (v[1] ~= 0 or v[2] ~= 0 or v[4] ~= 0) then
+ return false
+ end
+ end
+ end
+ end
+ return coverage
+ end
+
+ for i=1,nofsteps do
+ local step = steps[i]
+ if step.format == "pair" then
+ local coverage = onlykerns(step)
+ if coverage then
+ if trace_optimizations then
+ report_optimizations("turning pairs of step %a of %a lookup %a into kerns",i,lookup.type,lookup.name)
+ end
+ for g1, d1 in next, coverage do
+ local d = { }
+ for g2, d2 in next, d1 do
+ local v = d2[1]
+ if v == true then
+ -- ignore -- d1[g2] = nil
+ elseif v then
+ d[g2] = v[3] -- d1[g2] = v[3]
+ end
+ end
+ coverage[g1] = d
+ end
+ step.format = "move"
+ kerned = kerned + 1
+ end
+ end
+ end
+ return kerned
+end
+
+local compact_pairs = true
+local compact_singles = true
+
+local merge_pairs = true
+local merge_singles = true
+local merge_substitutions = true
+local merge_alternates = true
+local merge_multiples = true
+local merge_ligatures = true
+local merge_cursives = true
+local merge_marks = true
+
+directives.register("otf.compact.pairs", function(v) compact_pairs = v end)
+directives.register("otf.compact.singles", function(v) compact_singles = v end)
+
+directives.register("otf.merge.pairs", function(v) merge_pairs = v end)
+directives.register("otf.merge.singles", function(v) merge_singles = v end)
+directives.register("otf.merge.substitutions", function(v) merge_substitutions = v end)
+directives.register("otf.merge.alternates", function(v) merge_alternates = v end)
+directives.register("otf.merge.multiples", function(v) merge_multiples = v end)
+directives.register("otf.merge.ligatures", function(v) merge_ligatures = v end)
+directives.register("otf.merge.cursives", function(v) merge_cursives = v end)
+directives.register("otf.merge.marks", function(v) merge_marks = v end)
+
+function readers.compact(data)
+ if not data or data.compacted then
+ return
+ else
+ data.compacted = true
+ end
+ local resources = data.resources
+ local merged = 0
+ local kerned = 0
+ local allsteps = 0
+ local function compact(what)
+ local lookups = resources[what]
+ if lookups then
+ for i=1,#lookups do
+ local lookup = lookups[i]
+ local nofsteps = lookup.nofsteps
+ local kind = lookup.type
+ allsteps = allsteps + nofsteps
+ if nofsteps > 1 then
+ local merg = merged
+ if kind == "gsub_single" then
+ if merge_substitutions then
+ merged = merged + mergesteps_1(lookup)
+ end
+ elseif kind == "gsub_alternate" then
+ if merge_alternates then
+ merged = merged + mergesteps_1(lookup)
+ end
+ elseif kind == "gsub_multiple" then
+ if merge_multiples then
+ merged = merged + mergesteps_1(lookup)
+ end
+ elseif kind == "gsub_ligature" then
+ if merge_ligatures then
+ merged = merged + mergesteps_4(lookup)
+ end
+ elseif kind == "gpos_single" then
+ if merge_singles then
+ merged = merged + mergesteps_1(lookup,true)
+ end
+ if compact_singles then
+ kerned = kerned + checkkerns(lookup)
+ end
+ elseif kind == "gpos_pair" then
+ if merge_pairs then
+ merged = merged + mergesteps_2(lookup)
+ end
+ if compact_pairs then
+ kerned = kerned + checkpairs(lookup)
+ end
+ elseif kind == "gpos_cursive" then
+ if merge_cursives then
+ merged = merged + mergesteps_5(lookup)
+ end
+ elseif kind == "gpos_mark2mark" or kind == "gpos_mark2base" or kind == "gpos_mark2ligature" then
+ if merge_marks then
+ merged = merged + mergesteps_3(lookup)
+ end
+ end
+ if merg ~= merged then
+ lookup.merged = true
+ end
+ elseif nofsteps == 1 then
+ local kern = kerned
+ if kind == "gpos_single" then
+ if compact_singles then
+ kerned = kerned + checkkerns(lookup)
+ end
+ elseif kind == "gpos_pair" then
+ if compact_pairs then
+ kerned = kerned + checkpairs(lookup)
+ end
+ end
+ if kern ~= kerned then
+ -- lookup.kerned = true
+ end
+ end
+ end
+ elseif trace_optimizations then
+ report_optimizations("no lookups in %a",what)
+ end
+ end
+ compact("sequences")
+ compact("sublookups")
+ if trace_optimizations then
+ if merged > 0 then
+ report_optimizations("%i steps of %i removed due to merging",merged,allsteps)
+ end
+ if kerned > 0 then
+ report_optimizations("%i steps of %i steps turned from pairs into kerns",kerned,allsteps)
+ end
+ end
+end
+
+local function mergesteps(t,k)
+ if k == "merged" then
+ local merged = { }
+ for i=1,#t do
+ local step = t[i]
+ local coverage = step.coverage
+ for k in next, coverage do
+ local m = merged[k]
+ if m then
+ m[2] = i
+ -- m[#m+1] = step
+ else
+ merged[k] = { i, i }
+ -- merged[k] = { step }
+ end
+ end
+ end
+ t.merged = merged
+ return merged
+ end
+end
+
+local function checkmerge(sequence)
+ local steps = sequence.steps
+ if steps then
+ setmetatableindex(steps,mergesteps)
+ end
+end
+
+local function checkflags(sequence,resources)
+ if not sequence.skiphash then
+ local flags = sequence.flags
+ if flags then
+ local skipmark = flags[1]
+ local skipligature = flags[2]
+ local skipbase = flags[3]
+ local markclass = sequence.markclass
+ local skipsome = skipmark or skipligature or skipbase or markclass or false
+ if skipsome then
+ sequence.skiphash = setmetatableindex(function(t,k)
+ local c = resources.classes[k] -- delayed table
+ local v = c == skipmark
+ or (markclass and c == "mark" and not markclass[k])
+ or c == skipligature
+ or c == skipbase
+ or false
+ t[k] = v
+ return v
+ end)
+ else
+ sequence.skiphash = false
+ end
+ else
+ sequence.skiphash = false
+ end
+ end
+end
+
+local function checksteps(sequence)
+ local steps = sequence.steps
+ if steps then
+ for i=1,#steps do
+ steps[i].index = i
+ end
+ end
+end
+
+if fonts.helpers then
+ fonts.helpers.checkmerge = checkmerge
+ fonts.helpers.checkflags = checkflags
+ fonts.helpers.checksteps = checksteps -- has to happen last
+end
+
+function readers.expand(data)
+ if not data or data.expanded then
+ return
+ else
+ data.expanded = true
+ end
+ local resources = data.resources
+ local sublookups = resources.sublookups
+ local sequences = resources.sequences -- were one level up
+ local markclasses = resources.markclasses
+ local descriptions = data.descriptions
+ if descriptions then
+ local defaultwidth = resources.defaultwidth or 0
+ local defaultheight = resources.defaultheight or 0
+ local defaultdepth = resources.defaultdepth or 0
+ local basename = trace_markwidth and file.basename(resources.filename)
+ for u, d in next, descriptions do
+ local bb = d.boundingbox
+ local wd = d.width
+ if not wd then
+ -- or bb?
+ d.width = defaultwidth
+ elseif trace_markwidth and wd ~= 0 and d.class == "mark" then
+ report_markwidth("mark %a with width %b found in %a",d.name or "<noname>",wd,basename)
+ end
+ if bb then
+ local ht = bb[4]
+ local dp = -bb[2]
+ if ht == 0 or ht < 0 then
+ -- not set
+ else
+ d.height = ht
+ end
+ if dp == 0 or dp < 0 then
+ -- not set
+ else
+ d.depth = dp
+ end
+ end
+ end
+ end
+
+ -- using a merged combined hash as first test saves some 30% on ebgaramond and
+ -- about 15% on arabtype .. then moving the a test also saves a bit (even when
+ -- often a is not set at all so that one is a bit debatable
+
+ local function expandlookups(sequences)
+ if sequences then
+ -- we also need to do sublookups
+ for i=1,#sequences do
+ local sequence = sequences[i]
+ local steps = sequence.steps
+ if steps then
+ local nofsteps = sequence.nofsteps
+
+ local kind = sequence.type
+ local markclass = sequence.markclass
+ if markclass then
+ if not markclasses then
+ report_warning("missing markclasses")
+ sequence.markclass = false
+ else
+ sequence.markclass = markclasses[markclass]
+ end
+ end
+
+ for i=1,nofsteps do
+ local step = steps[i]
+ local baseclasses = step.baseclasses
+ if baseclasses then
+ local coverage = step.coverage
+ for k, v in next, coverage do
+ v[1] = baseclasses[v[1]] -- slot 1 is a placeholder
+ end
+ elseif kind == "gpos_cursive" then
+ local coverage = step.coverage
+ for k, v in next, coverage do
+ v[1] = coverage -- slot 1 is a placeholder
+ end
+ end
+ local rules = step.rules
+ if rules then
+ local rulehash = { n = 0 } -- is contexts in font-ots
+ local rulesize = 0
+ local coverage = { }
+ local lookuptype = sequence.type
+ local nofrules = #rules
+ step.coverage = coverage -- combined hits
+ for currentrule=1,nofrules do
+ local rule = rules[currentrule]
+ local current = rule.current
+ local before = rule.before
+ local after = rule.after
+ local replacements = rule.replacements or false
+ local sequence = { }
+ local nofsequences = 0
+ if before then
+ for n=1,#before do
+ nofsequences = nofsequences + 1
+ sequence[nofsequences] = before[n]
+ end
+ end
+ local start = nofsequences + 1
+ for n=1,#current do
+ nofsequences = nofsequences + 1
+ sequence[nofsequences] = current[n]
+ end
+ local stop = nofsequences
+ if after then
+ for n=1,#after do
+ nofsequences = nofsequences + 1
+ sequence[nofsequences] = after[n]
+ end
+ end
+ local lookups = rule.lookups or false
+ local subtype = nil
+ if lookups then
+ for i=1,#lookups do
+ local lookups = lookups[i]
+ if lookups then
+ for k, v in next, lookups do -- actually this one is indexed
+ local lookup = sublookups[v]
+ if lookup then
+ lookups[k] = lookup
+ if not subtype then
+ subtype = lookup.type
+ end
+ else
+ -- already expanded
+ end
+ end
+ end
+ end
+ end
+ if sequence[1] then -- we merge coverage into one
+ sequence.n = #sequence -- tiny speedup
+ local ruledata = {
+ currentrule, -- 1 -- original rule number, only use this for tracing!
+ lookuptype, -- 2
+ sequence, -- 3
+ start, -- 4
+ stop, -- 5
+ lookups, -- 6 (6/7 also signal of what to do)
+ replacements, -- 7
+ subtype, -- 8
+ }
+ --
+ -- possible optimization: per [unic] a rulehash, but beware:
+ -- contexts have unique coverage and chains can have multiple
+ -- hits (rules) per coverage entry
+ --
+ -- so: we can combine multiple steps as well as multiple rules
+ -- but that takes careful checking, in which case we can go the
+ -- step list approach and turn contexts into steps .. in fact,
+ -- if we turn multiple contexts into steps we're already ok as
+ -- steps gets a coverage hash by metatable
+ --
+ rulesize = rulesize + 1
+ rulehash[rulesize] = ruledata
+ rulehash.n = rulesize -- tiny speedup
+ --
+ if true then -- nofrules > 1
+
+ for unic in next, sequence[start] do
+ local cu = coverage[unic]
+ if cu then
+ local n = #cu+1
+ cu[n] = ruledata
+ cu.n = n
+ else
+ coverage[unic] = { ruledata, n = 1 }
+ end
+ end
+
+ else
+
+ for unic in next, sequence[start] do
+ local cu = coverage[unic]
+ if cu then
+ -- we can have a contextchains with many matches which we
+ -- can actually optimize
+ else
+ coverage[unic] = rulehash
+ end
+ end
+
+ end
+ end
+ end
+ end
+ end
+
+ checkmerge(sequence)
+ checkflags(sequence,resources)
+ checksteps(sequence)
+
+ end
+ end
+ end
+ end
+
+ expandlookups(sequences)
+ expandlookups(sublookups)
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-ttf.lua b/macros/luatex/generic/luaotfload/fontloader-font-ttf.lua
new file mode 100644
index 0000000000..651ede17e2
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-ttf.lua
@@ -0,0 +1,1379 @@
+if not modules then modules = { } end modules ['font-ttf'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- This version is different from previous in the sense that we no longer store
+-- contours but keep points and contours (endpoints) separate for a while
+-- because later on we need to apply deltas and that is easier on a list of
+-- points.
+
+-- The code is a bit messy. I looked at the ff code but it's messy too. It has
+-- to do with the fact that we need to look at points on the curve and control
+-- points in between. This also means that we start at point 2 and have to look
+-- at point 1 when we're at the end. We still use a ps like storage with the
+-- operator last in an entry. It's typical code that evolves stepwise till a
+-- point of no comprehension.
+
+-- For deltas we need a rather complex loop over points that can have holes and
+-- be less than nofpoints and even can have duplicates and also the x and y value
+-- lists can be shorter than etc. I need fonts in order to complete this simply
+-- because I need to visualize in order to understand (what the standard tries
+-- to explain).
+
+-- 0 point then none applied
+-- 1 points then applied to all
+-- otherwise inferred deltas using nearest
+-- if no lower point then use highest referenced point
+-- if no higher point then use lowest referenced point
+-- factor = (target-left)/(right-left)
+-- delta = (1-factor)*left + factor * right
+
+local next, type, unpack = next, type, unpack
+local band, rshift = bit32.band, bit32.rshift
+local sqrt, round = math.sqrt, math.round
+local char, rep = string.char, string.rep
+local concat = table.concat
+local idiv = number.idiv
+local setmetatableindex = table.setmetatableindex
+
+local report = logs.reporter("otf reader","ttf")
+
+local trace_deltas = false
+
+local readers = fonts.handlers.otf.readers
+local streamreader = readers.streamreader
+
+local setposition = streamreader.setposition
+local getposition = streamreader.getposition
+local skipbytes = streamreader.skip
+local readbyte = streamreader.readcardinal1 -- 8-bit unsigned integer
+local readushort = streamreader.readcardinal2 -- 16-bit unsigned integer
+local readulong = streamreader.readcardinal4 -- 24-bit unsigned integer
+local readchar = streamreader.readinteger1 -- 8-bit signed integer
+local readshort = streamreader.readinteger2 -- 16-bit signed integer
+local read2dot14 = streamreader.read2dot14 -- 16-bit signed fixed number with the low 14 bits of fraction (2.14) (F2DOT14)
+local readinteger = streamreader.readinteger1
+local readcardinaltable = streamreader.readcardinaltable
+local readintegertable = streamreader.readintegertable
+
+directives.register("fonts.streamreader",function()
+
+ streamreader = utilities.streams
+
+ setposition = streamreader.setposition
+ getposition = streamreader.getposition
+ skipbytes = streamreader.skip
+ readbyte = streamreader.readcardinal1
+ readushort = streamreader.readcardinal2
+ readulong = streamreader.readcardinal4
+ readchar = streamreader.readinteger1
+ readshort = streamreader.readinteger2
+ read2dot14 = streamreader.read2dot14
+ readinteger = streamreader.readinteger1
+ readcardinaltable = streamreader.readcardinaltable
+ readintegertable = streamreader.readintegertable
+
+end)
+
+local short = 2
+local ushort = 2
+local ulong = 4
+
+local helpers = readers.helpers
+local gotodatatable = helpers.gotodatatable
+
+local function mergecomposites(glyphs,shapes)
+
+ -- todo : deltas
+
+ local function merge(index,shape,components)
+ local contours = { }
+ local points = { }
+ local nofcontours = 0
+ local nofpoints = 0
+ local offset = 0
+ local deltas = shape.deltas
+ for i=1,#components do
+ local component = components[i]
+ local subindex = component.index
+ local subshape = shapes[subindex]
+ local subcontours = subshape.contours
+ local subpoints = subshape.points
+ if not subcontours then
+ local subcomponents = subshape.components
+ if subcomponents then
+ subcontours, subpoints = merge(subindex,subshape,subcomponents)
+ end
+ end
+ if subpoints then
+ local matrix = component.matrix
+ local xscale = matrix[1]
+ local xrotate = matrix[2]
+ local yrotate = matrix[3]
+ local yscale = matrix[4]
+ local xoffset = matrix[5]
+ local yoffset = matrix[6]
+ local count = #subpoints
+ if xscale == 1 and yscale == 1 and xrotate == 0 and yrotate == 0 then
+ for i=1,count do
+ local p = subpoints[i]
+ nofpoints = nofpoints + 1
+ points[nofpoints] = {
+ p[1] + xoffset,
+ p[2] + yoffset,
+ p[3]
+ }
+ end
+ else
+ for i=1,count do
+ local p = subpoints[i]
+ local x = p[1]
+ local y = p[2]
+ nofpoints = nofpoints + 1
+ points[nofpoints] = {
+ xscale * x + xrotate * y + xoffset,
+ yscale * y + yrotate * x + yoffset,
+ p[3]
+ }
+ end
+ end
+ local subcount = #subcontours
+ if subcount == 1 then
+ nofcontours = nofcontours + 1
+ contours[nofcontours] = offset + subcontours[1]
+ else
+ for i=1,#subcontours do
+ nofcontours = nofcontours + 1
+ contours[nofcontours] = offset + subcontours[i]
+ end
+ end
+ offset = offset + count
+ else
+ report("missing contours composite %s, component %s of %s, glyph %s",index,i,#components,subindex)
+ end
+ end
+ shape.points = points -- todo : phantom points
+ shape.contours = contours
+ shape.components = nil
+ return contours, points
+ end
+
+-- for index=1,#glyphs do
+ for index=0,#glyphs-1 do
+ local shape = shapes[index]
+ if shape then
+ local components = shape.components
+ if components then
+ merge(index,shape,components)
+ end
+ end
+ end
+
+end
+
+local function readnothing(f)
+ return {
+ type = "nothing",
+ }
+end
+
+-- begin of converter
+
+local function curveto(m_x,m_y,l_x,l_y,r_x,r_y) -- todo: inline this
+ return
+ l_x + 2/3 *(m_x-l_x), l_y + 2/3 *(m_y-l_y),
+ r_x + 2/3 *(m_x-r_x), r_y + 2/3 *(m_y-r_y),
+ r_x, r_y, "c"
+end
+
+-- We could omit the operator which saves some 10%:
+--
+-- #2=lineto #4=quadratic #6=cubic #3=moveto (with "m")
+--
+-- This is tricky ... something to do with phantom points .. however, the hvar
+-- and vvar tables should take care of the width .. the test font doesn't have
+-- those so here we go then (we need a flag for hvar).
+--
+-- h-advance left-side-bearing v-advance top-side-bearing
+--
+-- We had two loops (going backward) but can do it in one loop .. but maybe we
+-- should only accept fonts with proper hvar tables.
+
+local function applyaxis(glyph,shape,deltas,dowidth)
+ local points = shape.points
+ if points then
+ local nofpoints = #points
+ local h = nofpoints + 2 -- weird, the example font seems to have left first
+ local l = nofpoints + 1
+ ----- v = nofpoints + 3
+ ----- t = nofpoints + 4
+ local dw = 0
+ local dl = 0
+ for i=1,#deltas do
+ local deltaset = deltas[i]
+ local xvalues = deltaset.xvalues
+ local yvalues = deltaset.yvalues
+ local dpoints = deltaset.points
+ local factor = deltaset.factor
+ if dpoints then
+ -- todo: interpolate
+ local nofdpoints = #dpoints
+ for i=1,nofdpoints do
+ local d = dpoints[i]
+ local p = points[d]
+ if p then
+ if xvalues then
+ local x = xvalues[i]
+ if x and x ~= 0 then
+ p[1] = p[1] + factor * x
+ end
+ end
+ if yvalues then
+ local y = yvalues[i]
+ if y and y ~= 0 then
+ p[2] = p[2] + factor * y
+ end
+ end
+ elseif dowidth then
+ -- we've now ran into phantom points which is a bit fuzzy because:
+ -- are there gaps in there?
+ --
+ -- todo: move this outside the loop (when we can be sure of all 4 being there)
+ if d == h then
+ -- we have a phantom point hadvance
+ local x = xvalues[i]
+ if x then
+ dw = dw + factor * x
+ end
+ elseif d == l then
+ local x = xvalues[i]
+ if x then
+ dl = dl + factor * x
+ end
+ end
+ end
+ end
+ else
+ for i=1,nofpoints do
+ local p = points[i]
+ if xvalues then
+ local x = xvalues[i]
+ if x and x ~= 0 then
+ p[1] = p[1] + factor * x
+ end
+ end
+ if yvalues then
+ local y = yvalues[i]
+ if y and y ~= 0 then
+ p[2] = p[2] + factor * y
+ end
+ end
+ end
+ if dowidth then
+ local x = xvalues[h]
+ if x then
+ dw = dw + factor * x
+ end
+ local x = xvalues[l]
+ if x then
+ dl = dl + factor * x
+ end
+ end
+ end
+ end
+ -- for i=1,nofpoints do
+ -- local p = points[i]
+ -- p[1] = round(p[1])
+ -- p[2] = round(p[2])
+ -- end
+ if dowidth then
+ local width = glyph.width or 0
+ -- local lsb = glyph.lsb or 0
+ glyph.width = width + dw - dl
+ end
+ else
+ report("no points for glyph %a",glyph.name)
+ end
+end
+
+-- round or not ?
+
+-- local quadratic = true -- both methods work, todo: install a directive
+local quadratic = false
+
+local function contours2outlines_normal(glyphs,shapes) -- maybe accept the bbox overhead
+-- for index=1,#glyphs do
+ for index=0,#glyphs-1 do
+ local shape = shapes[index]
+ if shape then
+ local glyph = glyphs[index]
+ local contours = shape.contours
+ local points = shape.points
+ if contours then
+ local nofcontours = #contours
+ local segments = { }
+ local nofsegments = 0
+ glyph.segments = segments
+ if nofcontours > 0 then
+ local px = 0
+ local py = 0
+ local first = 1
+ for i=1,nofcontours do
+ local last = contours[i]
+ if last >= first then
+ local first_pt = points[first]
+ local first_on = first_pt[3]
+ -- todo no new tables but reuse lineto and quadratic
+ if first == last then
+ first_pt[3] = "m" -- "moveto"
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = first_pt
+ else -- maybe also treat n == 2 special
+ local first_on = first_pt[3]
+ local last_pt = points[last]
+ local last_on = last_pt[3]
+ local start = 1
+ local control_pt = false
+ if first_on then
+ start = 2
+ else
+ if last_on then
+ first_pt = last_pt
+ else
+ first_pt = { (first_pt[1]+last_pt[1])/2, (first_pt[2]+last_pt[2])/2, false }
+ end
+ control_pt = first_pt
+ end
+ local x = first_pt[1]
+ local y = first_pt[2]
+ if not done then
+ xmin = x
+ ymin = y
+ xmax = x
+ ymax = y
+ done = true
+ end
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x, y, "m" } -- "moveto"
+ if not quadratic then
+ px = x
+ py = y
+ end
+ local previous_pt = first_pt
+ for i=first,last do
+ local current_pt = points[i]
+ local current_on = current_pt[3]
+ local previous_on = previous_pt[3]
+ if previous_on then
+ if current_on then
+ -- both normal points
+ local x, y = current_pt[1], current_pt[2]
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x, y, "l" } -- "lineto"
+ if not quadratic then
+ px, py = x, y
+ end
+ else
+ control_pt = current_pt
+ end
+ elseif current_on then
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ local x2 = current_pt[1]
+ local y2 = current_pt[2]
+ nofsegments = nofsegments + 1
+ if quadratic then
+ segments[nofsegments] = { x1, y1, x2, y2, "q" } -- "quadraticto"
+ else
+ x1, y1, x2, y2, px, py = curveto(x1, y1, px, py, x2, y2)
+ segments[nofsegments] = { x1, y1, x2, y2, px, py, "c" } -- "curveto"
+ end
+ control_pt = false
+ else
+ local x2 = (previous_pt[1]+current_pt[1])/2
+ local y2 = (previous_pt[2]+current_pt[2])/2
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ nofsegments = nofsegments + 1
+ if quadratic then
+ segments[nofsegments] = { x1, y1, x2, y2, "q" } -- "quadraticto"
+ else
+ x1, y1, x2, y2, px, py = curveto(x1, y1, px, py, x2, y2)
+ segments[nofsegments] = { x1, y1, x2, y2, px, py, "c" } -- "curveto"
+ end
+ control_pt = current_pt
+ end
+ previous_pt = current_pt
+ end
+ if first_pt == last_pt then
+ -- we're already done, probably a simple curve
+ else
+ nofsegments = nofsegments + 1
+ local x2 = first_pt[1]
+ local y2 = first_pt[2]
+ if not control_pt then
+ segments[nofsegments] = { x2, y2, "l" } -- "lineto"
+ elseif quadratic then
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ segments[nofsegments] = { x1, y1, x2, y2, "q" } -- "quadraticto"
+ else
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ x1, y1, x2, y2, px, py = curveto(x1, y1, px, py, x2, y2)
+ segments[nofsegments] = { x1, y1, x2, y2, px, py, "c" } -- "curveto"
+ -- px, py = x2, y2
+ end
+ end
+ end
+ end
+ first = last + 1
+ end
+ end
+ end
+ end
+ end
+end
+
+local function contours2outlines_shaped(glyphs,shapes,keepcurve)
+-- for index=1,#glyphs do
+ for index=0,#glyphs-1 do
+ local shape = shapes[index]
+ if shape then
+ local glyph = glyphs[index]
+ local contours = shape.contours
+ local points = shape.points
+ if contours then
+ local nofcontours = #contours
+ local segments = keepcurve and { } or nil
+ local nofsegments = 0
+ if keepcurve then
+ glyph.segments = segments
+ end
+ if nofcontours > 0 then
+ local xmin, ymin, xmax, ymax, done = 0, 0, 0, 0, false
+ local px, py = 0, 0 -- we could use these in calculations which saves a copy
+ local first = 1
+ for i=1,nofcontours do
+ local last = contours[i]
+ if last >= first then
+ local first_pt = points[first]
+ local first_on = first_pt[3]
+ -- todo no new tables but reuse lineto and quadratic
+ if first == last then
+ -- this can influence the boundingbox
+ if keepcurve then
+ first_pt[3] = "m" -- "moveto"
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = first_pt
+ end
+ else -- maybe also treat n == 2 special
+ local first_on = first_pt[3]
+ local last_pt = points[last]
+ local last_on = last_pt[3]
+ local start = 1
+ local control_pt = false
+ if first_on then
+ start = 2
+ else
+ if last_on then
+ first_pt = last_pt
+ else
+ first_pt = { (first_pt[1]+last_pt[1])/2, (first_pt[2]+last_pt[2])/2, false }
+ end
+ control_pt = first_pt
+ end
+ local x = first_pt[1]
+ local y = first_pt[2]
+ if not done then
+ xmin, ymin, xmax, ymax = x, y, x, y
+ done = true
+ else
+ if x < xmin then xmin = x elseif x > xmax then xmax = x end
+ if y < ymin then ymin = y elseif y > ymax then ymax = y end
+ end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x, y, "m" } -- "moveto"
+ end
+ if not quadratic then
+ px = x
+ py = y
+ end
+ local previous_pt = first_pt
+ for i=first,last do
+ local current_pt = points[i]
+ local current_on = current_pt[3]
+ local previous_on = previous_pt[3]
+ if previous_on then
+ if current_on then
+ -- both normal points
+ local x = current_pt[1]
+ local y = current_pt[2]
+ if x < xmin then xmin = x elseif x > xmax then xmax = x end
+ if y < ymin then ymin = y elseif y > ymax then ymax = y end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x, y, "l" } -- "lineto"
+ end
+ if not quadratic then
+ px = x
+ py = y
+ end
+ else
+ control_pt = current_pt
+ end
+ elseif current_on then
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ local x2 = current_pt[1]
+ local y2 = current_pt[2]
+ if quadratic then
+ if x1 < xmin then xmin = x1 elseif x1 > xmax then xmax = x1 end
+ if y1 < ymin then ymin = y1 elseif y1 > ymax then ymax = y1 end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x1, y1, x2, y2, "q" } -- "quadraticto"
+ end
+ else
+ x1, y1, x2, y2, px, py = curveto(x1, y1, px, py, x2, y2)
+ if x1 < xmin then xmin = x1 elseif x1 > xmax then xmax = x1 end
+ if y1 < ymin then ymin = y1 elseif y1 > ymax then ymax = y1 end
+ if x2 < xmin then xmin = x2 elseif x2 > xmax then xmax = x2 end
+ if y2 < ymin then ymin = y2 elseif y2 > ymax then ymax = y2 end
+ if px < xmin then xmin = px elseif px > xmax then xmax = px end
+ if py < ymin then ymin = py elseif py > ymax then ymax = py end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x1, y1, x2, y2, px, py, "c" } -- "curveto"
+ end
+ end
+ control_pt = false
+ else
+ local x2 = (previous_pt[1]+current_pt[1])/2
+ local y2 = (previous_pt[2]+current_pt[2])/2
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ if quadratic then
+ if x1 < xmin then xmin = x1 elseif x1 > xmax then xmax = x1 end
+ if y1 < ymin then ymin = y1 elseif y1 > ymax then ymax = y1 end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x1, y1, x2, y2, "q" } -- "quadraticto"
+ end
+ else
+ x1, y1, x2, y2, px, py = curveto(x1, y1, px, py, x2, y2)
+ if x1 < xmin then xmin = x1 elseif x1 > xmax then xmax = x1 end
+ if y1 < ymin then ymin = y1 elseif y1 > ymax then ymax = y1 end
+ if x2 < xmin then xmin = x2 elseif x2 > xmax then xmax = x2 end
+ if y2 < ymin then ymin = y2 elseif y2 > ymax then ymax = y2 end
+ if px < xmin then xmin = px elseif px > xmax then xmax = px end
+ if py < ymin then ymin = py elseif py > ymax then ymax = py end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x1, y1, x2, y2, px, py, "c" } -- "curveto"
+ end
+ end
+ control_pt = current_pt
+ end
+ previous_pt = current_pt
+ end
+ if first_pt == last_pt then
+ -- we're already done, probably a simple curve
+ elseif not control_pt then
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { first_pt[1], first_pt[2], "l" } -- "lineto"
+ end
+ else
+ local x1 = control_pt[1]
+ local y1 = control_pt[2]
+ local x2 = first_pt[1]
+ local y2 = first_pt[2]
+ if x1 < xmin then xmin = x1 elseif x1 > xmax then xmax = x1 end
+ if y1 < ymin then ymin = y1 elseif y1 > ymax then ymax = y1 end
+ if quadratic then
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x1, y1, x2, y2, "q" } -- "quadraticto"
+ end
+ else
+ x1, y1, x2, y2, px, py = curveto(x1, y1, px, py, x2, y2)
+ if x2 < xmin then xmin = x2 elseif x2 > xmax then xmax = x2 end
+ if y2 < ymin then ymin = y2 elseif y2 > ymax then ymax = y2 end
+ if px < xmin then xmin = px elseif px > xmax then xmax = px end
+ if py < ymin then ymin = py elseif py > ymax then ymax = py end
+ if keepcurve then
+ nofsegments = nofsegments + 1
+ segments[nofsegments] = { x1, y1, x2, y2, px, py, "c" } -- "curveto"
+ end
+ -- px, py = x2, y2
+ end
+ end
+ end
+ end
+ first = last + 1
+ end
+ glyph.boundingbox = { round(xmin), round(ymin), round(xmax), round(ymax) }
+ end
+ end
+ end
+ end
+end
+
+-- optimize for zero
+
+local c_zero = char(0)
+local s_zero = char(0,0)
+
+-- local shorthash = setmetatableindex(function(t,k)
+-- t[k] = char(band(rshift(k,8),0xFF),band(k,0xFF)) return t[k]
+-- end)
+
+local function toushort(n)
+ return char(band(rshift(n,8),0xFF),band(n,0xFF))
+ -- return shorthash[n]
+end
+
+local function toshort(n)
+ if n < 0 then
+ n = n + 0x10000
+ end
+ return char(band(rshift(n,8),0xFF),band(n,0xFF))
+ -- return shorthash[n]
+end
+
+-- todo: we can reuse result, xpoints and ypoints
+
+local chars = setmetatableindex(function(t,k)
+ for i=0,255 do local v = char(i) t[i] = v end return t[k]
+end)
+
+local function repackpoints(glyphs,shapes)
+ local noboundingbox = { 0, 0, 0, 0 }
+ local result = { } -- reused
+ local xpoints = { } -- reused
+ local ypoints = { } -- reused
+ for index=0,#glyphs-1 do
+ local shape = shapes[index]
+ if shape then
+ local r = 0
+ local glyph = glyphs[index]
+ local contours = shape.contours
+ local nofcontours = contours and #contours or 0
+ local boundingbox = glyph.boundingbox or noboundingbox
+ r = r + 1 result[r] = toshort(nofcontours)
+ r = r + 1 result[r] = toshort(boundingbox[1]) -- xmin
+ r = r + 1 result[r] = toshort(boundingbox[2]) -- ymin
+ r = r + 1 result[r] = toshort(boundingbox[3]) -- xmax
+ r = r + 1 result[r] = toshort(boundingbox[4]) -- ymax
+ if nofcontours > 0 then
+ for i=1,nofcontours do
+ r = r + 1 result[r] = toshort(contours[i]-1)
+ end
+ r = r + 1 result[r] = s_zero -- no instructions
+ local points = shape.points
+ local currentx = 0
+ local currenty = 0
+ -- local xpoints = { }
+ -- local ypoints = { }
+ local x = 0
+ local y = 0
+ local lastflag = nil
+ local nofflags = 0
+ for i=1,#points do
+ local pt = points[i]
+ local px = pt[1]
+ local py = pt[2]
+ local fl = pt[3] and 0x01 or 0x00
+ if px == currentx then
+ fl = fl + 0x10
+ else
+ local dx = round(px - currentx)
+ x = x + 1
+ if dx < -255 or dx > 255 then
+ xpoints[x] = toshort(dx)
+ elseif dx < 0 then
+ fl = fl + 0x02
+ -- xpoints[x] = char(-dx)
+ xpoints[x] = chars[-dx]
+ elseif dx > 0 then
+ fl = fl + 0x12
+ -- xpoints[x] = char(dx)
+ xpoints[x] = chars[dx]
+ else
+ fl = fl + 0x02
+ xpoints[x] = c_zero
+ end
+ end
+ if py == currenty then
+ fl = fl + 0x20
+ else
+ local dy = round(py - currenty)
+ y = y + 1
+ if dy < -255 or dy > 255 then
+ ypoints[y] = toshort(dy)
+ elseif dy < 0 then
+ fl = fl + 0x04
+ -- ypoints[y] = char(-dy)
+ ypoints[y] = chars[-dy]
+ elseif dy > 0 then
+ fl = fl + 0x24
+ -- ypoints[y] = char(dy)
+ ypoints[y] = chars[dy]
+ else
+ fl = fl + 0x04
+ ypoints[y] = c_zero
+ end
+ end
+ currentx = px
+ currenty = py
+ if lastflag == fl then
+ if nofflags == 255 then
+ -- This happens in koeieletters!
+ lastflag = lastflag + 0x08
+ r = r + 1 result[r] = char(lastflag,nofflags-1)
+ nofflags = 1
+ lastflag = fl
+ else
+ nofflags = nofflags + 1
+ end
+ else -- if > 255
+ if nofflags == 1 then
+ -- r = r + 1 result[r] = char(lastflag)
+ r = r + 1 result[r] = chars[lastflag]
+ elseif nofflags == 2 then
+ r = r + 1 result[r] = char(lastflag,lastflag)
+ elseif nofflags > 2 then
+ lastflag = lastflag + 0x08
+ r = r + 1 result[r] = char(lastflag,nofflags-1)
+ end
+ nofflags = 1
+ lastflag = fl
+ end
+ end
+ if nofflags == 1 then
+ -- r = r + 1 result[r] = char(lastflag)
+ r = r + 1 result[r] = chars[lastflag]
+ elseif nofflags == 2 then
+ r = r + 1 result[r] = char(lastflag,lastflag)
+ elseif nofflags > 2 then
+ lastflag = lastflag + 0x08
+ r = r + 1 result[r] = char(lastflag,nofflags-1)
+ end
+ -- r = r + 1 result[r] = concat(xpoints)
+ -- r = r + 1 result[r] = concat(ypoints)
+ r = r + 1 result[r] = concat(xpoints,"",1,x)
+ r = r + 1 result[r] = concat(ypoints,"",1,y)
+ end
+ -- can be helper or delegated to user
+ local stream = concat(result,"",1,r)
+ local length = #stream
+ local padding = idiv(length+3,4) * 4 - length
+ if padding > 0 then
+ -- stream = stream .. rep("\0",padding) -- can be a repeater
+ if padding == 1 then
+ padding = "\0"
+ elseif padding == 2 then
+ padding = "\0\0"
+ else
+ padding = "\0\0\0"
+ end
+ padding = stream .. padding
+ end
+ glyph.stream = stream
+ end
+ end
+end
+
+-- end of converter
+
+local flags = { }
+
+local function readglyph(f,nofcontours) -- read deltas here, saves space
+ local points = { }
+ -- local instructions = { }
+ local contours = { } -- readintegertable(f,nofcontours,short)
+ for i=1,nofcontours do
+ contours[i] = readshort(f) + 1
+ end
+ local nofpoints = contours[nofcontours]
+ local nofinstructions = readushort(f)
+ skipbytes(f,nofinstructions)
+ -- because flags can repeat we don't know the amount ... in fact this is
+ -- not that efficient (small files but more mem)
+ local i = 1
+ while i <= nofpoints do
+ local flag = readbyte(f)
+ flags[i] = flag
+ if band(flag,0x08) ~= 0 then
+ local n = readbyte(f)
+ if n == 1 then
+ i = i + 1
+ flags[i] = flag
+ else
+ for j=1,n do
+ i = i + 1
+ flags[i] = flag
+ end
+ end
+ end
+ i = i + 1
+ end
+ -- first come the x coordinates, and next the y coordinates and they
+ -- can be repeated
+ local x = 0
+ for i=1,nofpoints do
+ local flag = flags[i]
+ -- local short = band(flag,0x04) ~= 0
+ -- local same = band(flag,0x20) ~= 0
+ if band(flag,0x02) ~= 0 then
+ if band(flag,0x10) ~= 0 then
+ x = x + readbyte(f)
+ else
+ x = x - readbyte(f)
+ end
+ elseif band(flag,0x10) ~= 0 then
+ -- copy
+ else
+ x = x + readshort(f)
+ end
+ points[i] = { x, 0, band(flag,0x01) ~= 0 }
+ end
+ local y = 0
+ for i=1,nofpoints do
+ local flag = flags[i]
+ -- local short = band(flag,0x04) ~= 0
+ -- local same = band(flag,0x20) ~= 0
+ if band(flag,0x04) ~= 0 then
+ if band(flag,0x20) ~= 0 then
+ y = y + readbyte(f)
+ else
+ y = y - readbyte(f)
+ end
+ elseif band(flag,0x20) ~= 0 then
+ -- copy
+ else
+ y = y + readshort(f)
+ end
+ points[i][2] = y
+ end
+ return {
+ type = "glyph",
+ points = points,
+ contours = contours,
+ nofpoints = nofpoints,
+ }
+end
+
+local function readcomposite(f)
+ local components = { }
+ local nofcomponents = 0
+ local instructions = false
+ while true do
+ local flags = readushort(f)
+ local index = readushort(f)
+ ----- f_words = band(flags,0x0001) ~= 0
+ local f_xyarg = band(flags,0x0002) ~= 0
+ ----- f_round = band(flags,0x0006) ~= 0 -- 2 + 4
+ ----- f_scale = band(flags,0x0008) ~= 0
+ ----- f_reserved = band(flags,0x0010) ~= 0
+ ----- f_more = band(flags,0x0020) ~= 0
+ ----- f_xyscale = band(flags,0x0040) ~= 0
+ ----- f_matrix = band(flags,0x0080) ~= 0
+ ----- f_instruct = band(flags,0x0100) ~= 0
+ ----- f_usemine = band(flags,0x0200) ~= 0
+ ----- f_overlap = band(flags,0x0400) ~= 0
+ local f_offset = band(flags,0x0800) ~= 0
+ ----- f_uoffset = band(flags,0x1000) ~= 0
+ local xscale = 1
+ local xrotate = 0
+ local yrotate = 0
+ local yscale = 1
+ local xoffset = 0
+ local yoffset = 0
+ local base = false
+ local reference = false
+ if f_xyarg then
+ if band(flags,0x0001) ~= 0 then -- f_words
+ xoffset = readshort(f)
+ yoffset = readshort(f)
+ else
+ xoffset = readchar(f) -- signed byte, stupid name
+ yoffset = readchar(f) -- signed byte, stupid name
+ end
+ else
+ if band(flags,0x0001) ~= 0 then -- f_words
+ base = readshort(f)
+ reference = readshort(f)
+ else
+ base = readchar(f) -- signed byte, stupid name
+ reference = readchar(f) -- signed byte, stupid name
+ end
+ end
+ if band(flags,0x0008) ~= 0 then -- f_scale
+ xscale = read2dot14(f)
+ yscale = xscale
+ if f_xyarg and f_offset then
+ xoffset = xoffset * xscale
+ yoffset = yoffset * yscale
+ end
+ elseif band(flags,0x0040) ~= 0 then -- f_xyscale
+ xscale = read2dot14(f)
+ yscale = read2dot14(f)
+ if f_xyarg and f_offset then
+ xoffset = xoffset * xscale
+ yoffset = yoffset * yscale
+ end
+ elseif band(flags,0x0080) ~= 0 then -- f_matrix
+ xscale = read2dot14(f)
+ xrotate = read2dot14(f)
+ yrotate = read2dot14(f)
+ yscale = read2dot14(f)
+ if f_xyarg and f_offset then
+ xoffset = xoffset * sqrt(xscale ^2 + xrotate^2)
+ yoffset = yoffset * sqrt(yrotate^2 + yscale ^2)
+ end
+ end
+ nofcomponents = nofcomponents + 1
+ components[nofcomponents] = {
+ index = index,
+ usemine = band(flags,0x0200) ~= 0, -- f_usemine
+ round = band(flags,0x0006) ~= 0, -- f_round,
+ base = base,
+ reference = reference,
+ matrix = { xscale, xrotate, yrotate, yscale, xoffset, yoffset },
+ }
+ if band(flags,0x0100) ~= 0 then
+ instructions = true
+ end
+ if band(flags,0x0020) == 0 then -- f_more
+ break
+ end
+ end
+ return {
+ type = "composite",
+ components = components,
+ }
+end
+
+-- function readers.cff(f,offset,glyphs,doshapes) -- false == no shapes (nil or true otherwise)
+
+-- The glyf table depends on the loca table. We have one entry to much
+-- in the locations table (the last one is a dummy) because we need to
+-- calculate the size of a glyph blob from the delta, although we not
+-- need it in our usage (yet). We can remove the locations table when
+-- we're done (todo: cleanup finalizer).
+
+function readers.loca(f,fontdata,specification)
+ if specification.glyphs then
+ local datatable = fontdata.tables.loca
+ if datatable then
+ -- locations are relative to the glypdata table (glyf)
+ local offset = fontdata.tables.glyf.offset
+ local format = fontdata.fontheader.indextolocformat
+ local profile = fontdata.maximumprofile
+ local nofglyphs = profile and profile.nofglyphs
+ local locations = { }
+ setposition(f,datatable.offset)
+ if format == 1 then
+ if not nofglyphs then
+ nofglyphs = idiv(datatable.length,4) - 1
+ end
+ for i=0,nofglyphs do
+ locations[i] = offset + readulong(f)
+ end
+ fontdata.nofglyphs = nofglyphs
+ else
+ if not nofglyphs then
+ nofglyphs = idiv(datatable.length,2) - 1
+ end
+ for i=0,nofglyphs do
+ locations[i] = offset + readushort(f) * 2
+ end
+ end
+ fontdata.nofglyphs = nofglyphs
+ fontdata.locations = locations
+ end
+ end
+end
+
+function readers.glyf(f,fontdata,specification) -- part goes to cff module
+ local tableoffset = gotodatatable(f,fontdata,"glyf",specification.glyphs)
+ if tableoffset then
+ local locations = fontdata.locations
+ if locations then
+ local glyphs = fontdata.glyphs
+ local nofglyphs = fontdata.nofglyphs
+ local filesize = fontdata.filesize
+ local nothing = { 0, 0, 0, 0 }
+ local shapes = { }
+ local loadshapes = specification.shapes or specification.instance or specification.streams
+ for index=0,nofglyphs-1 do
+ local location = locations[index]
+ local length = locations[index+1] - location
+ if location >= filesize then
+ report("discarding %s glyphs due to glyph location bug",nofglyphs-index+1)
+ fontdata.nofglyphs = index - 1
+ fontdata.badfont = true
+ break
+ elseif length > 0 then
+ setposition(f,location)
+ local nofcontours = readshort(f)
+ glyphs[index].boundingbox = {
+ readshort(f), -- xmin
+ readshort(f), -- ymin
+ readshort(f), -- xmax
+ readshort(f), -- ymax
+ }
+ if not loadshapes then
+ -- save space
+ elseif nofcontours == 0 then
+ shapes[index] = readnothing(f)
+ elseif nofcontours > 0 then
+ shapes[index] = readglyph(f,nofcontours)
+ else
+ shapes[index] = readcomposite(f,nofcontours)
+ end
+ else
+ if loadshapes then
+ shapes[index] = readnothing(f)
+ end
+ glyphs[index].boundingbox = nothing
+ end
+ end
+ if loadshapes then
+ if readers.gvar then
+ readers.gvar(f,fontdata,specification,glyphs,shapes)
+ end
+ mergecomposites(glyphs,shapes)
+ if specification.instance then
+ if specification.streams then
+ repackpoints(glyphs,shapes)
+ else
+ contours2outlines_shaped(glyphs,shapes,specification.shapes)
+ end
+ elseif specification.shapes then
+ if specification.streams then
+ repackpoints(glyphs,shapes)
+ else
+ contours2outlines_normal(glyphs,shapes)
+ end
+ elseif specification.streams then
+ repackpoints(glyphs,shapes)
+ end
+ end
+ end
+ end
+end
+
+-- gvar is a bit crazy format and one can really wonder if the bit-jugling obscurity
+-- is still needed in these days .. cff is much nicer with these blends while the ttf
+-- coding variant looks quite horrible
+
+local function readtuplerecord(f,nofaxis)
+ local record = { }
+ for i=1,nofaxis do
+ record[i] = read2dot14(f)
+ end
+ return record
+end
+
+-- (1) the first is a real point the rest deltas
+-- (2) points can be present more than once (multiple deltas then)
+
+local function readpoints(f)
+ local count = readbyte(f)
+ if count == 0 then
+ -- second byte not used, deltas for all point numbers
+ return nil, 0 -- todo
+ else
+ if count < 128 then
+ -- no second byte, use count
+ elseif band(count,0x80) ~= 0 then
+ count = band(count,0x7F) * 256 + readbyte(f)
+ else
+ -- bad news
+ end
+ local points = { }
+ local p = 0
+ local n = 1 -- indices
+ while p < count do
+ local control = readbyte(f)
+ local runreader = band(control,0x80) ~= 0 and readushort or readbyte
+ local runlength = band(control,0x7F)
+ for i=1,runlength+1 do
+ n = n + runreader(f)
+ p = p + 1
+ points[p] = n
+ end
+ end
+ return points, p
+ end
+end
+
+local function readdeltas(f,nofpoints)
+ local deltas = { }
+ local p = 0
+ local z = 0
+ while nofpoints > 0 do
+ local control = readbyte(f)
+if not control then
+ break
+end
+ local allzero = band(control,0x80) ~= 0
+ local runlength = band(control,0x3F) + 1
+ if allzero then
+ z = z + runlength
+ else
+ local runreader = band(control,0x40) ~= 0 and readshort or readinteger
+ if z > 0 then
+ for i=1,z do
+ p = p + 1
+ deltas[p] = 0
+ end
+ z = 0
+ end
+ for i=1,runlength do
+ p = p + 1
+ deltas[p] = runreader(f)
+ end
+ end
+ nofpoints = nofpoints - runlength
+ end
+ -- saves space
+-- if z > 0 then
+-- for i=1,z do
+-- p = p + 1
+-- deltas[p] = 0
+-- end
+-- end
+ if p > 0 then
+ -- forget about trailing zeros
+ return deltas
+ else
+ -- forget about all zeros
+ end
+end
+
+local function readdeltas(f,nofpoints)
+ local deltas = { }
+ local p = 0
+ while nofpoints > 0 do
+ local control = readbyte(f)
+ if control then
+ local allzero = band(control,0x80) ~= 0
+ local runlength = band(control,0x3F) + 1
+ if allzero then
+ for i=1,runlength do
+ p = p + 1
+ deltas[p] = 0
+ end
+ else
+ local runreader = band(control,0x40) ~= 0 and readshort or readinteger
+ for i=1,runlength do
+ p = p + 1
+ deltas[p] = runreader(f)
+ end
+ end
+ nofpoints = nofpoints - runlength
+ else
+ -- it happens
+ break
+ end
+ end
+ -- saves space
+ if p > 0 then
+ return deltas
+ else
+ -- forget about all zeros
+ end
+end
+
+function readers.gvar(f,fontdata,specification,glyphdata,shapedata)
+ -- this is one of the messiest tables
+ local instance = specification.instance
+ if not instance then
+ return
+ end
+ local factors = specification.factors
+ if not factors then
+ return
+ end
+ local tableoffset = gotodatatable(f,fontdata,"gvar",specification.variable or specification.shapes)
+ if tableoffset then
+ local version = readulong(f) -- 1.0
+ local nofaxis = readushort(f)
+ local noftuples = readushort(f)
+ local tupleoffset = tableoffset + readulong(f)
+ local nofglyphs = readushort(f)
+ local flags = readushort(f)
+ local dataoffset = tableoffset + readulong(f)
+ local data = { }
+ local tuples = { }
+ local glyphdata = fontdata.glyphs
+ local dowidth = not fontdata.variabledata.hvarwidths
+ -- there is one more offset (so that one can calculate the size i suppose)
+ -- so we could test for overflows but we simply assume sane font files
+ if band(flags,0x0001) ~= 0 then
+ for i=1,nofglyphs+1 do
+ data[i] = dataoffset + readulong(f)
+ end
+ else
+ for i=1,nofglyphs+1 do
+ data[i] = dataoffset + 2*readushort(f)
+ end
+ end
+ --
+ if noftuples > 0 then
+ setposition(f,tupleoffset)
+ for i=1,noftuples do
+ tuples[i] = readtuplerecord(f,nofaxis)
+ end
+ end
+ local nextoffset = false
+ local startoffset = data[1]
+ for i=1,nofglyphs do -- hm one more cf spec
+ nextoffset = data[i+1]
+ local glyph = glyphdata[i-1]
+ local name = trace_deltas and glyph.name
+ if startoffset == nextoffset then
+ if name then
+ report("no deltas for glyph %a",name)
+ end
+ else
+ local shape = shapedata[i-1] -- todo 0
+ if not shape then
+ if name then
+ report("no shape for glyph %a",name)
+ end
+ else
+ lastoffset = startoffset
+ setposition(f,startoffset)
+ local flags = readushort(f)
+ local count = band(flags,0x0FFF)
+ local offset = startoffset + readushort(f) -- to serialized
+ local deltas = { }
+ local allpoints = (shape.nofpoints or 0) -- + 1
+ local shared = false
+ local nofshared = 0
+ if band(flags,0x8000) ~= 0 then -- has shared points
+ -- go to the packed stream (get them once)
+ local current = getposition(f)
+ setposition(f,offset)
+ shared, nofshared = readpoints(f)
+ offset = getposition(f)
+ setposition(f,current)
+ -- and back to the table
+ end
+ for j=1,count do
+ local size = readushort(f) -- check
+ local flags = readushort(f)
+ local index = band(flags,0x0FFF)
+ local haspeak = band(flags,0x8000) ~= 0
+ local intermediate = band(flags,0x4000) ~= 0
+ local private = band(flags,0x2000) ~= 0
+ local peak = nil
+ local start = nil
+ local stop = nil
+ local xvalues = nil
+ local yvalues = nil
+ local points = shared -- we default to shared
+ local nofpoints = nofshared -- we default to shared
+ -- local advance = 4
+ if haspeak then
+ peak = readtuplerecord(f,nofaxis)
+ -- advance = advance + 2*nofaxis
+ else
+ if index+1 > #tuples then
+ report("error, bad tuple index",index)
+ end
+ peak = tuples[index+1] -- hm, needs checking, only peak?
+ end
+ if intermediate then
+ start = readtuplerecord(f,nofaxis)
+ stop = readtuplerecord(f,nofaxis)
+ -- advance = advance + 4*nofaxis
+ end
+ -- get the deltas
+ if size > 0 then
+ local current = getposition(f)
+ -- goto the packed stream
+ setposition(f,offset)
+ if private then
+ points, nofpoints = readpoints(f)
+ end -- else
+ if nofpoints == 0 then
+ nofpoints = allpoints + 4
+ end
+ if nofpoints > 0 then
+ -- a nice test is to do only one
+ xvalues = readdeltas(f,nofpoints)
+ yvalues = readdeltas(f,nofpoints)
+ end
+ -- resync offset
+ offset = offset + size
+ -- back to the table
+ setposition(f,current)
+ end
+ if not xvalues and not yvalues then
+ points = nil
+ end
+ local s = 1
+ for i=1,nofaxis do
+ local f = factors[i]
+ local peak = peak and peak [i] or 0
+ -- local start = start and start[i] or 0
+ -- local stop = stop and stop [i] or 0
+ local start = start and start[i] or (peak < 0 and peak or 0)
+ local stop = stop and stop [i] or (peak > 0 and peak or 0)
+ -- do we really need these tests ... can't we assume sane values
+ if start > peak or peak > stop then
+ -- * 1
+ elseif start < 0 and stop > 0 and peak ~= 0 then
+ -- * 1
+ elseif peak == 0 then
+ -- * 1
+ elseif f < start or f > stop then
+ -- * 0
+ s = 0
+ break
+ elseif f < peak then
+-- s = - s * (f - start) / (peak - start)
+ s = s * (f - start) / (peak - start)
+ elseif f > peak then
+ s = s * (stop - f) / (stop - peak)
+ else
+ -- * 1
+ end
+ end
+ if s == 0 then
+ if name then
+ report("no deltas applied for glyph %a",name)
+ end
+ else
+ deltas[#deltas+1] = {
+ factor = s,
+ points = points,
+ xvalues = xvalues,
+ yvalues = yvalues,
+ }
+ end
+ end
+ if shape.type == "glyph" then
+ applyaxis(glyph,shape,deltas,dowidth)
+ else
+ -- todo: args_are_xy_values mess .. i have to be really bored
+ -- and motivated to deal with it
+ shape.deltas = deltas
+ end
+ end
+ end
+ startoffset = nextoffset
+ end
+ end
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-font-vfc.lua b/macros/luatex/generic/luaotfload/fontloader-font-vfc.lua
new file mode 100644
index 0000000000..dfe6b3afc4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-font-vfc.lua
@@ -0,0 +1,123 @@
+if not modules then modules = { } end modules ['font-vfc'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv and hand-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local select, type = select, type
+local insert = table.insert
+
+local fonts = fonts
+local helpers = fonts.helpers
+
+local setmetatableindex = table.setmetatableindex
+local makeweak = table.makeweak
+
+-- Helpers dealing with virtual fonts: beware, these are final values so
+-- don't change the content of tables gotten this way!
+
+local push = { "push" }
+local pop = { "pop" }
+local dummy = { "comment" }
+
+function helpers.prependcommands(commands,...)
+ insert(commands,1,push)
+ for i=select("#",...),1,-1 do
+ local s = (select(i,...))
+ if s then
+ insert(commands,1,s)
+ end
+ end
+ insert(commands,pop)
+ return commands
+end
+
+function helpers.appendcommands(commands,...)
+ insert(commands,1,push)
+ insert(commands,pop)
+ for i=1,select("#",...) do
+ local s = (select(i,...))
+ if s then
+ insert(commands,s)
+ end
+ end
+ return commands
+end
+
+function helpers.prependcommandtable(commands,t)
+ insert(commands,1,push)
+ for i=#t,1,-1 do
+ local s = t[i]
+ if s then
+ insert(commands,1,s)
+ end
+ end
+ insert(commands,pop)
+ return commands
+end
+
+function helpers.appendcommandtable(commands,t)
+ insert(commands,1,push)
+ insert(commands,pop)
+ for i=1,#t do
+ local s = t[i]
+ if s then
+ insert(commands,s)
+ end
+ end
+ return commands
+end
+
+-- todo: maybe weak
+-- todo: maybe indirect so that we can't change them
+
+local char = setmetatableindex(function(t,k)
+ -- local v = { "char", k }
+ local v = { "slot", 0, k }
+ t[k] = v
+ return v
+end)
+
+local right = setmetatableindex(function(t,k)
+ local v = { "right", k }
+ t[k] = v
+ return v
+end)
+
+local left = setmetatableindex(function(t,k)
+ local v = { "right", -k }
+ t[k] = v
+ return v
+end)
+
+local down = setmetatableindex(function(t,k)
+ local v = { "down", k }
+ t[k] = v
+ return v
+end)
+
+local up = setmetatableindex(function(t,k)
+ local v = { "down", -k }
+ t[k] = v
+ return v
+end)
+
+-- makeweak(char)
+-- makeweak(right)
+-- makeweak(left)
+-- makeweak(up)
+-- makeweak(down)
+
+helpers.commands = utilities.storage.allocate {
+ char = char,
+ right = right,
+ left = left,
+ down = down,
+ up = up,
+ push = push,
+ pop = pop,
+ dummy = dummy,
+}
+
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-def.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-def.lua
new file mode 100644
index 0000000000..883451fb5e
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-def.lua
@@ -0,0 +1,98 @@
+if not modules then modules = { } end modules ['luatex-fonts-def'] = {
+ version = 1.001,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+local fonts = fonts
+
+-- A bit of tuning for definitions.
+
+fonts.constructors.namemode = "specification" -- somehow latex needs this (changed name!) => will change into an overload
+
+-- tricky: we sort of bypass the parser and directly feed all into
+-- the sub parser
+
+function fonts.definers.getspecification(str)
+ return "", str, "", ":", str
+end
+
+-- the generic name parser (different from context!)
+
+local list = { } -- we could pass Carg but let's keep the old one
+
+local function issome () list.lookup = 'name' end -- xetex mode prefers name (not in context!)
+local function isfile () list.lookup = 'file' end
+local function isname () list.lookup = 'name' end
+local function thename(s) list.name = s end
+local function issub (v) list.sub = v end
+local function iscrap (s) list.crap = string.lower(s) end
+local function iskey (k,v) list[k] = v end
+local function istrue (s) list[s] = true end
+local function isfalse(s) list[s] = false end
+
+local P, S, R, C, Cs = lpeg.P, lpeg.S, lpeg.R, lpeg.C, lpeg.Cs
+
+local spaces = P(" ")^0
+local namespec = Cs((P("{")/"") * (1-S("}"))^0 * (P("}")/"") + (1-S("/:("))^0)
+local crapspec = spaces * P("/") * (((1-P(":"))^0)/iscrap) * spaces
+local filename_1 = P("file:")/isfile * (namespec/thename)
+local filename_2 = P("[") * P(true)/isfile * (((1-P("]"))^0)/thename) * P("]")
+local fontname_1 = P("name:")/isname * (namespec/thename)
+local fontname_2 = P(true)/issome * (namespec/thename)
+local sometext = R("az","AZ","09")^1
+local somekey = R("az","AZ","09")^1
+local somevalue = (P("{")/"")*(1-P("}"))^0*(P("}")/"") + (1-S(";"))^1
+local truevalue = P("+") * spaces * (sometext/istrue)
+local falsevalue = P("-") * spaces * (sometext/isfalse)
+local keyvalue = (C(somekey) * spaces * P("=") * spaces * C(somevalue))/iskey
+local somevalue = sometext/istrue
+local subvalue = P("(") * (C(P(1-S("()"))^1)/issub) * P(")") -- for Kim
+local option = spaces * (keyvalue + falsevalue + truevalue + somevalue) * spaces
+local options = P(":") * spaces * (P(";")^0 * option)^0
+
+local pattern = (filename_1 + filename_2 + fontname_1 + fontname_2)
+ * subvalue^0 * crapspec^0 * options^0
+
+function fonts.definers.analyze(str,size)
+ local specification = fonts.definers.makespecification(str,nil,nil,nil,":",nil,size)
+ list = { }
+ lpeg.match(pattern,str)
+ list.crap = nil
+ if list.name then
+ specification.name = list.name
+ list.name = nil
+ end
+ if list.lookup then
+ specification.lookup = list.lookup
+ list.lookup = nil
+ end
+ if list.sub then
+ specification.sub = list.sub
+ list.sub = nil
+ end
+ specification.features.normal = fonts.handlers.otf.features.normalize(list)
+ list = nil
+ return specification
+end
+
+function fonts.definers.applypostprocessors(tfmdata)
+ local postprocessors = tfmdata.postprocessors
+ if postprocessors then
+ for i=1,#postprocessors do
+ local extrahash = postprocessors[i](tfmdata) -- after scaling etc
+ if type(extrahash) == "string" and extrahash ~= "" then
+ -- e.g. a reencoding needs this
+ extrahash = string.gsub(lower(extrahash),"[^a-z]","-")
+ tfmdata.properties.fullname = format("%s-%s",tfmdata.properties.fullname,extrahash)
+ end
+ end
+ end
+ return tfmdata
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-enc.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-enc.lua
new file mode 100644
index 0000000000..2bc6b71bf4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-enc.lua
@@ -0,0 +1,75 @@
+if not modules then modules = { } end modules ['luatex-font-enc'] = {
+ version = 1.001,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+local fonts = fonts
+local encodings = { }
+fonts.encodings = encodings
+encodings.agl = { }
+encodings.known = { }
+
+setmetatable(encodings.agl, { __index = function(t,k)
+ if k == "unicodes" then
+ logs.report("fonts","loading (extended) adobe glyph list")
+ local unicodes = dofile(resolvers.findfile("font-age.lua"))
+ encodings.agl = { unicodes = unicodes }
+ return unicodes
+ else
+ return nil
+ end
+end })
+
+-- adapted for generic
+
+encodings.cache = containers.define("fonts", "enc", encodings.version, true)
+
+function encodings.load(filename)
+ local name = file.removesuffix(filename)
+ local data = containers.read(encodings.cache,name)
+ if data then
+ return data
+ end
+ local vector, tag, hash, unicodes = { }, "", { }, { }
+ local foundname = resolvers.findfile(filename,'enc')
+ if foundname and foundname ~= "" then
+ local ok, encoding, size = resolvers.loadbinfile(foundname)
+ if ok and encoding then
+ encoding = string.gsub(encoding,"%%(.-)\n","")
+ local unicoding = encodings.agl.unicodes
+ local tag, vec = string.match(encoding,"/(%w+)%s*%[(.*)%]%s*def")
+ local i = 0
+ for ch in string.gmatch(vec,"/([%a%d%.]+)") do
+ if ch ~= ".notdef" then
+ vector[i] = ch
+ if not hash[ch] then
+ hash[ch] = i
+ else
+ -- duplicate, play safe for tex ligs and take first
+ end
+ local u = unicoding[ch]
+ if u then
+ unicodes[u] = i
+ end
+ end
+ i = i + 1
+ end
+ end
+ end
+ local data = {
+ name = name,
+ tag = tag,
+ vector = vector,
+ hash = hash,
+ unicodes = unicodes
+ }
+ return containers.write(encodings.cache, name, data)
+end
+
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-ext.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-ext.lua
new file mode 100644
index 0000000000..aee43ec4b3
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-ext.lua
@@ -0,0 +1,244 @@
+if not modules then modules = { } end modules ['luatex-fonts-ext'] = {
+ version = 1.001,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+local byte = string.byte
+
+local fonts = fonts
+local handlers = fonts.handlers
+local otf = handlers.otf
+local afm = handlers.afm
+local registerotffeature = otf.features.register
+local registerafmfeature = afm.features.register
+
+-- extra generic stuff
+
+function fonts.loggers.onetimemessage() end
+
+-- done elsewhere
+--
+-- loadmodule('font-ext-imp-italic.lua')
+-- loadmodule('font-ext-imp-effect.lua')
+-- loadmodule('luatex-fonts-lig.lua')
+
+-- protrusion (simplified version)
+
+fonts.protrusions = fonts.protrusions or { }
+fonts.protrusions.setups = fonts.protrusions.setups or { }
+local setups = fonts.protrusions.setups
+
+setups['default'] = { -- demo vector
+
+ factor = 1,
+ left = 1,
+ right = 1,
+
+ [0x002C] = { 0, 1 }, -- comma
+ [0x002E] = { 0, 1 }, -- period
+ [0x003A] = { 0, 1 }, -- colon
+ [0x003B] = { 0, 1 }, -- semicolon
+ [0x002D] = { 0, 1 }, -- hyphen
+ [0x2013] = { 0, 0.50 }, -- endash
+ [0x2014] = { 0, 0.33 }, -- emdash
+ [0x3001] = { 0, 1 }, -- ideographic comma 、
+ [0x3002] = { 0, 1 }, -- ideographic full stop 。
+ [0x060C] = { 0, 1 }, -- arabic comma ،
+ [0x061B] = { 0, 1 }, -- arabic semicolon ؛
+ [0x06D4] = { 0, 1 }, -- arabic full stop ۔
+
+}
+
+local function initializeprotrusion(tfmdata,value)
+ if value then
+ local setup = setups[value]
+ if setup then
+ local factor, left, right = setup.factor or 1, setup.left or 1, setup.right or 1
+ local emwidth = tfmdata.parameters.quad
+ tfmdata.parameters.protrusion = {
+ auto = true,
+ }
+ for i, chr in next, tfmdata.characters do
+ local v, pl, pr = setup[i], nil, nil
+ if v then
+ pl, pr = v[1], v[2]
+ end
+ if pl and pl ~= 0 then chr.left_protruding = left *pl*factor end
+ if pr and pr ~= 0 then chr.right_protruding = right*pr*factor end
+ end
+ end
+ end
+end
+
+local specification = {
+ name = "protrusion",
+ description = "shift characters into the left and or right margin",
+ initializers = {
+ base = initializeprotrusion,
+ node = initializeprotrusion,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+-- expansion (simplified version)
+
+fonts.expansions = fonts.expansions or { }
+fonts.expansions.setups = fonts.expansions.setups or { }
+local setups = fonts.expansions.setups
+
+setups['default'] = { -- demo vector
+
+ stretch = 2,
+ shrink = 2,
+ step = .5,
+ factor = 1,
+
+ [byte('A')] = 0.5, [byte('B')] = 0.7, [byte('C')] = 0.7, [byte('D')] = 0.5, [byte('E')] = 0.7,
+ [byte('F')] = 0.7, [byte('G')] = 0.5, [byte('H')] = 0.7, [byte('K')] = 0.7, [byte('M')] = 0.7,
+ [byte('N')] = 0.7, [byte('O')] = 0.5, [byte('P')] = 0.7, [byte('Q')] = 0.5, [byte('R')] = 0.7,
+ [byte('S')] = 0.7, [byte('U')] = 0.7, [byte('W')] = 0.7, [byte('Z')] = 0.7,
+ [byte('a')] = 0.7, [byte('b')] = 0.7, [byte('c')] = 0.7, [byte('d')] = 0.7, [byte('e')] = 0.7,
+ [byte('g')] = 0.7, [byte('h')] = 0.7, [byte('k')] = 0.7, [byte('m')] = 0.7, [byte('n')] = 0.7,
+ [byte('o')] = 0.7, [byte('p')] = 0.7, [byte('q')] = 0.7, [byte('s')] = 0.7, [byte('u')] = 0.7,
+ [byte('w')] = 0.7, [byte('z')] = 0.7,
+ [byte('2')] = 0.7, [byte('3')] = 0.7, [byte('6')] = 0.7, [byte('8')] = 0.7, [byte('9')] = 0.7,
+}
+
+local function initializeexpansion(tfmdata,value)
+ if value then
+ local setup = setups[value]
+ if setup then
+ local factor = setup.factor or 1
+ tfmdata.parameters.expansion = {
+ stretch = 10 * (setup.stretch or 0),
+ shrink = 10 * (setup.shrink or 0),
+ step = 10 * (setup.step or 0),
+ auto = true,
+ }
+ for i, chr in next, tfmdata.characters do
+ local v = setup[i]
+ if v and v ~= 0 then
+ chr.expansion_factor = v*factor
+ else -- can be option
+ chr.expansion_factor = factor
+ end
+ end
+ end
+ end
+end
+
+local specification = {
+ name = "expansion",
+ description = "apply hz optimization",
+ initializers = {
+ base = initializeexpansion,
+ node = initializeexpansion,
+ }
+}
+
+registerotffeature(specification)
+registerafmfeature(specification)
+
+-- normalizer (generic only)
+
+if not otf.features.normalize then
+
+ otf.features.normalize = function(t)
+ if t.rand then
+ t.rand = "random"
+ end
+ return t
+ end
+
+end
+
+-- bonus
+
+function fonts.helpers.nametoslot(name)
+ local t = type(name)
+ if t == "string" then
+ local tfmdata = fonts.hashes.identifiers[currentfont()]
+ local shared = tfmdata and tfmdata.shared
+ local fntdata = shared and shared.rawdata
+ return fntdata and fntdata.resources.unicodes[name]
+ elseif t == "number" then
+ return n
+ end
+end
+
+-- \font\test=file:somefont:reencode=mymessup
+--
+-- fonts.encodings.reencodings.mymessup = {
+-- [109] = 110, -- m
+-- [110] = 109, -- n
+-- }
+
+-- reencoding (generic only)
+
+fonts.encodings = fonts.encodings or { }
+local reencodings = { }
+fonts.encodings.reencodings = reencodings
+
+local function specialreencode(tfmdata,value)
+ -- we forget about kerns as we assume symbols and we
+ -- could issue a message if ther are kerns but it's
+ -- a hack anyway so we odn't care too much here
+ local encoding = value and reencodings[value]
+ if encoding then
+ local temp = { }
+ local char = tfmdata.characters
+ for k, v in next, encoding do
+ temp[k] = char[v]
+ end
+ for k, v in next, temp do
+ char[k] = temp[k]
+ end
+ -- if we use the font otherwise luatex gets confused so
+ -- we return an additional hash component for fullname
+ return string.format("reencoded:%s",value)
+ end
+end
+
+local function initialize(tfmdata,value)
+ tfmdata.postprocessors = tfmdata.postprocessors or { }
+ table.insert(tfmdata.postprocessors,
+ function(tfmdata)
+ return specialreencode(tfmdata,value)
+ end
+ )
+end
+
+registerotffeature {
+ name = "reencode",
+ description = "reencode characters",
+ manipulators = {
+ base = initialize,
+ node = initialize,
+ }
+}
+
+-- math stuff (generic only)
+
+local function initialize(tfmdata,key,value)
+ if value then
+ tfmdata.mathparameters = nil
+ end
+end
+
+registerotffeature {
+ name = "ignoremathconstants",
+ description = "ignore math constants table",
+ initializers = {
+ base = initialize,
+ node = initialize,
+ }
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-gbn.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-gbn.lua
new file mode 100644
index 0000000000..53be41c7ed
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-gbn.lua
@@ -0,0 +1,300 @@
+if not modules then modules = { } end modules ['luatex-fonts-gbn'] = {
+ version = 1.001,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- generic [base|node] mode handler
+
+if context then
+ os.exit()
+end
+
+local next = next
+
+local fonts = fonts
+local nodes = nodes
+
+local nuts = nodes.nuts -- context abstraction of direct nodes
+
+local traverse_id = nuts.traverse_id
+local flush_node = nuts.flush_node
+
+local glyph_code = nodes.nodecodes.glyph
+local disc_code = nodes.nodecodes.disc
+
+local tonode = nuts.tonode
+local tonut = nuts.tonut
+
+local getfont = nuts.getfont
+local getchar = nuts.getchar
+local getid = nuts.getid
+local getboth = nuts.getboth
+local getprev = nuts.getprev
+local getnext = nuts.getnext
+local getdisc = nuts.getdisc
+local setchar = nuts.setchar
+local setlink = nuts.setlink
+local setprev = nuts.setprev
+
+-- from now on we apply ligaturing and kerning here because it might interfere with complex
+-- opentype discretionary handling where the base ligature pass expect some weird extra
+-- pointers (which then confuse the tail slider that has some checking built in)
+
+local n_ligaturing = node.ligaturing
+local n_kerning = node.kerning
+
+local d_ligaturing = nuts.ligaturing
+local d_kerning = nuts.kerning
+
+local basemodepass = true
+
+local function l_warning() logs.report("fonts","don't call 'node.ligaturing' directly") l_warning = nil end
+local function k_warning() logs.report("fonts","don't call 'node.kerning' directly") k_warning = nil end
+
+function node.ligaturing(...)
+ if basemodepass and l_warning then
+ l_warning()
+ end
+ return n_ligaturing(...)
+end
+
+function node.kerning(...)
+ if basemodepass and k_warning then
+ k_warning()
+ end
+ return n_kerning(...)
+end
+
+function nuts.ligaturing(...)
+ if basemodepass and l_warning then
+ l_warning()
+ end
+ return d_ligaturing(...)
+end
+
+function nuts.kerning(...)
+ if basemodepass and k_warning then
+ k_warning()
+ end
+ return d_kerning(...)
+end
+
+-- direct.ligaturing = nuts.ligaturing
+-- direct.kerning = nuts.kerning
+
+function nodes.handlers.setbasemodepass(v)
+ basemodepass = v
+end
+
+local function nodepass(head,groupcode,size,packtype,direction)
+ local fontdata = fonts.hashes.identifiers
+ if fontdata then
+ local usedfonts = { }
+ local basefonts = { }
+ local prevfont = nil
+ local basefont = nil
+ local variants = nil
+ local redundant = nil
+ local nofused = 0
+ for n in traverse_id(glyph_code,head) do
+ local font = getfont(n)
+ if font ~= prevfont then
+ if basefont then
+ basefont[2] = getprev(n)
+ end
+ prevfont = font
+ local used = usedfonts[font]
+ if not used then
+ local tfmdata = fontdata[font] --
+ if tfmdata then
+ local shared = tfmdata.shared -- we need to check shared, only when same features
+ if shared then
+ local processors = shared.processes
+ if processors and #processors > 0 then
+ usedfonts[font] = processors
+ nofused = nofused + 1
+ elseif basemodepass then
+ basefont = { n, nil }
+ basefonts[#basefonts+1] = basefont
+ end
+ end
+ local resources = tfmdata.resources
+ variants = resources and resources.variants
+ variants = variants and next(variants) and variants or false
+ end
+ else
+ local tfmdata = fontdata[prevfont]
+ if tfmdata then
+ local resources = tfmdata.resources
+ variants = resources and resources.variants
+ variants = variants and next(variants) and variants or false
+ end
+ end
+ end
+ if variants then
+ local char = getchar(n)
+ if (char >= 0xFE00 and char <= 0xFE0F) or (char >= 0xE0100 and char <= 0xE01EF) then
+ local hash = variants[char]
+ if hash then
+ local p = getprev(n)
+ if p and getid(p) == glyph_code then
+ local variant = hash[getchar(p)]
+ if variant then
+ setchar(p,variant)
+ end
+ end
+ end
+ -- per generic user request we always remove selectors
+ if not redundant then
+ redundant = { n }
+ else
+ redundant[#redundant+1] = n
+ end
+ end
+ end
+ end
+ local nofbasefonts = #basefonts
+ if redundant then
+ for i=1,#redundant do
+ local r = redundant[i]
+ local p, n = getboth(r)
+ if r == head then
+ head = n
+ setprev(n)
+ else
+ setlink(p,n)
+ end
+ if nofbasefonts > 0 then
+ for i=1,nofbasefonts do
+ local bi = basefonts[i]
+ if r == bi[1] then
+ bi[1] = n
+ end
+ if r == bi[2] then
+ bi[2] = n
+ end
+ end
+ end
+ flush_node(r)
+ end
+ end
+ for d in traverse_id(disc_code,head) do
+ local _, _, r = getdisc(d)
+ if r then
+ for n in traverse_id(glyph_code,r) do
+ local font = getfont(n)
+ if font ~= prevfont then
+ prevfont = font
+ local used = usedfonts[font]
+ if not used then
+ local tfmdata = fontdata[font] --
+ if tfmdata then
+ local shared = tfmdata.shared -- we need to check shared, only when same features
+ if shared then
+ local processors = shared.processes
+ if processors and #processors > 0 then
+ usedfonts[font] = processors
+ nofused = nofused + 1
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if next(usedfonts) then
+ for font, processors in next, usedfonts do
+ for i=1,#processors do
+ head = processors[i](head,font,0,direction,nofused) or head
+ end
+ end
+ end
+ if basemodepass and nofbasefonts > 0 then
+ for i=1,nofbasefonts do
+ local range = basefonts[i]
+ local start = range[1]
+ local stop = range[2]
+ if start then
+ local front = head == start
+ local prev, next
+ if stop then
+ next = getnext(stop)
+ start, stop = d_ligaturing(start,stop)
+ start, stop = d_kerning(start,stop)
+ else
+ prev = getprev(start)
+ start = d_ligaturing(start)
+ start = d_kerning(start)
+ end
+ if prev then
+ setlink(prev,start)
+ end
+ if next then
+ setlink(stop,next)
+ end
+ if front and head ~= start then
+ head = start
+ end
+ end
+ end
+ end
+ end
+ return head
+end
+
+local function basepass(head)
+ if basemodepass then
+ head = d_ligaturing(head)
+ head = d_kerning(head)
+ end
+ return head
+end
+
+local protectpass = node.direct.protect_glyphs
+local injectpass = nodes.injections.handler
+
+-- This is the only official public interface and this one can be hooked into a callback (chain) and
+-- everything else can change!@ Functione being visibel doesn't mean that it's part of the api.
+
+function nodes.handlers.nodepass(head,...)
+ if head then
+ return tonode(nodepass(tonut(head),...))
+ end
+end
+
+function nodes.handlers.basepass(head)
+ if head then
+ return tonode(basepass(tonut(head)))
+ end
+end
+
+function nodes.handlers.injectpass(head)
+ if head then
+ return tonode(injectpass(tonut(head)))
+ end
+end
+
+function nodes.handlers.protectpass(head)
+ if head then
+ protectpass(tonut(head))
+ return head
+ end
+end
+
+function nodes.simple_font_handler(head,groupcode,size,packtype,direction)
+ if head then
+ head = tonut(head)
+ head = nodepass(head,groupcode,size,packtype,direction)
+ head = injectpass(head)
+ if not basemodepass then
+ head = basepass(head)
+ end
+ protectpass(head)
+ head = tonode(head)
+ end
+ return head
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-lig.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-lig.lua
new file mode 100644
index 0000000000..4ce1265338
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-lig.lua
@@ -0,0 +1,2067 @@
+-- this file is generated by context
+
+fonts.handlers.otf.addfeature {
+ ["dataset"]={
+ {
+ ["data"]={
+ ["À"]={ "A", "̀" },
+ ["Á"]={ "A", "́" },
+ ["Â"]={ "A", "̂" },
+ ["Ã"]={ "A", "̃" },
+ ["Ä"]={ "A", "̈" },
+ ["Å"]={ "A", "̊" },
+ ["Ç"]={ "C", "̧" },
+ ["È"]={ "E", "̀" },
+ ["É"]={ "E", "́" },
+ ["Ê"]={ "E", "̂" },
+ ["Ë"]={ "E", "̈" },
+ ["Ì"]={ "I", "̀" },
+ ["Í"]={ "I", "́" },
+ ["Î"]={ "I", "̂" },
+ ["Ï"]={ "I", "̈" },
+ ["Ñ"]={ "N", "̃" },
+ ["Ò"]={ "O", "̀" },
+ ["Ó"]={ "O", "́" },
+ ["Ô"]={ "O", "̂" },
+ ["Õ"]={ "O", "̃" },
+ ["Ö"]={ "O", "̈" },
+ ["Ù"]={ "U", "̀" },
+ ["Ú"]={ "U", "́" },
+ ["Û"]={ "U", "̂" },
+ ["Ü"]={ "U", "̈" },
+ ["Ý"]={ "Y", "́" },
+ ["à"]={ "a", "̀" },
+ ["á"]={ "a", "́" },
+ ["â"]={ "a", "̂" },
+ ["ã"]={ "a", "̃" },
+ ["ä"]={ "a", "̈" },
+ ["å"]={ "a", "̊" },
+ ["ç"]={ "c", "̧" },
+ ["è"]={ "e", "̀" },
+ ["é"]={ "e", "́" },
+ ["ê"]={ "e", "̂" },
+ ["ë"]={ "e", "̈" },
+ ["ì"]={ "i", "̀" },
+ ["í"]={ "i", "́" },
+ ["î"]={ "i", "̂" },
+ ["ï"]={ "i", "̈" },
+ ["ñ"]={ "n", "̃" },
+ ["ò"]={ "o", "̀" },
+ ["ó"]={ "o", "́" },
+ ["ô"]={ "o", "̂" },
+ ["õ"]={ "o", "̃" },
+ ["ö"]={ "o", "̈" },
+ ["ù"]={ "u", "̀" },
+ ["ú"]={ "u", "́" },
+ ["û"]={ "u", "̂" },
+ ["ü"]={ "u", "̈" },
+ ["ý"]={ "y", "́" },
+ ["ÿ"]={ "y", "̈" },
+ ["Ā"]={ "A", "̄" },
+ ["ā"]={ "a", "̄" },
+ ["Ă"]={ "A", "̆" },
+ ["ă"]={ "a", "̆" },
+ ["Ą"]={ "A", "̨" },
+ ["ą"]={ "a", "̨" },
+ ["Ć"]={ "C", "́" },
+ ["ć"]={ "c", "́" },
+ ["Ĉ"]={ "C", "̂" },
+ ["ĉ"]={ "c", "̂" },
+ ["Ċ"]={ "C", "̇" },
+ ["ċ"]={ "c", "̇" },
+ ["Č"]={ "C", "̌" },
+ ["č"]={ "c", "̌" },
+ ["Ď"]={ "D", "̌" },
+ ["ď"]={ "d", "̌" },
+ ["Ē"]={ "E", "̄" },
+ ["ē"]={ "e", "̄" },
+ ["Ĕ"]={ "E", "̆" },
+ ["ĕ"]={ "e", "̆" },
+ ["Ė"]={ "E", "̇" },
+ ["ė"]={ "e", "̇" },
+ ["Ę"]={ "E", "̨" },
+ ["ę"]={ "e", "̨" },
+ ["Ě"]={ "E", "̌" },
+ ["ě"]={ "e", "̌" },
+ ["Ĝ"]={ "G", "̂" },
+ ["ĝ"]={ "g", "̂" },
+ ["Ğ"]={ "G", "̆" },
+ ["ğ"]={ "g", "̆" },
+ ["Ġ"]={ "G", "̇" },
+ ["ġ"]={ "g", "̇" },
+ ["Ģ"]={ "G", "̧" },
+ ["ģ"]={ "g", "̧" },
+ ["Ĥ"]={ "H", "̂" },
+ ["ĥ"]={ "h", "̂" },
+ ["Ĩ"]={ "I", "̃" },
+ ["ĩ"]={ "i", "̃" },
+ ["Ī"]={ "I", "̄" },
+ ["ī"]={ "i", "̄" },
+ ["Ĭ"]={ "I", "̆" },
+ ["ĭ"]={ "i", "̆" },
+ ["Į"]={ "I", "̨" },
+ ["į"]={ "i", "̨" },
+ ["İ"]={ "I", "̇" },
+ ["Ĵ"]={ "J", "̂" },
+ ["ĵ"]={ "j", "̂" },
+ ["Ķ"]={ "K", "̧" },
+ ["ķ"]={ "k", "̧" },
+ ["Ĺ"]={ "L", "́" },
+ ["ĺ"]={ "l", "́" },
+ ["Ļ"]={ "L", "̧" },
+ ["ļ"]={ "l", "̧" },
+ ["Ľ"]={ "L", "̌" },
+ ["ľ"]={ "l", "̌" },
+ ["Ń"]={ "N", "́" },
+ ["ń"]={ "n", "́" },
+ ["Ņ"]={ "N", "̧" },
+ ["ņ"]={ "n", "̧" },
+ ["Ň"]={ "N", "̌" },
+ ["ň"]={ "n", "̌" },
+ ["Ō"]={ "O", "̄" },
+ ["ō"]={ "o", "̄" },
+ ["Ŏ"]={ "O", "̆" },
+ ["ŏ"]={ "o", "̆" },
+ ["Ő"]={ "O", "̋" },
+ ["ő"]={ "o", "̋" },
+ ["Ŕ"]={ "R", "́" },
+ ["ŕ"]={ "r", "́" },
+ ["Ŗ"]={ "R", "̧" },
+ ["ŗ"]={ "r", "̧" },
+ ["Ř"]={ "R", "̌" },
+ ["ř"]={ "r", "̌" },
+ ["Ś"]={ "S", "́" },
+ ["ś"]={ "s", "́" },
+ ["Ŝ"]={ "S", "̂" },
+ ["ŝ"]={ "s", "̂" },
+ ["Ş"]={ "S", "̧" },
+ ["ş"]={ "s", "̧" },
+ ["Š"]={ "S", "̌" },
+ ["š"]={ "s", "̌" },
+ ["Ţ"]={ "T", "̧" },
+ ["ţ"]={ "t", "̧" },
+ ["Ť"]={ "T", "̌" },
+ ["ť"]={ "t", "̌" },
+ ["Ũ"]={ "U", "̃" },
+ ["ũ"]={ "u", "̃" },
+ ["Ū"]={ "U", "̄" },
+ ["ū"]={ "u", "̄" },
+ ["Ŭ"]={ "U", "̆" },
+ ["ŭ"]={ "u", "̆" },
+ ["Ů"]={ "U", "̊" },
+ ["ů"]={ "u", "̊" },
+ ["Ű"]={ "U", "̋" },
+ ["ű"]={ "u", "̋" },
+ ["Ų"]={ "U", "̨" },
+ ["ų"]={ "u", "̨" },
+ ["Ŵ"]={ "W", "̂" },
+ ["ŵ"]={ "w", "̂" },
+ ["Ŷ"]={ "Y", "̂" },
+ ["ŷ"]={ "y", "̂" },
+ ["Ÿ"]={ "Y", "̈" },
+ ["Ź"]={ "Z", "́" },
+ ["ź"]={ "z", "́" },
+ ["Ż"]={ "Z", "̇" },
+ ["ż"]={ "z", "̇" },
+ ["Ž"]={ "Z", "̌" },
+ ["ž"]={ "z", "̌" },
+ ["Ơ"]={ "O", "̛" },
+ ["ơ"]={ "o", "̛" },
+ ["Ư"]={ "U", "̛" },
+ ["ư"]={ "u", "̛" },
+ ["Ǎ"]={ "A", "̌" },
+ ["ǎ"]={ "a", "̌" },
+ ["Ǐ"]={ "I", "̌" },
+ ["ǐ"]={ "i", "̌" },
+ ["Ǒ"]={ "O", "̌" },
+ ["ǒ"]={ "o", "̌" },
+ ["Ǔ"]={ "U", "̌" },
+ ["ǔ"]={ "u", "̌" },
+ ["Ǖ"]={ "Ü", "̄" },
+ ["ǖ"]={ "ü", "̄" },
+ ["Ǘ"]={ "Ü", "́" },
+ ["ǘ"]={ "ü", "́" },
+ ["Ǚ"]={ "Ü", "̌" },
+ ["ǚ"]={ "ü", "̌" },
+ ["Ǜ"]={ "Ü", "̀" },
+ ["ǜ"]={ "ü", "̀" },
+ ["Ǟ"]={ "Ä", "̄" },
+ ["ǟ"]={ "ä", "̄" },
+ ["Ǡ"]={ "Ȧ", "̄" },
+ ["ǡ"]={ "ȧ", "̄" },
+ ["Ǣ"]={ "Æ", "̄" },
+ ["ǣ"]={ "æ", "̄" },
+ ["Ǧ"]={ "G", "̌" },
+ ["ǧ"]={ "g", "̌" },
+ ["Ǩ"]={ "K", "̌" },
+ ["ǩ"]={ "k", "̌" },
+ ["Ǫ"]={ "O", "̨" },
+ ["ǫ"]={ "o", "̨" },
+ ["Ǭ"]={ "Ǫ", "̄" },
+ ["ǭ"]={ "ǫ", "̄" },
+ ["Ǯ"]={ "Ʒ", "̌" },
+ ["ǯ"]={ "ʒ", "̌" },
+ ["ǰ"]={ "j", "̌" },
+ ["Ǵ"]={ "G", "́" },
+ ["ǵ"]={ "g", "́" },
+ ["Ǹ"]={ "N", "̀" },
+ ["ǹ"]={ "n", "̀" },
+ ["Ǻ"]={ "Å", "́" },
+ ["ǻ"]={ "å", "́" },
+ ["Ǽ"]={ "Æ", "́" },
+ ["ǽ"]={ "æ", "́" },
+ ["Ǿ"]={ "Ø", "́" },
+ ["ǿ"]={ "ø", "́" },
+ ["Ȁ"]={ "A", "̏" },
+ ["ȁ"]={ "a", "̏" },
+ ["Ȃ"]={ "A", "̑" },
+ ["ȃ"]={ "a", "̑" },
+ ["Ȅ"]={ "E", "̏" },
+ ["ȅ"]={ "e", "̏" },
+ ["Ȇ"]={ "E", "̑" },
+ ["ȇ"]={ "e", "̑" },
+ ["Ȉ"]={ "I", "̏" },
+ ["ȉ"]={ "i", "̏" },
+ ["Ȋ"]={ "I", "̑" },
+ ["ȋ"]={ "i", "̑" },
+ ["Ȍ"]={ "O", "̏" },
+ ["ȍ"]={ "o", "̏" },
+ ["Ȏ"]={ "O", "̑" },
+ ["ȏ"]={ "o", "̑" },
+ ["Ȑ"]={ "R", "̏" },
+ ["ȑ"]={ "r", "̏" },
+ ["Ȓ"]={ "R", "̑" },
+ ["ȓ"]={ "r", "̑" },
+ ["Ȕ"]={ "U", "̏" },
+ ["ȕ"]={ "u", "̏" },
+ ["Ȗ"]={ "U", "̑" },
+ ["ȗ"]={ "u", "̑" },
+ ["Ș"]={ "S", "̦" },
+ ["ș"]={ "s", "̦" },
+ ["Ț"]={ "T", "̦" },
+ ["ț"]={ "t", "̦" },
+ ["Ȟ"]={ "H", "̌" },
+ ["ȟ"]={ "h", "̌" },
+ ["Ȧ"]={ "A", "̇" },
+ ["ȧ"]={ "a", "̇" },
+ ["Ȩ"]={ "E", "̧" },
+ ["ȩ"]={ "e", "̧" },
+ ["Ȫ"]={ "Ö", "̄" },
+ ["ȫ"]={ "ö", "̄" },
+ ["Ȭ"]={ "Õ", "̄" },
+ ["ȭ"]={ "õ", "̄" },
+ ["Ȯ"]={ "O", "̇" },
+ ["ȯ"]={ "o", "̇" },
+ ["Ȱ"]={ "Ȯ", "̄" },
+ ["ȱ"]={ "ȯ", "̄" },
+ ["Ȳ"]={ "Y", "̄" },
+ ["ȳ"]={ "y", "̄" },
+ ["̈́"]={ "̈", "́" },
+ ["΅"]={ "¨", "́" },
+ ["Ά"]={ "Α", "́" },
+ ["Έ"]={ "Ε", "́" },
+ ["Ή"]={ "Η", "́" },
+ ["Ί"]={ "Ι", "́" },
+ ["Ό"]={ "Ο", "́" },
+ ["Ύ"]={ "Υ", "́" },
+ ["Ώ"]={ "Ω", "́" },
+ ["ΐ"]={ "ϊ", "́" },
+ ["Ϊ"]={ "Ι", "̈" },
+ ["Ϋ"]={ "Υ", "̈" },
+ ["ά"]={ "α", "́" },
+ ["έ"]={ "ε", "́" },
+ ["ή"]={ "η", "́" },
+ ["ί"]={ "ι", "́" },
+ ["ΰ"]={ "ϋ", "́" },
+ ["ϊ"]={ "ι", "̈" },
+ ["ϋ"]={ "υ", "̈" },
+ ["ό"]={ "ο", "́" },
+ ["ύ"]={ "υ", "́" },
+ ["ώ"]={ "ω", "́" },
+ ["ϓ"]={ "ϒ", "́" },
+ ["ϔ"]={ "ϒ", "̈" },
+ ["Ѐ"]={ "Е", "̀" },
+ ["Ё"]={ "Е", "̈" },
+ ["Ѓ"]={ "Г", "́" },
+ ["Ї"]={ "І", "̈" },
+ ["Ќ"]={ "К", "́" },
+ ["Ѝ"]={ "И", "̀" },
+ ["Ў"]={ "У", "̆" },
+ ["Й"]={ "И", "̆" },
+ ["й"]={ "и", "̆" },
+ ["ѐ"]={ "е", "̀" },
+ ["ё"]={ "е", "̈" },
+ ["ѓ"]={ "г", "́" },
+ ["ї"]={ "і", "̈" },
+ ["ќ"]={ "к", "́" },
+ ["ѝ"]={ "и", "̀" },
+ ["ў"]={ "у", "̆" },
+ ["Ѷ"]={ "Ѵ", "̏" },
+ ["ѷ"]={ "ѵ", "̏" },
+ ["Ӂ"]={ "Ж", "̆" },
+ ["ӂ"]={ "ж", "̆" },
+ ["Ӑ"]={ "А", "̆" },
+ ["ӑ"]={ "а", "̆" },
+ ["Ӓ"]={ "А", "̈" },
+ ["ӓ"]={ "а", "̈" },
+ ["Ӗ"]={ "Е", "̆" },
+ ["ӗ"]={ "е", "̆" },
+ ["Ӛ"]={ "Ә", "̈" },
+ ["ӛ"]={ "ә", "̈" },
+ ["Ӝ"]={ "Ж", "̈" },
+ ["ӝ"]={ "ж", "̈" },
+ ["Ӟ"]={ "З", "̈" },
+ ["ӟ"]={ "з", "̈" },
+ ["Ӣ"]={ "И", "̄" },
+ ["ӣ"]={ "и", "̄" },
+ ["Ӥ"]={ "И", "̈" },
+ ["ӥ"]={ "и", "̈" },
+ ["Ӧ"]={ "О", "̈" },
+ ["ӧ"]={ "о", "̈" },
+ ["Ӫ"]={ "Ө", "̈" },
+ ["ӫ"]={ "ө", "̈" },
+ ["Ӭ"]={ "Э", "̈" },
+ ["ӭ"]={ "э", "̈" },
+ ["Ӯ"]={ "У", "̄" },
+ ["ӯ"]={ "у", "̄" },
+ ["Ӱ"]={ "У", "̈" },
+ ["ӱ"]={ "у", "̈" },
+ ["Ӳ"]={ "У", "̋" },
+ ["ӳ"]={ "у", "̋" },
+ ["Ӵ"]={ "Ч", "̈" },
+ ["ӵ"]={ "ч", "̈" },
+ ["Ӹ"]={ "Ы", "̈" },
+ ["ӹ"]={ "ы", "̈" },
+ ["آ"]={ "ا", "ٓ" },
+ ["أ"]={ "ا", "ٔ" },
+ ["ؤ"]={ "و", "ٔ" },
+ ["إ"]={ "ا", "ٕ" },
+ ["ئ"]={ "ي", "ٔ" },
+ ["ۀ"]={ "ە", "ٔ" },
+ ["ۂ"]={ "ہ", "ٔ" },
+ ["ۓ"]={ "ے", "ٔ" },
+ ["ऩ"]={ "न", "़" },
+ ["ऱ"]={ "र", "़" },
+ ["ऴ"]={ "ळ", "़" },
+ ["क़"]={ "क", "़" },
+ ["ख़"]={ "ख", "़" },
+ ["ग़"]={ "ग", "़" },
+ ["ज़"]={ "ज", "़" },
+ ["ड़"]={ "ड", "़" },
+ ["ढ़"]={ "ढ", "़" },
+ ["फ़"]={ "फ", "़" },
+ ["य़"]={ "य", "़" },
+ ["ো"]={ "ে", "া" },
+ ["ৌ"]={ "ে", "ৗ" },
+ ["ড়"]={ "ড", "়" },
+ ["ঢ়"]={ "ঢ", "়" },
+ ["য়"]={ "য", "়" },
+ ["ਲ਼"]={ "ਲ", "਼" },
+ ["ਸ਼"]={ "ਸ", "਼" },
+ ["ਖ਼"]={ "ਖ", "਼" },
+ ["ਗ਼"]={ "ਗ", "਼" },
+ ["ਜ਼"]={ "ਜ", "਼" },
+ ["ਫ਼"]={ "ਫ", "਼" },
+ ["ୈ"]={ "େ", "ୖ" },
+ ["ୋ"]={ "େ", "ା" },
+ ["ୌ"]={ "େ", "ୗ" },
+ ["ଡ଼"]={ "ଡ", "଼" },
+ ["ଢ଼"]={ "ଢ", "଼" },
+ ["ஔ"]={ "ஒ", "ௗ" },
+ ["ொ"]={ "ெ", "ா" },
+ ["ோ"]={ "ே", "ா" },
+ ["ௌ"]={ "ெ", "ௗ" },
+ ["ై"]={ "ె", "ౖ" },
+ ["ೀ"]={ "ಿ", "ೕ" },
+ ["ೇ"]={ "ೆ", "ೕ" },
+ ["ೈ"]={ "ೆ", "ೖ" },
+ ["ೊ"]={ "ೆ", "ೂ" },
+ ["ೋ"]={ "ೊ", "ೕ" },
+ ["ൊ"]={ "െ", "ാ" },
+ ["ോ"]={ "േ", "ാ" },
+ ["ൌ"]={ "െ", "ൗ" },
+ ["ේ"]={ "ෙ", "්" },
+ ["ො"]={ "ෙ", "ා" },
+ ["ෝ"]={ "ො", "්" },
+ ["ෞ"]={ "ෙ", "ෟ" },
+ ["གྷ"]={ "ག", "ྷ" },
+ ["ཌྷ"]={ "ཌ", "ྷ" },
+ ["དྷ"]={ "ད", "ྷ" },
+ ["བྷ"]={ "བ", "ྷ" },
+ ["ཛྷ"]={ "ཛ", "ྷ" },
+ ["ཀྵ"]={ "ཀ", "ྵ" },
+ ["ཱི"]={ "ཱ", "ི" },
+ ["ཱུ"]={ "ཱ", "ུ" },
+ ["ྲྀ"]={ "ྲ", "ྀ" },
+ ["ླྀ"]={ "ླ", "ྀ" },
+ ["ཱྀ"]={ "ཱ", "ྀ" },
+ ["ྒྷ"]={ "ྒ", "ྷ" },
+ ["ྜྷ"]={ "ྜ", "ྷ" },
+ ["ྡྷ"]={ "ྡ", "ྷ" },
+ ["ྦྷ"]={ "ྦ", "ྷ" },
+ ["ྫྷ"]={ "ྫ", "ྷ" },
+ ["ྐྵ"]={ "ྐ", "ྵ" },
+ ["ဦ"]={ "ဥ", "ီ" },
+ ["ᬆ"]={ "ᬅ", "ᬵ" },
+ ["ᬈ"]={ "ᬇ", "ᬵ" },
+ ["ᬊ"]={ "ᬉ", "ᬵ" },
+ ["ᬌ"]={ "ᬋ", "ᬵ" },
+ ["ᬎ"]={ "ᬍ", "ᬵ" },
+ ["ᬒ"]={ "ᬑ", "ᬵ" },
+ ["ᬻ"]={ "ᬺ", "ᬵ" },
+ ["ᬽ"]={ "ᬼ", "ᬵ" },
+ ["ᭀ"]={ "ᬾ", "ᬵ" },
+ ["ᭁ"]={ "ᬿ", "ᬵ" },
+ ["ᭃ"]={ "ᭂ", "ᬵ" },
+ ["Ḁ"]={ "A", "̥" },
+ ["ḁ"]={ "a", "̥" },
+ ["Ḃ"]={ "B", "̇" },
+ ["ḃ"]={ "b", "̇" },
+ ["Ḅ"]={ "B", "̣" },
+ ["ḅ"]={ "b", "̣" },
+ ["Ḇ"]={ "B", "̱" },
+ ["ḇ"]={ "b", "̱" },
+ ["Ḉ"]={ "Ç", "́" },
+ ["ḉ"]={ "ç", "́" },
+ ["Ḋ"]={ "D", "̇" },
+ ["ḋ"]={ "d", "̇" },
+ ["Ḍ"]={ "D", "̣" },
+ ["ḍ"]={ "d", "̣" },
+ ["Ḏ"]={ "D", "̱" },
+ ["ḏ"]={ "d", "̱" },
+ ["Ḑ"]={ "D", "̧" },
+ ["ḑ"]={ "d", "̧" },
+ ["Ḓ"]={ "D", "̭" },
+ ["ḓ"]={ "d", "̭" },
+ ["Ḕ"]={ "Ē", "̀" },
+ ["ḕ"]={ "ē", "̀" },
+ ["Ḗ"]={ "Ē", "́" },
+ ["ḗ"]={ "ē", "́" },
+ ["Ḙ"]={ "E", "̭" },
+ ["ḙ"]={ "e", "̭" },
+ ["Ḛ"]={ "E", "̰" },
+ ["ḛ"]={ "e", "̰" },
+ ["Ḝ"]={ "Ȩ", "̆" },
+ ["ḝ"]={ "ȩ", "̆" },
+ ["Ḟ"]={ "F", "̇" },
+ ["ḟ"]={ "f", "̇" },
+ ["Ḡ"]={ "G", "̄" },
+ ["ḡ"]={ "g", "̄" },
+ ["Ḣ"]={ "H", "̇" },
+ ["ḣ"]={ "h", "̇" },
+ ["Ḥ"]={ "H", "̣" },
+ ["ḥ"]={ "h", "̣" },
+ ["Ḧ"]={ "H", "̈" },
+ ["ḧ"]={ "h", "̈" },
+ ["Ḩ"]={ "H", "̧" },
+ ["ḩ"]={ "h", "̧" },
+ ["Ḫ"]={ "H", "̮" },
+ ["ḫ"]={ "h", "̮" },
+ ["Ḭ"]={ "I", "̰" },
+ ["ḭ"]={ "i", "̰" },
+ ["Ḯ"]={ "Ï", "́" },
+ ["ḯ"]={ "ï", "́" },
+ ["Ḱ"]={ "K", "́" },
+ ["ḱ"]={ "k", "́" },
+ ["Ḳ"]={ "K", "̣" },
+ ["ḳ"]={ "k", "̣" },
+ ["Ḵ"]={ "K", "̱" },
+ ["ḵ"]={ "k", "̱" },
+ ["Ḷ"]={ "L", "̣" },
+ ["ḷ"]={ "l", "̣" },
+ ["Ḹ"]={ "Ḷ", "̄" },
+ ["ḹ"]={ "ḷ", "̄" },
+ ["Ḻ"]={ "L", "̱" },
+ ["ḻ"]={ "l", "̱" },
+ ["Ḽ"]={ "L", "̭" },
+ ["ḽ"]={ "l", "̭" },
+ ["Ḿ"]={ "M", "́" },
+ ["ḿ"]={ "m", "́" },
+ ["Ṁ"]={ "M", "̇" },
+ ["ṁ"]={ "m", "̇" },
+ ["Ṃ"]={ "M", "̣" },
+ ["ṃ"]={ "m", "̣" },
+ ["Ṅ"]={ "N", "̇" },
+ ["ṅ"]={ "n", "̇" },
+ ["Ṇ"]={ "N", "̣" },
+ ["ṇ"]={ "n", "̣" },
+ ["Ṉ"]={ "N", "̱" },
+ ["ṉ"]={ "n", "̱" },
+ ["Ṋ"]={ "N", "̭" },
+ ["ṋ"]={ "n", "̭" },
+ ["Ṍ"]={ "Õ", "́" },
+ ["ṍ"]={ "õ", "́" },
+ ["Ṏ"]={ "Õ", "̈" },
+ ["ṏ"]={ "õ", "̈" },
+ ["Ṑ"]={ "Ō", "̀" },
+ ["ṑ"]={ "ō", "̀" },
+ ["Ṓ"]={ "Ō", "́" },
+ ["ṓ"]={ "ō", "́" },
+ ["Ṕ"]={ "P", "́" },
+ ["ṕ"]={ "p", "́" },
+ ["Ṗ"]={ "P", "̇" },
+ ["ṗ"]={ "p", "̇" },
+ ["Ṙ"]={ "R", "̇" },
+ ["ṙ"]={ "r", "̇" },
+ ["Ṛ"]={ "R", "̣" },
+ ["ṛ"]={ "r", "̣" },
+ ["Ṝ"]={ "Ṛ", "̄" },
+ ["ṝ"]={ "ṛ", "̄" },
+ ["Ṟ"]={ "R", "̱" },
+ ["ṟ"]={ "r", "̱" },
+ ["Ṡ"]={ "S", "̇" },
+ ["ṡ"]={ "s", "̇" },
+ ["Ṣ"]={ "S", "̣" },
+ ["ṣ"]={ "s", "̣" },
+ ["Ṥ"]={ "Ś", "̇" },
+ ["ṥ"]={ "ś", "̇" },
+ ["Ṧ"]={ "Š", "̇" },
+ ["ṧ"]={ "š", "̇" },
+ ["Ṩ"]={ "Ṣ", "̇" },
+ ["ṩ"]={ "ṣ", "̇" },
+ ["Ṫ"]={ "T", "̇" },
+ ["ṫ"]={ "t", "̇" },
+ ["Ṭ"]={ "T", "̣" },
+ ["ṭ"]={ "t", "̣" },
+ ["Ṯ"]={ "T", "̱" },
+ ["ṯ"]={ "t", "̱" },
+ ["Ṱ"]={ "T", "̭" },
+ ["ṱ"]={ "t", "̭" },
+ ["Ṳ"]={ "U", "̤" },
+ ["ṳ"]={ "u", "̤" },
+ ["Ṵ"]={ "U", "̰" },
+ ["ṵ"]={ "u", "̰" },
+ ["Ṷ"]={ "U", "̭" },
+ ["ṷ"]={ "u", "̭" },
+ ["Ṹ"]={ "Ũ", "́" },
+ ["ṹ"]={ "ũ", "́" },
+ ["Ṻ"]={ "Ū", "̈" },
+ ["ṻ"]={ "ū", "̈" },
+ ["Ṽ"]={ "V", "̃" },
+ ["ṽ"]={ "v", "̃" },
+ ["Ṿ"]={ "V", "̣" },
+ ["ṿ"]={ "v", "̣" },
+ ["Ẁ"]={ "W", "̀" },
+ ["ẁ"]={ "w", "̀" },
+ ["Ẃ"]={ "W", "́" },
+ ["ẃ"]={ "w", "́" },
+ ["Ẅ"]={ "W", "̈" },
+ ["ẅ"]={ "w", "̈" },
+ ["Ẇ"]={ "W", "̇" },
+ ["ẇ"]={ "w", "̇" },
+ ["Ẉ"]={ "W", "̣" },
+ ["ẉ"]={ "w", "̣" },
+ ["Ẋ"]={ "X", "̇" },
+ ["ẋ"]={ "x", "̇" },
+ ["Ẍ"]={ "X", "̈" },
+ ["ẍ"]={ "x", "̈" },
+ ["Ẏ"]={ "Y", "̇" },
+ ["ẏ"]={ "y", "̇" },
+ ["Ẑ"]={ "Z", "̂" },
+ ["ẑ"]={ "z", "̂" },
+ ["Ẓ"]={ "Z", "̣" },
+ ["ẓ"]={ "z", "̣" },
+ ["Ẕ"]={ "Z", "̱" },
+ ["ẕ"]={ "z", "̱" },
+ ["ẖ"]={ "h", "̱" },
+ ["ẗ"]={ "t", "̈" },
+ ["ẘ"]={ "w", "̊" },
+ ["ẙ"]={ "y", "̊" },
+ ["ẛ"]={ "ſ", "̇" },
+ ["Ạ"]={ "A", "̣" },
+ ["ạ"]={ "a", "̣" },
+ ["Ả"]={ "A", "̉" },
+ ["ả"]={ "a", "̉" },
+ ["Ấ"]={ "Â", "́" },
+ ["ấ"]={ "â", "́" },
+ ["Ầ"]={ "Â", "̀" },
+ ["ầ"]={ "â", "̀" },
+ ["Ẩ"]={ "Â", "̉" },
+ ["ẩ"]={ "â", "̉" },
+ ["Ẫ"]={ "Â", "̃" },
+ ["ẫ"]={ "â", "̃" },
+ ["Ậ"]={ "Ạ", "̂" },
+ ["ậ"]={ "ạ", "̂" },
+ ["Ắ"]={ "Ă", "́" },
+ ["ắ"]={ "ă", "́" },
+ ["Ằ"]={ "Ă", "̀" },
+ ["ằ"]={ "ă", "̀" },
+ ["Ẳ"]={ "Ă", "̉" },
+ ["ẳ"]={ "ă", "̉" },
+ ["Ẵ"]={ "Ă", "̃" },
+ ["ẵ"]={ "ă", "̃" },
+ ["Ặ"]={ "Ạ", "̆" },
+ ["ặ"]={ "ạ", "̆" },
+ ["Ẹ"]={ "E", "̣" },
+ ["ẹ"]={ "e", "̣" },
+ ["Ẻ"]={ "E", "̉" },
+ ["ẻ"]={ "e", "̉" },
+ ["Ẽ"]={ "E", "̃" },
+ ["ẽ"]={ "e", "̃" },
+ ["Ế"]={ "Ê", "́" },
+ ["ế"]={ "ê", "́" },
+ ["Ề"]={ "Ê", "̀" },
+ ["ề"]={ "ê", "̀" },
+ ["Ể"]={ "Ê", "̉" },
+ ["ể"]={ "ê", "̉" },
+ ["Ễ"]={ "Ê", "̃" },
+ ["ễ"]={ "ê", "̃" },
+ ["Ệ"]={ "Ẹ", "̂" },
+ ["ệ"]={ "ẹ", "̂" },
+ ["Ỉ"]={ "I", "̉" },
+ ["ỉ"]={ "i", "̉" },
+ ["Ị"]={ "I", "̣" },
+ ["ị"]={ "i", "̣" },
+ ["Ọ"]={ "O", "̣" },
+ ["ọ"]={ "o", "̣" },
+ ["Ỏ"]={ "O", "̉" },
+ ["ỏ"]={ "o", "̉" },
+ ["Ố"]={ "Ô", "́" },
+ ["ố"]={ "ô", "́" },
+ ["Ồ"]={ "Ô", "̀" },
+ ["ồ"]={ "ô", "̀" },
+ ["Ổ"]={ "Ô", "̉" },
+ ["ổ"]={ "ô", "̉" },
+ ["Ỗ"]={ "Ô", "̃" },
+ ["ỗ"]={ "ô", "̃" },
+ ["Ộ"]={ "Ọ", "̂" },
+ ["ộ"]={ "ọ", "̂" },
+ ["Ớ"]={ "Ơ", "́" },
+ ["ớ"]={ "ơ", "́" },
+ ["Ờ"]={ "Ơ", "̀" },
+ ["ờ"]={ "ơ", "̀" },
+ ["Ở"]={ "Ơ", "̉" },
+ ["ở"]={ "ơ", "̉" },
+ ["Ỡ"]={ "Ơ", "̃" },
+ ["ỡ"]={ "ơ", "̃" },
+ ["Ợ"]={ "Ơ", "̣" },
+ ["ợ"]={ "ơ", "̣" },
+ ["Ụ"]={ "U", "̣" },
+ ["ụ"]={ "u", "̣" },
+ ["Ủ"]={ "U", "̉" },
+ ["ủ"]={ "u", "̉" },
+ ["Ứ"]={ "Ư", "́" },
+ ["ứ"]={ "ư", "́" },
+ ["Ừ"]={ "Ư", "̀" },
+ ["ừ"]={ "ư", "̀" },
+ ["Ử"]={ "Ư", "̉" },
+ ["ử"]={ "ư", "̉" },
+ ["Ữ"]={ "Ư", "̃" },
+ ["ữ"]={ "ư", "̃" },
+ ["Ự"]={ "Ư", "̣" },
+ ["ự"]={ "ư", "̣" },
+ ["Ỳ"]={ "Y", "̀" },
+ ["ỳ"]={ "y", "̀" },
+ ["Ỵ"]={ "Y", "̣" },
+ ["ỵ"]={ "y", "̣" },
+ ["Ỷ"]={ "Y", "̉" },
+ ["ỷ"]={ "y", "̉" },
+ ["Ỹ"]={ "Y", "̃" },
+ ["ỹ"]={ "y", "̃" },
+ ["ἀ"]={ "α", "̓" },
+ ["ἁ"]={ "α", "̔" },
+ ["ἂ"]={ "ἀ", "̀" },
+ ["ἃ"]={ "ἁ", "̀" },
+ ["ἄ"]={ "ἀ", "́" },
+ ["ἅ"]={ "ἁ", "́" },
+ ["ἆ"]={ "ἀ", "͂" },
+ ["ἇ"]={ "ἁ", "͂" },
+ ["Ἀ"]={ "Α", "̓" },
+ ["Ἁ"]={ "Α", "̔" },
+ ["Ἂ"]={ "Ἀ", "̀" },
+ ["Ἃ"]={ "Ἁ", "̀" },
+ ["Ἄ"]={ "Ἀ", "́" },
+ ["Ἅ"]={ "Ἁ", "́" },
+ ["Ἆ"]={ "Ἀ", "͂" },
+ ["Ἇ"]={ "Ἁ", "͂" },
+ ["ἐ"]={ "ε", "̓" },
+ ["ἑ"]={ "ε", "̔" },
+ ["ἒ"]={ "ἐ", "̀" },
+ ["ἓ"]={ "ἑ", "̀" },
+ ["ἔ"]={ "ἐ", "́" },
+ ["ἕ"]={ "ἑ", "́" },
+ ["Ἐ"]={ "Ε", "̓" },
+ ["Ἑ"]={ "Ε", "̔" },
+ ["Ἒ"]={ "Ἐ", "̀" },
+ ["Ἓ"]={ "Ἑ", "̀" },
+ ["Ἔ"]={ "Ἐ", "́" },
+ ["Ἕ"]={ "Ἑ", "́" },
+ ["ἠ"]={ "η", "̓" },
+ ["ἡ"]={ "η", "̔" },
+ ["ἢ"]={ "ἠ", "̀" },
+ ["ἣ"]={ "ἡ", "̀" },
+ ["ἤ"]={ "ἠ", "́" },
+ ["ἥ"]={ "ἡ", "́" },
+ ["ἦ"]={ "ἠ", "͂" },
+ ["ἧ"]={ "ἡ", "͂" },
+ ["Ἠ"]={ "Η", "̓" },
+ ["Ἡ"]={ "Η", "̔" },
+ ["Ἢ"]={ "Ἠ", "̀" },
+ ["Ἣ"]={ "Ἡ", "̀" },
+ ["Ἤ"]={ "Ἠ", "́" },
+ ["Ἥ"]={ "Ἡ", "́" },
+ ["Ἦ"]={ "Ἠ", "͂" },
+ ["Ἧ"]={ "Ἡ", "͂" },
+ ["ἰ"]={ "ι", "̓" },
+ ["ἱ"]={ "ι", "̔" },
+ ["ἲ"]={ "ἰ", "̀" },
+ ["ἳ"]={ "ἱ", "̀" },
+ ["ἴ"]={ "ἰ", "́" },
+ ["ἵ"]={ "ἱ", "́" },
+ ["ἶ"]={ "ἰ", "͂" },
+ ["ἷ"]={ "ἱ", "͂" },
+ ["Ἰ"]={ "Ι", "̓" },
+ ["Ἱ"]={ "Ι", "̔" },
+ ["Ἲ"]={ "Ἰ", "̀" },
+ ["Ἳ"]={ "Ἱ", "̀" },
+ ["Ἴ"]={ "Ἰ", "́" },
+ ["Ἵ"]={ "Ἱ", "́" },
+ ["Ἶ"]={ "Ἰ", "͂" },
+ ["Ἷ"]={ "Ἱ", "͂" },
+ ["ὀ"]={ "ο", "̓" },
+ ["ὁ"]={ "ο", "̔" },
+ ["ὂ"]={ "ὀ", "̀" },
+ ["ὃ"]={ "ὁ", "̀" },
+ ["ὄ"]={ "ὀ", "́" },
+ ["ὅ"]={ "ὁ", "́" },
+ ["Ὀ"]={ "Ο", "̓" },
+ ["Ὁ"]={ "Ο", "̔" },
+ ["Ὂ"]={ "Ὀ", "̀" },
+ ["Ὃ"]={ "Ὁ", "̀" },
+ ["Ὄ"]={ "Ὀ", "́" },
+ ["Ὅ"]={ "Ὁ", "́" },
+ ["ὐ"]={ "υ", "̓" },
+ ["ὑ"]={ "υ", "̔" },
+ ["ὒ"]={ "ὐ", "̀" },
+ ["ὓ"]={ "ὑ", "̀" },
+ ["ὔ"]={ "ὐ", "́" },
+ ["ὕ"]={ "ὑ", "́" },
+ ["ὖ"]={ "ὐ", "͂" },
+ ["ὗ"]={ "ὑ", "͂" },
+ ["Ὑ"]={ "Υ", "̔" },
+ ["Ὓ"]={ "Ὑ", "̀" },
+ ["Ὕ"]={ "Ὑ", "́" },
+ ["Ὗ"]={ "Ὑ", "͂" },
+ ["ὠ"]={ "ω", "̓" },
+ ["ὡ"]={ "ω", "̔" },
+ ["ὢ"]={ "ὠ", "̀" },
+ ["ὣ"]={ "ὡ", "̀" },
+ ["ὤ"]={ "ὠ", "́" },
+ ["ὥ"]={ "ὡ", "́" },
+ ["ὦ"]={ "ὠ", "͂" },
+ ["ὧ"]={ "ὡ", "͂" },
+ ["Ὠ"]={ "Ω", "̓" },
+ ["Ὡ"]={ "Ω", "̔" },
+ ["Ὢ"]={ "Ὠ", "̀" },
+ ["Ὣ"]={ "Ὡ", "̀" },
+ ["Ὤ"]={ "Ὠ", "́" },
+ ["Ὥ"]={ "Ὡ", "́" },
+ ["Ὦ"]={ "Ὠ", "͂" },
+ ["Ὧ"]={ "Ὡ", "͂" },
+ ["ὰ"]={ "α", "̀" },
+ ["ὲ"]={ "ε", "̀" },
+ ["ὴ"]={ "η", "̀" },
+ ["ὶ"]={ "ι", "̀" },
+ ["ὸ"]={ "ο", "̀" },
+ ["ὺ"]={ "υ", "̀" },
+ ["ὼ"]={ "ω", "̀" },
+ ["ᾀ"]={ "ἀ", "ͅ" },
+ ["ᾁ"]={ "ἁ", "ͅ" },
+ ["ᾂ"]={ "ἂ", "ͅ" },
+ ["ᾃ"]={ "ἃ", "ͅ" },
+ ["ᾄ"]={ "ἄ", "ͅ" },
+ ["ᾅ"]={ "ἅ", "ͅ" },
+ ["ᾆ"]={ "ἆ", "ͅ" },
+ ["ᾇ"]={ "ἇ", "ͅ" },
+ ["ᾈ"]={ "Ἀ", "ͅ" },
+ ["ᾉ"]={ "Ἁ", "ͅ" },
+ ["ᾊ"]={ "Ἂ", "ͅ" },
+ ["ᾋ"]={ "Ἃ", "ͅ" },
+ ["ᾌ"]={ "Ἄ", "ͅ" },
+ ["ᾍ"]={ "Ἅ", "ͅ" },
+ ["ᾎ"]={ "Ἆ", "ͅ" },
+ ["ᾏ"]={ "Ἇ", "ͅ" },
+ ["ᾐ"]={ "ἠ", "ͅ" },
+ ["ᾑ"]={ "ἡ", "ͅ" },
+ ["ᾒ"]={ "ἢ", "ͅ" },
+ ["ᾓ"]={ "ἣ", "ͅ" },
+ ["ᾔ"]={ "ἤ", "ͅ" },
+ ["ᾕ"]={ "ἥ", "ͅ" },
+ ["ᾖ"]={ "ἦ", "ͅ" },
+ ["ᾗ"]={ "ἧ", "ͅ" },
+ ["ᾘ"]={ "Ἠ", "ͅ" },
+ ["ᾙ"]={ "Ἡ", "ͅ" },
+ ["ᾚ"]={ "Ἢ", "ͅ" },
+ ["ᾛ"]={ "Ἣ", "ͅ" },
+ ["ᾜ"]={ "Ἤ", "ͅ" },
+ ["ᾝ"]={ "Ἥ", "ͅ" },
+ ["ᾞ"]={ "Ἦ", "ͅ" },
+ ["ᾟ"]={ "Ἧ", "ͅ" },
+ ["ᾠ"]={ "ὠ", "ͅ" },
+ ["ᾡ"]={ "ὡ", "ͅ" },
+ ["ᾢ"]={ "ὢ", "ͅ" },
+ ["ᾣ"]={ "ὣ", "ͅ" },
+ ["ᾤ"]={ "ὤ", "ͅ" },
+ ["ᾥ"]={ "ὥ", "ͅ" },
+ ["ᾦ"]={ "ὦ", "ͅ" },
+ ["ᾧ"]={ "ὧ", "ͅ" },
+ ["ᾨ"]={ "Ὠ", "ͅ" },
+ ["ᾩ"]={ "Ὡ", "ͅ" },
+ ["ᾪ"]={ "Ὢ", "ͅ" },
+ ["ᾫ"]={ "Ὣ", "ͅ" },
+ ["ᾬ"]={ "Ὤ", "ͅ" },
+ ["ᾭ"]={ "Ὥ", "ͅ" },
+ ["ᾮ"]={ "Ὦ", "ͅ" },
+ ["ᾯ"]={ "Ὧ", "ͅ" },
+ ["ᾰ"]={ "α", "̆" },
+ ["ᾱ"]={ "α", "̄" },
+ ["ᾲ"]={ "ὰ", "ͅ" },
+ ["ᾳ"]={ "α", "ͅ" },
+ ["ᾴ"]={ "ά", "ͅ" },
+ ["ᾶ"]={ "α", "͂" },
+ ["ᾷ"]={ "ᾶ", "ͅ" },
+ ["Ᾰ"]={ "Α", "̆" },
+ ["Ᾱ"]={ "Α", "̄" },
+ ["Ὰ"]={ "Α", "̀" },
+ ["ᾼ"]={ "Α", "ͅ" },
+ ["῁"]={ "¨", "͂" },
+ ["ῂ"]={ "ὴ", "ͅ" },
+ ["ῃ"]={ "η", "ͅ" },
+ ["ῄ"]={ "ή", "ͅ" },
+ ["ῆ"]={ "η", "͂" },
+ ["ῇ"]={ "ῆ", "ͅ" },
+ ["Ὲ"]={ "Ε", "̀" },
+ ["Ὴ"]={ "Η", "̀" },
+ ["ῌ"]={ "Η", "ͅ" },
+ ["῍"]={ "᾿", "̀" },
+ ["῎"]={ "᾿", "́" },
+ ["῏"]={ "᾿", "͂" },
+ ["ῐ"]={ "ι", "̆" },
+ ["ῑ"]={ "ι", "̄" },
+ ["ῒ"]={ "ϊ", "̀" },
+ ["ῖ"]={ "ι", "͂" },
+ ["ῗ"]={ "ϊ", "͂" },
+ ["Ῐ"]={ "Ι", "̆" },
+ ["Ῑ"]={ "Ι", "̄" },
+ ["Ὶ"]={ "Ι", "̀" },
+ ["῝"]={ "῾", "̀" },
+ ["῞"]={ "῾", "́" },
+ ["῟"]={ "῾", "͂" },
+ ["ῠ"]={ "υ", "̆" },
+ ["ῡ"]={ "υ", "̄" },
+ ["ῢ"]={ "ϋ", "̀" },
+ ["ῤ"]={ "ρ", "̓" },
+ ["ῥ"]={ "ρ", "̔" },
+ ["ῦ"]={ "υ", "͂" },
+ ["ῧ"]={ "ϋ", "͂" },
+ ["Ῠ"]={ "Υ", "̆" },
+ ["Ῡ"]={ "Υ", "̄" },
+ ["Ὺ"]={ "Υ", "̀" },
+ ["Ῥ"]={ "Ρ", "̔" },
+ ["῭"]={ "¨", "̀" },
+ ["ῲ"]={ "ὼ", "ͅ" },
+ ["ῳ"]={ "ω", "ͅ" },
+ ["ῴ"]={ "ώ", "ͅ" },
+ ["ῶ"]={ "ω", "͂" },
+ ["ῷ"]={ "ῶ", "ͅ" },
+ ["Ὸ"]={ "Ο", "̀" },
+ ["Ὼ"]={ "Ω", "̀" },
+ ["ῼ"]={ "Ω", "ͅ" },
+ ["↚"]={ "←", "̸" },
+ ["↛"]={ "→", "̸" },
+ ["↮"]={ "↔", "̸" },
+ ["⇍"]={ "⇐", "̸" },
+ ["⇎"]={ "⇔", "̸" },
+ ["⇏"]={ "⇒", "̸" },
+ ["∄"]={ "∃", "̸" },
+ ["∉"]={ "∈", "̸" },
+ ["∌"]={ "∋", "̸" },
+ ["∤"]={ "∣", "̸" },
+ ["∦"]={ "∥", "̸" },
+ ["≁"]={ "∼", "̸" },
+ ["≄"]={ "≃", "̸" },
+ ["≇"]={ "≅", "̸" },
+ ["≉"]={ "≈", "̸" },
+ ["≠"]={ "=", "̸" },
+ ["≢"]={ "≡", "̸" },
+ ["≭"]={ "≍", "̸" },
+ ["≮"]={ "<", "̸" },
+ ["≯"]={ ">", "̸" },
+ ["≰"]={ "≤", "̸" },
+ ["≱"]={ "≥", "̸" },
+ ["≴"]={ "≲", "̸" },
+ ["≵"]={ "≳", "̸" },
+ ["≸"]={ "≶", "̸" },
+ ["≹"]={ "≷", "̸" },
+ ["⊀"]={ "≺", "̸" },
+ ["⊁"]={ "≻", "̸" },
+ ["⊄"]={ "⊂", "̸" },
+ ["⊅"]={ "⊃", "̸" },
+ ["⊈"]={ "⊆", "̸" },
+ ["⊉"]={ "⊇", "̸" },
+ ["⊬"]={ "⊢", "̸" },
+ ["⊭"]={ "⊨", "̸" },
+ ["⊮"]={ "⊩", "̸" },
+ ["⊯"]={ "⊫", "̸" },
+ ["⋠"]={ "≼", "̸" },
+ ["⋡"]={ "≽", "̸" },
+ ["⋢"]={ "⊑", "̸" },
+ ["⋣"]={ "⊒", "̸" },
+ ["⋪"]={ "⊲", "̸" },
+ ["⋫"]={ "⊳", "̸" },
+ ["⋬"]={ "⊴", "̸" },
+ ["⋭"]={ "⊵", "̸" },
+ ["⫝̸"]={ "⫝", "̸" },
+ ["が"]={ "か", "゙" },
+ ["ぎ"]={ "き", "゙" },
+ ["ぐ"]={ "く", "゙" },
+ ["げ"]={ "け", "゙" },
+ ["ご"]={ "こ", "゙" },
+ ["ざ"]={ "さ", "゙" },
+ ["じ"]={ "し", "゙" },
+ ["ず"]={ "す", "゙" },
+ ["ぜ"]={ "せ", "゙" },
+ ["ぞ"]={ "そ", "゙" },
+ ["だ"]={ "た", "゙" },
+ ["ぢ"]={ "ち", "゙" },
+ ["づ"]={ "つ", "゙" },
+ ["で"]={ "て", "゙" },
+ ["ど"]={ "と", "゙" },
+ ["ば"]={ "は", "゙" },
+ ["ぱ"]={ "は", "゚" },
+ ["び"]={ "ひ", "゙" },
+ ["ぴ"]={ "ひ", "゚" },
+ ["ぶ"]={ "ふ", "゙" },
+ ["ぷ"]={ "ふ", "゚" },
+ ["べ"]={ "へ", "゙" },
+ ["ぺ"]={ "へ", "゚" },
+ ["ぼ"]={ "ほ", "゙" },
+ ["ぽ"]={ "ほ", "゚" },
+ ["ゔ"]={ "う", "゙" },
+ ["ゞ"]={ "ゝ", "゙" },
+ ["ガ"]={ "カ", "゙" },
+ ["ギ"]={ "キ", "゙" },
+ ["グ"]={ "ク", "゙" },
+ ["ゲ"]={ "ケ", "゙" },
+ ["ゴ"]={ "コ", "゙" },
+ ["ザ"]={ "サ", "゙" },
+ ["ジ"]={ "シ", "゙" },
+ ["ズ"]={ "ス", "゙" },
+ ["ゼ"]={ "セ", "゙" },
+ ["ゾ"]={ "ソ", "゙" },
+ ["ダ"]={ "タ", "゙" },
+ ["ヂ"]={ "チ", "゙" },
+ ["ヅ"]={ "ツ", "゙" },
+ ["デ"]={ "テ", "゙" },
+ ["ド"]={ "ト", "゙" },
+ ["バ"]={ "ハ", "゙" },
+ ["パ"]={ "ハ", "゚" },
+ ["ビ"]={ "ヒ", "゙" },
+ ["ピ"]={ "ヒ", "゚" },
+ ["ブ"]={ "フ", "゙" },
+ ["プ"]={ "フ", "゚" },
+ ["ベ"]={ "ヘ", "゙" },
+ ["ペ"]={ "ヘ", "゚" },
+ ["ボ"]={ "ホ", "゙" },
+ ["ポ"]={ "ホ", "゚" },
+ ["ヴ"]={ "ウ", "゙" },
+ ["ヷ"]={ "ワ", "゙" },
+ ["ヸ"]={ "ヰ", "゙" },
+ ["ヹ"]={ "ヱ", "゙" },
+ ["ヺ"]={ "ヲ", "゙" },
+ ["ヾ"]={ "ヽ", "゙" },
+ ["יִ"]={ "י", "ִ" },
+ ["ײַ"]={ "ײ", "ַ" },
+ ["שׁ"]={ "ש", "ׁ" },
+ ["שׂ"]={ "ש", "ׂ" },
+ ["שּׁ"]={ "שּ", "ׁ" },
+ ["שּׂ"]={ "שּ", "ׂ" },
+ ["אַ"]={ "א", "ַ" },
+ ["אָ"]={ "א", "ָ" },
+ ["אּ"]={ "א", "ּ" },
+ ["בּ"]={ "ב", "ּ" },
+ ["גּ"]={ "ג", "ּ" },
+ ["דּ"]={ "ד", "ּ" },
+ ["הּ"]={ "ה", "ּ" },
+ ["וּ"]={ "ו", "ּ" },
+ ["זּ"]={ "ז", "ּ" },
+ ["טּ"]={ "ט", "ּ" },
+ ["יּ"]={ "י", "ּ" },
+ ["ךּ"]={ "ך", "ּ" },
+ ["כּ"]={ "כ", "ּ" },
+ ["לּ"]={ "ל", "ּ" },
+ ["מּ"]={ "מ", "ּ" },
+ ["נּ"]={ "נ", "ּ" },
+ ["סּ"]={ "ס", "ּ" },
+ ["ףּ"]={ "ף", "ּ" },
+ ["פּ"]={ "פ", "ּ" },
+ ["צּ"]={ "צ", "ּ" },
+ ["קּ"]={ "ק", "ּ" },
+ ["רּ"]={ "ר", "ּ" },
+ ["שּ"]={ "ש", "ּ" },
+ ["תּ"]={ "ת", "ּ" },
+ ["וֹ"]={ "ו", "ֹ" },
+ ["בֿ"]={ "ב", "ֿ" },
+ ["כֿ"]={ "כ", "ֿ" },
+ ["פֿ"]={ "פ", "ֿ" },
+ ["𑂚"]={ "𑂙", "𑂺" },
+ ["𑂜"]={ "𑂛", "𑂺" },
+ ["𑂫"]={ "𑂥", "𑂺" },
+ ["𑄮"]={ "𑄱", "𑄧" },
+ ["𑄯"]={ "𑄲", "𑄧" },
+ ["𑍋"]={ "𑍇", "𑌾" },
+ ["𑍌"]={ "𑍇", "𑍗" },
+ ["𑒻"]={ "𑒹", "𑒺" },
+ ["𑒼"]={ "𑒹", "𑒰" },
+ ["𑒾"]={ "𑒹", "𑒽" },
+ ["𑖺"]={ "𑖸", "𑖯" },
+ ["𑖻"]={ "𑖹", "𑖯" },
+ ["𝅗𝅥"]={ "𝅗", "𝅥" },
+ ["𝅘𝅥"]={ "𝅘", "𝅥" },
+ ["𝅘𝅥𝅮"]={ "𝅘𝅥", "𝅮" },
+ ["𝅘𝅥𝅯"]={ "𝅘𝅥", "𝅯" },
+ ["𝅘𝅥𝅰"]={ "𝅘𝅥", "𝅰" },
+ ["𝅘𝅥𝅱"]={ "𝅘𝅥", "𝅱" },
+ ["𝅘𝅥𝅲"]={ "𝅘𝅥", "𝅲" },
+ ["𝆹𝅥"]={ "𝆹", "𝅥" },
+ ["𝆺𝅥"]={ "𝆺", "𝅥" },
+ ["𝆹𝅥𝅮"]={ "𝆹𝅥", "𝅮" },
+ ["𝆺𝅥𝅮"]={ "𝆺𝅥", "𝅮" },
+ ["𝆹𝅥𝅯"]={ "𝆹𝅥", "𝅯" },
+ ["𝆺𝅥𝅯"]={ "𝆺𝅥", "𝅯" },
+ },
+ },
+ {
+ ["data"]={
+ ["À"]={ "A", "̀" },
+ ["Á"]={ "A", "́" },
+ ["Â"]={ "A", "̂" },
+ ["Ã"]={ "A", "̃" },
+ ["Ä"]={ "A", "̈" },
+ ["Å"]={ "A", "̊" },
+ ["Ç"]={ "C", "̧" },
+ ["È"]={ "E", "̀" },
+ ["É"]={ "E", "́" },
+ ["Ê"]={ "E", "̂" },
+ ["Ë"]={ "E", "̈" },
+ ["Ì"]={ "I", "̀" },
+ ["Í"]={ "I", "́" },
+ ["Î"]={ "I", "̂" },
+ ["Ï"]={ "I", "̈" },
+ ["Ñ"]={ "N", "̃" },
+ ["Ò"]={ "O", "̀" },
+ ["Ó"]={ "O", "́" },
+ ["Ô"]={ "O", "̂" },
+ ["Õ"]={ "O", "̃" },
+ ["Ö"]={ "O", "̈" },
+ ["Ù"]={ "U", "̀" },
+ ["Ú"]={ "U", "́" },
+ ["Û"]={ "U", "̂" },
+ ["Ü"]={ "U", "̈" },
+ ["Ý"]={ "Y", "́" },
+ ["à"]={ "a", "̀" },
+ ["á"]={ "a", "́" },
+ ["â"]={ "a", "̂" },
+ ["ã"]={ "a", "̃" },
+ ["ä"]={ "a", "̈" },
+ ["å"]={ "a", "̊" },
+ ["ç"]={ "c", "̧" },
+ ["è"]={ "e", "̀" },
+ ["é"]={ "e", "́" },
+ ["ê"]={ "e", "̂" },
+ ["ë"]={ "e", "̈" },
+ ["ì"]={ "i", "̀" },
+ ["í"]={ "i", "́" },
+ ["î"]={ "i", "̂" },
+ ["ï"]={ "i", "̈" },
+ ["ñ"]={ "n", "̃" },
+ ["ò"]={ "o", "̀" },
+ ["ó"]={ "o", "́" },
+ ["ô"]={ "o", "̂" },
+ ["õ"]={ "o", "̃" },
+ ["ö"]={ "o", "̈" },
+ ["ù"]={ "u", "̀" },
+ ["ú"]={ "u", "́" },
+ ["û"]={ "u", "̂" },
+ ["ü"]={ "u", "̈" },
+ ["ý"]={ "y", "́" },
+ ["ÿ"]={ "y", "̈" },
+ ["Ā"]={ "A", "̄" },
+ ["ā"]={ "a", "̄" },
+ ["Ă"]={ "A", "̆" },
+ ["ă"]={ "a", "̆" },
+ ["Ą"]={ "A", "̨" },
+ ["ą"]={ "a", "̨" },
+ ["Ć"]={ "C", "́" },
+ ["ć"]={ "c", "́" },
+ ["Ĉ"]={ "C", "̂" },
+ ["ĉ"]={ "c", "̂" },
+ ["Ċ"]={ "C", "̇" },
+ ["ċ"]={ "c", "̇" },
+ ["Č"]={ "C", "̌" },
+ ["č"]={ "c", "̌" },
+ ["Ď"]={ "D", "̌" },
+ ["ď"]={ "d", "̌" },
+ ["Ē"]={ "E", "̄" },
+ ["ē"]={ "e", "̄" },
+ ["Ĕ"]={ "E", "̆" },
+ ["ĕ"]={ "e", "̆" },
+ ["Ė"]={ "E", "̇" },
+ ["ė"]={ "e", "̇" },
+ ["Ę"]={ "E", "̨" },
+ ["ę"]={ "e", "̨" },
+ ["Ě"]={ "E", "̌" },
+ ["ě"]={ "e", "̌" },
+ ["Ĝ"]={ "G", "̂" },
+ ["ĝ"]={ "g", "̂" },
+ ["Ğ"]={ "G", "̆" },
+ ["ğ"]={ "g", "̆" },
+ ["Ġ"]={ "G", "̇" },
+ ["ġ"]={ "g", "̇" },
+ ["Ģ"]={ "G", "̧" },
+ ["ģ"]={ "g", "̧" },
+ ["Ĥ"]={ "H", "̂" },
+ ["ĥ"]={ "h", "̂" },
+ ["Ĩ"]={ "I", "̃" },
+ ["ĩ"]={ "i", "̃" },
+ ["Ī"]={ "I", "̄" },
+ ["ī"]={ "i", "̄" },
+ ["Ĭ"]={ "I", "̆" },
+ ["ĭ"]={ "i", "̆" },
+ ["Į"]={ "I", "̨" },
+ ["į"]={ "i", "̨" },
+ ["İ"]={ "I", "̇" },
+ ["Ĵ"]={ "J", "̂" },
+ ["ĵ"]={ "j", "̂" },
+ ["Ķ"]={ "K", "̧" },
+ ["ķ"]={ "k", "̧" },
+ ["Ĺ"]={ "L", "́" },
+ ["ĺ"]={ "l", "́" },
+ ["Ļ"]={ "L", "̧" },
+ ["ļ"]={ "l", "̧" },
+ ["Ľ"]={ "L", "̌" },
+ ["ľ"]={ "l", "̌" },
+ ["Ń"]={ "N", "́" },
+ ["ń"]={ "n", "́" },
+ ["Ņ"]={ "N", "̧" },
+ ["ņ"]={ "n", "̧" },
+ ["Ň"]={ "N", "̌" },
+ ["ň"]={ "n", "̌" },
+ ["Ō"]={ "O", "̄" },
+ ["ō"]={ "o", "̄" },
+ ["Ŏ"]={ "O", "̆" },
+ ["ŏ"]={ "o", "̆" },
+ ["Ő"]={ "O", "̋" },
+ ["ő"]={ "o", "̋" },
+ ["Ŕ"]={ "R", "́" },
+ ["ŕ"]={ "r", "́" },
+ ["Ŗ"]={ "R", "̧" },
+ ["ŗ"]={ "r", "̧" },
+ ["Ř"]={ "R", "̌" },
+ ["ř"]={ "r", "̌" },
+ ["Ś"]={ "S", "́" },
+ ["ś"]={ "s", "́" },
+ ["Ŝ"]={ "S", "̂" },
+ ["ŝ"]={ "s", "̂" },
+ ["Ş"]={ "S", "̧" },
+ ["ş"]={ "s", "̧" },
+ ["Š"]={ "S", "̌" },
+ ["š"]={ "s", "̌" },
+ ["Ţ"]={ "T", "̧" },
+ ["ţ"]={ "t", "̧" },
+ ["Ť"]={ "T", "̌" },
+ ["ť"]={ "t", "̌" },
+ ["Ũ"]={ "U", "̃" },
+ ["ũ"]={ "u", "̃" },
+ ["Ū"]={ "U", "̄" },
+ ["ū"]={ "u", "̄" },
+ ["Ŭ"]={ "U", "̆" },
+ ["ŭ"]={ "u", "̆" },
+ ["Ů"]={ "U", "̊" },
+ ["ů"]={ "u", "̊" },
+ ["Ű"]={ "U", "̋" },
+ ["ű"]={ "u", "̋" },
+ ["Ų"]={ "U", "̨" },
+ ["ų"]={ "u", "̨" },
+ ["Ŵ"]={ "W", "̂" },
+ ["ŵ"]={ "w", "̂" },
+ ["Ŷ"]={ "Y", "̂" },
+ ["ŷ"]={ "y", "̂" },
+ ["Ÿ"]={ "Y", "̈" },
+ ["Ź"]={ "Z", "́" },
+ ["ź"]={ "z", "́" },
+ ["Ż"]={ "Z", "̇" },
+ ["ż"]={ "z", "̇" },
+ ["Ž"]={ "Z", "̌" },
+ ["ž"]={ "z", "̌" },
+ ["Ơ"]={ "O", "̛" },
+ ["ơ"]={ "o", "̛" },
+ ["Ư"]={ "U", "̛" },
+ ["ư"]={ "u", "̛" },
+ ["Ǎ"]={ "A", "̌" },
+ ["ǎ"]={ "a", "̌" },
+ ["Ǐ"]={ "I", "̌" },
+ ["ǐ"]={ "i", "̌" },
+ ["Ǒ"]={ "O", "̌" },
+ ["ǒ"]={ "o", "̌" },
+ ["Ǔ"]={ "U", "̌" },
+ ["ǔ"]={ "u", "̌" },
+ ["Ǖ"]={ "Ü", "̄" },
+ ["ǖ"]={ "ü", "̄" },
+ ["Ǘ"]={ "Ü", "́" },
+ ["ǘ"]={ "ü", "́" },
+ ["Ǚ"]={ "Ü", "̌" },
+ ["ǚ"]={ "ü", "̌" },
+ ["Ǜ"]={ "Ü", "̀" },
+ ["ǜ"]={ "ü", "̀" },
+ ["Ǟ"]={ "Ä", "̄" },
+ ["ǟ"]={ "ä", "̄" },
+ ["Ǡ"]={ "Ȧ", "̄" },
+ ["ǡ"]={ "ȧ", "̄" },
+ ["Ǣ"]={ "Æ", "̄" },
+ ["ǣ"]={ "æ", "̄" },
+ ["Ǧ"]={ "G", "̌" },
+ ["ǧ"]={ "g", "̌" },
+ ["Ǩ"]={ "K", "̌" },
+ ["ǩ"]={ "k", "̌" },
+ ["Ǫ"]={ "O", "̨" },
+ ["ǫ"]={ "o", "̨" },
+ ["Ǭ"]={ "Ǫ", "̄" },
+ ["ǭ"]={ "ǫ", "̄" },
+ ["Ǯ"]={ "Ʒ", "̌" },
+ ["ǯ"]={ "ʒ", "̌" },
+ ["ǰ"]={ "j", "̌" },
+ ["Ǵ"]={ "G", "́" },
+ ["ǵ"]={ "g", "́" },
+ ["Ǹ"]={ "N", "̀" },
+ ["ǹ"]={ "n", "̀" },
+ ["Ǻ"]={ "Å", "́" },
+ ["ǻ"]={ "å", "́" },
+ ["Ǽ"]={ "Æ", "́" },
+ ["ǽ"]={ "æ", "́" },
+ ["Ǿ"]={ "Ø", "́" },
+ ["ǿ"]={ "ø", "́" },
+ ["Ȁ"]={ "A", "̏" },
+ ["ȁ"]={ "a", "̏" },
+ ["Ȃ"]={ "A", "̑" },
+ ["ȃ"]={ "a", "̑" },
+ ["Ȅ"]={ "E", "̏" },
+ ["ȅ"]={ "e", "̏" },
+ ["Ȇ"]={ "E", "̑" },
+ ["ȇ"]={ "e", "̑" },
+ ["Ȉ"]={ "I", "̏" },
+ ["ȉ"]={ "i", "̏" },
+ ["Ȋ"]={ "I", "̑" },
+ ["ȋ"]={ "i", "̑" },
+ ["Ȍ"]={ "O", "̏" },
+ ["ȍ"]={ "o", "̏" },
+ ["Ȏ"]={ "O", "̑" },
+ ["ȏ"]={ "o", "̑" },
+ ["Ȑ"]={ "R", "̏" },
+ ["ȑ"]={ "r", "̏" },
+ ["Ȓ"]={ "R", "̑" },
+ ["ȓ"]={ "r", "̑" },
+ ["Ȕ"]={ "U", "̏" },
+ ["ȕ"]={ "u", "̏" },
+ ["Ȗ"]={ "U", "̑" },
+ ["ȗ"]={ "u", "̑" },
+ ["Ș"]={ "S", "̦" },
+ ["ș"]={ "s", "̦" },
+ ["Ț"]={ "T", "̦" },
+ ["ț"]={ "t", "̦" },
+ ["Ȟ"]={ "H", "̌" },
+ ["ȟ"]={ "h", "̌" },
+ ["Ȧ"]={ "A", "̇" },
+ ["ȧ"]={ "a", "̇" },
+ ["Ȩ"]={ "E", "̧" },
+ ["ȩ"]={ "e", "̧" },
+ ["Ȫ"]={ "Ö", "̄" },
+ ["ȫ"]={ "ö", "̄" },
+ ["Ȭ"]={ "Õ", "̄" },
+ ["ȭ"]={ "õ", "̄" },
+ ["Ȯ"]={ "O", "̇" },
+ ["ȯ"]={ "o", "̇" },
+ ["Ȱ"]={ "Ȯ", "̄" },
+ ["ȱ"]={ "ȯ", "̄" },
+ ["Ȳ"]={ "Y", "̄" },
+ ["ȳ"]={ "y", "̄" },
+ ["̈́"]={ "̈", "́" },
+ ["΅"]={ "¨", "́" },
+ ["Ά"]={ "Α", "́" },
+ ["Έ"]={ "Ε", "́" },
+ ["Ή"]={ "Η", "́" },
+ ["Ί"]={ "Ι", "́" },
+ ["Ό"]={ "Ο", "́" },
+ ["Ύ"]={ "Υ", "́" },
+ ["Ώ"]={ "Ω", "́" },
+ ["ΐ"]={ "ϊ", "́" },
+ ["Ϊ"]={ "Ι", "̈" },
+ ["Ϋ"]={ "Υ", "̈" },
+ ["ά"]={ "α", "́" },
+ ["έ"]={ "ε", "́" },
+ ["ή"]={ "η", "́" },
+ ["ί"]={ "ι", "́" },
+ ["ΰ"]={ "ϋ", "́" },
+ ["ϊ"]={ "ι", "̈" },
+ ["ϋ"]={ "υ", "̈" },
+ ["ό"]={ "ο", "́" },
+ ["ύ"]={ "υ", "́" },
+ ["ώ"]={ "ω", "́" },
+ ["ϓ"]={ "ϒ", "́" },
+ ["ϔ"]={ "ϒ", "̈" },
+ ["Ѐ"]={ "Е", "̀" },
+ ["Ё"]={ "Е", "̈" },
+ ["Ѓ"]={ "Г", "́" },
+ ["Ї"]={ "І", "̈" },
+ ["Ќ"]={ "К", "́" },
+ ["Ѝ"]={ "И", "̀" },
+ ["Ў"]={ "У", "̆" },
+ ["Й"]={ "И", "̆" },
+ ["й"]={ "и", "̆" },
+ ["ѐ"]={ "е", "̀" },
+ ["ё"]={ "е", "̈" },
+ ["ѓ"]={ "г", "́" },
+ ["ї"]={ "і", "̈" },
+ ["ќ"]={ "к", "́" },
+ ["ѝ"]={ "и", "̀" },
+ ["ў"]={ "у", "̆" },
+ ["Ѷ"]={ "Ѵ", "̏" },
+ ["ѷ"]={ "ѵ", "̏" },
+ ["Ӂ"]={ "Ж", "̆" },
+ ["ӂ"]={ "ж", "̆" },
+ ["Ӑ"]={ "А", "̆" },
+ ["ӑ"]={ "а", "̆" },
+ ["Ӓ"]={ "А", "̈" },
+ ["ӓ"]={ "а", "̈" },
+ ["Ӗ"]={ "Е", "̆" },
+ ["ӗ"]={ "е", "̆" },
+ ["Ӛ"]={ "Ә", "̈" },
+ ["ӛ"]={ "ә", "̈" },
+ ["Ӝ"]={ "Ж", "̈" },
+ ["ӝ"]={ "ж", "̈" },
+ ["Ӟ"]={ "З", "̈" },
+ ["ӟ"]={ "з", "̈" },
+ ["Ӣ"]={ "И", "̄" },
+ ["ӣ"]={ "и", "̄" },
+ ["Ӥ"]={ "И", "̈" },
+ ["ӥ"]={ "и", "̈" },
+ ["Ӧ"]={ "О", "̈" },
+ ["ӧ"]={ "о", "̈" },
+ ["Ӫ"]={ "Ө", "̈" },
+ ["ӫ"]={ "ө", "̈" },
+ ["Ӭ"]={ "Э", "̈" },
+ ["ӭ"]={ "э", "̈" },
+ ["Ӯ"]={ "У", "̄" },
+ ["ӯ"]={ "у", "̄" },
+ ["Ӱ"]={ "У", "̈" },
+ ["ӱ"]={ "у", "̈" },
+ ["Ӳ"]={ "У", "̋" },
+ ["ӳ"]={ "у", "̋" },
+ ["Ӵ"]={ "Ч", "̈" },
+ ["ӵ"]={ "ч", "̈" },
+ ["Ӹ"]={ "Ы", "̈" },
+ ["ӹ"]={ "ы", "̈" },
+ ["آ"]={ "ا", "ٓ" },
+ ["أ"]={ "ا", "ٔ" },
+ ["ؤ"]={ "و", "ٔ" },
+ ["إ"]={ "ا", "ٕ" },
+ ["ئ"]={ "ي", "ٔ" },
+ ["ۀ"]={ "ە", "ٔ" },
+ ["ۂ"]={ "ہ", "ٔ" },
+ ["ۓ"]={ "ے", "ٔ" },
+ ["ऩ"]={ "न", "़" },
+ ["ऱ"]={ "र", "़" },
+ ["ऴ"]={ "ळ", "़" },
+ ["क़"]={ "क", "़" },
+ ["ख़"]={ "ख", "़" },
+ ["ग़"]={ "ग", "़" },
+ ["ज़"]={ "ज", "़" },
+ ["ड़"]={ "ड", "़" },
+ ["ढ़"]={ "ढ", "़" },
+ ["फ़"]={ "फ", "़" },
+ ["य़"]={ "य", "़" },
+ ["ো"]={ "ে", "া" },
+ ["ৌ"]={ "ে", "ৗ" },
+ ["ড়"]={ "ড", "়" },
+ ["ঢ়"]={ "ঢ", "়" },
+ ["য়"]={ "য", "়" },
+ ["ਲ਼"]={ "ਲ", "਼" },
+ ["ਸ਼"]={ "ਸ", "਼" },
+ ["ਖ਼"]={ "ਖ", "਼" },
+ ["ਗ਼"]={ "ਗ", "਼" },
+ ["ਜ਼"]={ "ਜ", "਼" },
+ ["ਫ਼"]={ "ਫ", "਼" },
+ ["ୈ"]={ "େ", "ୖ" },
+ ["ୋ"]={ "େ", "ା" },
+ ["ୌ"]={ "େ", "ୗ" },
+ ["ଡ଼"]={ "ଡ", "଼" },
+ ["ଢ଼"]={ "ଢ", "଼" },
+ ["ஔ"]={ "ஒ", "ௗ" },
+ ["ொ"]={ "ெ", "ா" },
+ ["ோ"]={ "ே", "ா" },
+ ["ௌ"]={ "ெ", "ௗ" },
+ ["ై"]={ "ె", "ౖ" },
+ ["ೀ"]={ "ಿ", "ೕ" },
+ ["ೇ"]={ "ೆ", "ೕ" },
+ ["ೈ"]={ "ೆ", "ೖ" },
+ ["ೊ"]={ "ೆ", "ೂ" },
+ ["ೋ"]={ "ೊ", "ೕ" },
+ ["ൊ"]={ "െ", "ാ" },
+ ["ോ"]={ "േ", "ാ" },
+ ["ൌ"]={ "െ", "ൗ" },
+ ["ේ"]={ "ෙ", "්" },
+ ["ො"]={ "ෙ", "ා" },
+ ["ෝ"]={ "ො", "්" },
+ ["ෞ"]={ "ෙ", "ෟ" },
+ ["གྷ"]={ "ག", "ྷ" },
+ ["ཌྷ"]={ "ཌ", "ྷ" },
+ ["དྷ"]={ "ད", "ྷ" },
+ ["བྷ"]={ "བ", "ྷ" },
+ ["ཛྷ"]={ "ཛ", "ྷ" },
+ ["ཀྵ"]={ "ཀ", "ྵ" },
+ ["ཱི"]={ "ཱ", "ི" },
+ ["ཱུ"]={ "ཱ", "ུ" },
+ ["ྲྀ"]={ "ྲ", "ྀ" },
+ ["ླྀ"]={ "ླ", "ྀ" },
+ ["ཱྀ"]={ "ཱ", "ྀ" },
+ ["ྒྷ"]={ "ྒ", "ྷ" },
+ ["ྜྷ"]={ "ྜ", "ྷ" },
+ ["ྡྷ"]={ "ྡ", "ྷ" },
+ ["ྦྷ"]={ "ྦ", "ྷ" },
+ ["ྫྷ"]={ "ྫ", "ྷ" },
+ ["ྐྵ"]={ "ྐ", "ྵ" },
+ ["ဦ"]={ "ဥ", "ီ" },
+ ["ᬆ"]={ "ᬅ", "ᬵ" },
+ ["ᬈ"]={ "ᬇ", "ᬵ" },
+ ["ᬊ"]={ "ᬉ", "ᬵ" },
+ ["ᬌ"]={ "ᬋ", "ᬵ" },
+ ["ᬎ"]={ "ᬍ", "ᬵ" },
+ ["ᬒ"]={ "ᬑ", "ᬵ" },
+ ["ᬻ"]={ "ᬺ", "ᬵ" },
+ ["ᬽ"]={ "ᬼ", "ᬵ" },
+ ["ᭀ"]={ "ᬾ", "ᬵ" },
+ ["ᭁ"]={ "ᬿ", "ᬵ" },
+ ["ᭃ"]={ "ᭂ", "ᬵ" },
+ ["Ḁ"]={ "A", "̥" },
+ ["ḁ"]={ "a", "̥" },
+ ["Ḃ"]={ "B", "̇" },
+ ["ḃ"]={ "b", "̇" },
+ ["Ḅ"]={ "B", "̣" },
+ ["ḅ"]={ "b", "̣" },
+ ["Ḇ"]={ "B", "̱" },
+ ["ḇ"]={ "b", "̱" },
+ ["Ḉ"]={ "Ç", "́" },
+ ["ḉ"]={ "ç", "́" },
+ ["Ḋ"]={ "D", "̇" },
+ ["ḋ"]={ "d", "̇" },
+ ["Ḍ"]={ "D", "̣" },
+ ["ḍ"]={ "d", "̣" },
+ ["Ḏ"]={ "D", "̱" },
+ ["ḏ"]={ "d", "̱" },
+ ["Ḑ"]={ "D", "̧" },
+ ["ḑ"]={ "d", "̧" },
+ ["Ḓ"]={ "D", "̭" },
+ ["ḓ"]={ "d", "̭" },
+ ["Ḕ"]={ "Ē", "̀" },
+ ["ḕ"]={ "ē", "̀" },
+ ["Ḗ"]={ "Ē", "́" },
+ ["ḗ"]={ "ē", "́" },
+ ["Ḙ"]={ "E", "̭" },
+ ["ḙ"]={ "e", "̭" },
+ ["Ḛ"]={ "E", "̰" },
+ ["ḛ"]={ "e", "̰" },
+ ["Ḝ"]={ "Ȩ", "̆" },
+ ["ḝ"]={ "ȩ", "̆" },
+ ["Ḟ"]={ "F", "̇" },
+ ["ḟ"]={ "f", "̇" },
+ ["Ḡ"]={ "G", "̄" },
+ ["ḡ"]={ "g", "̄" },
+ ["Ḣ"]={ "H", "̇" },
+ ["ḣ"]={ "h", "̇" },
+ ["Ḥ"]={ "H", "̣" },
+ ["ḥ"]={ "h", "̣" },
+ ["Ḧ"]={ "H", "̈" },
+ ["ḧ"]={ "h", "̈" },
+ ["Ḩ"]={ "H", "̧" },
+ ["ḩ"]={ "h", "̧" },
+ ["Ḫ"]={ "H", "̮" },
+ ["ḫ"]={ "h", "̮" },
+ ["Ḭ"]={ "I", "̰" },
+ ["ḭ"]={ "i", "̰" },
+ ["Ḯ"]={ "Ï", "́" },
+ ["ḯ"]={ "ï", "́" },
+ ["Ḱ"]={ "K", "́" },
+ ["ḱ"]={ "k", "́" },
+ ["Ḳ"]={ "K", "̣" },
+ ["ḳ"]={ "k", "̣" },
+ ["Ḵ"]={ "K", "̱" },
+ ["ḵ"]={ "k", "̱" },
+ ["Ḷ"]={ "L", "̣" },
+ ["ḷ"]={ "l", "̣" },
+ ["Ḹ"]={ "Ḷ", "̄" },
+ ["ḹ"]={ "ḷ", "̄" },
+ ["Ḻ"]={ "L", "̱" },
+ ["ḻ"]={ "l", "̱" },
+ ["Ḽ"]={ "L", "̭" },
+ ["ḽ"]={ "l", "̭" },
+ ["Ḿ"]={ "M", "́" },
+ ["ḿ"]={ "m", "́" },
+ ["Ṁ"]={ "M", "̇" },
+ ["ṁ"]={ "m", "̇" },
+ ["Ṃ"]={ "M", "̣" },
+ ["ṃ"]={ "m", "̣" },
+ ["Ṅ"]={ "N", "̇" },
+ ["ṅ"]={ "n", "̇" },
+ ["Ṇ"]={ "N", "̣" },
+ ["ṇ"]={ "n", "̣" },
+ ["Ṉ"]={ "N", "̱" },
+ ["ṉ"]={ "n", "̱" },
+ ["Ṋ"]={ "N", "̭" },
+ ["ṋ"]={ "n", "̭" },
+ ["Ṍ"]={ "Õ", "́" },
+ ["ṍ"]={ "õ", "́" },
+ ["Ṏ"]={ "Õ", "̈" },
+ ["ṏ"]={ "õ", "̈" },
+ ["Ṑ"]={ "Ō", "̀" },
+ ["ṑ"]={ "ō", "̀" },
+ ["Ṓ"]={ "Ō", "́" },
+ ["ṓ"]={ "ō", "́" },
+ ["Ṕ"]={ "P", "́" },
+ ["ṕ"]={ "p", "́" },
+ ["Ṗ"]={ "P", "̇" },
+ ["ṗ"]={ "p", "̇" },
+ ["Ṙ"]={ "R", "̇" },
+ ["ṙ"]={ "r", "̇" },
+ ["Ṛ"]={ "R", "̣" },
+ ["ṛ"]={ "r", "̣" },
+ ["Ṝ"]={ "Ṛ", "̄" },
+ ["ṝ"]={ "ṛ", "̄" },
+ ["Ṟ"]={ "R", "̱" },
+ ["ṟ"]={ "r", "̱" },
+ ["Ṡ"]={ "S", "̇" },
+ ["ṡ"]={ "s", "̇" },
+ ["Ṣ"]={ "S", "̣" },
+ ["ṣ"]={ "s", "̣" },
+ ["Ṥ"]={ "Ś", "̇" },
+ ["ṥ"]={ "ś", "̇" },
+ ["Ṧ"]={ "Š", "̇" },
+ ["ṧ"]={ "š", "̇" },
+ ["Ṩ"]={ "Ṣ", "̇" },
+ ["ṩ"]={ "ṣ", "̇" },
+ ["Ṫ"]={ "T", "̇" },
+ ["ṫ"]={ "t", "̇" },
+ ["Ṭ"]={ "T", "̣" },
+ ["ṭ"]={ "t", "̣" },
+ ["Ṯ"]={ "T", "̱" },
+ ["ṯ"]={ "t", "̱" },
+ ["Ṱ"]={ "T", "̭" },
+ ["ṱ"]={ "t", "̭" },
+ ["Ṳ"]={ "U", "̤" },
+ ["ṳ"]={ "u", "̤" },
+ ["Ṵ"]={ "U", "̰" },
+ ["ṵ"]={ "u", "̰" },
+ ["Ṷ"]={ "U", "̭" },
+ ["ṷ"]={ "u", "̭" },
+ ["Ṹ"]={ "Ũ", "́" },
+ ["ṹ"]={ "ũ", "́" },
+ ["Ṻ"]={ "Ū", "̈" },
+ ["ṻ"]={ "ū", "̈" },
+ ["Ṽ"]={ "V", "̃" },
+ ["ṽ"]={ "v", "̃" },
+ ["Ṿ"]={ "V", "̣" },
+ ["ṿ"]={ "v", "̣" },
+ ["Ẁ"]={ "W", "̀" },
+ ["ẁ"]={ "w", "̀" },
+ ["Ẃ"]={ "W", "́" },
+ ["ẃ"]={ "w", "́" },
+ ["Ẅ"]={ "W", "̈" },
+ ["ẅ"]={ "w", "̈" },
+ ["Ẇ"]={ "W", "̇" },
+ ["ẇ"]={ "w", "̇" },
+ ["Ẉ"]={ "W", "̣" },
+ ["ẉ"]={ "w", "̣" },
+ ["Ẋ"]={ "X", "̇" },
+ ["ẋ"]={ "x", "̇" },
+ ["Ẍ"]={ "X", "̈" },
+ ["ẍ"]={ "x", "̈" },
+ ["Ẏ"]={ "Y", "̇" },
+ ["ẏ"]={ "y", "̇" },
+ ["Ẑ"]={ "Z", "̂" },
+ ["ẑ"]={ "z", "̂" },
+ ["Ẓ"]={ "Z", "̣" },
+ ["ẓ"]={ "z", "̣" },
+ ["Ẕ"]={ "Z", "̱" },
+ ["ẕ"]={ "z", "̱" },
+ ["ẖ"]={ "h", "̱" },
+ ["ẗ"]={ "t", "̈" },
+ ["ẘ"]={ "w", "̊" },
+ ["ẙ"]={ "y", "̊" },
+ ["ẛ"]={ "ſ", "̇" },
+ ["Ạ"]={ "A", "̣" },
+ ["ạ"]={ "a", "̣" },
+ ["Ả"]={ "A", "̉" },
+ ["ả"]={ "a", "̉" },
+ ["Ấ"]={ "Â", "́" },
+ ["ấ"]={ "â", "́" },
+ ["Ầ"]={ "Â", "̀" },
+ ["ầ"]={ "â", "̀" },
+ ["Ẩ"]={ "Â", "̉" },
+ ["ẩ"]={ "â", "̉" },
+ ["Ẫ"]={ "Â", "̃" },
+ ["ẫ"]={ "â", "̃" },
+ ["Ậ"]={ "Ạ", "̂" },
+ ["ậ"]={ "ạ", "̂" },
+ ["Ắ"]={ "Ă", "́" },
+ ["ắ"]={ "ă", "́" },
+ ["Ằ"]={ "Ă", "̀" },
+ ["ằ"]={ "ă", "̀" },
+ ["Ẳ"]={ "Ă", "̉" },
+ ["ẳ"]={ "ă", "̉" },
+ ["Ẵ"]={ "Ă", "̃" },
+ ["ẵ"]={ "ă", "̃" },
+ ["Ặ"]={ "Ạ", "̆" },
+ ["ặ"]={ "ạ", "̆" },
+ ["Ẹ"]={ "E", "̣" },
+ ["ẹ"]={ "e", "̣" },
+ ["Ẻ"]={ "E", "̉" },
+ ["ẻ"]={ "e", "̉" },
+ ["Ẽ"]={ "E", "̃" },
+ ["ẽ"]={ "e", "̃" },
+ ["Ế"]={ "Ê", "́" },
+ ["ế"]={ "ê", "́" },
+ ["Ề"]={ "Ê", "̀" },
+ ["ề"]={ "ê", "̀" },
+ ["Ể"]={ "Ê", "̉" },
+ ["ể"]={ "ê", "̉" },
+ ["Ễ"]={ "Ê", "̃" },
+ ["ễ"]={ "ê", "̃" },
+ ["Ệ"]={ "Ẹ", "̂" },
+ ["ệ"]={ "ẹ", "̂" },
+ ["Ỉ"]={ "I", "̉" },
+ ["ỉ"]={ "i", "̉" },
+ ["Ị"]={ "I", "̣" },
+ ["ị"]={ "i", "̣" },
+ ["Ọ"]={ "O", "̣" },
+ ["ọ"]={ "o", "̣" },
+ ["Ỏ"]={ "O", "̉" },
+ ["ỏ"]={ "o", "̉" },
+ ["Ố"]={ "Ô", "́" },
+ ["ố"]={ "ô", "́" },
+ ["Ồ"]={ "Ô", "̀" },
+ ["ồ"]={ "ô", "̀" },
+ ["Ổ"]={ "Ô", "̉" },
+ ["ổ"]={ "ô", "̉" },
+ ["Ỗ"]={ "Ô", "̃" },
+ ["ỗ"]={ "ô", "̃" },
+ ["Ộ"]={ "Ọ", "̂" },
+ ["ộ"]={ "ọ", "̂" },
+ ["Ớ"]={ "Ơ", "́" },
+ ["ớ"]={ "ơ", "́" },
+ ["Ờ"]={ "Ơ", "̀" },
+ ["ờ"]={ "ơ", "̀" },
+ ["Ở"]={ "Ơ", "̉" },
+ ["ở"]={ "ơ", "̉" },
+ ["Ỡ"]={ "Ơ", "̃" },
+ ["ỡ"]={ "ơ", "̃" },
+ ["Ợ"]={ "Ơ", "̣" },
+ ["ợ"]={ "ơ", "̣" },
+ ["Ụ"]={ "U", "̣" },
+ ["ụ"]={ "u", "̣" },
+ ["Ủ"]={ "U", "̉" },
+ ["ủ"]={ "u", "̉" },
+ ["Ứ"]={ "Ư", "́" },
+ ["ứ"]={ "ư", "́" },
+ ["Ừ"]={ "Ư", "̀" },
+ ["ừ"]={ "ư", "̀" },
+ ["Ử"]={ "Ư", "̉" },
+ ["ử"]={ "ư", "̉" },
+ ["Ữ"]={ "Ư", "̃" },
+ ["ữ"]={ "ư", "̃" },
+ ["Ự"]={ "Ư", "̣" },
+ ["ự"]={ "ư", "̣" },
+ ["Ỳ"]={ "Y", "̀" },
+ ["ỳ"]={ "y", "̀" },
+ ["Ỵ"]={ "Y", "̣" },
+ ["ỵ"]={ "y", "̣" },
+ ["Ỷ"]={ "Y", "̉" },
+ ["ỷ"]={ "y", "̉" },
+ ["Ỹ"]={ "Y", "̃" },
+ ["ỹ"]={ "y", "̃" },
+ ["ἀ"]={ "α", "̓" },
+ ["ἁ"]={ "α", "̔" },
+ ["ἂ"]={ "ἀ", "̀" },
+ ["ἃ"]={ "ἁ", "̀" },
+ ["ἄ"]={ "ἀ", "́" },
+ ["ἅ"]={ "ἁ", "́" },
+ ["ἆ"]={ "ἀ", "͂" },
+ ["ἇ"]={ "ἁ", "͂" },
+ ["Ἀ"]={ "Α", "̓" },
+ ["Ἁ"]={ "Α", "̔" },
+ ["Ἂ"]={ "Ἀ", "̀" },
+ ["Ἃ"]={ "Ἁ", "̀" },
+ ["Ἄ"]={ "Ἀ", "́" },
+ ["Ἅ"]={ "Ἁ", "́" },
+ ["Ἆ"]={ "Ἀ", "͂" },
+ ["Ἇ"]={ "Ἁ", "͂" },
+ ["ἐ"]={ "ε", "̓" },
+ ["ἑ"]={ "ε", "̔" },
+ ["ἒ"]={ "ἐ", "̀" },
+ ["ἓ"]={ "ἑ", "̀" },
+ ["ἔ"]={ "ἐ", "́" },
+ ["ἕ"]={ "ἑ", "́" },
+ ["Ἐ"]={ "Ε", "̓" },
+ ["Ἑ"]={ "Ε", "̔" },
+ ["Ἒ"]={ "Ἐ", "̀" },
+ ["Ἓ"]={ "Ἑ", "̀" },
+ ["Ἔ"]={ "Ἐ", "́" },
+ ["Ἕ"]={ "Ἑ", "́" },
+ ["ἠ"]={ "η", "̓" },
+ ["ἡ"]={ "η", "̔" },
+ ["ἢ"]={ "ἠ", "̀" },
+ ["ἣ"]={ "ἡ", "̀" },
+ ["ἤ"]={ "ἠ", "́" },
+ ["ἥ"]={ "ἡ", "́" },
+ ["ἦ"]={ "ἠ", "͂" },
+ ["ἧ"]={ "ἡ", "͂" },
+ ["Ἠ"]={ "Η", "̓" },
+ ["Ἡ"]={ "Η", "̔" },
+ ["Ἢ"]={ "Ἠ", "̀" },
+ ["Ἣ"]={ "Ἡ", "̀" },
+ ["Ἤ"]={ "Ἠ", "́" },
+ ["Ἥ"]={ "Ἡ", "́" },
+ ["Ἦ"]={ "Ἠ", "͂" },
+ ["Ἧ"]={ "Ἡ", "͂" },
+ ["ἰ"]={ "ι", "̓" },
+ ["ἱ"]={ "ι", "̔" },
+ ["ἲ"]={ "ἰ", "̀" },
+ ["ἳ"]={ "ἱ", "̀" },
+ ["ἴ"]={ "ἰ", "́" },
+ ["ἵ"]={ "ἱ", "́" },
+ ["ἶ"]={ "ἰ", "͂" },
+ ["ἷ"]={ "ἱ", "͂" },
+ ["Ἰ"]={ "Ι", "̓" },
+ ["Ἱ"]={ "Ι", "̔" },
+ ["Ἲ"]={ "Ἰ", "̀" },
+ ["Ἳ"]={ "Ἱ", "̀" },
+ ["Ἴ"]={ "Ἰ", "́" },
+ ["Ἵ"]={ "Ἱ", "́" },
+ ["Ἶ"]={ "Ἰ", "͂" },
+ ["Ἷ"]={ "Ἱ", "͂" },
+ ["ὀ"]={ "ο", "̓" },
+ ["ὁ"]={ "ο", "̔" },
+ ["ὂ"]={ "ὀ", "̀" },
+ ["ὃ"]={ "ὁ", "̀" },
+ ["ὄ"]={ "ὀ", "́" },
+ ["ὅ"]={ "ὁ", "́" },
+ ["Ὀ"]={ "Ο", "̓" },
+ ["Ὁ"]={ "Ο", "̔" },
+ ["Ὂ"]={ "Ὀ", "̀" },
+ ["Ὃ"]={ "Ὁ", "̀" },
+ ["Ὄ"]={ "Ὀ", "́" },
+ ["Ὅ"]={ "Ὁ", "́" },
+ ["ὐ"]={ "υ", "̓" },
+ ["ὑ"]={ "υ", "̔" },
+ ["ὒ"]={ "ὐ", "̀" },
+ ["ὓ"]={ "ὑ", "̀" },
+ ["ὔ"]={ "ὐ", "́" },
+ ["ὕ"]={ "ὑ", "́" },
+ ["ὖ"]={ "ὐ", "͂" },
+ ["ὗ"]={ "ὑ", "͂" },
+ ["Ὑ"]={ "Υ", "̔" },
+ ["Ὓ"]={ "Ὑ", "̀" },
+ ["Ὕ"]={ "Ὑ", "́" },
+ ["Ὗ"]={ "Ὑ", "͂" },
+ ["ὠ"]={ "ω", "̓" },
+ ["ὡ"]={ "ω", "̔" },
+ ["ὢ"]={ "ὠ", "̀" },
+ ["ὣ"]={ "ὡ", "̀" },
+ ["ὤ"]={ "ὠ", "́" },
+ ["ὥ"]={ "ὡ", "́" },
+ ["ὦ"]={ "ὠ", "͂" },
+ ["ὧ"]={ "ὡ", "͂" },
+ ["Ὠ"]={ "Ω", "̓" },
+ ["Ὡ"]={ "Ω", "̔" },
+ ["Ὢ"]={ "Ὠ", "̀" },
+ ["Ὣ"]={ "Ὡ", "̀" },
+ ["Ὤ"]={ "Ὠ", "́" },
+ ["Ὥ"]={ "Ὡ", "́" },
+ ["Ὦ"]={ "Ὠ", "͂" },
+ ["Ὧ"]={ "Ὡ", "͂" },
+ ["ὰ"]={ "α", "̀" },
+ ["ὲ"]={ "ε", "̀" },
+ ["ὴ"]={ "η", "̀" },
+ ["ὶ"]={ "ι", "̀" },
+ ["ὸ"]={ "ο", "̀" },
+ ["ὺ"]={ "υ", "̀" },
+ ["ὼ"]={ "ω", "̀" },
+ ["ᾀ"]={ "ἀ", "ͅ" },
+ ["ᾁ"]={ "ἁ", "ͅ" },
+ ["ᾂ"]={ "ἂ", "ͅ" },
+ ["ᾃ"]={ "ἃ", "ͅ" },
+ ["ᾄ"]={ "ἄ", "ͅ" },
+ ["ᾅ"]={ "ἅ", "ͅ" },
+ ["ᾆ"]={ "ἆ", "ͅ" },
+ ["ᾇ"]={ "ἇ", "ͅ" },
+ ["ᾈ"]={ "Ἀ", "ͅ" },
+ ["ᾉ"]={ "Ἁ", "ͅ" },
+ ["ᾊ"]={ "Ἂ", "ͅ" },
+ ["ᾋ"]={ "Ἃ", "ͅ" },
+ ["ᾌ"]={ "Ἄ", "ͅ" },
+ ["ᾍ"]={ "Ἅ", "ͅ" },
+ ["ᾎ"]={ "Ἆ", "ͅ" },
+ ["ᾏ"]={ "Ἇ", "ͅ" },
+ ["ᾐ"]={ "ἠ", "ͅ" },
+ ["ᾑ"]={ "ἡ", "ͅ" },
+ ["ᾒ"]={ "ἢ", "ͅ" },
+ ["ᾓ"]={ "ἣ", "ͅ" },
+ ["ᾔ"]={ "ἤ", "ͅ" },
+ ["ᾕ"]={ "ἥ", "ͅ" },
+ ["ᾖ"]={ "ἦ", "ͅ" },
+ ["ᾗ"]={ "ἧ", "ͅ" },
+ ["ᾘ"]={ "Ἠ", "ͅ" },
+ ["ᾙ"]={ "Ἡ", "ͅ" },
+ ["ᾚ"]={ "Ἢ", "ͅ" },
+ ["ᾛ"]={ "Ἣ", "ͅ" },
+ ["ᾜ"]={ "Ἤ", "ͅ" },
+ ["ᾝ"]={ "Ἥ", "ͅ" },
+ ["ᾞ"]={ "Ἦ", "ͅ" },
+ ["ᾟ"]={ "Ἧ", "ͅ" },
+ ["ᾠ"]={ "ὠ", "ͅ" },
+ ["ᾡ"]={ "ὡ", "ͅ" },
+ ["ᾢ"]={ "ὢ", "ͅ" },
+ ["ᾣ"]={ "ὣ", "ͅ" },
+ ["ᾤ"]={ "ὤ", "ͅ" },
+ ["ᾥ"]={ "ὥ", "ͅ" },
+ ["ᾦ"]={ "ὦ", "ͅ" },
+ ["ᾧ"]={ "ὧ", "ͅ" },
+ ["ᾨ"]={ "Ὠ", "ͅ" },
+ ["ᾩ"]={ "Ὡ", "ͅ" },
+ ["ᾪ"]={ "Ὢ", "ͅ" },
+ ["ᾫ"]={ "Ὣ", "ͅ" },
+ ["ᾬ"]={ "Ὤ", "ͅ" },
+ ["ᾭ"]={ "Ὥ", "ͅ" },
+ ["ᾮ"]={ "Ὦ", "ͅ" },
+ ["ᾯ"]={ "Ὧ", "ͅ" },
+ ["ᾰ"]={ "α", "̆" },
+ ["ᾱ"]={ "α", "̄" },
+ ["ᾲ"]={ "ὰ", "ͅ" },
+ ["ᾳ"]={ "α", "ͅ" },
+ ["ᾴ"]={ "ά", "ͅ" },
+ ["ᾶ"]={ "α", "͂" },
+ ["ᾷ"]={ "ᾶ", "ͅ" },
+ ["Ᾰ"]={ "Α", "̆" },
+ ["Ᾱ"]={ "Α", "̄" },
+ ["Ὰ"]={ "Α", "̀" },
+ ["ᾼ"]={ "Α", "ͅ" },
+ ["῁"]={ "¨", "͂" },
+ ["ῂ"]={ "ὴ", "ͅ" },
+ ["ῃ"]={ "η", "ͅ" },
+ ["ῄ"]={ "ή", "ͅ" },
+ ["ῆ"]={ "η", "͂" },
+ ["ῇ"]={ "ῆ", "ͅ" },
+ ["Ὲ"]={ "Ε", "̀" },
+ ["Ὴ"]={ "Η", "̀" },
+ ["ῌ"]={ "Η", "ͅ" },
+ ["῍"]={ "᾿", "̀" },
+ ["῎"]={ "᾿", "́" },
+ ["῏"]={ "᾿", "͂" },
+ ["ῐ"]={ "ι", "̆" },
+ ["ῑ"]={ "ι", "̄" },
+ ["ῒ"]={ "ϊ", "̀" },
+ ["ῖ"]={ "ι", "͂" },
+ ["ῗ"]={ "ϊ", "͂" },
+ ["Ῐ"]={ "Ι", "̆" },
+ ["Ῑ"]={ "Ι", "̄" },
+ ["Ὶ"]={ "Ι", "̀" },
+ ["῝"]={ "῾", "̀" },
+ ["῞"]={ "῾", "́" },
+ ["῟"]={ "῾", "͂" },
+ ["ῠ"]={ "υ", "̆" },
+ ["ῡ"]={ "υ", "̄" },
+ ["ῢ"]={ "ϋ", "̀" },
+ ["ῤ"]={ "ρ", "̓" },
+ ["ῥ"]={ "ρ", "̔" },
+ ["ῦ"]={ "υ", "͂" },
+ ["ῧ"]={ "ϋ", "͂" },
+ ["Ῠ"]={ "Υ", "̆" },
+ ["Ῡ"]={ "Υ", "̄" },
+ ["Ὺ"]={ "Υ", "̀" },
+ ["Ῥ"]={ "Ρ", "̔" },
+ ["῭"]={ "¨", "̀" },
+ ["ῲ"]={ "ὼ", "ͅ" },
+ ["ῳ"]={ "ω", "ͅ" },
+ ["ῴ"]={ "ώ", "ͅ" },
+ ["ῶ"]={ "ω", "͂" },
+ ["ῷ"]={ "ῶ", "ͅ" },
+ ["Ὸ"]={ "Ο", "̀" },
+ ["Ὼ"]={ "Ω", "̀" },
+ ["ῼ"]={ "Ω", "ͅ" },
+ ["↚"]={ "←", "̸" },
+ ["↛"]={ "→", "̸" },
+ ["↮"]={ "↔", "̸" },
+ ["⇍"]={ "⇐", "̸" },
+ ["⇎"]={ "⇔", "̸" },
+ ["⇏"]={ "⇒", "̸" },
+ ["∄"]={ "∃", "̸" },
+ ["∉"]={ "∈", "̸" },
+ ["∌"]={ "∋", "̸" },
+ ["∤"]={ "∣", "̸" },
+ ["∦"]={ "∥", "̸" },
+ ["≁"]={ "∼", "̸" },
+ ["≄"]={ "≃", "̸" },
+ ["≇"]={ "≅", "̸" },
+ ["≉"]={ "≈", "̸" },
+ ["≠"]={ "=", "̸" },
+ ["≢"]={ "≡", "̸" },
+ ["≭"]={ "≍", "̸" },
+ ["≮"]={ "<", "̸" },
+ ["≯"]={ ">", "̸" },
+ ["≰"]={ "≤", "̸" },
+ ["≱"]={ "≥", "̸" },
+ ["≴"]={ "≲", "̸" },
+ ["≵"]={ "≳", "̸" },
+ ["≸"]={ "≶", "̸" },
+ ["≹"]={ "≷", "̸" },
+ ["⊀"]={ "≺", "̸" },
+ ["⊁"]={ "≻", "̸" },
+ ["⊄"]={ "⊂", "̸" },
+ ["⊅"]={ "⊃", "̸" },
+ ["⊈"]={ "⊆", "̸" },
+ ["⊉"]={ "⊇", "̸" },
+ ["⊬"]={ "⊢", "̸" },
+ ["⊭"]={ "⊨", "̸" },
+ ["⊮"]={ "⊩", "̸" },
+ ["⊯"]={ "⊫", "̸" },
+ ["⋠"]={ "≼", "̸" },
+ ["⋡"]={ "≽", "̸" },
+ ["⋢"]={ "⊑", "̸" },
+ ["⋣"]={ "⊒", "̸" },
+ ["⋪"]={ "⊲", "̸" },
+ ["⋫"]={ "⊳", "̸" },
+ ["⋬"]={ "⊴", "̸" },
+ ["⋭"]={ "⊵", "̸" },
+ ["⫝̸"]={ "⫝", "̸" },
+ ["が"]={ "か", "゙" },
+ ["ぎ"]={ "き", "゙" },
+ ["ぐ"]={ "く", "゙" },
+ ["げ"]={ "け", "゙" },
+ ["ご"]={ "こ", "゙" },
+ ["ざ"]={ "さ", "゙" },
+ ["じ"]={ "し", "゙" },
+ ["ず"]={ "す", "゙" },
+ ["ぜ"]={ "せ", "゙" },
+ ["ぞ"]={ "そ", "゙" },
+ ["だ"]={ "た", "゙" },
+ ["ぢ"]={ "ち", "゙" },
+ ["づ"]={ "つ", "゙" },
+ ["で"]={ "て", "゙" },
+ ["ど"]={ "と", "゙" },
+ ["ば"]={ "は", "゙" },
+ ["ぱ"]={ "は", "゚" },
+ ["び"]={ "ひ", "゙" },
+ ["ぴ"]={ "ひ", "゚" },
+ ["ぶ"]={ "ふ", "゙" },
+ ["ぷ"]={ "ふ", "゚" },
+ ["べ"]={ "へ", "゙" },
+ ["ぺ"]={ "へ", "゚" },
+ ["ぼ"]={ "ほ", "゙" },
+ ["ぽ"]={ "ほ", "゚" },
+ ["ゔ"]={ "う", "゙" },
+ ["ゞ"]={ "ゝ", "゙" },
+ ["ガ"]={ "カ", "゙" },
+ ["ギ"]={ "キ", "゙" },
+ ["グ"]={ "ク", "゙" },
+ ["ゲ"]={ "ケ", "゙" },
+ ["ゴ"]={ "コ", "゙" },
+ ["ザ"]={ "サ", "゙" },
+ ["ジ"]={ "シ", "゙" },
+ ["ズ"]={ "ス", "゙" },
+ ["ゼ"]={ "セ", "゙" },
+ ["ゾ"]={ "ソ", "゙" },
+ ["ダ"]={ "タ", "゙" },
+ ["ヂ"]={ "チ", "゙" },
+ ["ヅ"]={ "ツ", "゙" },
+ ["デ"]={ "テ", "゙" },
+ ["ド"]={ "ト", "゙" },
+ ["バ"]={ "ハ", "゙" },
+ ["パ"]={ "ハ", "゚" },
+ ["ビ"]={ "ヒ", "゙" },
+ ["ピ"]={ "ヒ", "゚" },
+ ["ブ"]={ "フ", "゙" },
+ ["プ"]={ "フ", "゚" },
+ ["ベ"]={ "ヘ", "゙" },
+ ["ペ"]={ "ヘ", "゚" },
+ ["ボ"]={ "ホ", "゙" },
+ ["ポ"]={ "ホ", "゚" },
+ ["ヴ"]={ "ウ", "゙" },
+ ["ヷ"]={ "ワ", "゙" },
+ ["ヸ"]={ "ヰ", "゙" },
+ ["ヹ"]={ "ヱ", "゙" },
+ ["ヺ"]={ "ヲ", "゙" },
+ ["ヾ"]={ "ヽ", "゙" },
+ ["יִ"]={ "י", "ִ" },
+ ["ײַ"]={ "ײ", "ַ" },
+ ["שׁ"]={ "ש", "ׁ" },
+ ["שׂ"]={ "ש", "ׂ" },
+ ["שּׁ"]={ "שּ", "ׁ" },
+ ["שּׂ"]={ "שּ", "ׂ" },
+ ["אַ"]={ "א", "ַ" },
+ ["אָ"]={ "א", "ָ" },
+ ["אּ"]={ "א", "ּ" },
+ ["בּ"]={ "ב", "ּ" },
+ ["גּ"]={ "ג", "ּ" },
+ ["דּ"]={ "ד", "ּ" },
+ ["הּ"]={ "ה", "ּ" },
+ ["וּ"]={ "ו", "ּ" },
+ ["זּ"]={ "ז", "ּ" },
+ ["טּ"]={ "ט", "ּ" },
+ ["יּ"]={ "י", "ּ" },
+ ["ךּ"]={ "ך", "ּ" },
+ ["כּ"]={ "כ", "ּ" },
+ ["לּ"]={ "ל", "ּ" },
+ ["מּ"]={ "מ", "ּ" },
+ ["נּ"]={ "נ", "ּ" },
+ ["סּ"]={ "ס", "ּ" },
+ ["ףּ"]={ "ף", "ּ" },
+ ["פּ"]={ "פ", "ּ" },
+ ["צּ"]={ "צ", "ּ" },
+ ["קּ"]={ "ק", "ּ" },
+ ["רּ"]={ "ר", "ּ" },
+ ["שּ"]={ "ש", "ּ" },
+ ["תּ"]={ "ת", "ּ" },
+ ["וֹ"]={ "ו", "ֹ" },
+ ["בֿ"]={ "ב", "ֿ" },
+ ["כֿ"]={ "כ", "ֿ" },
+ ["פֿ"]={ "פ", "ֿ" },
+ ["𑂚"]={ "𑂙", "𑂺" },
+ ["𑂜"]={ "𑂛", "𑂺" },
+ ["𑂫"]={ "𑂥", "𑂺" },
+ ["𑄮"]={ "𑄱", "𑄧" },
+ ["𑄯"]={ "𑄲", "𑄧" },
+ ["𑍋"]={ "𑍇", "𑌾" },
+ ["𑍌"]={ "𑍇", "𑍗" },
+ ["𑒻"]={ "𑒹", "𑒺" },
+ ["𑒼"]={ "𑒹", "𑒰" },
+ ["𑒾"]={ "𑒹", "𑒽" },
+ ["𑖺"]={ "𑖸", "𑖯" },
+ ["𑖻"]={ "𑖹", "𑖯" },
+ ["𝅗𝅥"]={ "𝅗", "𝅥" },
+ ["𝅘𝅥"]={ "𝅘", "𝅥" },
+ ["𝅘𝅥𝅮"]={ "𝅘𝅥", "𝅮" },
+ ["𝅘𝅥𝅯"]={ "𝅘𝅥", "𝅯" },
+ ["𝅘𝅥𝅰"]={ "𝅘𝅥", "𝅰" },
+ ["𝅘𝅥𝅱"]={ "𝅘𝅥", "𝅱" },
+ ["𝅘𝅥𝅲"]={ "𝅘𝅥", "𝅲" },
+ ["𝆹𝅥"]={ "𝆹", "𝅥" },
+ ["𝆺𝅥"]={ "𝆺", "𝅥" },
+ ["𝆹𝅥𝅮"]={ "𝆹𝅥", "𝅮" },
+ ["𝆺𝅥𝅮"]={ "𝆺𝅥", "𝅮" },
+ ["𝆹𝅥𝅯"]={ "𝆹𝅥", "𝅯" },
+ ["𝆺𝅥𝅯"]={ "𝆺𝅥", "𝅯" },
+ },
+ },
+ },
+ ["name"]="collapse",
+ ["prepend"]=true,
+ ["type"]="ligature",
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-mis.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-mis.lua
new file mode 100644
index 0000000000..b472b86dda
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-mis.lua
@@ -0,0 +1,35 @@
+if not modules then modules = { } end modules ['luatex-font-mis'] = {
+ version = 1.001,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+local currentfont = font.current
+
+local hashes = fonts.hashes
+local identifiers = hashes.identifiers or { }
+local marks = hashes.marks or { }
+
+hashes.identifiers = identifiers
+hashes.marks = marks
+
+table.setmetatableindex(marks,function(t,k)
+ if k == true then
+ return marks[currentfont()]
+ else
+ local resources = identifiers[k].resources or { }
+ local marks = resources.marks or { }
+ t[k] = marks
+ return marks
+ end
+end)
+
+function font.each()
+ return table.sortedhash(fonts.hashes.identifiers)
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-syn.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-syn.lua
new file mode 100644
index 0000000000..2ec075434f
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-syn.lua
@@ -0,0 +1,104 @@
+if not modules then modules = { } end modules ['luatex-fonts-syn'] = {
+ version = 1.001,
+ comment = "companion to luatex-*.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if context then
+ os.exit()
+end
+
+-- Generic font names support.
+--
+-- Watch out, the version number is the same as the one used in
+-- the mtx-fonts.lua function scripts.fonts.names as we use a
+-- simplified font database in the plain solution and by using
+-- a different number we're less dependent on context.
+--
+-- mtxrun --script font --reload --simple
+--
+-- The format of the file is as follows:
+--
+-- return {
+-- ["version"] = 1.001,
+-- ["cache_version"] = 1.001,
+-- ["mappings"] = {
+-- ["somettcfontone"] = { "Some TTC Font One", "SomeFontA.ttc", 1 },
+-- ["somettcfonttwo"] = { "Some TTC Font Two", "SomeFontA.ttc", 2 },
+-- ["somettffont"] = { "Some TTF Font", "SomeFontB.ttf" },
+-- ["someotffont"] = { "Some OTF Font", "SomeFontC.otf" },
+-- },
+-- }
+
+local fonts = fonts
+fonts.names = fonts.names or { }
+
+fonts.names.version = 1.001 -- not the same as in context but matches mtx-fonts --simple
+fonts.names.basename = "luatex-fonts-names"
+fonts.names.cache = containers.define("fonts","data",fonts.names.version,true)
+
+local data = nil
+local loaded = false
+
+local fileformats = { "lua", "tex", "other text files" }
+
+function fonts.names.reportmissingbase()
+ logs.report("fonts","missing font database, run: mtxrun --script fonts --reload --simple")
+ fonts.names.reportmissingbase = nil
+end
+
+function fonts.names.reportmissingname()
+ logs.report("fonts","unknown font in font database, run: mtxrun --script fonts --reload --simple")
+ fonts.names.reportmissingname = nil
+end
+
+function fonts.names.resolve(name,sub)
+ if not loaded then
+ local basename = fonts.names.basename
+ if basename and basename ~= "" then
+ data = containers.read(fonts.names.cache,basename)
+ if not data then
+ basename = file.addsuffix(basename,"lua")
+ for i=1,#fileformats do
+ local format = fileformats[i]
+ local foundname = resolvers.findfile(basename,format) or ""
+ if foundname ~= "" then
+ data = dofile(foundname)
+ logs.report("fonts","font database '%s' loaded",foundname)
+ break
+ end
+ end
+ end
+ end
+ loaded = true
+ end
+ if type(data) == "table" and data.version == fonts.names.version then
+ local condensed = string.gsub(string.lower(name),"[^%a%d]","")
+ local found = data.mappings and data.mappings[condensed]
+ if found then
+ local fontname, filename, subfont = found[1], found[2], found[3]
+ if subfont then
+ return filename, fontname
+ else
+ return filename, false
+ end
+ elseif fonts.names.reportmissingname then
+ fonts.names.reportmissingname()
+ return name, false -- fallback to filename
+ end
+ elseif fonts.names.reportmissingbase then
+ fonts.names.reportmissingbase()
+ end
+end
+
+fonts.names.resolvespec = fonts.names.resolve -- only supported in mkiv
+
+function fonts.names.getfilename(askedname,suffix) -- only supported in mkiv
+ return ""
+end
+
+function fonts.names.ignoredfile(filename) -- only supported in mkiv
+ return false -- will be overloaded
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-fonts-tfm.lua b/macros/luatex/generic/luaotfload/fontloader-fonts-tfm.lua
new file mode 100644
index 0000000000..0b6e09a8f9
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-fonts-tfm.lua
@@ -0,0 +1,654 @@
+if not modules then modules = { } end modules ['luatex-fonts-tfm'] = {
+ version = 1.001,
+ comment = "companion to font-ini.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- This is the generic tfm/vf loader. There are no fundamental differences with
+-- the one used in ConTeXt but we save some byte(codes) this way.
+
+local next, type = next, type
+local match, format = string.match, string.format
+local concat, sortedhash = table.concat, table.sortedhash
+local idiv = number.idiv
+
+local trace_defining = false trackers.register("fonts.defining", function(v) trace_defining = v end)
+local trace_features = false trackers.register("tfm.features", function(v) trace_features = v end)
+
+local report_defining = logs.reporter("fonts","defining")
+local report_tfm = logs.reporter("fonts","tfm loading")
+
+local findbinfile = resolvers.findbinfile
+local setmetatableindex = table.setmetatableindex
+
+local fonts = fonts
+local handlers = fonts.handlers
+local helpers = fonts.helpers
+local readers = fonts.readers
+local constructors = fonts.constructors
+local encodings = fonts.encodings
+
+local tfm = constructors.handlers.tfm
+tfm.version = 1.000
+tfm.maxnestingdepth = 5
+tfm.maxnestingsize = 65536*1024
+
+local otf = fonts.handlers.otf
+local otfenhancers = otf.enhancers
+
+local tfmfeatures = constructors.features.tfm
+local registertfmfeature = tfmfeatures.register
+
+local tfmenhancers = constructors.enhancers.tfm
+local registertfmenhancer = tfmenhancers.register
+
+local charcommand = helpers.commands.char
+
+constructors.resolvevirtualtoo = false -- wil be set in font-ctx.lua
+
+fonts.formats.tfm = "type1" -- we need to have at least a value here
+fonts.formats.ofm = "type1" -- we need to have at least a value here
+
+function tfm.setfeatures(tfmdata,features)
+ local okay = constructors.initializefeatures("tfm",tfmdata,features,trace_features,report_tfm)
+ if okay then
+ return constructors.collectprocessors("tfm",tfmdata,features,trace_features,report_tfm)
+ else
+ return { } -- will become false
+ end
+end
+
+local depth = { } -- table.setmetatableindex("number")
+
+local loadtfm = font.read_tfm
+local loadvf = font.read_vf
+
+local function read_from_tfm(specification)
+ local filename = specification.filename
+ local size = specification.size
+ depth[filename] = (depth[filename] or 0) + 1
+ if trace_defining then
+ report_defining("loading tfm file %a at size %s",filename,size)
+ end
+ local tfmdata = loadtfm(filename,size)
+ if tfmdata then
+
+ local features = specification.features and specification.features.normal or { }
+ local features = constructors.checkedfeatures("tfm",features)
+ specification.features.normal = features
+
+ -- If reencode returns a new table, we assume that we're doing something
+ -- special. An 'auto' reencode picks up its vector from the pfb file.
+
+ local newtfmdata = (depth[filename] == 1) and tfm.reencode(tfmdata,specification)
+ if newtfmdata then
+ tfmdata = newtfmdata
+ end
+
+ local resources = tfmdata.resources or { }
+ local properties = tfmdata.properties or { }
+ local parameters = tfmdata.parameters or { }
+ local shared = tfmdata.shared or { }
+ --
+ shared.features = features
+ shared.resources = resources
+ --
+ properties.name = tfmdata.name -- todo: fallback
+ properties.fontname = tfmdata.fontname -- todo: fallback
+ properties.psname = tfmdata.psname -- todo: fallback
+ properties.fullname = tfmdata.fullname -- todo: fallback
+ properties.filename = specification.filename -- todo: fallback
+ properties.format = tfmdata.format or fonts.formats.tfm -- better than nothing
+ properties.usedbitmap = tfmdata.usedbitmap
+ --
+ tfmdata.properties = properties
+ tfmdata.resources = resources
+ tfmdata.parameters = parameters
+ tfmdata.shared = shared
+ --
+ shared.rawdata = { resources = resources }
+ shared.features = features
+ --
+ -- The next branch is only entered when we have a proper encoded file i.e.
+ -- unicodes and such. It really nakes no sense to do feature juggling when
+ -- we have no names and unicodes.
+ --
+ if newtfmdata then
+ --
+ -- Some opentype processing assumes these to be present:
+ --
+ if not resources.marks then
+ resources.marks = { }
+ end
+ if not resources.sequences then
+ resources.sequences = { }
+ end
+ if not resources.features then
+ resources.features = {
+ gsub = { },
+ gpos = { },
+ }
+ end
+ if not tfmdata.changed then
+ tfmdata.changed = { }
+ end
+ if not tfmdata.descriptions then
+ tfmdata.descriptions = tfmdata.characters
+ end
+ --
+ -- It might be handy to have this:
+ --
+ otf.readers.addunicodetable(tfmdata)
+ --
+ -- We make a pseudo opentype font, e.g. kerns and ligatures etc:
+ --
+ tfmenhancers.apply(tfmdata,filename)
+ --
+ -- Now user stuff can kick in.
+ --
+ constructors.applymanipulators("tfm",tfmdata,features,trace_features,report_tfm)
+ --
+ -- As that can also mess with names and such, we are now ready for finalizing
+ -- the unicode information. This is a different order that for instance type one
+ -- (afm) files. First we try to deduce unicodes from already present information.
+ --
+ otf.readers.unifymissing(tfmdata)
+ --
+ -- Next we fill in the gaps, based on names from teh agl. Probably not much will
+ -- happen here.
+ --
+ fonts.mappings.addtounicode(tfmdata,filename)
+ --
+ -- The tounicode data is passed to the backend that constructs the vectors for us.
+ --
+ tfmdata.tounicode = 1
+ local tounicode = fonts.mappings.tounicode
+ for unicode, v in next, tfmdata.characters do
+ local u = v.unicode
+ if u then
+ v.tounicode = tounicode(u)
+ end
+ end
+ --
+ -- However, when we use a bitmap font those vectors can't be constructed because
+ -- that information is not carried with those fonts (there is no name info, nor
+ -- proper index info, nor unicodes at that end). So, we provide it ourselves.
+ --
+ if tfmdata.usedbitmap then
+ tfm.addtounicode(tfmdata)
+ end
+ end
+ --
+ shared.processes = next(features) and tfm.setfeatures(tfmdata,features) or nil
+ --
+ if size < 0 then
+ size = idiv(65536 * -size,100)
+ end
+ parameters.factor = 1 -- already scaled
+ parameters.units = 1000 -- just in case
+ parameters.size = size
+ parameters.slant = parameters.slant or parameters[1] or 0
+ parameters.space = parameters.space or parameters[2] or 0
+ parameters.space_stretch = parameters.space_stretch or parameters[3] or 0
+ parameters.space_shrink = parameters.space_shrink or parameters[4] or 0
+ parameters.x_height = parameters.x_height or parameters[5] or 0
+ parameters.quad = parameters.quad or parameters[6] or 0
+ parameters.extra_space = parameters.extra_space or parameters[7] or 0
+ --
+ constructors.enhanceparameters(parameters) -- official copies for us
+ --
+ properties.private = properties.private or tfmdata.private or privateoffset
+ --
+ if newtfmdata then
+ --
+ -- We do nothing as we assume flat tfm files. It would become real messy
+ -- otherwise and I don't have something for testing on my system anyway.
+ --
+ elseif constructors.resolvevirtualtoo then
+ fonts.loggers.register(tfmdata,file.suffix(filename),specification) -- strange, why here
+ local vfname = findbinfile(specification.name, 'ovf')
+ if vfname and vfname ~= "" then
+ local vfdata = loadvf(vfname,size)
+ if vfdata then
+ local chars = tfmdata.characters
+ for k,v in next, vfdata.characters do
+ chars[k].commands = v.commands
+ end
+ properties.virtualized = true
+ tfmdata.fonts = vfdata.fonts
+ tfmdata.type = "virtual" -- else nested calls with cummulative scaling
+ local fontlist = vfdata.fonts
+ local name = file.nameonly(filename)
+ for i=1,#fontlist do
+ local n = fontlist[i].name
+ local s = fontlist[i].size
+ local d = depth[filename]
+ s = constructors.scaled(s,vfdata.designsize)
+ if d > tfm.maxnestingdepth then
+ report_defining("too deeply nested virtual font %a with size %a, max nesting depth %s",n,s,tfm.maxnestingdepth)
+ fontlist[i] = { id = 0 }
+ elseif (d > 1) and (s > tfm.maxnestingsize) then
+ report_defining("virtual font %a exceeds size %s",n,s)
+ fontlist[i] = { id = 0 }
+ else
+ local t, id = constructors.readanddefine(n,s)
+ fontlist[i] = { id = id }
+ end
+ end
+ end
+ end
+ end
+ --
+ properties.haskerns = true
+ properties.hasligatures = true
+ properties.hasitalics = true
+ resources.unicodes = { }
+ resources.lookuptags = { }
+ --
+ depth[filename] = depth[filename] - 1
+ --
+ return tfmdata
+ else
+ depth[filename] = depth[filename] - 1
+ end
+end
+
+local function check_tfm(specification,fullname) -- we could split up like afm/otf
+ local foundname = findbinfile(fullname, 'tfm') or ""
+ if foundname == "" then
+ foundname = findbinfile(fullname, 'ofm') or "" -- not needed in context
+ end
+ if foundname == "" then
+ foundname = fonts.names.getfilename(fullname,"tfm") or ""
+ end
+ if foundname ~= "" then
+ specification.filename = foundname
+ specification.format = "ofm"
+ return read_from_tfm(specification)
+ elseif trace_defining then
+ report_defining("loading tfm with name %a fails",specification.name)
+ end
+end
+
+readers.check_tfm = check_tfm
+
+function readers.tfm(specification)
+ local fullname = specification.filename or ""
+ if fullname == "" then
+ local forced = specification.forced or ""
+ if forced ~= "" then
+ fullname = specification.name .. "." .. forced
+ else
+ fullname = specification.name
+ end
+ end
+ return check_tfm(specification,fullname)
+end
+
+readers.ofm = readers.tfm
+
+-- The reencoding acts upon the 'reencode' feature which can have values 'auto' or
+-- an enc file. You can also specify a 'pfbfile' feature (but it defaults to the
+-- tfm filename) and a 'bitmap' feature. When no enc file is givven (auto) we will
+-- get the vectors from the pfb file.
+
+do
+
+ local outfiles = { }
+
+ local tfmcache = table.setmetatableindex(function(t,tfmdata)
+ local id = font.define(tfmdata)
+ t[tfmdata] = id
+ return id
+ end)
+
+ local encdone = table.setmetatableindex("table")
+
+ function tfm.reencode(tfmdata,specification)
+
+ local features = specification.features
+
+ if not features then
+ return
+ end
+
+ local features = features.normal
+
+ if not features then
+ return
+ end
+
+ local tfmfile = file.basename(tfmdata.name)
+ local encfile = features.reencode -- or features.enc
+ local pfbfile = features.pfbfile -- or features.pfb
+ local bitmap = features.bitmap -- or features.pk
+
+ if not encfile then
+ return
+ end
+
+ local pfbfile = outfiles[tfmfile]
+
+ if pfbfile == nil then
+ if bitmap then
+ pfbfile = false
+ elseif type(pfbfile) ~= "string" then
+ pfbfile = tfmfile
+ end
+ if type(pfbfile) == "string" then
+ pfbfile = file.addsuffix(pfbfile,"pfb")
+ -- pdf.mapline(tfmfile .. "<" .. pfbfile)
+ report_tfm("using type1 shapes from %a for %a",pfbfile,tfmfile)
+ else
+ report_tfm("using bitmap shapes for %a",tfmfile)
+ pfbfile = false -- use bitmap
+ end
+ outfiles[tfmfile] = pfbfile
+ end
+
+ local encoding = false
+ local vector = false
+
+ if type(pfbfile) == "string" then
+ local pfb = constructors.handlers.pfb
+ if pfb and pfb.loadvector then
+ local v, e = pfb.loadvector(pfbfile)
+ if v then
+ vector = v
+ end
+ if e then
+ encoding = e
+ end
+ end
+ end
+ if type(encfile) == "string" and encfile ~= "auto" then
+ encoding = fonts.encodings.load(file.addsuffix(encfile,"enc"))
+ if encoding then
+ encoding = encoding.vector
+ end
+ end
+ if not encoding then
+ report_tfm("bad encoding for %a, quitting",tfmfile)
+ return
+ end
+
+ local unicoding = fonts.encodings.agl and fonts.encodings.agl.unicodes
+ local virtualid = tfmcache[tfmdata]
+ local tfmdata = table.copy(tfmdata) -- good enough for small fonts
+ local characters = { }
+ local originals = tfmdata.characters
+ local indices = { }
+ local parentfont = { "font", 1 }
+ local private = tfmdata.privateoffset or constructors.privateoffset
+ local reported = encdone[tfmfile][encfile]
+
+ -- create characters table
+
+ local backmap = vector and table.swapped(vector)
+ local done = { } -- prevent duplicate
+
+ for index, name in sortedhash(encoding) do -- predictable order
+ local unicode = unicoding[name]
+ local original = originals[index]
+ if original then
+ if unicode then
+ original.unicode = unicode
+ else
+ unicode = private
+ private = private + 1
+ if not reported then
+ report_tfm("glyph %a in font %a with encoding %a gets unicode %U",name,tfmfile,encfile,unicode)
+ end
+ end
+ characters[unicode] = original
+ indices[index] = unicode
+ original.name = name -- so one can lookup weird names
+ if backmap then
+ original.index = backmap[name]
+ else -- probably bitmap
+ original.commands = { parentfont, charcommand[index] } -- or "slot"
+ original.oindex = index
+ end
+ done[name] = true
+ elseif not done[name] then
+ report_tfm("bad index %a in font %a with name %a",index,tfmfile,name)
+ end
+ end
+
+ encdone[tfmfile][encfile] = true
+
+ -- redo kerns and ligatures
+
+ for k, v in next, characters do
+ local kerns = v.kerns
+ if kerns then
+ local t = { }
+ for k, v in next, kerns do
+ local i = indices[k]
+ if i then
+ t[i] = v
+ end
+ end
+ v.kerns = next(t) and t or nil
+ end
+ local ligatures = v.ligatures
+ if ligatures then
+ local t = { }
+ for k, v in next, ligatures do
+ local i = indices[k]
+ if i then
+ t[i] = v
+ v.char = indices[v.char]
+ end
+ end
+ v.ligatures = next(t) and t or nil
+ end
+ end
+
+ -- wrap up
+
+ tfmdata.fonts = { { id = virtualid } }
+ tfmdata.characters = characters
+ tfmdata.fullname = tfmdata.fullname or tfmdata.name
+ tfmdata.psname = file.nameonly(pfbfile or tfmdata.name)
+ tfmdata.filename = pfbfile
+ tfmdata.encodingbytes = 2
+ -- tfmdata.format = bitmap and "type3" or "type1"
+ tfmdata.format = "type1"
+ tfmdata.tounicode = 1
+ tfmdata.embedding = "subset"
+ tfmdata.usedbitmap = bitmap and virtualid
+ tfmdata.private = private
+
+ return tfmdata
+ end
+
+end
+
+-- This code adds a ToUnicode vector for bitmap fonts. We don't bother about
+-- ranges because we have small fonts. it works ok with acrobat but fails with
+-- the other viewers (they get confused by the bitmaps I guess).
+
+do
+
+ local template = [[
+/CIDInit /ProcSet findresource begin
+ 12 dict begin
+ begincmap
+ /CIDSystemInfo << /Registry (TeX) /Ordering (bitmap-%s) /Supplement 0 >> def
+ /CMapName /TeX-bitmap-%s def
+ /CMapType 2 def
+ 1 begincodespacerange
+ <00> <FF>
+ endcodespacerange
+ %s beginbfchar
+%s
+ endbfchar
+ endcmap
+CMapName currentdict /CMap defineresource pop end
+end
+end
+]]
+
+ local flushstreamobject = lpdf and lpdf.flushstreamobject -- context
+ local setfontattributes = lpdf and lpdf.setfontattributes -- context
+
+ if not flushstreamobject then
+ flushstreamobject = function(data)
+ return pdf.obj { immediate = true, type = "stream", string = data } -- generic
+ end
+ end
+
+ if not setfontattributes then
+ setfontattributes = function(id,data)
+ return pdf.setfontattributes(id,data) -- generic
+ end
+ end
+
+ function tfm.addtounicode(tfmdata)
+ local id = tfmdata.usedbitmap
+ local map = { }
+ local char = { } -- no need for range, hardly used
+ for k, v in next, tfmdata.characters do
+ local index = v.oindex
+ local tounicode = v.tounicode
+ if index and tounicode then
+ map[index] = tounicode
+ end
+ end
+ for k, v in sortedhash(map) do
+ char[#char+1] = format("<%02X> <%s>",k,v)
+ end
+ char = concat(char,"\n")
+ local stream = format(template,id,id,#char,char)
+ local reference = flushstreamobject(stream,nil,true)
+ setfontattributes(id,format("/ToUnicode %i 0 R",reference))
+ end
+
+end
+
+-- Now we implement the regular features handlers. We need to convert the
+-- tfm specific structures to opentype structures. In basemode they are
+-- converted back so that is a bit of a waste but it's fast enough.
+
+do
+
+ local everywhere = { ["*"] = { ["*"] = true } } -- or: { ["*"] = { "*" } }
+ local noflags = { false, false, false, false }
+
+ local function enhance_normalize_features(data)
+ local ligatures = setmetatableindex("table")
+ local kerns = setmetatableindex("table")
+ local characters = data.characters
+ for u, c in next, characters do
+ local l = c.ligatures
+ local k = c.kerns
+ if l then
+ ligatures[u] = l
+ for u, v in next, l do
+ l[u] = { ligature = v.char }
+ end
+ c.ligatures = nil
+ end
+ if k then
+ kerns[u] = k
+ for u, v in next, k do
+ k[u] = v -- { v, 0 }
+ end
+ c.kerns = nil
+ end
+ end
+
+ for u, l in next, ligatures do
+ for k, v in next, l do
+ local vl = v.ligature
+ local dl = ligatures[vl]
+ if dl then
+ for kk, vv in next, dl do
+ v[kk] = vv -- table.copy(vv)
+ end
+ end
+ end
+ end
+
+ local features = {
+ gpos = { },
+ gsub = { },
+ }
+ local sequences = {
+ -- only filled ones
+ }
+ if next(ligatures) then
+ features.gsub.liga = everywhere
+ data.properties.hasligatures = true
+ sequences[#sequences+1] = {
+ features = {
+ liga = everywhere,
+ },
+ flags = noflags,
+ name = "s_s_0",
+ nofsteps = 1,
+ order = { "liga" },
+ type = "gsub_ligature",
+ steps = {
+ {
+ coverage = ligatures,
+ },
+ },
+ }
+ end
+ if next(kerns) then
+ features.gpos.kern = everywhere
+ data.properties.haskerns = true
+ sequences[#sequences+1] = {
+ features = {
+ kern = everywhere,
+ },
+ flags = noflags,
+ name = "p_s_0",
+ nofsteps = 1,
+ order = { "kern" },
+ type = "gpos_pair",
+ steps = {
+ {
+ format = "kern",
+ coverage = kerns,
+ },
+ },
+ }
+ end
+ data.resources.features = features
+ data.resources.sequences = sequences
+ data.shared.resources = data.shared.resources or resources
+ end
+
+ registertfmenhancer("normalize features", enhance_normalize_features)
+ registertfmenhancer("check extra features", otfenhancers.enhance)
+
+end
+
+-- As with type one (afm) loading, we just use the opentype ones:
+
+registertfmfeature {
+ name = "mode",
+ description = "mode",
+ initializers = {
+ base = otf.modeinitializer,
+ node = otf.modeinitializer,
+ }
+}
+
+registertfmfeature {
+ name = "features",
+ description = "features",
+ default = true,
+ initializers = {
+ base = otf.basemodeinitializer,
+ node = otf.nodemodeinitializer,
+ },
+ processors = {
+ node = otf.featuresprocessor,
+ }
+}
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-boolean.lua b/macros/luatex/generic/luaotfload/fontloader-l-boolean.lua
new file mode 100644
index 0000000000..8f18d4c003
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-boolean.lua
@@ -0,0 +1,69 @@
+if not modules then modules = { } end modules ['l-boolean'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local type, tonumber = type, tonumber
+
+boolean = boolean or { }
+local boolean = boolean
+
+function boolean.tonumber(b)
+ if b then return 1 else return 0 end -- test and return or return
+end
+
+function toboolean(str,tolerant) -- global
+ if str == nil then
+ return false
+ elseif str == false then
+ return false
+ elseif str == true then
+ return true
+ elseif str == "true" then
+ return true
+ elseif str == "false" then
+ return false
+ elseif not tolerant then
+ return false
+ elseif str == 0 then
+ return false
+ elseif (tonumber(str) or 0) > 0 then
+ return true
+ else
+ return str == "yes" or str == "on" or str == "t"
+ end
+end
+
+string.toboolean = toboolean
+
+function string.booleanstring(str)
+ if str == "0" then
+ return false
+ elseif str == "1" then
+ return true
+ elseif str == "" then
+ return false
+ elseif str == "false" then
+ return false
+ elseif str == "true" then
+ return true
+ elseif (tonumber(str) or 0) > 0 then
+ return true
+ else
+ return str == "yes" or str == "on" or str == "t"
+ end
+end
+
+function string.is_boolean(str,default,strict)
+ if type(str) == "string" then
+ if str == "true" or str == "yes" or str == "on" or str == "t" or (not strict and str == "1") then
+ return true
+ elseif str == "false" or str == "no" or str == "off" or str == "f" or (not strict and str == "0") then
+ return false
+ end
+ end
+ return default
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-file.lua b/macros/luatex/generic/luaotfload/fontloader-l-file.lua
new file mode 100644
index 0000000000..1b039a4386
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-file.lua
@@ -0,0 +1,738 @@
+if not modules then modules = { } end modules ['l-file'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- needs a cleanup
+
+file = file or { }
+local file = file
+
+if not lfs then
+ lfs = optionalrequire("lfs")
+end
+
+-- -- see later
+--
+-- if not lfs then
+--
+-- lfs = {
+-- getcurrentdir = function()
+-- return "."
+-- end,
+-- attributes = function()
+-- return nil
+-- end,
+-- isfile = function(name)
+-- local f = io.open(name,'rb')
+-- if f then
+-- f:close()
+-- return true
+-- end
+-- end,
+-- isdir = function(name)
+-- print("you need to load lfs")
+-- return false
+-- end
+-- }
+--
+-- elseif not lfs.isfile then
+--
+-- local attributes = lfs.attributes
+--
+-- function lfs.isdir(name)
+-- return attributes(name,"mode") == "directory"
+-- end
+--
+-- function lfs.isfile(name)
+-- return attributes(name,"mode") == "file"
+-- end
+--
+-- -- function lfs.isdir(name)
+-- -- local a = attributes(name)
+-- -- return a and a.mode == "directory"
+-- -- end
+--
+-- -- function lfs.isfile(name)
+-- -- local a = attributes(name)
+-- -- return a and a.mode == "file"
+-- -- end
+--
+-- end
+
+local insert, concat = table.insert, table.concat
+local match, find, gmatch = string.match, string.find, string.gmatch
+local lpegmatch = lpeg.match
+local getcurrentdir, attributes = lfs.currentdir, lfs.attributes
+local checkedsplit = string.checkedsplit
+
+local P, R, S, C, Cs, Cp, Cc, Ct = lpeg.P, lpeg.R, lpeg.S, lpeg.C, lpeg.Cs, lpeg.Cp, lpeg.Cc, lpeg.Ct
+
+-- better this way:
+
+local attributes = lfs.attributes
+
+function lfs.isdir(name)
+ return attributes(name,"mode") == "directory"
+end
+
+function lfs.isfile(name)
+ local a = attributes(name,"mode")
+ return a == "file" or a == "link" or nil
+end
+
+function lfs.isfound(name)
+ local a = attributes(name,"mode")
+ return (a == "file" or a == "link") and name or nil
+end
+
+if sandbox then
+ sandbox.redefine(lfs.isfile,"lfs.isfile")
+ sandbox.redefine(lfs.isdir, "lfs.isdir")
+ sandbox.redefine(lfs.isfound, "lfs.isfound")
+end
+
+local colon = P(":")
+local period = P(".")
+local periods = P("..")
+local fwslash = P("/")
+local bwslash = P("\\")
+local slashes = S("\\/")
+local noperiod = 1-period
+local noslashes = 1-slashes
+local name = noperiod^1
+local suffix = period/"" * (1-period-slashes)^1 * -1
+
+----- pattern = C((noslashes^0 * slashes^1)^1)
+local pattern = C((1 - (slashes^1 * noslashes^1 * -1))^1) * P(1) -- there must be a more efficient way
+
+local function pathpart(name,default)
+ return name and lpegmatch(pattern,name) or default or ""
+end
+
+local pattern = (noslashes^0 * slashes)^1 * C(noslashes^1) * -1
+
+local function basename(name)
+ return name and lpegmatch(pattern,name) or name
+end
+
+-- print(pathpart("file"))
+-- print(pathpart("dir/file"))
+-- print(pathpart("/dir/file"))
+-- print(basename("file"))
+-- print(basename("dir/file"))
+-- print(basename("/dir/file"))
+
+local pattern = (noslashes^0 * slashes^1)^0 * Cs((1-suffix)^1) * suffix^0
+
+local function nameonly(name)
+ return name and lpegmatch(pattern,name) or name
+end
+
+local pattern = (noslashes^0 * slashes)^0 * (noperiod^1 * period)^1 * C(noperiod^1) * -1
+
+local function suffixonly(name)
+ return name and lpegmatch(pattern,name) or ""
+end
+
+local pattern = (noslashes^0 * slashes)^0 * noperiod^1 * ((period * C(noperiod^1))^1) * -1 + Cc("")
+
+local function suffixesonly(name)
+ if name then
+ return lpegmatch(pattern,name)
+ else
+ return ""
+ end
+end
+
+file.pathpart = pathpart
+file.basename = basename
+file.nameonly = nameonly
+file.suffixonly = suffixonly
+file.suffix = suffixonly
+file.suffixesonly = suffixesonly
+file.suffixes = suffixesonly
+
+file.dirname = pathpart -- obsolete
+file.extname = suffixonly -- obsolete
+
+-- actually these are schemes
+
+local drive = C(R("az","AZ")) * colon
+local path = C((noslashes^0 * slashes)^0)
+local suffix = period * C(P(1-period)^0 * P(-1))
+local base = C((1-suffix)^0)
+local rest = C(P(1)^0)
+
+drive = drive + Cc("")
+path = path + Cc("")
+base = base + Cc("")
+suffix = suffix + Cc("")
+
+local pattern_a = drive * path * base * suffix
+local pattern_b = path * base * suffix
+local pattern_c = C(drive * path) * C(base * suffix) -- trick: two extra captures
+local pattern_d = path * rest
+
+function file.splitname(str,splitdrive)
+ if not str then
+ -- error
+ elseif splitdrive then
+ return lpegmatch(pattern_a,str) -- returns drive, path, base, suffix
+ else
+ return lpegmatch(pattern_b,str) -- returns path, base, suffix
+ end
+end
+
+function file.splitbase(str)
+ if str then
+ return lpegmatch(pattern_d,str) -- returns path, base+suffix (path has / appended, might change at some point)
+ else
+ return "", str -- assume no path
+ end
+end
+
+---- stripslash = C((1 - P("/")^1*P(-1))^0)
+
+function file.nametotable(str,splitdrive)
+ if str then
+ local path, drive, subpath, name, base, suffix = lpegmatch(pattern_c,str)
+ -- if path ~= "" then
+ -- path = lpegmatch(stripslash,path) -- unfortunate hack, maybe this becomes default
+ -- end
+ if splitdrive then
+ return {
+ path = path,
+ drive = drive,
+ subpath = subpath,
+ name = name,
+ base = base,
+ suffix = suffix,
+ }
+ else
+ return {
+ path = path,
+ name = name,
+ base = base,
+ suffix = suffix,
+ }
+ end
+ end
+end
+
+-- print(file.splitname("file"))
+-- print(file.splitname("dir/file"))
+-- print(file.splitname("/dir/file"))
+-- print(file.splitname("file"))
+-- print(file.splitname("dir/file"))
+-- print(file.splitname("/dir/file"))
+
+-- inspect(file.nametotable("file.ext"))
+-- inspect(file.nametotable("dir/file.ext"))
+-- inspect(file.nametotable("/dir/file.ext"))
+-- inspect(file.nametotable("file.ext"))
+-- inspect(file.nametotable("dir/file.ext"))
+-- inspect(file.nametotable("/dir/file.ext"))
+
+----- pattern = Cs(((period * noperiod^1 * -1) / "" + 1)^1)
+local pattern = Cs(((period * (1-period-slashes)^1 * -1) / "" + 1)^1)
+
+function file.removesuffix(name)
+ return name and lpegmatch(pattern,name)
+end
+
+-- local pattern = (noslashes^0 * slashes)^0 * (noperiod^1 * period)^1 * Cp() * noperiod^1 * -1
+--
+-- function file.addsuffix(name, suffix)
+-- local p = lpegmatch(pattern,name)
+-- if p then
+-- return name
+-- else
+-- return name .. "." .. suffix
+-- end
+-- end
+
+local suffix = period/"" * (1-period-slashes)^1 * -1
+local pattern = Cs((noslashes^0 * slashes^1)^0 * ((1-suffix)^1)) * Cs(suffix)
+
+function file.addsuffix(filename,suffix,criterium)
+ if not filename or not suffix or suffix == "" then
+ return filename
+ elseif criterium == true then
+ return filename .. "." .. suffix
+ elseif not criterium then
+ local n, s = lpegmatch(pattern,filename)
+ if not s or s == "" then
+ return filename .. "." .. suffix
+ else
+ return filename
+ end
+ else
+ local n, s = lpegmatch(pattern,filename)
+ if s and s ~= "" then
+ local t = type(criterium)
+ if t == "table" then
+ -- keep if in criterium
+ for i=1,#criterium do
+ if s == criterium[i] then
+ return filename
+ end
+ end
+ elseif t == "string" then
+ -- keep if criterium
+ if s == criterium then
+ return filename
+ end
+ end
+ end
+ return (n or filename) .. "." .. suffix
+ end
+end
+
+-- print("1 " .. file.addsuffix("name","new") .. " -> name.new")
+-- print("2 " .. file.addsuffix("name.old","new") .. " -> name.old")
+-- print("3 " .. file.addsuffix("name.old","new",true) .. " -> name.old.new")
+-- print("4 " .. file.addsuffix("name.old","new","new") .. " -> name.new")
+-- print("5 " .. file.addsuffix("name.old","new","old") .. " -> name.old")
+-- print("6 " .. file.addsuffix("name.old","new","foo") .. " -> name.new")
+-- print("7 " .. file.addsuffix("name.old","new",{"foo","bar"}) .. " -> name.new")
+-- print("8 " .. file.addsuffix("name.old","new",{"old","bar"}) .. " -> name.old")
+
+local suffix = period * (1-period-slashes)^1 * -1
+local pattern = Cs((1-suffix)^0)
+
+function file.replacesuffix(name,suffix)
+ if name and suffix and suffix ~= "" then
+ return lpegmatch(pattern,name) .. "." .. suffix
+ else
+ return name
+ end
+end
+
+--
+
+local reslasher = lpeg.replacer(P("\\"),"/")
+
+function file.reslash(str)
+ return str and lpegmatch(reslasher,str)
+end
+
+-- We should be able to use:
+--
+-- local writable = P(1) * P("w") * Cc(true)
+--
+-- function file.is_writable(name)
+-- local a = attributes(name) or attributes(pathpart(name,"."))
+-- return a and lpegmatch(writable,a.permissions) or false
+-- end
+--
+-- But after some testing Taco and I came up with the more robust
+-- variant:
+
+if lfs.isreadablefile and lfs.iswritablefile then
+
+ file.is_readable = lfs.isreadablefile
+ file.is_writable = lfs.iswritablefile
+
+else
+
+ function file.is_writable(name)
+ if not name then
+ -- error
+ elseif lfs.isdir(name) then
+ name = name .. "/m_t_x_t_e_s_t.tmp"
+ local f = io.open(name,"wb")
+ if f then
+ f:close()
+ os.remove(name)
+ return true
+ end
+ elseif lfs.isfile(name) then
+ local f = io.open(name,"ab")
+ if f then
+ f:close()
+ return true
+ end
+ else
+ local f = io.open(name,"ab")
+ if f then
+ f:close()
+ os.remove(name)
+ return true
+ end
+ end
+ return false
+ end
+
+ local readable = P("r") * Cc(true)
+
+ function file.is_readable(name)
+ if name then
+ local a = attributes(name)
+ return a and lpegmatch(readable,a.permissions) or false
+ else
+ return false
+ end
+ end
+
+end
+
+file.isreadable = file.is_readable -- depricated
+file.iswritable = file.is_writable -- depricated
+
+function file.size(name)
+ if name then
+ local a = attributes(name)
+ return a and a.size or 0
+ else
+ return 0
+ end
+end
+
+function file.splitpath(str,separator) -- string .. reslash is a bonus (we could do a direct split)
+ return str and checkedsplit(lpegmatch(reslasher,str),separator or io.pathseparator)
+end
+
+function file.joinpath(tab,separator) -- table
+ return tab and concat(tab,separator or io.pathseparator) -- can have trailing //
+end
+
+local someslash = S("\\/")
+local stripper = Cs(P(fwslash)^0/"" * reslasher)
+local isnetwork = someslash * someslash * (1-someslash)
+ + (1-fwslash-colon)^1 * colon
+local isroot = fwslash^1 * -1
+local hasroot = fwslash^1
+
+local reslasher = lpeg.replacer(S("\\/"),"/")
+local deslasher = lpeg.replacer(S("\\/")^1,"/")
+
+-- If we have a network or prefix then there is a change that we end up with two
+-- // in the middle ... we could prevent this if we (1) expand prefixes: and (2)
+-- split and rebuild as url. Of course we could assume no network paths (which
+-- makes sense) adn assume either mapped drives (windows) or mounts (unix) but
+-- then we still have to deal with urls ... anyhow, multiple // are never a real
+-- problem but just ugly.
+
+-- function file.join(...)
+-- local lst = { ... }
+-- local one = lst[1]
+-- if lpegmatch(isnetwork,one) then
+-- local one = lpegmatch(reslasher,one)
+-- local two = lpegmatch(deslasher,concat(lst,"/",2))
+-- if lpegmatch(hasroot,two) then
+-- return one .. two
+-- else
+-- return one .. "/" .. two
+-- end
+-- elseif lpegmatch(isroot,one) then
+-- local two = lpegmatch(deslasher,concat(lst,"/",2))
+-- if lpegmatch(hasroot,two) then
+-- return two
+-- else
+-- return "/" .. two
+-- end
+-- elseif one == "" then
+-- return lpegmatch(stripper,concat(lst,"/",2))
+-- else
+-- return lpegmatch(deslasher,concat(lst,"/"))
+-- end
+-- end
+
+function file.join(one, two, three, ...)
+ if not two then
+ return one == "" and one or lpegmatch(reslasher,one)
+ end
+ if one == "" then
+ return lpegmatch(stripper,three and concat({ two, three, ... },"/") or two)
+ end
+ if lpegmatch(isnetwork,one) then
+ local one = lpegmatch(reslasher,one)
+ local two = lpegmatch(deslasher,three and concat({ two, three, ... },"/") or two)
+ if lpegmatch(hasroot,two) then
+ return one .. two
+ else
+ return one .. "/" .. two
+ end
+ elseif lpegmatch(isroot,one) then
+ local two = lpegmatch(deslasher,three and concat({ two, three, ... },"/") or two)
+ if lpegmatch(hasroot,two) then
+ return two
+ else
+ return "/" .. two
+ end
+ else
+ return lpegmatch(deslasher,concat({ one, two, three, ... },"/"))
+ end
+end
+
+-- or we can use this:
+--
+-- function file.join(...)
+-- local n = select("#",...)
+-- local one = select(1,...)
+-- if n == 1 then
+-- return one == "" and one or lpegmatch(stripper,one)
+-- end
+-- if one == "" then
+-- return lpegmatch(stripper,n > 2 and concat({ ... },"/",2) or select(2,...))
+-- end
+-- if lpegmatch(isnetwork,one) then
+-- local one = lpegmatch(reslasher,one)
+-- local two = lpegmatch(deslasher,n > 2 and concat({ ... },"/",2) or select(2,...))
+-- if lpegmatch(hasroot,two) then
+-- return one .. two
+-- else
+-- return one .. "/" .. two
+-- end
+-- elseif lpegmatch(isroot,one) then
+-- local two = lpegmatch(deslasher,n > 2 and concat({ ... },"/",2) or select(2,...))
+-- if lpegmatch(hasroot,two) then
+-- return two
+-- else
+-- return "/" .. two
+-- end
+-- else
+-- return lpegmatch(deslasher,concat({ ... },"/"))
+-- end
+-- end
+
+-- print(file.join("c:/whatever"))
+-- print(file.join("c:/whatever","name"))
+-- print(file.join("//","/y"))
+-- print(file.join("/","/y"))
+-- print(file.join("","/y"))
+-- print(file.join("/x/","/y"))
+-- print(file.join("x/","/y"))
+-- print(file.join("http://","/y"))
+-- print(file.join("http://a","/y"))
+-- print(file.join("http:///a","/y"))
+-- print(file.join("//nas-1","/y"))
+-- print(file.join("//nas-1/a/b/c","/y"))
+-- print(file.join("\\\\nas-1\\a\\b\\c","\\y"))
+
+-- The previous one fails on "a.b/c" so Taco came up with a split based
+-- variant. After some skyping we got it sort of compatible with the old
+-- one. After that the anchoring to currentdir was added in a better way.
+-- Of course there are some optimizations too. Finally we had to deal with
+-- windows drive prefixes and things like sys://. Eventually gsubs and
+-- finds were replaced by lpegs.
+
+local drivespec = R("az","AZ")^1 * colon
+local anchors = fwslash
+ + drivespec
+local untouched = periods
+ + (1-period)^1 * P(-1)
+local mswindrive = Cs(drivespec * (bwslash/"/" + fwslash)^0)
+local mswinuncpath = (bwslash + fwslash) * (bwslash + fwslash) * Cc("//")
+local splitstarter = (mswindrive + mswinuncpath + Cc(false))
+ * Ct(lpeg.splitat(S("/\\")^1))
+local absolute = fwslash
+
+function file.collapsepath(str,anchor) -- anchor: false|nil, true, "."
+ if not str then
+ return
+ end
+ if anchor == true and not lpegmatch(anchors,str) then
+ str = getcurrentdir() .. "/" .. str
+ end
+ if str == "" or str =="." then
+ return "."
+ elseif lpegmatch(untouched,str) then
+ return lpegmatch(reslasher,str)
+ end
+ local starter, oldelements = lpegmatch(splitstarter,str)
+ local newelements = { }
+ local i = #oldelements
+ while i > 0 do
+ local element = oldelements[i]
+ if element == '.' then
+ -- do nothing
+ elseif element == '..' then
+ local n = i - 1
+ while n > 0 do
+ local element = oldelements[n]
+ if element ~= '..' and element ~= '.' then
+ oldelements[n] = '.'
+ break
+ else
+ n = n - 1
+ end
+ end
+ if n < 1 then
+ insert(newelements,1,'..')
+ end
+ elseif element ~= "" then
+ insert(newelements,1,element)
+ end
+ i = i - 1
+ end
+ if #newelements == 0 then
+ return starter or "."
+ elseif starter then
+ return starter .. concat(newelements, '/')
+ elseif lpegmatch(absolute,str) then
+ return "/" .. concat(newelements,'/')
+ else
+ newelements = concat(newelements, '/')
+ if anchor == "." and find(str,"^%./") then
+ return "./" .. newelements
+ else
+ return newelements
+ end
+ end
+end
+
+-- local function test(str,...)
+-- print(string.format("%-20s %-15s %-30s %-20s",str,file.collapsepath(str),file.collapsepath(str,true),file.collapsepath(str,".")))
+-- end
+-- test("a/b.c/d") test("b.c/d") test("b.c/..")
+-- test("/") test("c:/..") test("sys://..")
+-- test("") test("./") test(".") test("..") test("./..") test("../..")
+-- test("a") test("./a") test("/a") test("a/../..")
+-- test("a/./b/..") test("a/aa/../b/bb") test("a/.././././b/..") test("a/./././b/..")
+-- test("a/b/c/../..") test("./a/b/c/../..") test("a/b/c/../..")
+-- test("./a")
+-- test([[\\a.b.c\d\e]])
+
+local validchars = R("az","09","AZ","--","..")
+local pattern_a = lpeg.replacer(1-validchars)
+local pattern_a = Cs((validchars + P(1)/"-")^1)
+local whatever = P("-")^0 / ""
+local pattern_b = Cs(whatever * (1 - whatever * -1)^1)
+
+function file.robustname(str,strict)
+ if str then
+ str = lpegmatch(pattern_a,str) or str
+ if strict then
+ return lpegmatch(pattern_b,str) or str -- two step is cleaner (less backtracking)
+ else
+ return str
+ end
+ end
+end
+
+local loaddata = io.loaddata
+local savedata = io.savedata
+
+file.readdata = loaddata
+file.savedata = savedata
+
+function file.copy(oldname,newname)
+ if oldname and newname then
+ local data = loaddata(oldname)
+ if data and data ~= "" then
+ savedata(newname,data)
+ end
+ end
+end
+
+-- also rewrite previous
+
+local letter = R("az","AZ") + S("_-+")
+local separator = P("://")
+
+local qualified = period^0 * fwslash
+ + letter * colon
+ + letter^1 * separator
+ + letter^1 * fwslash
+local rootbased = fwslash
+ + letter * colon
+
+lpeg.patterns.qualified = qualified
+lpeg.patterns.rootbased = rootbased
+
+-- ./name ../name /name c: :// name/name
+
+function file.is_qualified_path(filename)
+ return filename and lpegmatch(qualified,filename) ~= nil
+end
+
+function file.is_rootbased_path(filename)
+ return filename and lpegmatch(rootbased,filename) ~= nil
+end
+
+-- function test(t) for k, v in next, t do print(v, "=>", file.splitname(v)) end end
+--
+-- test { "c:", "c:/aa", "c:/aa/bb", "c:/aa/bb/cc", "c:/aa/bb/cc.dd", "c:/aa/bb/cc.dd.ee" }
+-- test { "c:", "c:aa", "c:aa/bb", "c:aa/bb/cc", "c:aa/bb/cc.dd", "c:aa/bb/cc.dd.ee" }
+-- test { "/aa", "/aa/bb", "/aa/bb/cc", "/aa/bb/cc.dd", "/aa/bb/cc.dd.ee" }
+-- test { "aa", "aa/bb", "aa/bb/cc", "aa/bb/cc.dd", "aa/bb/cc.dd.ee" }
+
+-- -- maybe:
+--
+-- if os.type == "windows" then
+-- local currentdir = getcurrentdir
+-- function getcurrentdir()
+-- return lpegmatch(reslasher,currentdir())
+-- end
+-- end
+
+-- for myself:
+
+function file.strip(name,dir)
+ if name then
+ local b, a = match(name,"^(.-)" .. dir .. "(.*)$")
+ return a ~= "" and a or name
+ end
+end
+
+-- local debuglist = {
+-- "pathpart", "basename", "nameonly", "suffixonly", "suffix", "dirname", "extname",
+-- "addsuffix", "removesuffix", "replacesuffix", "join",
+-- "strip","collapsepath", "joinpath", "splitpath",
+-- }
+
+-- for i=1,#debuglist do
+-- local name = debuglist[i]
+-- local f = file[name]
+-- file[name] = function(...)
+-- print(name,f(...))
+-- return f(...)
+-- end
+-- end
+
+-- a goodie: a dumb version of mkdirs (not used in context itself, only
+-- in generic usage)
+
+function lfs.mkdirs(path)
+ local full = ""
+ for sub in gmatch(path,"(/*[^\\/]+)") do -- accepts leading c: and /
+ full = full .. sub
+ -- lfs.isdir("/foo") mistakenly returns true on windows so
+ -- so we don't test and just make as that one is not too picky
+ lfs.mkdir(full)
+ end
+end
+
+-- here is oen i ran into when messign around with xavante code (keppler project)
+-- where it's called in_base .. no gain in using lpeg here
+
+function file.withinbase(path) -- don't go beyond root
+ local l = 0
+ if not find(path,"^/") then
+ path = "/" .. path
+ end
+ for dir in gmatch(path,"/([^/]+)") do
+ if dir == ".." then
+ l = l - 1
+ elseif dir ~= "." then
+ l = l + 1
+ end
+ if l < 0 then
+ return false
+ end
+ end
+ return true
+end
+
+-- not used in context but was in luatex once:
+
+local symlinkattributes = lfs.symlinkattributes
+
+function lfs.readlink(name)
+ return symlinkattributes(name,"target") or nil
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-function.lua b/macros/luatex/generic/luaotfload/fontloader-l-function.lua
new file mode 100644
index 0000000000..7ded8ceecd
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-function.lua
@@ -0,0 +1,11 @@
+if not modules then modules = { } end modules ['l-functions'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+functions = functions or { }
+
+function functions.dummy() end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-io.lua b/macros/luatex/generic/luaotfload/fontloader-l-io.lua
new file mode 100644
index 0000000000..fa3ad3c4cd
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-io.lua
@@ -0,0 +1,473 @@
+if not modules then modules = { } end modules ['l-io'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local io = io
+local open, flush, write, read = io.open, io.flush, io.write, io.read
+local byte, find, gsub, format = string.byte, string.find, string.gsub, string.format
+local concat = table.concat
+----- floor = math.floor
+local type = type
+
+if string.find(os.getenv("PATH"),";",1,true) then
+ io.fileseparator, io.pathseparator = "\\", ";"
+else
+ io.fileseparator, io.pathseparator = "/" , ":"
+end
+
+-- local function readall(f)
+-- return f:read("*all")
+-- end
+
+-- The next one is upto 50% faster on large files and less memory consumption due
+-- to less intermediate large allocations. This phenomena was discussed on the
+-- luatex dev list.
+
+local large = 0x01000000 -- 2^24 16.777.216
+local medium = 0x00100000 -- 2^20 1.048.576
+local small = 0x00020000 -- 2^17 131.072
+
+-- local function readall(f)
+-- local size = f:seek("end")
+-- if size == 0 then
+-- return ""
+-- end
+-- f:seek("set",0)
+-- if size < medium then
+-- return f:read('*all')
+-- else
+-- local step = (size > large) and large or (floor(size/(medium)) * small)
+-- local data = { }
+-- while true do
+-- local r = f:read(step)
+-- if not r then
+-- return concat(data)
+-- else
+-- data[#data+1] = r
+-- end
+-- end
+-- end
+-- end
+
+local function readall(f)
+ -- return f:read("*all")
+ local size = f:seek("end")
+ if size > 0 then
+ f:seek("set",0)
+ return f:read(size)
+ else
+ return ""
+ end
+end
+
+io.readall = readall
+
+function io.loaddata(filename,textmode) -- return nil if empty
+ local f = open(filename,(textmode and 'r') or 'rb')
+ if f then
+ local size = f:seek("end")
+ local data = nil
+ if size > 0 then
+ -- data = f:read("*all")
+ f:seek("set",0)
+ data = f:read(size)
+ end
+ f:close()
+ return data
+ end
+end
+
+-- function io.copydata(source,target,action)
+-- local f = open(source,"rb")
+-- if f then
+-- local g = open(target,"wb")
+-- if g then
+-- local size = f:seek("end")
+-- if size == 0 then
+-- -- empty
+-- else
+-- f:seek("set",0)
+-- if size < medium then
+-- local data = f:read('*all')
+-- if action then
+-- data = action(data)
+-- end
+-- if data then
+-- g:write(data)
+-- end
+-- else
+-- local step = (size > large) and large or (floor(size/(medium)) * small)
+-- while true do
+-- local data = f:read(step)
+-- if data then
+-- if action then
+-- data = action(data)
+-- end
+-- if data then
+-- g:write(data)
+-- end
+-- else
+-- break
+-- end
+-- end
+-- end
+-- end
+-- g:close()
+-- end
+-- f:close()
+-- flush()
+-- end
+-- end
+
+function io.copydata(source,target,action)
+ local f = open(source,"rb")
+ if f then
+ local g = open(target,"wb")
+ if g then
+ local size = f:seek("end")
+ if size > 0 then
+ -- local data = f:read('*all')
+ f:seek("set",0)
+ local data = f:read(size)
+ if action then
+ data = action(data)
+ end
+ if data then
+ g:write(data)
+ end
+ end
+ g:close()
+ end
+ f:close()
+ flush()
+ end
+end
+
+function io.savedata(filename,data,joiner)
+ local f = open(filename,"wb")
+ if f then
+ if type(data) == "table" then
+ f:write(concat(data,joiner or ""))
+ elseif type(data) == "function" then
+ data(f)
+ else
+ f:write(data or "")
+ end
+ f:close()
+ flush()
+ return true
+ else
+ return false
+ end
+end
+
+-- we can also chunk this one if needed: io.lines(filename,chunksize,"*l")
+
+-- ffi.readline
+
+if fio and fio.readline then
+
+ local readline = fio.readline
+
+ function io.loadlines(filename,n) -- return nil if empty
+ local f = open(filename,'r')
+ if not f then
+ -- no file
+ elseif n then
+ local lines = { }
+ for i=1,n do
+ local line = readline(f)
+ if line then
+ lines[i] = line
+ else
+ break
+ end
+ end
+ f:close()
+ lines = concat(lines,"\n")
+ if #lines > 0 then
+ return lines
+ end
+ else
+ local line = readline(f)
+ f:close()
+ if line and #line > 0 then
+ return line
+ end
+ end
+ end
+
+else
+
+ function io.loadlines(filename,n) -- return nil if empty
+ local f = open(filename,'r')
+ if not f then
+ -- no file
+ elseif n then
+ local lines = { }
+ for i=1,n do
+ local line = f:read("*lines")
+ if line then
+ lines[i] = line
+ else
+ break
+ end
+ end
+ f:close()
+ lines = concat(lines,"\n")
+ if #lines > 0 then
+ return lines
+ end
+ else
+ local line = f:read("*line") or ""
+ f:close()
+ if #line > 0 then
+ return line
+ end
+ end
+ end
+
+end
+
+function io.loadchunk(filename,n)
+ local f = open(filename,'rb')
+ if f then
+ local data = f:read(n or 1024)
+ f:close()
+ if #data > 0 then
+ return data
+ end
+ end
+end
+
+function io.exists(filename)
+ local f = open(filename)
+ if f == nil then
+ return false
+ else
+ f:close()
+ return true
+ end
+end
+
+function io.size(filename)
+ local f = open(filename)
+ if f == nil then
+ return 0
+ else
+ local s = f:seek("end")
+ f:close()
+ return s
+ end
+end
+
+local function noflines(f)
+ if type(f) == "string" then
+ local f = open(filename)
+ if f then
+ local n = f and noflines(f) or 0
+ f:close()
+ return n
+ else
+ return 0
+ end
+ else
+ -- todo: load and lpeg
+ local n = 0
+ for _ in f:lines() do
+ n = n + 1
+ end
+ f:seek('set',0)
+ return n
+ end
+end
+
+io.noflines = noflines
+
+-- inlined is faster ... beware, better use util-fil
+
+local nextchar = {
+ [ 4] = function(f)
+ return f:read(1,1,1,1)
+ end,
+ [ 2] = function(f)
+ return f:read(1,1)
+ end,
+ [ 1] = function(f)
+ return f:read(1)
+ end,
+ [-2] = function(f)
+ local a, b = f:read(1,1)
+ return b, a
+ end,
+ [-4] = function(f)
+ local a, b, c, d = f:read(1,1,1,1)
+ return d, c, b, a
+ end
+}
+
+function io.characters(f,n)
+ if f then
+ return nextchar[n or 1], f
+ end
+end
+
+local nextbyte = {
+ [4] = function(f)
+ local a, b, c, d = f:read(1,1,1,1)
+ if d then
+ return byte(a), byte(b), byte(c), byte(d)
+ end
+ end,
+ [3] = function(f)
+ local a, b, c = f:read(1,1,1)
+ if b then
+ return byte(a), byte(b), byte(c)
+ end
+ end,
+ [2] = function(f)
+ local a, b = f:read(1,1)
+ if b then
+ return byte(a), byte(b)
+ end
+ end,
+ [1] = function (f)
+ local a = f:read(1)
+ if a then
+ return byte(a)
+ end
+ end,
+ [-2] = function (f)
+ local a, b = f:read(1,1)
+ if b then
+ return byte(b), byte(a)
+ end
+ end,
+ [-3] = function(f)
+ local a, b, c = f:read(1,1,1)
+ if b then
+ return byte(c), byte(b), byte(a)
+ end
+ end,
+ [-4] = function(f)
+ local a, b, c, d = f:read(1,1,1,1)
+ if d then
+ return byte(d), byte(c), byte(b), byte(a)
+ end
+ end
+}
+
+function io.bytes(f,n)
+ if f then
+ return nextbyte[n or 1], f
+ else
+ return nil, nil
+ end
+end
+
+function io.ask(question,default,options)
+ while true do
+ write(question)
+ if options then
+ write(format(" [%s]",concat(options,"|")))
+ end
+ if default then
+ write(format(" [%s]",default))
+ end
+ write(format(" "))
+ flush()
+ local answer = read()
+ answer = gsub(answer,"^%s*(.*)%s*$","%1")
+ if answer == "" and default then
+ return default
+ elseif not options then
+ return answer
+ else
+ for k=1,#options do
+ if options[k] == answer then
+ return answer
+ end
+ end
+ local pattern = "^" .. answer
+ for k=1,#options do
+ local v = options[k]
+ if find(v,pattern) then
+ return v
+ end
+ end
+ end
+ end
+end
+
+local function readnumber(f,n,m) -- to be replaced
+ if m then
+ f:seek("set",n)
+ n = m
+ end
+ if n == 1 then
+ return byte(f:read(1))
+ elseif n == 2 then
+ local a, b = byte(f:read(2),1,2)
+ return 0x100 * a + b
+ elseif n == 3 then
+ local a, b, c = byte(f:read(3),1,3)
+ return 0x10000 * a + 0x100 * b + c
+ elseif n == 4 then
+ local a, b, c, d = byte(f:read(4),1,4)
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d
+ elseif n == 8 then
+ local a, b = readnumber(f,4), readnumber(f,4)
+ return 0x100 * a + b
+ elseif n == 12 then
+ local a, b, c = readnumber(f,4), readnumber(f,4), readnumber(f,4)
+ return 0x10000 * a + 0x100 * b + c
+ elseif n == -2 then
+ local b, a = byte(f:read(2),1,2)
+ return 0x100 * a + b
+ elseif n == -3 then
+ local c, b, a = byte(f:read(3),1,3)
+ return 0x10000 * a + 0x100 * b + c
+ elseif n == -4 then
+ local d, c, b, a = byte(f:read(4),1,4)
+ return 0x1000000 * a + 0x10000 * b + 0x100*c + d
+ elseif n == -8 then
+ local h, g, f, e, d, c, b, a = byte(f:read(8),1,8)
+ return 0x100000000000000 * a + 0x1000000000000 * b + 0x10000000000 * c + 0x100000000 * d +
+ 0x1000000 * e + 0x10000 * f + 0x100 * g + h
+ else
+ return 0
+ end
+end
+
+io.readnumber = readnumber
+
+function io.readstring(f,n,m)
+ if m then
+ f:seek("set",n)
+ n = m
+ end
+ local str = gsub(f:read(n),"\000","")
+ return str
+end
+
+-- This works quite ok:
+--
+-- function io.piped(command,writer)
+-- local pipe = io.popen(command)
+-- -- for line in pipe:lines() do
+-- -- print(line)
+-- -- end
+-- while true do
+-- local line = pipe:read(1)
+-- if not line then
+-- break
+-- elseif line ~= "\n" then
+-- writer(line)
+-- end
+-- end
+-- return pipe:close() -- ok, status, (error)code
+-- end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-lpeg.lua b/macros/luatex/generic/luaotfload/fontloader-l-lpeg.lua
new file mode 100644
index 0000000000..51bc1d3df3
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-lpeg.lua
@@ -0,0 +1,1196 @@
+if not modules then modules = { } end modules ['l-lpeg'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- we can get too many captures (e.g. on largexml files) which makes me wonder
+-- if P(foo)/"" can't be simplfied to N(foo) i.e. some direct instruction to the
+-- lpeg virtual machine to ignore it
+
+-- lpeg 12 vs lpeg 10: slower compilation, similar parsing speed (i need to check
+-- if i can use new features like capture / 2 and .B (at first sight the xml
+-- parser is some 5% slower)
+
+-- lpeg.P("abc") is faster than lpeg.P("a") * lpeg.P("b") * lpeg.P("c")
+
+-- a new lpeg fails on a #(1-P(":")) test and really needs a + P(-1)
+
+-- move utf -> l-unicode
+-- move string -> l-string or keep it here
+
+-- lpeg.B : backward without consumption
+-- lpeg.F = getmetatable(lpeg.P(1)).__len : forward without consumption
+
+
+lpeg = require("lpeg") -- does lpeg register itself global?
+
+local lpeg = lpeg
+
+-- The latest lpeg doesn't have print any more, and even the new ones are not
+-- available by default (only when debug mode is enabled), which is a pitty as
+-- as it helps nailing down bottlenecks. Performance seems comparable: some 10%
+-- slower pattern compilation, same parsing speed, although,
+--
+-- local p = lpeg.C(lpeg.P(1)^0 * lpeg.P(-1))
+-- local a = string.rep("123",100)
+-- lpeg.match(p,a)
+--
+-- seems slower and is also still suboptimal (i.e. a match that runs from begin
+-- to end, one of the cases where string matchers win).
+
+if not lpeg.print then function lpeg.print(...) print(lpeg.pcode(...)) end end
+
+-- tracing (only used when we encounter a problem in integration of lpeg in luatex)
+
+-- some code will move to unicode and string
+
+-- local lpmatch = lpeg.match
+-- local lpprint = lpeg.print
+-- local lpp = lpeg.P
+-- local lpr = lpeg.R
+-- local lps = lpeg.S
+-- local lpc = lpeg.C
+-- local lpb = lpeg.B
+-- local lpv = lpeg.V
+-- local lpcf = lpeg.Cf
+-- local lpcb = lpeg.Cb
+-- local lpcg = lpeg.Cg
+-- local lpct = lpeg.Ct
+-- local lpcs = lpeg.Cs
+-- local lpcc = lpeg.Cc
+-- local lpcmt = lpeg.Cmt
+-- local lpcarg = lpeg.Carg
+
+-- function lpeg.match(l,...) print("LPEG MATCH") lpprint(l) return lpmatch(l,...) end
+
+-- function lpeg.P (l) local p = lpp (l) print("LPEG P =") lpprint(l) return p end
+-- function lpeg.R (l) local p = lpr (l) print("LPEG R =") lpprint(l) return p end
+-- function lpeg.S (l) local p = lps (l) print("LPEG S =") lpprint(l) return p end
+-- function lpeg.C (l) local p = lpc (l) print("LPEG C =") lpprint(l) return p end
+-- function lpeg.B (l) local p = lpb (l) print("LPEG B =") lpprint(l) return p end
+-- function lpeg.V (l) local p = lpv (l) print("LPEG V =") lpprint(l) return p end
+-- function lpeg.Cf (l) local p = lpcf (l) print("LPEG Cf =") lpprint(l) return p end
+-- function lpeg.Cb (l) local p = lpcb (l) print("LPEG Cb =") lpprint(l) return p end
+-- function lpeg.Cg (l) local p = lpcg (l) print("LPEG Cg =") lpprint(l) return p end
+-- function lpeg.Ct (l) local p = lpct (l) print("LPEG Ct =") lpprint(l) return p end
+-- function lpeg.Cs (l) local p = lpcs (l) print("LPEG Cs =") lpprint(l) return p end
+-- function lpeg.Cc (l) local p = lpcc (l) print("LPEG Cc =") lpprint(l) return p end
+-- function lpeg.Cmt (l) local p = lpcmt (l) print("LPEG Cmt =") lpprint(l) return p end
+-- function lpeg.Carg (l) local p = lpcarg(l) print("LPEG Carg =") lpprint(l) return p end
+
+local type, next, tostring = type, next, tostring
+local byte, char, gmatch, format = string.byte, string.char, string.gmatch, string.format
+----- mod, div = math.mod, math.div
+local floor = math.floor
+
+local P, R, S, V, Ct, C, Cs, Cc, Cp, Cmt = lpeg.P, lpeg.R, lpeg.S, lpeg.V, lpeg.Ct, lpeg.C, lpeg.Cs, lpeg.Cc, lpeg.Cp, lpeg.Cmt
+local lpegtype, lpegmatch, lpegprint = lpeg.type, lpeg.match, lpeg.print
+
+-- let's start with an inspector:
+
+if setinspector then
+ setinspector("lpeg",function(v) if lpegtype(v) then lpegprint(v) return true end end)
+end
+
+-- Beware, we predefine a bunch of patterns here and one reason for doing so
+-- is that we get consistent behaviour in some of the visualizers.
+
+lpeg.patterns = lpeg.patterns or { } -- so that we can share
+local patterns = lpeg.patterns
+
+local anything = P(1)
+local endofstring = P(-1)
+local alwaysmatched = P(true)
+
+patterns.anything = anything
+patterns.endofstring = endofstring
+patterns.beginofstring = alwaysmatched
+patterns.alwaysmatched = alwaysmatched
+
+local sign = S('+-')
+local zero = P('0')
+local digit = R('09')
+local digits = digit^1
+local octdigit = R("07")
+local octdigits = octdigit^1
+local lowercase = R("az")
+local uppercase = R("AZ")
+local underscore = P("_")
+local hexdigit = digit + lowercase + uppercase
+local hexdigits = hexdigit^1
+local cr, lf, crlf = P("\r"), P("\n"), P("\r\n")
+----- newline = crlf + S("\r\n") -- cr + lf
+local newline = P("\r") * (P("\n") + P(true)) + P("\n") -- P("\r")^-1 * P("\n")^-1
+local escaped = P("\\") * anything
+local squote = P("'")
+local dquote = P('"')
+local space = P(" ")
+local period = P(".")
+local comma = P(",")
+
+local utfbom_32_be = P('\000\000\254\255') -- 00 00 FE FF
+local utfbom_32_le = P('\255\254\000\000') -- FF FE 00 00
+local utfbom_16_be = P('\254\255') -- FE FF
+local utfbom_16_le = P('\255\254') -- FF FE
+local utfbom_8 = P('\239\187\191') -- EF BB BF
+local utfbom = utfbom_32_be + utfbom_32_le
+ + utfbom_16_be + utfbom_16_le
+ + utfbom_8
+local utftype = utfbom_32_be * Cc("utf-32-be") + utfbom_32_le * Cc("utf-32-le")
+ + utfbom_16_be * Cc("utf-16-be") + utfbom_16_le * Cc("utf-16-le")
+ + utfbom_8 * Cc("utf-8") + alwaysmatched * Cc("utf-8") -- assume utf8
+local utfstricttype = utfbom_32_be * Cc("utf-32-be") + utfbom_32_le * Cc("utf-32-le")
+ + utfbom_16_be * Cc("utf-16-be") + utfbom_16_le * Cc("utf-16-le")
+ + utfbom_8 * Cc("utf-8")
+local utfoffset = utfbom_32_be * Cc(4) + utfbom_32_le * Cc(4)
+ + utfbom_16_be * Cc(2) + utfbom_16_le * Cc(2)
+ + utfbom_8 * Cc(3) + Cc(0)
+
+local utf8next = R("\128\191")
+
+patterns.utfbom_32_be = utfbom_32_be
+patterns.utfbom_32_le = utfbom_32_le
+patterns.utfbom_16_be = utfbom_16_be
+patterns.utfbom_16_le = utfbom_16_le
+patterns.utfbom_8 = utfbom_8
+
+patterns.utf_16_be_nl = P("\000\r\000\n") + P("\000\r") + P("\000\n") -- P("\000\r") * (P("\000\n") + P(true)) + P("\000\n")
+patterns.utf_16_le_nl = P("\r\000\n\000") + P("\r\000") + P("\n\000") -- P("\r\000") * (P("\n\000") + P(true)) + P("\n\000")
+
+patterns.utf_32_be_nl = P("\000\000\000\r\000\000\000\n") + P("\000\000\000\r") + P("\000\000\000\n")
+patterns.utf_32_le_nl = P("\r\000\000\000\n\000\000\000") + P("\r\000\000\000") + P("\n\000\000\000")
+
+patterns.utf8one = R("\000\127")
+patterns.utf8two = R("\194\223") * utf8next
+patterns.utf8three = R("\224\239") * utf8next * utf8next
+patterns.utf8four = R("\240\244") * utf8next * utf8next * utf8next
+patterns.utfbom = utfbom
+patterns.utftype = utftype
+patterns.utfstricttype = utfstricttype
+patterns.utfoffset = utfoffset
+
+local utf8char = patterns.utf8one + patterns.utf8two + patterns.utf8three + patterns.utf8four
+local validutf8char = utf8char^0 * endofstring * Cc(true) + Cc(false)
+
+local utf8character = P(1) * R("\128\191")^0 -- unchecked but fast
+
+patterns.utf8 = utf8char
+patterns.utf8char = utf8char
+patterns.utf8character = utf8character -- this one can be used in most cases so we might use that one
+patterns.validutf8 = validutf8char
+patterns.validutf8char = validutf8char
+
+local eol = S("\n\r")
+local spacer = S(" \t\f\v") -- + char(0xc2, 0xa0) if we want utf (cf mail roberto)
+local whitespace = eol + spacer
+local nonspacer = 1 - spacer
+local nonwhitespace = 1 - whitespace
+
+patterns.eol = eol
+patterns.spacer = spacer
+patterns.whitespace = whitespace
+patterns.nonspacer = nonspacer
+patterns.nonwhitespace = nonwhitespace
+
+local stripper = spacer ^0 * C((spacer ^0 * nonspacer ^1)^0) -- from example by roberto
+local fullstripper = whitespace^0 * C((whitespace^0 * nonwhitespace^1)^0)
+
+----- collapser = Cs(spacer^0/"" * ((spacer^1 * endofstring / "") + (spacer^1/" ") + P(1))^0)
+local collapser = Cs(spacer^0/"" * nonspacer^0 * ((spacer^0/" " * nonspacer^1)^0))
+local nospacer = Cs((whitespace^1/"" + nonwhitespace^1)^0)
+
+local b_collapser = Cs( whitespace^0 /"" * (nonwhitespace^1 + whitespace^1/" ")^0)
+local e_collapser = Cs((whitespace^1 * endofstring/"" + nonwhitespace^1 + whitespace^1/" ")^0)
+local m_collapser = Cs( (nonwhitespace^1 + whitespace^1/" ")^0)
+
+local b_stripper = Cs( spacer^0 /"" * (nonspacer^1 + spacer^1/" ")^0)
+local e_stripper = Cs((spacer^1 * endofstring/"" + nonspacer^1 + spacer^1/" ")^0)
+local m_stripper = Cs( (nonspacer^1 + spacer^1/" ")^0)
+
+patterns.stripper = stripper
+patterns.fullstripper = fullstripper
+patterns.collapser = collapser
+patterns.nospacer = nospacer
+
+patterns.b_collapser = b_collapser
+patterns.m_collapser = m_collapser
+patterns.e_collapser = e_collapser
+
+patterns.b_stripper = b_stripper
+patterns.m_stripper = m_stripper
+patterns.e_stripper = e_stripper
+
+patterns.lowercase = lowercase
+patterns.uppercase = uppercase
+patterns.letter = patterns.lowercase + patterns.uppercase
+patterns.space = space
+patterns.tab = P("\t")
+patterns.spaceortab = patterns.space + patterns.tab
+patterns.newline = newline
+patterns.emptyline = newline^1
+patterns.equal = P("=")
+patterns.comma = comma
+patterns.commaspacer = comma * spacer^0
+patterns.period = period
+patterns.colon = P(":")
+patterns.semicolon = P(";")
+patterns.underscore = underscore
+patterns.escaped = escaped
+patterns.squote = squote
+patterns.dquote = dquote
+patterns.nosquote = (escaped + (1-squote))^0
+patterns.nodquote = (escaped + (1-dquote))^0
+patterns.unsingle = (squote/"") * patterns.nosquote * (squote/"") -- will change to C in the middle
+patterns.undouble = (dquote/"") * patterns.nodquote * (dquote/"") -- will change to C in the middle
+patterns.unquoted = patterns.undouble + patterns.unsingle -- more often undouble
+patterns.unspacer = ((patterns.spacer^1)/"")^0
+
+patterns.singlequoted = squote * patterns.nosquote * squote
+patterns.doublequoted = dquote * patterns.nodquote * dquote
+patterns.quoted = patterns.doublequoted + patterns.singlequoted
+
+patterns.digit = digit
+patterns.digits = digits
+patterns.octdigit = octdigit
+patterns.octdigits = octdigits
+patterns.hexdigit = hexdigit
+patterns.hexdigits = hexdigits
+patterns.sign = sign
+patterns.cardinal = digits
+patterns.integer = sign^-1 * digits
+patterns.unsigned = digit^0 * period * digits
+patterns.float = sign^-1 * patterns.unsigned
+patterns.cunsigned = digit^0 * comma * digits
+patterns.cpunsigned = digit^0 * (period + comma) * digits
+patterns.cfloat = sign^-1 * patterns.cunsigned
+patterns.cpfloat = sign^-1 * patterns.cpunsigned
+patterns.number = patterns.float + patterns.integer
+patterns.cnumber = patterns.cfloat + patterns.integer
+patterns.cpnumber = patterns.cpfloat + patterns.integer
+patterns.oct = zero * octdigits -- hm is this ok
+patterns.octal = patterns.oct
+patterns.HEX = zero * P("X") * (digit+uppercase)^1
+patterns.hex = zero * P("x") * (digit+lowercase)^1
+patterns.hexadecimal = zero * S("xX") * hexdigits
+
+patterns.hexafloat = sign^-1
+ * zero * S("xX")
+ * (hexdigit^0 * period * hexdigits + hexdigits * period * hexdigit^0 + hexdigits)
+ * (S("pP") * sign^-1 * hexdigits)^-1
+patterns.decafloat = sign^-1
+ * (digit^0 * period * digits + digits * period * digit^0 + digits)
+ * S("eE") * sign^-1 * digits
+
+patterns.propername = (uppercase + lowercase + underscore) * (uppercase + lowercase + underscore + digit)^0 * endofstring
+
+patterns.somecontent = (anything - newline - space)^1 -- (utf8char - newline - space)^1
+patterns.beginline = #(1-newline)
+
+patterns.longtostring = Cs(whitespace^0/"" * ((patterns.quoted + nonwhitespace^1 + whitespace^1/"" * (endofstring + Cc(" ")))^0))
+
+-- local function anywhere(pattern) -- slightly adapted from website
+-- return P { P(pattern) + 1 * V(1) }
+-- end
+
+function anywhere(pattern) -- faster
+ return (1-P(pattern))^0 * P(pattern)
+end
+
+lpeg.anywhere = anywhere
+
+function lpeg.instringchecker(p)
+ p = anywhere(p)
+ return function(str)
+ return lpegmatch(p,str) and true or false
+ end
+end
+
+-- function lpeg.splitter(pattern, action)
+-- return (((1-P(pattern))^1)/action+1)^0
+-- end
+
+-- function lpeg.tsplitter(pattern, action)
+-- return Ct((((1-P(pattern))^1)/action+1)^0)
+-- end
+
+function lpeg.splitter(pattern, action)
+ if action then
+ return (((1-P(pattern))^1)/action+1)^0
+ else
+ return (Cs((1-P(pattern))^1)+1)^0
+ end
+end
+
+function lpeg.tsplitter(pattern, action)
+ if action then
+ return Ct((((1-P(pattern))^1)/action+1)^0)
+ else
+ return Ct((Cs((1-P(pattern))^1)+1)^0)
+ end
+end
+
+-- probleem: separator can be lpeg and that does not hash too well, but
+-- it's quite okay as the key is then not garbage collected
+
+local splitters_s, splitters_m, splitters_t = { }, { }, { }
+
+local function splitat(separator,single)
+ local splitter = (single and splitters_s[separator]) or splitters_m[separator]
+ if not splitter then
+ separator = P(separator)
+ local other = C((1 - separator)^0)
+ if single then
+ local any = anything
+ splitter = other * (separator * C(any^0) + "") -- ?
+ splitters_s[separator] = splitter
+ else
+ splitter = other * (separator * other)^0
+ splitters_m[separator] = splitter
+ end
+ end
+ return splitter
+end
+
+local function tsplitat(separator)
+ local splitter = splitters_t[separator]
+ if not splitter then
+ splitter = Ct(splitat(separator))
+ splitters_t[separator] = splitter
+ end
+ return splitter
+end
+
+lpeg.splitat = splitat
+lpeg.tsplitat = tsplitat
+
+function string.splitup(str,separator)
+ if not separator then
+ separator = ","
+ end
+ return lpegmatch(splitters_m[separator] or splitat(separator),str)
+end
+
+-- local p = splitat("->",false) print(lpegmatch(p,"oeps->what->more")) -- oeps what more
+-- local p = splitat("->",true) print(lpegmatch(p,"oeps->what->more")) -- oeps what->more
+-- local p = splitat("->",false) print(lpegmatch(p,"oeps")) -- oeps
+-- local p = splitat("->",true) print(lpegmatch(p,"oeps")) -- oeps
+
+local cache = { }
+
+function lpeg.split(separator,str)
+ local c = cache[separator]
+ if not c then
+ c = tsplitat(separator)
+ cache[separator] = c
+ end
+ return lpegmatch(c,str)
+end
+
+function string.split(str,separator)
+ if separator then
+ local c = cache[separator]
+ if not c then
+ c = tsplitat(separator)
+ cache[separator] = c
+ end
+ return lpegmatch(c,str)
+ else
+ return { str }
+ end
+end
+
+local spacing = patterns.spacer^0 * newline -- sort of strip
+local empty = spacing * Cc("")
+local nonempty = Cs((1-spacing)^1) * spacing^-1
+local content = (empty + nonempty)^1
+
+patterns.textline = content
+
+local linesplitter = tsplitat(newline)
+
+patterns.linesplitter = linesplitter
+
+function string.splitlines(str)
+ return lpegmatch(linesplitter,str)
+end
+
+-- lpeg.splitters = cache -- no longer public
+
+local cache = { }
+
+function lpeg.checkedsplit(separator,str)
+ local c = cache[separator]
+ if not c then
+ separator = P(separator)
+ local other = C((1 - separator)^1)
+ c = Ct(separator^0 * other * (separator^1 * other)^0)
+ cache[separator] = c
+ end
+ return lpegmatch(c,str)
+end
+
+function string.checkedsplit(str,separator)
+ local c = cache[separator]
+ if not c then
+ separator = P(separator)
+ local other = C((1 - separator)^1)
+ c = Ct(separator^0 * other * (separator^1 * other)^0)
+ cache[separator] = c
+ end
+ return lpegmatch(c,str)
+end
+
+-- from roberto's site:
+
+local function f2(s) local c1, c2 = byte(s,1,2) return c1 * 64 + c2 - 12416 end
+local function f3(s) local c1, c2, c3 = byte(s,1,3) return (c1 * 64 + c2) * 64 + c3 - 925824 end
+local function f4(s) local c1, c2, c3, c4 = byte(s,1,4) return ((c1 * 64 + c2) * 64 + c3) * 64 + c4 - 63447168 end
+
+local utf8byte = patterns.utf8one/byte + patterns.utf8two/f2 + patterns.utf8three/f3 + patterns.utf8four/f4
+
+patterns.utf8byte = utf8byte
+
+--~ local str = " a b c d "
+
+--~ local s = lpeg.stripper(lpeg.R("az")) print("["..lpegmatch(s,str).."]")
+--~ local s = lpeg.keeper(lpeg.R("az")) print("["..lpegmatch(s,str).."]")
+--~ local s = lpeg.stripper("ab") print("["..lpegmatch(s,str).."]")
+--~ local s = lpeg.keeper("ab") print("["..lpegmatch(s,str).."]")
+
+local cache = { }
+
+function lpeg.stripper(str)
+ if type(str) == "string" then
+ local s = cache[str]
+ if not s then
+ s = Cs(((S(str)^1)/"" + 1)^0)
+ cache[str] = s
+ end
+ return s
+ else
+ return Cs(((str^1)/"" + 1)^0)
+ end
+end
+
+local cache = { }
+
+function lpeg.keeper(str)
+ if type(str) == "string" then
+ local s = cache[str]
+ if not s then
+ s = Cs((((1-S(str))^1)/"" + 1)^0)
+ cache[str] = s
+ end
+ return s
+ else
+ return Cs((((1-str)^1)/"" + 1)^0)
+ end
+end
+
+function lpeg.frontstripper(str) -- or pattern (yet undocumented)
+ return (P(str) + P(true)) * Cs(anything^0)
+end
+
+function lpeg.endstripper(str) -- or pattern (yet undocumented)
+ return Cs((1 - P(str) * endofstring)^0)
+end
+
+-- Just for fun I looked at the used bytecode and
+-- p = (p and p + pp) or pp gets one more (testset).
+
+-- todo: cache when string
+
+function lpeg.replacer(one,two,makefunction,isutf) -- in principle we should sort the keys
+ local pattern
+ local u = isutf and utf8char or 1
+ if type(one) == "table" then
+ local no = #one
+ local p = P(false)
+ if no == 0 then
+ for k, v in next, one do
+ p = p + P(k) / v
+ end
+ pattern = Cs((p + u)^0)
+ elseif no == 1 then
+ local o = one[1]
+ one, two = P(o[1]), o[2]
+ -- pattern = Cs(((1-one)^1 + one/two)^0)
+ pattern = Cs((one/two + u)^0)
+ else
+ for i=1,no do
+ local o = one[i]
+ p = p + P(o[1]) / o[2]
+ end
+ pattern = Cs((p + u)^0)
+ end
+ else
+ pattern = Cs((P(one)/(two or "") + u)^0)
+ end
+ if makefunction then
+ return function(str)
+ return lpegmatch(pattern,str)
+ end
+ else
+ return pattern
+ end
+end
+
+-- local pattern1 = P(1-P(pattern))^0 * P(pattern) : test for not nil
+-- local pattern2 = (P(pattern) * Cc(true) + P(1))^0 : test for true (could be faster, but not much)
+
+function lpeg.finder(lst,makefunction,isutf) -- beware: slower than find with 'patternless finds'
+ local pattern
+ if type(lst) == "table" then
+ pattern = P(false)
+ if #lst == 0 then
+ for k, v in next, lst do
+ pattern = pattern + P(k) -- ignore key, so we can use a replacer table
+ end
+ else
+ for i=1,#lst do
+ pattern = pattern + P(lst[i])
+ end
+ end
+ else
+ pattern = P(lst)
+ end
+ if isutf then
+ pattern = ((utf8char or 1)-pattern)^0 * pattern
+ else
+ pattern = (1-pattern)^0 * pattern
+ end
+ if makefunction then
+ return function(str)
+ return lpegmatch(pattern,str)
+ end
+ else
+ return pattern
+ end
+end
+
+-- print(lpeg.match(lpeg.replacer("e","a"),"test test"))
+-- print(lpeg.match(lpeg.replacer{{"e","a"}},"test test"))
+-- print(lpeg.match(lpeg.replacer({ e = "a", t = "x" }),"test test"))
+
+local splitters_f, splitters_s = { }, { }
+
+function lpeg.firstofsplit(separator) -- always return value
+ local splitter = splitters_f[separator]
+ if not splitter then
+ local pattern = P(separator)
+ splitter = C((1 - pattern)^0)
+ splitters_f[separator] = splitter
+ end
+ return splitter
+end
+
+function lpeg.secondofsplit(separator) -- nil if not split
+ local splitter = splitters_s[separator]
+ if not splitter then
+ local pattern = P(separator)
+ splitter = (1 - pattern)^0 * pattern * C(anything^0)
+ splitters_s[separator] = splitter
+ end
+ return splitter
+end
+
+local splitters_s, splitters_p = { }, { }
+
+function lpeg.beforesuffix(separator) -- nil if nothing but empty is ok
+ local splitter = splitters_s[separator]
+ if not splitter then
+ local pattern = P(separator)
+ splitter = C((1 - pattern)^0) * pattern * endofstring
+ splitters_s[separator] = splitter
+ end
+ return splitter
+end
+
+function lpeg.afterprefix(separator) -- nil if nothing but empty is ok
+ local splitter = splitters_p[separator]
+ if not splitter then
+ local pattern = P(separator)
+ splitter = pattern * C(anything^0)
+ splitters_p[separator] = splitter
+ end
+ return splitter
+end
+
+function lpeg.balancer(left,right)
+ left, right = P(left), P(right)
+ return P { left * ((1 - left - right) + V(1))^0 * right }
+end
+
+-- print(1,lpegmatch(lpeg.firstofsplit(":"),"bc:de"))
+-- print(2,lpegmatch(lpeg.firstofsplit(":"),":de")) -- empty
+-- print(3,lpegmatch(lpeg.firstofsplit(":"),"bc"))
+-- print(4,lpegmatch(lpeg.secondofsplit(":"),"bc:de"))
+-- print(5,lpegmatch(lpeg.secondofsplit(":"),"bc:")) -- empty
+-- print(6,lpegmatch(lpeg.secondofsplit(":",""),"bc"))
+-- print(7,lpegmatch(lpeg.secondofsplit(":"),"bc"))
+-- print(9,lpegmatch(lpeg.secondofsplit(":","123"),"bc"))
+
+-- this was slower but lpeg has been sped up in the meantime, so we no longer
+-- use this (still seems somewhat faster on long strings)
+--
+-- local nany = utf8char/""
+--
+-- function lpeg.counter(pattern)
+-- pattern = Cs((P(pattern)/" " + nany)^0)
+-- return function(str)
+-- return #lpegmatch(pattern,str)
+-- end
+-- end
+
+function lpeg.counter(pattern,action)
+ local n = 0
+ local pattern = (P(pattern) / function() n = n + 1 end + anything)^0
+ ----- pattern = (P(pattern) * (P(true) / function() n = n + 1 end) + anything)^0
+ ----- pattern = (P(pattern) * P(function() n = n + 1 end) + anything)^0
+ if action then
+ return function(str) n = 0 ; lpegmatch(pattern,str) ; action(n) end
+ else
+ return function(str) n = 0 ; lpegmatch(pattern,str) ; return n end
+ end
+end
+
+-- lpeg.print(lpeg.R("ab","cd","gh"))
+-- lpeg.print(lpeg.P("a","b","c"))
+-- lpeg.print(lpeg.S("a","b","c"))
+
+-- print(lpeg.count("äáàa",lpeg.P("á") + lpeg.P("à")))
+-- print(lpeg.count("äáàa",lpeg.UP("áà")))
+-- print(lpeg.count("äáàa",lpeg.US("àá")))
+-- print(lpeg.count("äáàa",lpeg.UR("aá")))
+-- print(lpeg.count("äáàa",lpeg.UR("àá")))
+-- print(lpeg.count("äáàa",lpeg.UR(0x0000,0xFFFF)))
+
+function lpeg.is_lpeg(p)
+ return p and lpegtype(p) == "pattern"
+end
+
+function lpeg.oneof(list,...) -- lpeg.oneof("elseif","else","if","then") -- assume proper order
+ if type(list) ~= "table" then
+ list = { list, ... }
+ end
+ -- table.sort(list) -- longest match first
+ local p = P(list[1])
+ for l=2,#list do
+ p = p + P(list[l])
+ end
+ return p
+end
+
+-- For the moment here, but it might move to utilities. Beware, we need to
+-- have the longest keyword first, so 'aaa' comes beforte 'aa' which is why we
+-- loop back from the end cq. prepend.
+
+local sort = table.sort
+
+local function copyindexed(old)
+ local new = { }
+ for i=1,#old do
+ new[i] = old
+ end
+ return new
+end
+
+local function sortedkeys(tab)
+ local keys, s = { }, 0
+ for key,_ in next, tab do
+ s = s + 1
+ keys[s] = key
+ end
+ sort(keys)
+ return keys
+end
+
+function lpeg.append(list,pp,delayed,checked)
+ local p = pp
+ if #list > 0 then
+ local keys = copyindexed(list)
+ sort(keys)
+ for i=#keys,1,-1 do
+ local k = keys[i]
+ if p then
+ p = P(k) + p
+ else
+ p = P(k)
+ end
+ end
+ elseif delayed then -- hm, it looks like the lpeg parser resolves anyway
+ local keys = sortedkeys(list)
+ if p then
+ for i=1,#keys,1 do
+ local k = keys[i]
+ local v = list[k]
+ p = P(k)/list + p
+ end
+ else
+ for i=1,#keys do
+ local k = keys[i]
+ local v = list[k]
+ if p then
+ p = P(k) + p
+ else
+ p = P(k)
+ end
+ end
+ if p then
+ p = p / list
+ end
+ end
+ elseif checked then
+ -- problem: substitution gives a capture
+ local keys = sortedkeys(list)
+ for i=1,#keys do
+ local k = keys[i]
+ local v = list[k]
+ if p then
+ if k == v then
+ p = P(k) + p
+ else
+ p = P(k)/v + p
+ end
+ else
+ if k == v then
+ p = P(k)
+ else
+ p = P(k)/v
+ end
+ end
+ end
+ else
+ local keys = sortedkeys(list)
+ for i=1,#keys do
+ local k = keys[i]
+ local v = list[k]
+ if p then
+ p = P(k)/v + p
+ else
+ p = P(k)/v
+ end
+ end
+ end
+ return p
+end
+
+-- inspect(lpeg.append({ a = "1", aa = "1", aaa = "1" } ,nil,true))
+-- inspect(lpeg.append({ ["degree celsius"] = "1", celsius = "1", degree = "1" } ,nil,true))
+
+-- function lpeg.exact_match(words,case_insensitive)
+-- local pattern = concat(words)
+-- if case_insensitive then
+-- local pattern = S(upper(characters)) + S(lower(characters))
+-- local list = { }
+-- for i=1,#words do
+-- list[lower(words[i])] = true
+-- end
+-- return Cmt(pattern^1, function(_,i,s)
+-- return list[lower(s)] and i
+-- end)
+-- else
+-- local pattern = S(concat(words))
+-- local list = { }
+-- for i=1,#words do
+-- list[words[i]] = true
+-- end
+-- return Cmt(pattern^1, function(_,i,s)
+-- return list[s] and i
+-- end)
+-- end
+-- end
+
+-- experiment:
+
+local p_false = P(false)
+local p_true = P(true)
+
+-- local function collapse(t,x)
+-- if type(t) ~= "table" then
+-- return t, x
+-- else
+-- local n = next(t)
+-- if n == nil then
+-- return t, x
+-- elseif next(t,n) == nil then
+-- -- one entry
+-- local k = n
+-- local v = t[k]
+-- if type(v) == "table" then
+-- return collapse(v,x..k)
+-- else
+-- return v, x .. k
+-- end
+-- else
+-- local tt = { }
+-- for k, v in next, t do
+-- local vv, kk = collapse(v,k)
+-- tt[kk] = vv
+-- end
+-- return tt, x
+-- end
+-- end
+-- end
+
+local lower = utf and utf.lower or string.lower
+local upper = utf and utf.upper or string.upper
+
+function lpeg.setutfcasers(l,u)
+ lower = l or lower
+ upper = u or upper
+end
+
+local function make1(t,rest)
+ local p = p_false
+ local keys = sortedkeys(t)
+ for i=1,#keys do
+ local k = keys[i]
+ if k ~= "" then
+ local v = t[k]
+ if v == true then
+ p = p + P(k) * p_true
+ elseif v == false then
+ -- can't happen
+ else
+ p = p + P(k) * make1(v,v[""])
+ end
+ end
+ end
+ if rest then
+ p = p + p_true
+ end
+ return p
+end
+
+local function make2(t,rest) -- only ascii
+ local p = p_false
+ local keys = sortedkeys(t)
+ for i=1,#keys do
+ local k = keys[i]
+ if k ~= "" then
+ local v = t[k]
+ if v == true then
+ p = p + (P(lower(k))+P(upper(k))) * p_true
+ elseif v == false then
+ -- can't happen
+ else
+ p = p + (P(lower(k))+P(upper(k))) * make2(v,v[""])
+ end
+ end
+ end
+ if rest then
+ p = p + p_true
+ end
+ return p
+end
+
+local function utfchartabletopattern(list,insensitive) -- goes to util-lpg
+ local tree = { }
+ local n = #list
+ if n == 0 then
+ for s in next, list do
+ local t = tree
+ local p, pk
+ for c in gmatch(s,".") do
+ if t == true then
+ t = { [c] = true, [""] = true }
+ p[pk] = t
+ p = t
+ t = false
+ elseif t == false then
+ t = { [c] = false }
+ p[pk] = t
+ p = t
+ t = false
+ else
+ local tc = t[c]
+ if not tc then
+ tc = false
+ t[c] = false
+ end
+ p = t
+ t = tc
+ end
+ pk = c
+ end
+ if t == false then
+ p[pk] = true
+ elseif t == true then
+ -- okay
+ else
+ t[""] = true
+ end
+ end
+ else
+ for i=1,n do
+ local s = list[i]
+ local t = tree
+ local p, pk
+ for c in gmatch(s,".") do
+ if t == true then
+ t = { [c] = true, [""] = true }
+ p[pk] = t
+ p = t
+ t = false
+ elseif t == false then
+ t = { [c] = false }
+ p[pk] = t
+ p = t
+ t = false
+ else
+ local tc = t[c]
+ if not tc then
+ tc = false
+ t[c] = false
+ end
+ p = t
+ t = tc
+ end
+ pk = c
+ end
+ if t == false then
+ p[pk] = true
+ elseif t == true then
+ -- okay
+ else
+ t[""] = true
+ end
+ end
+ end
+ -- collapse(tree,"") -- needs testing, maybe optional, slightly faster because P("x")*P("X") seems slower than P"(xX") (why)
+ -- inspect(tree)
+ return (insensitive and make2 or make1)(tree)
+end
+
+lpeg.utfchartabletopattern = utfchartabletopattern
+
+function lpeg.utfreplacer(list,insensitive)
+ local pattern = Cs((utfchartabletopattern(list,insensitive)/list + utf8character)^0)
+ return function(str)
+ return lpegmatch(pattern,str) or str
+ end
+end
+
+-- local t = { "start", "stoep", "staart", "paard" }
+-- local p = lpeg.Cs((lpeg.utfchartabletopattern(t)/string.upper + 1)^1)
+
+-- local t = { "a", "abc", "ac", "abe", "abxyz", "xy", "bef","aa" }
+-- local p = lpeg.Cs((lpeg.utfchartabletopattern(t)/string.upper + 1)^1)
+
+-- inspect(lpegmatch(p,"a")=="A")
+-- inspect(lpegmatch(p,"aa")=="AA")
+-- inspect(lpegmatch(p,"aaaa")=="AAAA")
+-- inspect(lpegmatch(p,"ac")=="AC")
+-- inspect(lpegmatch(p,"bc")=="bc")
+-- inspect(lpegmatch(p,"zzbczz")=="zzbczz")
+-- inspect(lpegmatch(p,"zzabezz")=="zzABEzz")
+-- inspect(lpegmatch(p,"ab")=="Ab")
+-- inspect(lpegmatch(p,"abc")=="ABC")
+-- inspect(lpegmatch(p,"abe")=="ABE")
+-- inspect(lpegmatch(p,"xa")=="xA")
+-- inspect(lpegmatch(p,"bx")=="bx")
+-- inspect(lpegmatch(p,"bax")=="bAx")
+-- inspect(lpegmatch(p,"abxyz")=="ABXYZ")
+-- inspect(lpegmatch(p,"foobarbefcrap")=="foobArBEFcrAp")
+
+-- local t = { ["^"] = 1, ["^^"] = 2, ["^^^"] = 3, ["^^^^"] = 4 }
+-- local p = lpeg.Cs((lpeg.utfchartabletopattern(t)/t + 1)^1)
+-- inspect(lpegmatch(p," ^ ^^ ^^^ ^^^^ ^^^^^ ^^^^^^ ^^^^^^^ "))
+
+-- local t = { ["^^"] = 2, ["^^^"] = 3, ["^^^^"] = 4 }
+-- local p = lpeg.Cs((lpeg.utfchartabletopattern(t)/t + 1)^1)
+-- inspect(lpegmatch(p," ^ ^^ ^^^ ^^^^ ^^^^^ ^^^^^^ ^^^^^^^ "))
+
+-- lpeg.utfchartabletopattern {
+-- utfchar(0x00A0), -- nbsp
+-- utfchar(0x2000), -- enquad
+-- utfchar(0x2001), -- emquad
+-- utfchar(0x2002), -- enspace
+-- utfchar(0x2003), -- emspace
+-- utfchar(0x2004), -- threeperemspace
+-- utfchar(0x2005), -- fourperemspace
+-- utfchar(0x2006), -- sixperemspace
+-- utfchar(0x2007), -- figurespace
+-- utfchar(0x2008), -- punctuationspace
+-- utfchar(0x2009), -- breakablethinspace
+-- utfchar(0x200A), -- hairspace
+-- utfchar(0x200B), -- zerowidthspace
+-- utfchar(0x202F), -- narrownobreakspace
+-- utfchar(0x205F), -- math thinspace
+-- }
+
+-- a few handy ones:
+--
+-- faster than find(str,"[\n\r]") when match and # > 7 and always faster when # > 3
+
+patterns.containseol = lpeg.finder(eol) -- (1-eol)^0 * eol
+
+-- The next pattern^n variant is based on an approach suggested
+-- by Roberto: constructing a big repetition in chunks.
+--
+-- Being sparse is not needed, and only complicate matters and
+-- the number of redundant entries is not that large.
+
+local function nextstep(n,step,result)
+ local m = n % step -- mod(n,step)
+ local d = floor(n/step) -- div(n,step)
+ if d > 0 then
+ local v = V(tostring(step))
+ local s = result.start
+ for i=1,d do
+ if s then
+ s = v * s
+ else
+ s = v
+ end
+ end
+ result.start = s
+ end
+ if step > 1 and result.start then
+ local v = V(tostring(step/2))
+ result[tostring(step)] = v * v
+ end
+ if step > 0 then
+ return nextstep(m,step/2,result)
+ else
+ return result
+ end
+end
+
+function lpeg.times(pattern,n)
+ return P(nextstep(n,2^16,{ "start", ["1"] = pattern }))
+end
+
+-- local p = lpeg.Cs((1 - lpeg.times(lpeg.P("AB"),25))^1)
+-- local s = "12" .. string.rep("AB",20) .. "34" .. string.rep("AB",30) .. "56"
+-- inspect(p)
+-- print(lpeg.match(p,s))
+
+-- moved here (before util-str)
+
+do
+
+ local trailingzeros = zero^0 * -digit -- suggested by Roberto
+ local stripper = Cs((
+ digits * (
+ period * trailingzeros / ""
+ + period * (digit - trailingzeros)^1 * (trailingzeros / "")
+ ) + 1
+ )^0)
+
+ lpeg.patterns.stripzeros = stripper -- multiple in string
+
+ local nonzero = digit - zero
+ local trailingzeros = zero^1 * endofstring
+ local stripper = Cs( (1-period)^0 * (
+ period * trailingzeros/""
+ + period * (nonzero^1 + (trailingzeros/"") + zero^1)^0
+ + endofstring
+ ))
+
+ lpeg.patterns.stripzero = stripper -- slightly more efficient but expects a float !
+
+ -- local sample = "bla 11.00 bla 11 bla 0.1100 bla 1.00100 bla 0.00 bla 0.001 bla 1.1100 bla 0.100100100 bla 0.00100100100"
+ -- collectgarbage("collect")
+ -- str = string.rep(sample,10000)
+ -- local ts = os.clock()
+ -- lpegmatch(stripper,str)
+ -- print(#str, os.clock()-ts, lpegmatch(stripper,sample))
+
+end
+
+-- for practical reasons we keep this here:
+
+local byte_to_HEX = { }
+local byte_to_hex = { }
+local byte_to_dec = { } -- for md5
+local hex_to_byte = { }
+
+for i=0,255 do
+ local H = format("%02X",i)
+ local h = format("%02x",i)
+ local d = format("%03i",i)
+ local c = char(i)
+ byte_to_HEX[c] = H
+ byte_to_hex[c] = h
+ byte_to_dec[c] = d
+ hex_to_byte[h] = c
+ hex_to_byte[H] = c
+end
+
+local hextobyte = P(2)/hex_to_byte
+local bytetoHEX = P(1)/byte_to_HEX
+local bytetohex = P(1)/byte_to_hex
+local bytetodec = P(1)/byte_to_dec
+local hextobytes = Cs(hextobyte^0)
+local bytestoHEX = Cs(bytetoHEX^0)
+local bytestohex = Cs(bytetohex^0)
+local bytestodec = Cs(bytetodec^0)
+
+patterns.hextobyte = hextobyte
+patterns.bytetoHEX = bytetoHEX
+patterns.bytetohex = bytetohex
+patterns.bytetodec = bytetodec
+patterns.hextobytes = hextobytes
+patterns.bytestoHEX = bytestoHEX
+patterns.bytestohex = bytestohex
+patterns.bytestodec = bytestodec
+
+function string.toHEX(s)
+ if not s or s == "" then
+ return s
+ else
+ return lpegmatch(bytestoHEX,s)
+ end
+end
+
+function string.tohex(s)
+ if not s or s == "" then
+ return s
+ else
+ return lpegmatch(bytestohex,s)
+ end
+end
+
+function string.todec(s)
+ if not s or s == "" then
+ return s
+ else
+ return lpegmatch(bytestodec,s)
+ end
+end
+
+function string.tobytes(s)
+ if not s or s == "" then
+ return s
+ else
+ return lpegmatch(hextobytes,s)
+ end
+end
+
+-- local h = "ADFE0345"
+-- local b = lpegmatch(patterns.hextobytes,h)
+-- print(h,b,string.tohex(b),string.toHEX(b))
+
+local patterns = { } -- can be made weak
+
+local function containsws(what)
+ local p = patterns[what]
+ if not p then
+ local p1 = P(what) * (whitespace + endofstring) * Cc(true)
+ local p2 = whitespace * P(p1)
+ p = P(p1) + P(1-p2)^0 * p2 + Cc(false)
+ patterns[what] = p
+ end
+ return p
+end
+
+lpeg.containsws = containsws
+
+function string.containsws(str,what)
+ return lpegmatch(patterns[what] or containsws(what),str)
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-lua.lua b/macros/luatex/generic/luaotfload/fontloader-l-lua.lua
new file mode 100644
index 0000000000..6e9606e849
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-lua.lua
@@ -0,0 +1,259 @@
+if not modules then modules = { } end modules ['l-lua'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- potential issues with 5.3:
+
+-- i'm not sure yet if the int/float change is good for luatex
+
+-- math.min
+-- math.max
+-- tostring
+-- tonumber
+-- utf.*
+-- bit32
+
+local next, type, tonumber = next, type, tonumber
+
+-- compatibility hacks and helpers
+
+LUAMAJORVERSION, LUAMINORVERSION = string.match(_VERSION,"^[^%d]+(%d+)%.(%d+).*$")
+
+LUAMAJORVERSION = tonumber(LUAMAJORVERSION) or 5
+LUAMINORVERSION = tonumber(LUAMINORVERSION) or 1
+LUAVERSION = LUAMAJORVERSION + LUAMINORVERSION/10
+
+if LUAVERSION < 5.2 and jit then
+ --
+ -- we want loadstring cum suis to behave like 5.2
+ --
+ MINORVERSION = 2
+ LUAVERSION = 5.2
+end
+
+-- lpeg
+
+if not lpeg then
+ lpeg = require("lpeg")
+end
+
+-- if utf8 then
+-- utf8lua = utf8
+-- utf8 = nil
+-- end
+
+-- basics:
+
+if loadstring then
+
+ local loadnormal = load
+
+ function load(first,...)
+ if type(first) == "string" then
+ return loadstring(first,...)
+ else
+ return loadnormal(first,...)
+ end
+ end
+
+else
+
+ loadstring = load
+
+end
+
+-- table:
+
+-- At some point it was announced that i[pairs would be dropped, which makes
+-- sense. As we already used the for loop and # in most places the impact on
+-- ConTeXt was not that large; the remaining ipairs already have been replaced.
+-- Hm, actually ipairs was retained, but we no longer use it anyway (nor
+-- pairs).
+--
+-- Just in case, we provide the fallbacks as discussed in Programming
+-- in Lua (http://www.lua.org/pil/7.3.html):
+
+if not ipairs then
+
+ -- for k, v in ipairs(t) do ... end
+ -- for k=1,#t do local v = t[k] ... end
+
+ local function iterate(a,i)
+ i = i + 1
+ local v = a[i]
+ if v ~= nil then
+ return i, v --, nil
+ end
+ end
+
+ function ipairs(a)
+ return iterate, a, 0
+ end
+
+end
+
+if not pairs then
+
+ -- for k, v in pairs(t) do ... end
+ -- for k, v in next, t do ... end
+
+ function pairs(t)
+ return next, t -- , nil
+ end
+
+end
+
+-- The unpack function has been moved to the table table, and for compatiility
+-- reasons we provide both now.
+
+if not table.unpack then
+
+ table.unpack = _G.unpack
+
+elseif not unpack then
+
+ _G.unpack = table.unpack
+
+end
+
+-- package:
+
+-- if not package.seachers then
+--
+-- package.searchers = package.loaders -- 5.2
+--
+-- elseif not package.loaders then
+--
+-- package.loaders = package.searchers
+--
+-- end
+
+if not package.loaders then -- brr, searchers is a special "loadlib function" userdata type
+
+ package.loaders = package.searchers
+
+end
+
+-- moved from util-deb to here:
+
+local print, select, tostring = print, select, tostring
+
+local inspectors = { }
+
+function setinspector(kind,inspector) -- global function
+ inspectors[kind] = inspector
+end
+
+function inspect(...) -- global function
+ for s=1,select("#",...) do
+ local value = select(s,...)
+ if value == nil then
+ print("nil")
+ else
+ local done = false
+ -- type driven (table)
+ local kind = type(value)
+ local inspector = inspectors[kind]
+ if inspector then
+ done = inspector(value)
+ if done then
+ break
+ end
+ end
+ -- whatever driven (token, node, ...)
+ for kind, inspector in next, inspectors do
+ done = inspector(value)
+ if done then
+ break
+ end
+ end
+ if not done then
+ print(tostring(value))
+ end
+ end
+ end
+end
+
+--
+
+local dummy = function() end
+
+function optionalrequire(...)
+ local ok, result = xpcall(require,dummy,...)
+ if ok then
+ return result
+ end
+end
+
+-- nice for non ascii scripts (this might move):
+
+if lua then
+ lua.mask = load([[τεχ = 1]]) and "utf" or "ascii"
+end
+
+local flush = io.flush
+
+if flush then
+
+ local execute = os.execute if execute then function os.execute(...) flush() return execute(...) end end
+ local exec = os.exec if exec then function os.exec (...) flush() return exec (...) end end
+ local spawn = os.spawn if spawn then function os.spawn (...) flush() return spawn (...) end end
+ local popen = io.popen if popen then function io.popen (...) flush() return popen (...) end end
+
+end
+
+-- new
+
+FFISUPPORTED = type(ffi) == "table" and ffi.os ~= "" and ffi.arch ~= "" and ffi.load
+
+if not FFISUPPORTED then
+
+ -- Maybe we should check for LUATEXENGINE but that's also a bit tricky as we still
+ -- can have a weird ffi library laying around. Checking for presence of 'jit' is
+ -- also not robust. So for now we hope for the best.
+
+ local okay ; okay, ffi = pcall(require,"ffi")
+
+ FFISUPPORTED = type(ffi) == "table" and ffi.os ~= "" and ffi.arch ~= "" and ffi.load
+
+end
+
+if not FFISUPPORTED then
+ ffi = nil
+elseif not ffi.number then
+ ffi.number = tonumber
+end
+
+-- if not bit32 then -- and utf8 then
+-- -- bit32 = load ( [[ -- replacement code with 5.3 syntax so that 5.2 doesn't bark on it ]] )
+-- bit32 = require("l-bit32")
+-- end
+
+-- We need this due a bug in luatex socket loading:
+
+-- local loaded = package.loaded
+--
+-- if not loaded["socket"] then loaded["socket"] = loaded["socket.core"] end
+-- if not loaded["mime"] then loaded["mime"] = loaded["mime.core"] end
+--
+-- if not socket.mime then socket.mime = package.loaded["mime"] end
+--
+-- if not loaded["socket.mime"] then loaded["socket.mime"] = socket.mime end
+-- if not loaded["socket.http"] then loaded["socket.http"] = socket.http end
+-- if not loaded["socket.ftp"] then loaded["socket.ftp"] = socket.ftp end
+-- if not loaded["socket.smtp"] then loaded["socket.smtp"] = socket.smtp end
+-- if not loaded["socket.tp"] then loaded["socket.tp"] = socket.tp end
+-- if not loaded["socket.url"] then loaded["socket.url"] = socket.url end
+
+if LUAVERSION > 5.3 then
+ -- collectgarbage("collect")
+ -- collectgarbage("generational") -- crashes on unix
+end
+
+if status and os.setenv then
+ os.setenv("engine",string.lower(status.luatex_engine or "unknown"))
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-math.lua b/macros/luatex/generic/luaotfload/fontloader-l-math.lua
new file mode 100644
index 0000000000..e5668a5db0
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-math.lua
@@ -0,0 +1,149 @@
+if not modules then modules = { } end modules ['l-math'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+if not math.ceiling then
+
+ math.ceiling = math.ceil
+
+end
+
+if not math.round then
+
+ local floor = math.floor
+
+ function math.round(x) return floor(x + 0.5) end
+
+end
+
+if not math.div then
+
+ local floor = math.floor
+
+ function math.div(n,m) return floor(n/m) end
+
+end
+
+if not math.mod then
+
+ function math.mod(n,m) return n % m end
+
+end
+
+if not math.sind then
+
+ local sin, cos, tan = math.sin, math.cos, math.tan
+
+ local pipi = 2*math.pi/360
+
+ function math.sind(d) return sin(d*pipi) end
+ function math.cosd(d) return cos(d*pipi) end
+ function math.tand(d) return tan(d*pipi) end
+
+end
+
+if not math.odd then
+
+ function math.odd (n) return n % 2 ~= 0 end
+ function math.even(n) return n % 2 == 0 end
+
+end
+
+if not math.cosh then
+
+ local exp = math.exp
+
+ function math.cosh(x)
+ local xx = exp(x)
+ return (xx+1/xx)/2
+ end
+ function math.sinh(x)
+ local xx = exp(x)
+ return (xx-1/xx)/2
+ end
+ function math.tanh(x)
+ local xx = exp(x)
+ return (xx-1/xx)/(xx+1/xx)
+ end
+
+end
+
+if not math.pow then
+
+ function math.pow(x,y)
+ return x^y
+ end
+
+end
+
+if not math.atan2 then
+
+ math.atan2 = math.atan
+
+end
+
+if not math.ldexp then
+
+ function math.ldexp(x,e)
+ return x * 2.0^e
+ end
+
+end
+
+-- if not math.frexp then
+--
+-- -- not a oneliner so use a math library instead
+--
+-- function math.frexp(x,e)
+-- -- returns m and e such that x = m2e, e is an integer and the absolute
+-- -- value of m is in the range [0.5, 1) (or zero when x is zero)
+-- end
+--
+-- end
+
+if not math.log10 then
+
+ local log = math.log
+
+ function math.log10(x)
+ return log(x,10)
+ end
+
+end
+
+if not math.type then
+
+ function math.type()
+ return "float"
+ end
+
+end
+
+if not math.tointeger then
+
+ math.mininteger = -0x4FFFFFFFFFFF
+ math.maxinteger = 0x4FFFFFFFFFFF
+
+ local floor = math.floor
+
+ function math.tointeger(n)
+ local f = floor(n)
+ return f == n and f or nil
+ end
+
+end
+
+if not math.ult then
+
+ local floor = math.floor
+
+ function math.tointeger(m,n)
+ -- not ok but i'm not motivated to look into it now
+ return floor(m) < floor(n) -- unsigned comparison needed
+ end
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-string.lua b/macros/luatex/generic/luaotfload/fontloader-l-string.lua
new file mode 100644
index 0000000000..1dee85e289
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-string.lua
@@ -0,0 +1,244 @@
+if not modules then modules = { } end modules ['l-string'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local string = string
+local sub, gmatch, format, char, byte, rep, lower = string.sub, string.gmatch, string.format, string.char, string.byte, string.rep, string.lower
+local lpegmatch, patterns = lpeg.match, lpeg.patterns
+local P, S, C, Ct, Cc, Cs = lpeg.P, lpeg.S, lpeg.C, lpeg.Ct, lpeg.Cc, lpeg.Cs
+
+-- Some functions are already defined in l-lpeg and maybe some from here will
+-- move there (unless we also expose caches).
+
+-- if not string.split then
+--
+-- function string.split(str,pattern)
+-- local t = { }
+-- if str ~= "" then
+-- local n = 1
+-- for s in gmatch(str..pattern,"(.-)"..pattern) do
+-- t[n] = s
+-- n = n + 1
+-- end
+-- end
+-- return t
+-- end
+--
+-- end
+
+-- function string.unquoted(str)
+-- return (gsub(str,"^([\"\'])(.*)%1$","%2")) -- interesting pattern
+-- end
+
+local unquoted = patterns.squote * C(patterns.nosquote) * patterns.squote
+ + patterns.dquote * C(patterns.nodquote) * patterns.dquote
+
+function string.unquoted(str)
+ return lpegmatch(unquoted,str) or str
+end
+
+-- print(string.unquoted("test"))
+-- print(string.unquoted([["t\"est"]]))
+-- print(string.unquoted([["t\"est"x]]))
+-- print(string.unquoted("\'test\'"))
+-- print(string.unquoted('"test"'))
+-- print(string.unquoted('"test"'))
+
+function string.quoted(str)
+ return format("%q",str) -- always double quote
+end
+
+function string.count(str,pattern) -- variant 3
+ local n = 0
+ for _ in gmatch(str,pattern) do -- not for utf
+ n = n + 1
+ end
+ return n
+end
+
+function string.limit(str,n,sentinel) -- not utf proof
+ if #str > n then
+ sentinel = sentinel or "..."
+ return sub(str,1,(n-#sentinel)) .. sentinel
+ else
+ return str
+ end
+end
+
+local stripper = patterns.stripper
+local fullstripper = patterns.fullstripper
+local collapser = patterns.collapser
+local nospacer = patterns.nospacer
+local longtostring = patterns.longtostring
+
+function string.strip(str)
+ return str and lpegmatch(stripper,str) or ""
+end
+
+function string.fullstrip(str)
+ return str and lpegmatch(fullstripper,str) or ""
+end
+
+function string.collapsespaces(str)
+ return str and lpegmatch(collapser,str) or ""
+end
+
+function string.nospaces(str)
+ return str and lpegmatch(nospacer,str) or ""
+end
+
+function string.longtostring(str)
+ return str and lpegmatch(longtostring,str) or ""
+end
+
+-- function string.is_empty(str)
+-- return not find(str,"%S")
+-- end
+
+local pattern = P(" ")^0 * P(-1) -- maybe also newlines
+
+-- patterns.onlyspaces = pattern
+
+function string.is_empty(str)
+ if not str or str == "" then
+ return true
+ else
+ return lpegmatch(pattern,str) and true or false
+ end
+end
+
+-- if not string.escapedpattern then
+--
+-- local patterns_escapes = {
+-- ["%"] = "%%",
+-- ["."] = "%.",
+-- ["+"] = "%+", ["-"] = "%-", ["*"] = "%*",
+-- ["["] = "%[", ["]"] = "%]",
+-- ["("] = "%(", [")"] = "%)",
+-- -- ["{"] = "%{", ["}"] = "%}"
+-- -- ["^"] = "%^", ["$"] = "%$",
+-- }
+--
+-- local simple_escapes = {
+-- ["-"] = "%-",
+-- ["."] = "%.",
+-- ["?"] = ".",
+-- ["*"] = ".*",
+-- }
+--
+-- function string.escapedpattern(str,simple)
+-- return (gsub(str,".",simple and simple_escapes or patterns_escapes))
+-- end
+--
+-- function string.topattern(str,lowercase,strict)
+-- if str == "" then
+-- return ".*"
+-- else
+-- str = gsub(str,".",simple_escapes)
+-- if lowercase then
+-- str = lower(str)
+-- end
+-- if strict then
+-- return "^" .. str .. "$"
+-- else
+-- return str
+-- end
+-- end
+-- end
+--
+-- end
+
+--- needs checking
+
+local anything = patterns.anything
+local moreescapes = Cc("%") * S(".-+%?()[]*$^{}")
+local allescapes = Cc("%") * S(".-+%?()[]*") -- also {} and ^$ ?
+local someescapes = Cc("%") * S(".-+%()[]") -- also {} and ^$ ?
+local matchescapes = Cc(".") * S("*?") -- wildcard and single match
+
+local pattern_m = Cs ( ( moreescapes + anything )^0 )
+local pattern_a = Cs ( ( allescapes + anything )^0 )
+local pattern_b = Cs ( ( someescapes + matchescapes + anything )^0 )
+local pattern_c = Cs ( Cc("^") * ( someescapes + matchescapes + anything )^0 * Cc("$") )
+
+function string.escapedpattern(str,simple)
+ return lpegmatch(simple and pattern_b or pattern_a,str)
+end
+
+function string.topattern(str,lowercase,strict)
+ if str == "" or type(str) ~= "string" then
+ return ".*"
+ elseif strict == "all" then
+ str = lpegmatch(pattern_m,str)
+ elseif strict then
+ str = lpegmatch(pattern_c,str)
+ else
+ str = lpegmatch(pattern_b,str)
+ end
+ if lowercase then
+ return lower(str)
+ else
+ return str
+ end
+end
+
+-- print(string.escapedpattern("abc*234",true))
+-- print(string.escapedpattern("12+34*.tex",false))
+-- print(string.escapedpattern("12+34*.tex",true))
+-- print(string.topattern ("12+34*.tex",false,false))
+-- print(string.topattern ("12+34*.tex",false,true))
+
+function string.valid(str,default)
+ return (type(str) == "string" and str ~= "" and str) or default or nil
+end
+
+-- handy fallback
+
+string.itself = function(s) return s end
+
+-- also handy (see utf variant)
+
+local pattern_c = Ct( C(1) ^0) -- string and not utf !
+local pattern_b = Ct((C(1)/byte)^0)
+
+function string.totable(str,bytes)
+ return lpegmatch(bytes and pattern_b or pattern_c,str)
+end
+
+-- handy from within tex:
+
+local replacer = lpeg.replacer("@","%%") -- Watch the escaped % in lpeg!
+
+function string.tformat(fmt,...)
+ return format(lpegmatch(replacer,fmt),...)
+end
+
+-- obsolete names:
+
+string.quote = string.quoted
+string.unquote = string.unquoted
+
+-- new
+
+if not string.bytetable then -- used in font-cff.lua
+
+ local limit = 5000 -- we can go to 8000 in luajit and much higher in lua if needed
+
+ function string.bytetable(str) -- from a string
+ local n = #str
+ if n > limit then
+ local t = { byte(str,1,limit) }
+ for i=limit+1,n do
+ t[i] = byte(str,i)
+ end
+ return t
+ else
+ return { byte(str,1,n) }
+ end
+ end
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-table.lua b/macros/luatex/generic/luaotfload/fontloader-l-table.lua
new file mode 100644
index 0000000000..cffdcc23e2
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-table.lua
@@ -0,0 +1,1471 @@
+if not modules then modules = { } end modules ['l-table'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local type, next, tostring, tonumber, select = type, next, tostring, tonumber, select
+local table, string = table, string
+local concat, sort = table.concat, table.sort
+local format, lower, dump = string.format, string.lower, string.dump
+local getmetatable, setmetatable = getmetatable, setmetatable
+local lpegmatch, patterns = lpeg.match, lpeg.patterns
+local floor = math.floor
+
+-- extra functions, some might go (when not used)
+--
+-- we could serialize using %a but that won't work well is in the code we mostly use
+-- floats and as such we get unequality e.g. in version comparisons
+
+local stripper = patterns.stripper
+
+function table.getn(t)
+ return t and #t -- for very old times sake
+end
+
+function table.strip(tab)
+ local lst = { }
+ local l = 0
+ for i=1,#tab do
+ local s = lpegmatch(stripper,tab[i]) or ""
+ if s == "" then
+ -- skip this one
+ else
+ l = l + 1
+ lst[l] = s
+ end
+ end
+ return lst
+end
+
+function table.keys(t)
+ if t then
+ local keys = { }
+ local k = 0
+ for key in next, t do
+ k = k + 1
+ keys[k] = key
+ end
+ return keys
+ else
+ return { }
+ end
+end
+
+-- local function compare(a,b)
+-- local ta = type(a) -- needed, else 11 < 2
+-- local tb = type(b) -- needed, else 11 < 2
+-- if ta == tb and ta == "number" then
+-- return a < b
+-- else
+-- return tostring(a) < tostring(b) -- not that efficient
+-- end
+-- end
+
+-- local function compare(a,b)
+-- local ta = type(a) -- needed, else 11 < 2
+-- local tb = type(b) -- needed, else 11 < 2
+-- if ta == tb and (ta == "number" or ta == "string") then
+-- return a < b
+-- else
+-- return tostring(a) < tostring(b) -- not that efficient
+-- end
+-- end
+
+-- local function sortedkeys(tab)
+-- if tab then
+-- local srt, category, s = { }, 0, 0 -- 0=unknown 1=string, 2=number 3=mixed
+-- for key in next, tab do
+-- s = s + 1
+-- srt[s] = key
+-- if category == 3 then
+-- -- no further check
+-- else
+-- local tkey = type(key)
+-- if tkey == "string" then
+-- category = (category == 2 and 3) or 1
+-- elseif tkey == "number" then
+-- category = (category == 1 and 3) or 2
+-- else
+-- category = 3
+-- end
+-- end
+-- end
+-- if category == 0 or category == 3 then
+-- sort(srt,compare)
+-- else
+-- sort(srt)
+-- end
+-- return srt
+-- else
+-- return { }
+-- end
+-- end
+
+-- local function compare(a,b)
+-- local ta = type(a) -- needed, else 11 < 2
+-- local tb = type(b) -- needed, else 11 < 2
+-- if ta == tb and (ta == "number" or ta == "string") then
+-- return a < b
+-- else
+-- return tostring(a) < tostring(b) -- not that efficient
+-- end
+-- end
+
+-- local function compare(a,b)
+-- local ta = type(a) -- needed, else 11 < 2
+-- if ta == "number" or ta == "string" then
+-- local tb = type(b) -- needed, else 11 < 2
+-- if ta == tb then
+-- return a < b
+-- end
+-- end
+-- return tostring(a) < tostring(b) -- not that efficient
+-- end
+
+local function compare(a,b)
+ local ta = type(a) -- needed, else 11 < 2
+ if ta == "number" then
+ local tb = type(b) -- needed, else 11 < 2
+ if ta == tb then
+ return a < b
+ elseif tb == "string" then
+ return tostring(a) < b
+ end
+ elseif ta == "string" then
+ local tb = type(b) -- needed, else 11 < 2
+ if ta == tb then
+ return a < b
+ else
+ return a < tostring(b)
+ end
+ end
+ return tostring(a) < tostring(b) -- not that efficient
+end
+
+local function sortedkeys(tab)
+ if tab then
+ local srt = { }
+ local category = 0 -- 0=unknown 1=string, 2=number 3=mixed
+ local s = 0
+ for key in next, tab do
+ s = s + 1
+ srt[s] = key
+ if category ~= 3 then
+ local tkey = type(key)
+ if category == 1 then
+ if tkey ~= "string" then
+ category = 3
+ end
+ elseif category == 2 then
+ if tkey ~= "number" then
+ category = 3
+ end
+ else
+ if tkey == "string" then
+ category = 1
+ elseif tkey == "number" then
+ category = 2
+ else
+ category = 3
+ end
+ end
+ end
+ end
+ if s < 2 then
+ -- nothing to sort
+ elseif category == 3 then
+ sort(srt,compare)
+ else
+ sort(srt)
+ end
+ return srt
+ else
+ return { }
+ end
+end
+
+local function sortedhashonly(tab)
+ if tab then
+ local srt = { }
+ local s = 0
+ for key in next, tab do
+ if type(key) == "string" then
+ s = s + 1
+ srt[s] = key
+ end
+ end
+ if s > 1 then
+ sort(srt)
+ end
+ return srt
+ else
+ return { }
+ end
+end
+
+local function sortedindexonly(tab)
+ if tab then
+ local srt = { }
+ local s = 0
+ for key in next, tab do
+ if type(key) == "number" then
+ s = s + 1
+ srt[s] = key
+ end
+ end
+ if s > 1 then
+ sort(srt)
+ end
+ return srt
+ else
+ return { }
+ end
+end
+
+local function sortedhashkeys(tab,cmp) -- fast one
+ if tab then
+ local srt = { }
+ local s = 0
+ for key in next, tab do
+ if key then
+ s= s + 1
+ srt[s] = key
+ end
+ end
+ if s > 1 then
+ sort(srt,cmp)
+ end
+ return srt
+ else
+ return { }
+ end
+end
+
+function table.allkeys(t)
+ local keys = { }
+ for k, v in next, t do
+ for k in next, v do
+ keys[k] = true
+ end
+ end
+ return sortedkeys(keys)
+end
+
+table.sortedkeys = sortedkeys
+table.sortedhashonly = sortedhashonly
+table.sortedindexonly = sortedindexonly
+table.sortedhashkeys = sortedhashkeys
+
+local function nothing() end
+
+local function sortedhash(t,cmp)
+ if t then
+ local s
+ if cmp then
+ -- it would be nice if the sort function would accept a third argument (or nicer, an optional first)
+ s = sortedhashkeys(t,function(a,b) return cmp(t,a,b) end)
+ else
+ s = sortedkeys(t) -- the robust one
+ end
+ local m = #s
+ if m == 1 then
+ return next, t
+ elseif m > 0 then
+ local n = 0
+ return function()
+ if n < m then
+ n = n + 1
+ local k = s[n]
+ return k, t[k]
+ end
+ end
+ end
+ end
+ return nothing
+end
+
+table.sortedhash = sortedhash
+table.sortedpairs = sortedhash -- obsolete
+
+function table.append(t,list)
+ local n = #t
+ for i=1,#list do
+ n = n + 1
+ t[n] = list[i]
+ end
+ return t
+end
+
+function table.prepend(t, list)
+ local nl = #list
+ local nt = nl + #t
+ for i=#t,1,-1 do
+ t[nt] = t[i]
+ nt = nt - 1
+ end
+ for i=1,#list do
+ t[i] = list[i]
+ end
+ return t
+end
+
+-- function table.merge(t, ...) -- first one is target
+-- t = t or { }
+-- local lst = { ... }
+-- for i=1,#lst do
+-- for k, v in next, lst[i] do
+-- t[k] = v
+-- end
+-- end
+-- return t
+-- end
+
+function table.merge(t, ...) -- first one is target
+ if not t then
+ t = { }
+ end
+ for i=1,select("#",...) do
+ for k, v in next, (select(i,...)) do
+ t[k] = v
+ end
+ end
+ return t
+end
+
+-- function table.merged(...)
+-- local tmp, lst = { }, { ... }
+-- for i=1,#lst do
+-- for k, v in next, lst[i] do
+-- tmp[k] = v
+-- end
+-- end
+-- return tmp
+-- end
+
+function table.merged(...)
+ local t = { }
+ for i=1,select("#",...) do
+ for k, v in next, (select(i,...)) do
+ t[k] = v
+ end
+ end
+ return t
+end
+
+-- function table.imerge(t, ...)
+-- local lst, nt = { ... }, #t
+-- for i=1,#lst do
+-- local nst = lst[i]
+-- for j=1,#nst do
+-- nt = nt + 1
+-- t[nt] = nst[j]
+-- end
+-- end
+-- return t
+-- end
+
+function table.imerge(t, ...)
+ local nt = #t
+ for i=1,select("#",...) do
+ local nst = select(i,...)
+ for j=1,#nst do
+ nt = nt + 1
+ t[nt] = nst[j]
+ end
+ end
+ return t
+end
+
+-- function table.imerged(...)
+-- local tmp, ntmp, lst = { }, 0, {...}
+-- for i=1,#lst do
+-- local nst = lst[i]
+-- for j=1,#nst do
+-- ntmp = ntmp + 1
+-- tmp[ntmp] = nst[j]
+-- end
+-- end
+-- return tmp
+-- end
+
+function table.imerged(...)
+ local tmp = { }
+ local ntmp = 0
+ for i=1,select("#",...) do
+ local nst = select(i,...)
+ for j=1,#nst do
+ ntmp = ntmp + 1
+ tmp[ntmp] = nst[j]
+ end
+ end
+ return tmp
+end
+
+local function fastcopy(old,metatabletoo) -- fast one
+ if old then
+ local new = { }
+ for k, v in next, old do
+ if type(v) == "table" then
+ new[k] = fastcopy(v,metatabletoo) -- was just table.copy
+ else
+ new[k] = v
+ end
+ end
+ if metatabletoo then
+ -- optional second arg
+ local mt = getmetatable(old)
+ if mt then
+ setmetatable(new,mt)
+ end
+ end
+ return new
+ else
+ return { }
+ end
+end
+
+-- todo : copy without metatable
+
+local function copy(t,tables) -- taken from lua wiki, slightly adapted
+ if not tables then
+ tables = { }
+ end
+ local tcopy = { }
+ if not tables[t] then
+ tables[t] = tcopy
+ end
+ for i,v in next, t do -- brrr, what happens with sparse indexed
+ if type(i) == "table" then
+ if tables[i] then
+ i = tables[i]
+ else
+ i = copy(i,tables)
+ end
+ end
+ if type(v) ~= "table" then
+ tcopy[i] = v
+ elseif tables[v] then
+ tcopy[i] = tables[v]
+ else
+ tcopy[i] = copy(v,tables)
+ end
+ end
+ local mt = getmetatable(t)
+ if mt then
+ setmetatable(tcopy,mt)
+ end
+ return tcopy
+end
+
+table.fastcopy = fastcopy
+table.copy = copy
+
+function table.derive(parent) -- for the moment not public
+ local child = { }
+ if parent then
+ setmetatable(child,{ __index = parent })
+ end
+ return child
+end
+
+function table.tohash(t,value)
+ local h = { }
+ if t then
+ if value == nil then value = true end
+ for _, v in next, t do
+ h[v] = value
+ end
+ end
+ return h
+end
+
+function table.fromhash(t)
+ local hsh = { }
+ local h = 0
+ for k, v in next, t do
+ if v then
+ h = h + 1
+ hsh[h] = k
+ end
+ end
+ return hsh
+end
+
+local noquotes, hexify, handle, compact, inline, functions, metacheck
+
+local reserved = table.tohash { -- intercept a language inconvenience: no reserved words as key
+ 'and', 'break', 'do', 'else', 'elseif', 'end', 'false', 'for', 'function', 'if',
+ 'in', 'local', 'nil', 'not', 'or', 'repeat', 'return', 'then', 'true', 'until', 'while',
+ 'NaN', 'goto',
+}
+
+-- local function is_simple_table(t)
+-- if #t > 0 then
+-- local n = 0
+-- for _,v in next, t do
+-- n = n + 1
+-- end
+-- if n == #t then
+-- local tt, nt = { }, 0
+-- for i=1,#t do
+-- local v = t[i]
+-- local tv = type(v)
+-- if tv == "number" then
+-- nt = nt + 1
+-- if hexify then
+-- tt[nt] = format("0x%X",v)
+-- else
+-- tt[nt] = tostring(v) -- tostring not needed
+-- end
+-- elseif tv == "string" then
+-- nt = nt + 1
+-- tt[nt] = format("%q",v)
+-- elseif tv == "boolean" then
+-- nt = nt + 1
+-- tt[nt] = v and "true" or "false"
+-- else
+-- return nil
+-- end
+-- end
+-- return tt
+-- end
+-- end
+-- return nil
+-- end
+
+-- local function is_simple_table(t)
+-- local nt = #t
+-- if nt > 0 then
+-- local n = 0
+-- for _,v in next, t do
+-- n = n + 1
+-- -- if type(v) == "table" then
+-- -- return nil
+-- -- end
+-- end
+-- if n == nt then
+-- local tt = { }
+-- for i=1,nt do
+-- local v = t[i]
+-- local tv = type(v)
+-- if tv == "number" then
+-- if hexify then
+-- tt[i] = format("0x%X",v)
+-- else
+-- tt[i] = tostring(v) -- tostring not needed
+-- end
+-- elseif tv == "string" then
+-- tt[i] = format("%q",v)
+-- elseif tv == "boolean" then
+-- tt[i] = v and "true" or "false"
+-- else
+-- return nil
+-- end
+-- end
+-- return tt
+-- end
+-- end
+-- return nil
+-- end
+
+local function is_simple_table(t,hexify) -- also used in util-tab so maybe public
+ local nt = #t
+ if nt > 0 then
+ local n = 0
+ for _, v in next, t do
+ n = n + 1
+ if type(v) == "table" then
+ return nil
+ end
+ end
+ -- local haszero = t[0]
+ local haszero = rawget(t,0) -- don't trigger meta
+ if n == nt then
+ local tt = { }
+ for i=1,nt do
+ local v = t[i]
+ local tv = type(v)
+ if tv == "number" then
+ -- tt[i] = v -- not needed tostring(v)
+ if hexify then
+ tt[i] = format("0x%X",v)
+ else
+ tt[i] = v -- not needed tostring(v)
+ end
+ elseif tv == "string" then
+ tt[i] = format("%q",v) -- f_string(v)
+ elseif tv == "boolean" then
+ tt[i] = v and "true" or "false"
+ else
+ return nil
+ end
+ end
+ return tt
+ elseif haszero and (n == nt + 1) then
+ local tt = { }
+ for i=0,nt do
+ local v = t[i]
+ local tv = type(v)
+ if tv == "number" then
+ -- tt[i+1] = v -- not needed tostring(v)
+ if hexify then
+ tt[i+1] = format("0x%X",v)
+ else
+ tt[i+1] = v -- not needed tostring(v)
+ end
+ elseif tv == "string" then
+ tt[i+1] = format("%q",v) -- f_string(v)
+ elseif tv == "boolean" then
+ tt[i+1] = v and "true" or "false"
+ else
+ return nil
+ end
+ end
+ tt[1] = "[0] = " .. tt[1]
+ return tt
+ end
+ end
+ return nil
+end
+
+table.is_simple_table = is_simple_table
+
+-- Because this is a core function of mkiv I moved some function calls
+-- inline.
+--
+-- twice as fast in a test:
+--
+-- local propername = lpeg.P(lpeg.R("AZ","az","__") * lpeg.R("09","AZ","az", "__")^0 * lpeg.P(-1) )
+
+-- problem: there no good number_to_string converter with the best resolution
+
+-- probably using .. is faster than format
+-- maybe split in a few cases (yes/no hexify)
+
+-- todo: %g faster on numbers than %s
+
+-- we can speed this up with repeaters and formatters but we haven't defined them
+-- yet
+
+local propername = patterns.propername -- was find(name,"^%a[%w%_]*$")
+
+local function dummy() end
+
+local function do_serialize(root,name,depth,level,indexed)
+ if level > 0 then
+ depth = depth .. " "
+ if indexed then
+ handle(format("%s{",depth))
+ else
+ local tn = type(name)
+ if tn == "number" then
+ if hexify then
+ handle(format("%s[0x%X]={",depth,name))
+ else
+ handle(format("%s[%s]={",depth,name))
+ end
+ elseif tn == "string" then
+ if noquotes and not reserved[name] and lpegmatch(propername,name) then
+ handle(format("%s%s={",depth,name))
+ else
+ handle(format("%s[%q]={",depth,name))
+ end
+ elseif tn == "boolean" then
+ handle(format("%s[%s]={",depth,name and "true" or "false"))
+ else
+ handle(format("%s{",depth))
+ end
+ end
+ end
+ -- we could check for k (index) being number (cardinal)
+ if root and next(root) ~= nil then
+ local first = nil
+ local last = 0
+ if compact then
+ last = #root
+ for k=1,last do
+ -- if root[k] == nil then
+ if rawget(root,k) == nil then
+ last = k - 1
+ break
+ end
+ end
+ if last > 0 then
+ first = 1
+ end
+ end
+ local sk = sortedkeys(root)
+ for i=1,#sk do
+ local k = sk[i]
+ local v = root[k]
+ local tv = type(v)
+ local tk = type(k)
+ if compact and first and tk == "number" and k >= first and k <= last then
+ if tv == "number" then
+ if hexify then
+ handle(format("%s 0x%X,",depth,v))
+ else
+ handle(format("%s %s,",depth,v)) -- %.99g
+ end
+ elseif tv == "string" then
+ handle(format("%s %q,",depth,v))
+ elseif tv == "table" then
+ if next(v) == nil then
+ handle(format("%s {},",depth))
+ elseif inline then -- and #t > 0
+ local st = is_simple_table(v,hexify)
+ if st then
+ handle(format("%s { %s },",depth,concat(st,", ")))
+ else
+ do_serialize(v,k,depth,level+1,true)
+ end
+ else
+ do_serialize(v,k,depth,level+1,true)
+ end
+ elseif tv == "boolean" then
+ handle(format("%s %s,",depth,v and "true" or "false"))
+ elseif tv == "function" then
+ if functions then
+ handle(format('%s load(%q),',depth,dump(v))) -- maybe strip
+ else
+ handle(format('%s "function",',depth))
+ end
+ else
+ handle(format("%s %q,",depth,tostring(v)))
+ end
+ elseif k == "__p__" then -- parent
+ if false then
+ handle(format("%s __p__=nil,",depth))
+ end
+ elseif tv == "number" then
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]=0x%X,",depth,k,v))
+ else
+ handle(format("%s [%s]=%s,",depth,k,v)) -- %.99g
+ end
+ elseif tk == "boolean" then
+ if hexify then
+ handle(format("%s [%s]=0x%X,",depth,k and "true" or "false",v))
+ else
+ handle(format("%s [%s]=%s,",depth,k and "true" or "false",v)) -- %.99g
+ end
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ if hexify then
+ handle(format("%s %s=0x%X,",depth,k,v))
+ else
+ handle(format("%s %s=%s,",depth,k,v)) -- %.99g
+ end
+ else
+ if hexify then
+ handle(format("%s [%q]=0x%X,",depth,k,v))
+ else
+ handle(format("%s [%q]=%s,",depth,k,v)) -- %.99g
+ end
+ end
+ elseif tv == "string" then
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]=%q,",depth,k,v))
+ else
+ handle(format("%s [%s]=%q,",depth,k,v))
+ end
+ elseif tk == "boolean" then
+ handle(format("%s [%s]=%q,",depth,k and "true" or "false",v))
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=%q,",depth,k,v))
+ else
+ handle(format("%s [%q]=%q,",depth,k,v))
+ end
+ elseif tv == "table" then
+ if next(v) == nil then
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]={},",depth,k))
+ else
+ handle(format("%s [%s]={},",depth,k))
+ end
+ elseif tk == "boolean" then
+ handle(format("%s [%s]={},",depth,k and "true" or "false"))
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s={},",depth,k))
+ else
+ handle(format("%s [%q]={},",depth,k))
+ end
+ elseif inline then
+ local st = is_simple_table(v,hexify)
+ if st then
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]={ %s },",depth,k,concat(st,", ")))
+ else
+ handle(format("%s [%s]={ %s },",depth,k,concat(st,", ")))
+ end
+ elseif tk == "boolean" then
+ handle(format("%s [%s]={ %s },",depth,k and "true" or "false",concat(st,", ")))
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s={ %s },",depth,k,concat(st,", ")))
+ else
+ handle(format("%s [%q]={ %s },",depth,k,concat(st,", ")))
+ end
+ else
+ do_serialize(v,k,depth,level+1)
+ end
+ else
+ do_serialize(v,k,depth,level+1)
+ end
+ elseif tv == "boolean" then
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]=%s,",depth,k,v and "true" or "false"))
+ else
+ handle(format("%s [%s]=%s,",depth,k,v and "true" or "false"))
+ end
+ elseif tk == "boolean" then
+ handle(format("%s [%s]=%s,",depth,tostring(k),v and "true" or "false"))
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=%s,",depth,k,v and "true" or "false"))
+ else
+ handle(format("%s [%q]=%s,",depth,k,v and "true" or "false"))
+ end
+ elseif tv == "function" then
+ if functions then
+ local getinfo = debug and debug.getinfo
+ if getinfo then
+ local f = getinfo(v).what == "C" and dump(dummy) or dump(v) -- maybe strip
+ -- local f = getinfo(v).what == "C" and dump(function(...) return v(...) end) or dump(v) -- maybe strip
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]=load(%q),",depth,k,f))
+ else
+ handle(format("%s [%s]=load(%q),",depth,k,f))
+ end
+ elseif tk == "boolean" then
+ handle(format("%s [%s]=load(%q),",depth,k and "true" or "false",f))
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=load(%q),",depth,k,f))
+ else
+ handle(format("%s [%q]=load(%q),",depth,k,f))
+ end
+ end
+ end
+ else
+ if tk == "number" then
+ if hexify then
+ handle(format("%s [0x%X]=%q,",depth,k,tostring(v)))
+ else
+ handle(format("%s [%s]=%q,",depth,k,tostring(v)))
+ end
+ elseif tk == "boolean" then
+ handle(format("%s [%s]=%q,",depth,k and "true" or "false",tostring(v)))
+ elseif tk ~= "string" then
+ -- ignore
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=%q,",depth,k,tostring(v)))
+ else
+ handle(format("%s [%q]=%q,",depth,k,tostring(v)))
+ end
+ end
+ end
+ end
+ if level > 0 then
+ handle(format("%s},",depth))
+ end
+end
+
+-- replacing handle by a direct t[#t+1] = ... (plus test) is not much
+-- faster (0.03 on 1.00 for zapfino.tma)
+
+local function serialize(_handle,root,name,specification) -- handle wins
+ local tname = type(name)
+ if type(specification) == "table" then
+ noquotes = specification.noquotes
+ hexify = specification.hexify
+ handle = _handle or specification.handle or print
+ functions = specification.functions
+ compact = specification.compact
+ inline = specification.inline and compact
+ metacheck = specification.metacheck
+ if functions == nil then
+ functions = true
+ end
+ if compact == nil then
+ compact = true
+ end
+ if inline == nil then
+ inline = compact
+ end
+ if metacheck == nil then
+ metacheck = true
+ end
+ else
+ noquotes = false
+ hexify = false
+ handle = _handle or print
+ compact = true
+ inline = true
+ functions = true
+ metacheck = true
+ end
+ if tname == "string" then
+ if name == "return" then
+ handle("return {")
+ else
+ handle(name .. "={")
+ end
+ elseif tname == "number" then
+ if hexify then
+ handle(format("[0x%X]={",name))
+ else
+ handle("[" .. name .. "]={")
+ end
+ elseif tname == "boolean" then
+ if name then
+ handle("return {")
+ else
+ handle("{")
+ end
+ else
+ handle("t={")
+ end
+ if root then
+ -- The dummy access will initialize a table that has a delayed initialization
+ -- using a metatable. (maybe explicitly test for metatable). This can crash on
+ -- metatables that check the index against a number.
+ if metacheck and getmetatable(root) then
+ local dummy = root._w_h_a_t_e_v_e_r_
+ root._w_h_a_t_e_v_e_r_ = nil
+ end
+ -- Let's forget about empty tables.
+ if next(root) ~= nil then
+ do_serialize(root,name,"",0)
+ end
+ end
+ handle("}")
+end
+
+-- A version with formatters is some 20% faster than using format (because formatters are
+-- much faster) but of course, inlining the format using .. is then again faster .. anyway,
+-- as we do some pretty printing as well there is not that much to gain unless we make a
+-- 'fast' ugly variant as well. But, we would have to move the formatter to l-string then.
+
+-- name:
+--
+-- true : return { }
+-- false : { }
+-- nil : t = { }
+-- string : string = { }
+-- "return" : return { }
+-- number : [number] = { }
+
+function table.serialize(root,name,specification)
+ local t = { }
+ local n = 0
+ local function flush(s)
+ n = n + 1
+ t[n] = s
+ end
+ serialize(flush,root,name,specification)
+ return concat(t,"\n")
+end
+
+-- local a = { e = { 1,2,3,4,5,6}, a = 1, b = 2, c = "ccc", d = { a = 1, b = 2, c = "ccc", d = { a = 1, b = 2, c = "ccc" } } }
+-- local t = os.clock()
+-- for i=1,10000 do
+-- table.serialize(a)
+-- end
+-- print(os.clock()-t,table.serialize(a))
+
+table.tohandle = serialize
+
+local maxtab = 2*1024
+
+function table.tofile(filename,root,name,specification)
+ local f = io.open(filename,'w')
+ if f then
+ if maxtab > 1 then
+ local t = { }
+ local n = 0
+ local function flush(s)
+ n = n + 1
+ t[n] = s
+ if n > maxtab then
+ f:write(concat(t,"\n"),"\n") -- hm, write(sometable) should be nice
+ t = { } -- we could recycle t if needed
+ n = 0
+ end
+ end
+ serialize(flush,root,name,specification)
+ f:write(concat(t,"\n"),"\n")
+ else
+ local function flush(s)
+ f:write(s,"\n")
+ end
+ serialize(flush,root,name,specification)
+ end
+ f:close()
+ io.flush()
+ end
+end
+
+local function flattened(t,f,depth) -- also handles { nil, 1, nil, 2 }
+ if f == nil then
+ f = { }
+ depth = 0xFFFF
+ elseif tonumber(f) then
+ -- assume that only two arguments are given
+ depth = f
+ f = { }
+ elseif not depth then
+ depth = 0xFFFF
+ end
+ for k, v in next, t do
+ if type(k) ~= "number" then
+ if depth > 0 and type(v) == "table" then
+ flattened(v,f,depth-1)
+ else
+ f[#f+1] = v
+ end
+ end
+ end
+ for k=1,#t do
+ local v = t[k]
+ if depth > 0 and type(v) == "table" then
+ flattened(v,f,depth-1)
+ else
+ f[#f+1] = v
+ end
+ end
+ return f
+end
+
+table.flattened = flattened
+
+local function collapsed(t,f,h)
+ if f == nil then
+ f = { }
+ h = { }
+ end
+ for k=1,#t do
+ local v = t[k]
+ if type(v) == "table" then
+ collapsed(v,f,h)
+ elseif not h[v] then
+ f[#f+1] = v
+ h[v] = true
+ end
+ end
+ return f
+end
+
+local function collapsedhash(t,h)
+ if h == nil then
+ h = { }
+ end
+ for k=1,#t do
+ local v = t[k]
+ if type(v) == "table" then
+ collapsedhash(v,h)
+ else
+ h[v] = true
+ end
+ end
+ return h
+end
+
+table.collapsed = collapsed -- 20% faster than unique(collapsed(t))
+table.collapsedhash = collapsedhash
+
+local function unnest(t,f) -- only used in mk, for old times sake
+ if not f then -- and only relevant for token lists
+ f = { } -- this one can become obsolete
+ end
+ for i=1,#t do
+ local v = t[i]
+ if type(v) == "table" then
+ if type(v[1]) == "table" then
+ unnest(v,f)
+ else
+ f[#f+1] = v
+ end
+ else
+ f[#f+1] = v
+ end
+ end
+ return f
+end
+
+function table.unnest(t) -- bad name
+ return unnest(t)
+end
+
+local function are_equal(a,b,n,m) -- indexed
+ if a == b then
+ return true
+ elseif a and b and #a == #b then
+ if not n then
+ n = 1
+ end
+ if not m then
+ m = #a
+ end
+ for i=n,m do
+ local ai, bi = a[i], b[i]
+ if ai==bi then
+ -- same
+ elseif type(ai) == "table" and type(bi) == "table" then
+ if not are_equal(ai,bi) then
+ return false
+ end
+ else
+ return false
+ end
+ end
+ return true
+ else
+ return false
+ end
+end
+
+local function identical(a,b) -- assumes same structure
+ if a ~= b then
+ for ka, va in next, a do
+ local vb = b[ka]
+ if va == vb then
+ -- same
+ elseif type(va) == "table" and type(vb) == "table" then
+ if not identical(va,vb) then
+ return false
+ end
+ else
+ return false
+ end
+ end
+ end
+ return true
+end
+
+table.identical = identical
+table.are_equal = are_equal
+
+local function sparse(old,nest,keeptables)
+ local new = { }
+ for k, v in next, old do
+ if not (v == "" or v == false) then
+ if nest and type(v) == "table" then
+ v = sparse(v,nest)
+ if keeptables or next(v) ~= nil then
+ new[k] = v
+ end
+ else
+ new[k] = v
+ end
+ end
+ end
+ return new
+end
+
+table.sparse = sparse
+
+function table.compact(t)
+ return sparse(t,true,true)
+end
+
+function table.contains(t, v)
+ if t then
+ for i=1, #t do
+ if t[i] == v then
+ return i
+ end
+ end
+ end
+ return false
+end
+
+function table.count(t)
+ local n = 0
+ for k, v in next, t do
+ n = n + 1
+ end
+ return n
+end
+
+function table.swapped(t,s) -- hash, we need to make sure we don't mess up next
+ local n = { }
+ if s then
+ for k, v in next, s do
+ n[k] = v
+ end
+ end
+ for k, v in next, t do
+ n[v] = k
+ end
+ return n
+end
+
+function table.hashed(t) -- list, add hash to index (save because we are not yet mixed
+ for i=1,#t do
+ t[t[i]] = i
+ end
+ return t
+end
+
+function table.mirrored(t) -- hash, we need to make sure we don't mess up next
+ local n = { }
+ for k, v in next, t do
+ n[v] = k
+ n[k] = v
+ end
+ return n
+end
+
+function table.reversed(t)
+ if t then
+ local tt = { }
+ local tn = #t
+ if tn > 0 then
+ local ttn = 0
+ for i=tn,1,-1 do
+ ttn = ttn + 1
+ tt[ttn] = t[i]
+ end
+ end
+ return tt
+ end
+end
+
+function table.reverse(t) -- check with 5.3 ?
+ if t then
+ local n = #t
+ local m = n + 1
+ for i=1,floor(n/2) do -- maybe just n//2
+ local j = m - i
+ t[i], t[j] = t[j], t[i]
+ end
+ return t
+ end
+end
+
+-- This one is for really simple cases where need a hash from a table.
+
+local function sequenced(t,sep,simple)
+ if not t then
+ return ""
+ elseif type(t) ~= "table" then
+ return t -- handy fallback
+ end
+ local n = #t
+ local s = { }
+ if n > 0 then
+ -- indexed
+ for i=1,n do
+ local v = t[i]
+ if type(v) == "table" then
+ s[i] = "{" .. sequenced(v,sep,simple) .. "}"
+ else
+ s[i] = tostring(t[i])
+ end
+ end
+ else
+ -- hashed
+ n = 0
+ for k, v in sortedhash(t) do
+ if simple then
+ if v == true then
+ n = n + 1
+ s[n] = k
+ elseif v and v~= "" then
+ n = n + 1
+ if type(v) == "table" then
+ s[n] = k .. "={" .. sequenced(v,sep,simple) .. "}"
+ else
+ s[n] = k .. "=" .. tostring(v)
+ end
+ end
+ else
+ n = n + 1
+ if type(v) == "table" then
+ s[n] = k .. "={" .. sequenced(v,sep,simple) .. "}"
+ else
+ s[n] = k .. "=" .. tostring(v)
+ end
+ end
+ end
+ end
+ if sep == true then
+ return "{ " .. concat(s,", ") .. " }"
+ else
+ return concat(s,sep or " | ")
+ end
+end
+
+table.sequenced = sequenced
+
+function table.print(t,...)
+ if type(t) ~= "table" then
+ print(tostring(t))
+ else
+ serialize(print,t,...)
+ end
+end
+
+if setinspector then
+ setinspector("table",function(v) if type(v) == "table" then serialize(print,v,"table") return true end end)
+end
+
+-- -- -- obsolete but we keep them for a while and might comment them later -- -- --
+
+-- roughly: copy-loop : unpack : sub == 0.9 : 0.4 : 0.45 (so in critical apps, use unpack)
+
+function table.sub(t,i,j)
+ return { unpack(t,i,j) }
+end
+
+-- slower than #t on indexed tables (#t only returns the size of the numerically indexed slice)
+
+function table.is_empty(t)
+ return not t or next(t) == nil
+end
+
+function table.has_one_entry(t)
+ return t and next(t,next(t)) == nil
+end
+
+-- new (rather basic, not indexed and nested)
+
+function table.loweredkeys(t) -- maybe utf
+ local l = { }
+ for k, v in next, t do
+ l[lower(k)] = v
+ end
+ return l
+end
+
+-- new, might move (maybe duplicate)
+
+function table.unique(old)
+ local hash = { }
+ local new = { }
+ local n = 0
+ for i=1,#old do
+ local oi = old[i]
+ if not hash[oi] then
+ n = n + 1
+ new[n] = oi
+ hash[oi] = true
+ end
+ end
+ return new
+end
+
+function table.sorted(t,...)
+ sort(t,...)
+ return t -- still sorts in-place
+end
+
+--
+
+function table.values(t,s) -- optional sort flag
+ if t then
+ local values = { }
+ local keys = { }
+ local v = 0
+ for key, value in next, t do
+ if not keys[value] then
+ v = v + 1
+ values[v] = value
+ keys[k] = key
+ end
+ end
+ if s then
+ sort(values)
+ end
+ return values
+ else
+ return { }
+ end
+end
+
+-- maybe this will move to util-tab.lua
+
+-- for k, v in table.filtered(t,pattern) do ... end
+-- for k, v in table.filtered(t,pattern,true) do ... end
+-- for k, v in table.filtered(t,pattern,true,cmp) do ... end
+
+function table.filtered(t,pattern,sort,cmp)
+ if t and type(pattern) == "string" then
+ if sort then
+ local s
+ if cmp then
+ -- it would be nice if the sort function would accept a third argument (or nicer, an optional first)
+ s = sortedhashkeys(t,function(a,b) return cmp(t,a,b) end)
+ else
+ s = sortedkeys(t) -- the robust one
+ end
+ local n = 0
+ local m = #s
+ local function kv(s)
+ while n < m do
+ n = n + 1
+ local k = s[n]
+ if find(k,pattern) then
+ return k, t[k]
+ end
+ end
+ end
+ return kv, s
+ else
+ local n = next(t)
+ local function iterator()
+ while n ~= nil do
+ local k = n
+ n = next(t,k)
+ if find(k,pattern) then
+ return k, t[k]
+ end
+ end
+ end
+ return iterator, t
+ end
+ else
+ return nothing
+ end
+end
+
+-- lua 5.3:
+
+if not table.move then
+
+ function table.move(a1,f,e,t,a2)
+ if a2 and a1 ~= a2 then
+ for i=f,e do
+ a2[t] = a1[i]
+ t = t + 1
+ end
+ return a2
+ else
+ t = t + e - f
+ for i=e,f,-1 do
+ a1[t] = a1[i]
+ t = t - 1
+ end
+ return a1
+ end
+ end
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-l-unicode.lua b/macros/luatex/generic/luaotfload/fontloader-l-unicode.lua
new file mode 100644
index 0000000000..13e0a3fa1c
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-l-unicode.lua
@@ -0,0 +1,1405 @@
+if not modules then modules = { } end modules ['l-unicode'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- floor(b/256) => rshift(b, 8)
+-- floor(b/1024) => rshift(b,10)
+
+-- in lua 5.3:
+
+-- utf8.char(···) : concatinated
+-- utf8.charpatt : "[\0-\x7F\xC2-\xF4][\x80-\xBF]*"
+-- utf8.codes(s) : for p, c in utf8.codes(s) do body end
+-- utf8.codepoint(s [, i [, j]])
+-- utf8.len(s [, i])
+-- utf8.offset(s, n [, i])
+
+-- todo: utf.sub replacement (used in syst-aux)
+-- we put these in the utf namespace:
+
+-- used : byte char len lower sub upper
+-- not used : dump find format gmatch gfind gsub match rep reverse
+
+-- utf = utf or (unicode and unicode.utf8) or { }
+
+-- not supported:
+--
+-- dump, find, format, gfind, gmatch, gsub, lower, match, rep, reverse, upper
+
+utf = utf or { }
+unicode = nil
+
+if not string.utfcharacters then
+
+ -- New: this gmatch hack is taken from the Lua 5.2 book. It's about two times slower
+ -- than the built-in string.utfcharacters.
+
+ local gmatch = string.gmatch
+
+ function string.characters(str)
+ return gmatch(str,".[\128-\191]*")
+ end
+
+
+end
+
+utf.characters = string.utfcharacters
+
+-- string.utfvalues
+-- string.utfcharacters
+-- string.characters
+-- string.characterpairs
+-- string.bytes
+-- string.bytepairs
+-- string.utflength
+-- string.utfvalues
+-- string.utfcharacters
+
+local type = type
+local char, byte, format, sub, gmatch = string.char, string.byte, string.format, string.sub, string.gmatch
+local concat = table.concat
+local P, C, R, Cs, Ct, Cmt, Cc, Carg, Cp = lpeg.P, lpeg.C, lpeg.R, lpeg.Cs, lpeg.Ct, lpeg.Cmt, lpeg.Cc, lpeg.Carg, lpeg.Cp
+
+local lpegmatch = lpeg.match
+local patterns = lpeg.patterns
+local tabletopattern = lpeg.utfchartabletopattern
+
+local bytepairs = string.bytepairs
+
+local finder = lpeg.finder
+local replacer = lpeg.replacer
+
+local p_utftype = patterns.utftype
+local p_utfstricttype = patterns.utfstricttype
+local p_utfoffset = patterns.utfoffset
+local p_utf8character = patterns.utf8character
+local p_utf8char = patterns.utf8char
+local p_utf8byte = patterns.utf8byte
+local p_utfbom = patterns.utfbom
+local p_newline = patterns.newline
+local p_whitespace = patterns.whitespace
+
+-- if not unicode then
+-- unicode = { utf = utf } -- for a while
+-- end
+
+if not utf.char then
+
+ utf.char = string.utfcharacter or (utf8 and utf8.char)
+
+ if not utf.char then
+
+ -- no multiples
+
+ local char = string.char
+
+ if bit32 then
+
+ local rshift = bit32.rshift
+
+ function utf.char(n)
+ if n < 0x80 then
+ -- 0aaaaaaa : 0x80
+ return char(n)
+ elseif n < 0x800 then
+ -- 110bbbaa : 0xC0 : n >> 6
+ -- 10aaaaaa : 0x80 : n & 0x3F
+ return char(
+ 0xC0 + rshift(n,6),
+ 0x80 + (n % 0x40)
+ )
+ elseif n < 0x10000 then
+ -- 1110bbbb : 0xE0 : n >> 12
+ -- 10bbbbaa : 0x80 : (n >> 6) & 0x3F
+ -- 10aaaaaa : 0x80 : n & 0x3F
+ return char(
+ 0xE0 + rshift(n,12),
+ 0x80 + (rshift(n,6) % 0x40),
+ 0x80 + (n % 0x40)
+ )
+ elseif n < 0x200000 then
+ -- 11110ccc : 0xF0 : n >> 18
+ -- 10ccbbbb : 0x80 : (n >> 12) & 0x3F
+ -- 10bbbbaa : 0x80 : (n >> 6) & 0x3F
+ -- 10aaaaaa : 0x80 : n & 0x3F
+ -- dddd : ccccc - 1
+ return char(
+ 0xF0 + rshift(n,18),
+ 0x80 + (rshift(n,12) % 0x40),
+ 0x80 + (rshift(n,6) % 0x40),
+ 0x80 + (n % 0x40)
+ )
+ else
+ return ""
+ end
+ end
+
+ else
+
+ local floor = math.floor
+
+ function utf.char(n)
+ if n < 0x80 then
+ return char(n)
+ elseif n < 0x800 then
+ return char(
+ 0xC0 + floor(n/0x40),
+ 0x80 + (n % 0x40)
+ )
+ elseif n < 0x10000 then
+ return char(
+ 0xE0 + floor(n/0x1000),
+ 0x80 + (floor(n/0x40) % 0x40),
+ 0x80 + (n % 0x40)
+ )
+ elseif n < 0x200000 then
+ return char(
+ 0xF0 + floor(n/0x40000),
+ 0x80 + (floor(n/0x1000) % 0x40),
+ 0x80 + (floor(n/0x40) % 0x40),
+ 0x80 + (n % 0x40)
+ )
+ else
+ return ""
+ end
+ end
+
+ end
+
+ end
+
+end
+
+if not utf.byte then
+
+ utf.byte = string.utfvalue or (utf8 and utf8.codepoint)
+
+ if not utf.byte then
+
+ function utf.byte(c)
+ return lpegmatch(p_utf8byte,c)
+ end
+
+ end
+
+end
+
+local utfchar, utfbyte = utf.char, utf.byte
+
+-- As we want to get rid of the (unmaintained) utf library we implement our own
+-- variants (in due time an independent module):
+
+function utf.filetype(data)
+ return data and lpegmatch(p_utftype,data) or "unknown"
+end
+
+local toentities = Cs (
+ (
+ patterns.utf8one
+ + (
+ patterns.utf8two
+ + patterns.utf8three
+ + patterns.utf8four
+ ) / function(s) local b = utfbyte(s) if b < 127 then return s else return format("&#%X;",b) end end
+ )^0
+)
+
+patterns.toentities = toentities
+
+function utf.toentities(str)
+ return lpegmatch(toentities,str)
+end
+
+-- local utfchr = { } -- 60K -> 2.638 M extra mem but currently not called that often (on latin)
+--
+-- setmetatable(utfchr, { __index = function(t,k) local v = utfchar(k) t[k] = v return v end } )
+--
+-- collectgarbage("collect")
+-- local u = collectgarbage("count")*1024
+-- local t = os.clock()
+-- for i=1,1000 do
+-- for i=1,600 do
+-- local a = utfchr[i]
+-- end
+-- end
+-- print(os.clock()-t,collectgarbage("count")*1024-u)
+
+-- collectgarbage("collect")
+-- local t = os.clock()
+-- for i=1,1000 do
+-- for i=1,600 do
+-- local a = utfchar(i)
+-- end
+-- end
+-- print(os.clock()-t,collectgarbage("count")*1024-u)
+
+-- local byte = string.byte
+-- local utfchar = utf.char
+
+local one = P(1)
+local two = C(1) * C(1)
+local four = C(R(utfchar(0xD8),utfchar(0xFF))) * C(1) * C(1) * C(1)
+
+local pattern = P("\254\255") * Cs( (
+ four / function(a,b,c,d)
+ local ab = 0xFF * byte(a) + byte(b)
+ local cd = 0xFF * byte(c) + byte(d)
+ return utfchar((ab-0xD800)*0x400 + (cd-0xDC00) + 0x10000)
+ end
+ + two / function(a,b)
+ return utfchar(byte(a)*256 + byte(b))
+ end
+ + one
+ )^1 )
+ + P("\255\254") * Cs( (
+ four / function(b,a,d,c)
+ local ab = 0xFF * byte(a) + byte(b)
+ local cd = 0xFF * byte(c) + byte(d)
+ return utfchar((ab-0xD800)*0x400 + (cd-0xDC00) + 0x10000)
+ end
+ + two / function(b,a)
+ return utfchar(byte(a)*256 + byte(b))
+ end
+ + one
+ )^1 )
+
+function string.toutf(s) -- in string namespace
+ return lpegmatch(pattern,s) or s -- todo: utf32
+end
+
+local validatedutf = Cs (
+ (
+ patterns.utf8one
+ + patterns.utf8two
+ + patterns.utf8three
+ + patterns.utf8four
+ + P(1) / "�"
+ )^0
+)
+
+patterns.validatedutf = validatedutf
+
+function utf.is_valid(str)
+ return type(str) == "string" and lpegmatch(validatedutf,str) or false
+end
+
+if not utf.len then
+
+ utf.len = string.utflength or (utf8 and utf8.len)
+
+ if not utf.len then
+
+ -- -- alternative 1: 0.77
+ --
+ -- local utfcharcounter = utfbom^-1 * Cs((p_utf8character/'!')^0)
+ --
+ -- function utf.len(str)
+ -- return #lpegmatch(utfcharcounter,str or "")
+ -- end
+ --
+ -- -- alternative 2: 1.70
+ --
+ -- local n = 0
+ --
+ -- local utfcharcounter = utfbom^-1 * (p_utf8character/function() n = n + 1 end)^0 -- slow
+ --
+ -- function utf.length(str)
+ -- n = 0
+ -- lpegmatch(utfcharcounter,str or "")
+ -- return n
+ -- end
+ --
+ -- -- alternative 3: 0.24 (native unicode.utf8.len: 0.047)
+
+ -- local n = 0
+ --
+ -- -- local utfcharcounter = lpeg.patterns.utfbom^-1 * P ( ( Cp() * (
+ -- -- patterns.utf8one ^1 * Cc(1)
+ -- -- + patterns.utf8two ^1 * Cc(2)
+ -- -- + patterns.utf8three^1 * Cc(3)
+ -- -- + patterns.utf8four ^1 * Cc(4) ) * Cp() / function(f,d,t) n = n + (t - f)/d end
+ -- -- )^0 ) -- just as many captures as below
+ --
+ -- -- local utfcharcounter = lpeg.patterns.utfbom^-1 * P ( (
+ -- -- (Cmt(patterns.utf8one ^1,function(_,_,s) n = n + #s return true end))
+ -- -- + (Cmt(patterns.utf8two ^1,function(_,_,s) n = n + #s/2 return true end))
+ -- -- + (Cmt(patterns.utf8three^1,function(_,_,s) n = n + #s/3 return true end))
+ -- -- + (Cmt(patterns.utf8four ^1,function(_,_,s) n = n + #s/4 return true end))
+ -- -- )^0 ) -- not interesting as it creates strings but sometimes faster
+ --
+ -- -- The best so far:
+ --
+ -- local utfcharcounter = utfbom^-1 * P ( (
+ -- Cp() * (patterns.utf8one )^1 * Cp() / function(f,t) n = n + t - f end
+ -- + Cp() * (patterns.utf8two )^1 * Cp() / function(f,t) n = n + (t - f)/2 end
+ -- + Cp() * (patterns.utf8three)^1 * Cp() / function(f,t) n = n + (t - f)/3 end
+ -- + Cp() * (patterns.utf8four )^1 * Cp() / function(f,t) n = n + (t - f)/4 end
+ -- )^0 )
+
+ -- function utf.len(str)
+ -- n = 0
+ -- lpegmatch(utfcharcounter,str or "")
+ -- return n
+ -- end
+
+ local n, f = 0, 1
+
+ local utfcharcounter = patterns.utfbom^-1 * Cmt (
+ Cc(1) * patterns.utf8one ^1
+ + Cc(2) * patterns.utf8two ^1
+ + Cc(3) * patterns.utf8three^1
+ + Cc(4) * patterns.utf8four ^1,
+ function(_,t,d) -- due to Cc no string captures, so faster
+ n = n + (t - f)/d
+ f = t
+ return true
+ end
+ )^0
+
+ function utf.len(str)
+ n, f = 0, 1
+ lpegmatch(utfcharcounter,str or "")
+ return n
+ end
+
+ -- -- these are quite a bit slower:
+
+ -- utfcharcounter = utfbom^-1 * (Cmt(P(1) * R("\128\191")^0, function() n = n + 1 return true end))^0 -- 50+ times slower
+ -- utfcharcounter = utfbom^-1 * (Cmt(P(1), function() n = n + 1 return true end) * R("\128\191")^0)^0 -- 50- times slower
+
+ end
+
+end
+
+utf.length = utf.len
+
+if not utf.sub then
+
+ -- inefficient as lpeg just copies ^n
+
+ -- local function sub(str,start,stop)
+ -- local pattern = p_utf8character^-(start-1) * C(p_utf8character^-(stop-start+1))
+ -- inspect(pattern)
+ -- return lpegmatch(pattern,str) or ""
+ -- end
+
+ -- local b, e, n, first, last = 0, 0, 0, 0, 0
+ --
+ -- local function slide(s,p)
+ -- n = n + 1
+ -- if n == first then
+ -- b = p
+ -- if not last then
+ -- return nil
+ -- end
+ -- end
+ -- if n == last then
+ -- e = p
+ -- return nil
+ -- else
+ -- return p
+ -- end
+ -- end
+ --
+ -- local pattern = Cmt(p_utf8character,slide)^0
+ --
+ -- function utf.sub(str,start,stop) -- todo: from the end
+ -- if not start then
+ -- return str
+ -- end
+ -- b, e, n, first, last = 0, 0, 0, start, stop
+ -- lpegmatch(pattern,str)
+ -- if not stop then
+ -- return sub(str,b)
+ -- else
+ -- return sub(str,b,e-1)
+ -- end
+ -- end
+
+ -- print(utf.sub("Hans Hagen is my name"))
+ -- print(utf.sub("Hans Hagen is my name",5))
+ -- print(utf.sub("Hans Hagen is my name",5,10))
+
+ local utflength = utf.length
+
+ -- also negative indices, upto 10 times slower than a c variant
+
+ local b, e, n, first, last = 0, 0, 0, 0, 0
+
+ local function slide_zero(s,p)
+ n = n + 1
+ if n >= last then
+ e = p - 1
+ else
+ return p
+ end
+ end
+
+ local function slide_one(s,p)
+ n = n + 1
+ if n == first then
+ b = p
+ end
+ if n >= last then
+ e = p - 1
+ else
+ return p
+ end
+ end
+
+ local function slide_two(s,p)
+ n = n + 1
+ if n == first then
+ b = p
+ else
+ return true
+ end
+ end
+
+ local pattern_zero = Cmt(p_utf8character,slide_zero)^0
+ local pattern_one = Cmt(p_utf8character,slide_one )^0
+ local pattern_two = Cmt(p_utf8character,slide_two )^0
+
+ local pattern_first = C(p_utf8character)
+
+ function utf.sub(str,start,stop)
+ if not start then
+ return str
+ end
+ if start == 0 then
+ start = 1
+ end
+ if not stop then
+ if start < 0 then
+ local l = utflength(str) -- we can inline this function if needed
+ start = l + start
+ else
+ start = start - 1
+ end
+ b, n, first = 0, 0, start
+ lpegmatch(pattern_two,str)
+ if n >= first then
+ return sub(str,b)
+ else
+ return ""
+ end
+ end
+ if start < 0 or stop < 0 then
+ local l = utf.length(str)
+ if start < 0 then
+ start = l + start
+ if start <= 0 then
+ start = 1
+ else
+ start = start + 1
+ end
+ end
+ if stop < 0 then
+ stop = l + stop
+ if stop == 0 then
+ stop = 1
+ else
+ stop = stop + 1
+ end
+ end
+ end
+ if start == 1 and stop == 1 then
+ return lpegmatch(pattern_first,str) or ""
+ elseif start > stop then
+ return ""
+ elseif start > 1 then
+ b, e, n, first, last = 0, 0, 0, start - 1, stop
+ lpegmatch(pattern_one,str)
+ if n >= first and e == 0 then
+ e = #str
+ end
+ return sub(str,b,e)
+ else
+ b, e, n, last = 1, 0, 0, stop
+ lpegmatch(pattern_zero,str)
+ if e == 0 then
+ e = #str
+ end
+ return sub(str,b,e)
+ end
+ end
+
+ -- local n = 100000
+ -- local str = string.rep("123456àáâãäå",100)
+ --
+ -- for i=-15,15,1 do
+ -- for j=-15,15,1 do
+ -- if utf.xsub(str,i,j) ~= utf.sub(str,i,j) then
+ -- print("error",i,j,"l>"..utf.xsub(str,i,j),"s>"..utf.sub(str,i,j))
+ -- end
+ -- end
+ -- if utf.xsub(str,i) ~= utf.sub(str,i) then
+ -- print("error",i,"l>"..utf.xsub(str,i),"s>"..utf.sub(str,i))
+ -- end
+ -- end
+
+ -- print(" 1, 7",utf.xsub(str, 1, 7),utf.sub(str, 1, 7))
+ -- print(" 0, 7",utf.xsub(str, 0, 7),utf.sub(str, 0, 7))
+ -- print(" 0, 9",utf.xsub(str, 0, 9),utf.sub(str, 0, 9))
+ -- print(" 4 ",utf.xsub(str, 4 ),utf.sub(str, 4 ))
+ -- print(" 0 ",utf.xsub(str, 0 ),utf.sub(str, 0 ))
+ -- print(" 0, 0",utf.xsub(str, 0, 0),utf.sub(str, 0, 0))
+ -- print(" 4, 4",utf.xsub(str, 4, 4),utf.sub(str, 4, 4))
+ -- print(" 4, 0",utf.xsub(str, 4, 0),utf.sub(str, 4, 0))
+ -- print("-3, 0",utf.xsub(str,-3, 0),utf.sub(str,-3, 0))
+ -- print(" 0,-3",utf.xsub(str, 0,-3),utf.sub(str, 0,-3))
+ -- print(" 5,-3",utf.xsub(str,-5,-3),utf.sub(str,-5,-3))
+ -- print("-3 ",utf.xsub(str,-3 ),utf.sub(str,-3 ))
+
+end
+
+-- a replacement for simple gsubs:
+
+-- function utf.remapper(mapping)
+-- local pattern = Cs((p_utf8character/mapping)^0)
+-- return function(str)
+-- if not str or str == "" then
+-- return ""
+-- else
+-- return lpegmatch(pattern,str)
+-- end
+-- end, pattern
+-- end
+
+function utf.remapper(mapping,option,action) -- static also returns a pattern
+ local variant = type(mapping)
+ if variant == "table" then
+ action = action or mapping
+ if option == "dynamic" then
+ local pattern = false
+ table.setmetatablenewindex(mapping,function(t,k,v) rawset(t,k,v) pattern = false end)
+ return function(str)
+ if not str or str == "" then
+ return ""
+ else
+ if not pattern then
+ pattern = Cs((tabletopattern(mapping)/action + p_utf8character)^0)
+ end
+ return lpegmatch(pattern,str)
+ end
+ end
+ elseif option == "pattern" then
+ return Cs((tabletopattern(mapping)/action + p_utf8character)^0)
+ -- elseif option == "static" then
+ else
+ local pattern = Cs((tabletopattern(mapping)/action + p_utf8character)^0)
+ return function(str)
+ if not str or str == "" then
+ return ""
+ else
+ return lpegmatch(pattern,str)
+ end
+ end, pattern
+ end
+ elseif variant == "function" then
+ if option == "pattern" then
+ return Cs((p_utf8character/mapping + p_utf8character)^0)
+ else
+ local pattern = Cs((p_utf8character/mapping + p_utf8character)^0)
+ return function(str)
+ if not str or str == "" then
+ return ""
+ else
+ return lpegmatch(pattern,str)
+ end
+ end, pattern
+ end
+ else
+ -- is actually an error
+ return function(str)
+ return str or ""
+ end
+ end
+end
+
+-- local remap = utf.remapper { a = 'd', b = "c", c = "b", d = "a" }
+-- print(remap("abcd 1234 abcd"))
+
+function utf.replacer(t) -- no precheck, always string builder
+ local r = replacer(t,false,false,true)
+ return function(str)
+ return lpegmatch(r,str)
+ end
+end
+
+function utf.subtituter(t) -- with precheck and no building if no match
+ local f = finder (t)
+ local r = replacer(t,false,false,true)
+ return function(str)
+ local i = lpegmatch(f,str)
+ if not i then
+ return str
+ elseif i > #str then
+ return str
+ else
+ -- return sub(str,1,i-2) .. lpegmatch(r,str,i-1) -- slower
+ return lpegmatch(r,str)
+ end
+ end
+end
+
+-- inspect(utf.split("a b c d"))
+-- inspect(utf.split("a b c d",true))
+
+local utflinesplitter = p_utfbom^-1 * lpeg.tsplitat(p_newline)
+local utfcharsplitter_ows = p_utfbom^-1 * Ct(C(p_utf8character)^0)
+local utfcharsplitter_iws = p_utfbom^-1 * Ct((p_whitespace^1 + C(p_utf8character))^0)
+local utfcharsplitter_raw = Ct(C(p_utf8character)^0)
+
+patterns.utflinesplitter = utflinesplitter
+
+function utf.splitlines(str)
+ return lpegmatch(utflinesplitter,str or "")
+end
+
+function utf.split(str,ignorewhitespace) -- new
+ if ignorewhitespace then
+ return lpegmatch(utfcharsplitter_iws,str or "")
+ else
+ return lpegmatch(utfcharsplitter_ows,str or "")
+ end
+end
+
+function utf.totable(str) -- keeps bom
+ return lpegmatch(utfcharsplitter_raw,str)
+end
+
+-- 0 EF BB BF UTF-8
+-- 1 FF FE UTF-16-little-endian
+-- 2 FE FF UTF-16-big-endian
+-- 3 FF FE 00 00 UTF-32-little-endian
+-- 4 00 00 FE FF UTF-32-big-endian
+--
+-- \000 fails in <= 5.0 but is valid in >=5.1 where %z is depricated
+
+-- utf.name = {
+-- [0] = 'utf-8',
+-- [1] = 'utf-16-le',
+-- [2] = 'utf-16-be',
+-- [3] = 'utf-32-le',
+-- [4] = 'utf-32-be'
+-- }
+--
+-- function utf.magic(f)
+-- local str = f:read(4)
+-- if not str then
+-- f:seek('set')
+-- return 0
+-- -- elseif find(str,"^%z%z\254\255") then -- depricated
+-- -- elseif find(str,"^\000\000\254\255") then -- not permitted and bugged
+-- elseif find(str,"\000\000\254\255",1,true) then -- seems to work okay (TH)
+-- return 4
+-- -- elseif find(str,"^\255\254%z%z") then -- depricated
+-- -- elseif find(str,"^\255\254\000\000") then -- not permitted and bugged
+-- elseif find(str,"\255\254\000\000",1,true) then -- seems to work okay (TH)
+-- return 3
+-- elseif find(str,"^\254\255") then
+-- f:seek('set',2)
+-- return 2
+-- elseif find(str,"^\255\254") then
+-- f:seek('set',2)
+-- return 1
+-- elseif find(str,"^\239\187\191") then
+-- f:seek('set',3)
+-- return 0
+-- else
+-- f:seek('set')
+-- return 0
+-- end
+-- end
+
+function utf.magic(f) -- not used
+ local str = f:read(4) or ""
+ local off = lpegmatch(p_utfoffset,str)
+ if off < 4 then
+ f:seek('set',off)
+ end
+ return lpegmatch(p_utftype,str)
+end
+
+local utf16_to_utf8_be, utf16_to_utf8_le
+local utf32_to_utf8_be, utf32_to_utf8_le
+
+local utf_16_be_getbom = patterns.utfbom_16_be^-1
+local utf_16_le_getbom = patterns.utfbom_16_le^-1
+local utf_32_be_getbom = patterns.utfbom_32_be^-1
+local utf_32_le_getbom = patterns.utfbom_32_le^-1
+
+local utf_16_be_linesplitter = utf_16_be_getbom * lpeg.tsplitat(patterns.utf_16_be_nl)
+local utf_16_le_linesplitter = utf_16_le_getbom * lpeg.tsplitat(patterns.utf_16_le_nl)
+local utf_32_be_linesplitter = utf_32_be_getbom * lpeg.tsplitat(patterns.utf_32_be_nl)
+local utf_32_le_linesplitter = utf_32_le_getbom * lpeg.tsplitat(patterns.utf_32_le_nl)
+
+-- we have three possibilities: bytepairs (using tables), gmatch (using tables), gsub and
+-- lpeg. Bytepairs are the fastert but as soon as we need to remove bombs and so the gain
+-- is less due to more testing. Also, we seldom have to convert utf16 so we don't care to
+-- much about a few milliseconds more runtime. The lpeg variant is upto 20% slower but
+-- still pretty fast.
+--
+-- for historic resone we keep the bytepairs variants around .. beware they don't grab the
+-- bom like the lpegs do so they're not dropins in the functions that follow
+--
+-- utf16_to_utf8_be = function(s)
+-- if not s then
+-- return nil
+-- elseif s == "" then
+-- return ""
+-- end
+-- local result, r, more = { }, 0, 0
+-- for left, right in bytepairs(s) do
+-- if right then
+-- local now = 256*left + right
+-- if more > 0 then
+-- now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000 -- the 0x10000 smells wrong
+-- more = 0
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- elseif now >= 0xD800 and now <= 0xDBFF then
+-- more = now
+-- else
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- end
+-- end
+-- end
+-- return concat(result)
+-- end
+--
+-- local utf16_to_utf8_be_t = function(t)
+-- if not t then
+-- return nil
+-- elseif type(t) == "string" then
+-- t = lpegmatch(utf_16_be_linesplitter,t)
+-- end
+-- local result = { } -- we reuse result
+-- for i=1,#t do
+-- local s = t[i]
+-- if s ~= "" then
+-- local r, more = 0, 0
+-- for left, right in bytepairs(s) do
+-- if right then
+-- local now = 256*left + right
+-- if more > 0 then
+-- now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000
+-- more = 0
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- elseif now >= 0xD800 and now <= 0xDBFF then
+-- more = now
+-- else
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- end
+-- end
+-- end
+-- t[i] = concat(result,"",1,r) -- we reused tmp, hence t
+-- end
+-- end
+-- return t
+-- end
+--
+-- utf16_to_utf8_le = function(s)
+-- if not s then
+-- return nil
+-- elseif s == "" then
+-- return ""
+-- end
+-- local result, r, more = { }, 0, 0
+-- for left, right in bytepairs(s) do
+-- if right then
+-- local now = 256*right + left
+-- if more > 0 then
+-- now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000
+-- more = 0
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- elseif now >= 0xD800 and now <= 0xDBFF then
+-- more = now
+-- else
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- end
+-- end
+-- end
+-- return concat(result)
+-- end
+--
+-- local utf16_to_utf8_le_t = function(t)
+-- if not t then
+-- return nil
+-- elseif type(t) == "string" then
+-- t = lpegmatch(utf_16_le_linesplitter,t)
+-- end
+-- local result = { } -- we reuse result
+-- for i=1,#t do
+-- local s = t[i]
+-- if s ~= "" then
+-- local r, more = 0, 0
+-- for left, right in bytepairs(s) do
+-- if right then
+-- local now = 256*right + left
+-- if more > 0 then
+-- now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000
+-- more = 0
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- elseif now >= 0xD800 and now <= 0xDBFF then
+-- more = now
+-- else
+-- r = r + 1
+-- result[r] = utfchar(now)
+-- end
+-- end
+-- end
+-- t[i] = concat(result,"",1,r) -- we reused tmp, hence t
+-- end
+-- end
+-- return t
+-- end
+--
+-- local utf32_to_utf8_be_t = function(t)
+-- if not t then
+-- return nil
+-- elseif type(t) == "string" then
+-- t = lpegmatch(utflinesplitter,t)
+-- end
+-- local result = { } -- we reuse result
+-- for i=1,#t do
+-- local r, more = 0, -1
+-- for a,b in bytepairs(t[i]) do
+-- if a and b then
+-- if more < 0 then
+-- more = 256*256*256*a + 256*256*b
+-- else
+-- r = r + 1
+-- result[t] = utfchar(more + 256*a + b)
+-- more = -1
+-- end
+-- else
+-- break
+-- end
+-- end
+-- t[i] = concat(result,"",1,r)
+-- end
+-- return t
+-- end
+--
+-- local utf32_to_utf8_le_t = function(t)
+-- if not t then
+-- return nil
+-- elseif type(t) == "string" then
+-- t = lpegmatch(utflinesplitter,t)
+-- end
+-- local result = { } -- we reuse result
+-- for i=1,#t do
+-- local r, more = 0, -1
+-- for a,b in bytepairs(t[i]) do
+-- if a and b then
+-- if more < 0 then
+-- more = 256*b + a
+-- else
+-- r = r + 1
+-- result[t] = utfchar(more + 256*256*256*b + 256*256*a)
+-- more = -1
+-- end
+-- else
+-- break
+-- end
+-- end
+-- t[i] = concat(result,"",1,r)
+-- end
+-- return t
+-- end
+
+local more = 0
+
+local p_utf16_to_utf8_be = C(1) * C(1) /function(left,right)
+ local now = 256*byte(left) + byte(right)
+ if more > 0 then
+ now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000
+ more = 0
+ return utfchar(now)
+ elseif now >= 0xD800 and now <= 0xDBFF then
+ more = now
+ return "" -- else the c's end up in the stream
+ else
+ return utfchar(now)
+ end
+end
+
+local p_utf16_to_utf8_le = C(1) * C(1) /function(right,left)
+ local now = 256*byte(left) + byte(right)
+ if more > 0 then
+ now = (more-0xD800)*0x400 + (now-0xDC00) + 0x10000
+ more = 0
+ return utfchar(now)
+ elseif now >= 0xD800 and now <= 0xDBFF then
+ more = now
+ return "" -- else the c's end up in the stream
+ else
+ return utfchar(now)
+ end
+end
+local p_utf32_to_utf8_be = C(1) * C(1) * C(1) * C(1) /function(a,b,c,d)
+ return utfchar(256*256*256*byte(a) + 256*256*byte(b) + 256*byte(c) + byte(d))
+end
+
+local p_utf32_to_utf8_le = C(1) * C(1) * C(1) * C(1) /function(a,b,c,d)
+ return utfchar(256*256*256*byte(d) + 256*256*byte(c) + 256*byte(b) + byte(a))
+end
+
+p_utf16_to_utf8_be = P(true) / function() more = 0 end * utf_16_be_getbom * Cs(p_utf16_to_utf8_be^0)
+p_utf16_to_utf8_le = P(true) / function() more = 0 end * utf_16_le_getbom * Cs(p_utf16_to_utf8_le^0)
+p_utf32_to_utf8_be = P(true) / function() more = 0 end * utf_32_be_getbom * Cs(p_utf32_to_utf8_be^0)
+p_utf32_to_utf8_le = P(true) / function() more = 0 end * utf_32_le_getbom * Cs(p_utf32_to_utf8_le^0)
+
+patterns.utf16_to_utf8_be = p_utf16_to_utf8_be
+patterns.utf16_to_utf8_le = p_utf16_to_utf8_le
+patterns.utf32_to_utf8_be = p_utf32_to_utf8_be
+patterns.utf32_to_utf8_le = p_utf32_to_utf8_le
+
+utf16_to_utf8_be = function(s)
+ if s and s ~= "" then
+ return lpegmatch(p_utf16_to_utf8_be,s)
+ else
+ return s
+ end
+end
+
+local utf16_to_utf8_be_t = function(t)
+ if not t then
+ return nil
+ elseif type(t) == "string" then
+ t = lpegmatch(utf_16_be_linesplitter,t)
+ end
+ for i=1,#t do
+ local s = t[i]
+ if s ~= "" then
+ t[i] = lpegmatch(p_utf16_to_utf8_be,s)
+ end
+ end
+ return t
+end
+
+utf16_to_utf8_le = function(s)
+ if s and s ~= "" then
+ return lpegmatch(p_utf16_to_utf8_le,s)
+ else
+ return s
+ end
+end
+
+local utf16_to_utf8_le_t = function(t)
+ if not t then
+ return nil
+ elseif type(t) == "string" then
+ t = lpegmatch(utf_16_le_linesplitter,t)
+ end
+ for i=1,#t do
+ local s = t[i]
+ if s ~= "" then
+ t[i] = lpegmatch(p_utf16_to_utf8_le,s)
+ end
+ end
+ return t
+end
+
+utf32_to_utf8_be = function(s)
+ if s and s ~= "" then
+ return lpegmatch(p_utf32_to_utf8_be,s)
+ else
+ return s
+ end
+end
+
+local utf32_to_utf8_be_t = function(t)
+ if not t then
+ return nil
+ elseif type(t) == "string" then
+ t = lpegmatch(utf_32_be_linesplitter,t)
+ end
+ for i=1,#t do
+ local s = t[i]
+ if s ~= "" then
+ t[i] = lpegmatch(p_utf32_to_utf8_be,s)
+ end
+ end
+ return t
+end
+
+utf32_to_utf8_le = function(s)
+ if s and s ~= "" then
+ return lpegmatch(p_utf32_to_utf8_le,s)
+ else
+ return s
+ end
+end
+
+local utf32_to_utf8_le_t = function(t)
+ if not t then
+ return nil
+ elseif type(t) == "string" then
+ t = lpegmatch(utf_32_le_linesplitter,t)
+ end
+ for i=1,#t do
+ local s = t[i]
+ if s ~= "" then
+ t[i] = lpegmatch(p_utf32_to_utf8_le,s)
+ end
+ end
+ return t
+end
+
+utf.utf16_to_utf8_le_t = utf16_to_utf8_le_t
+utf.utf16_to_utf8_be_t = utf16_to_utf8_be_t
+utf.utf32_to_utf8_le_t = utf32_to_utf8_le_t
+utf.utf32_to_utf8_be_t = utf32_to_utf8_be_t
+
+utf.utf16_to_utf8_le = utf16_to_utf8_le
+utf.utf16_to_utf8_be = utf16_to_utf8_be
+utf.utf32_to_utf8_le = utf32_to_utf8_le
+utf.utf32_to_utf8_be = utf32_to_utf8_be
+
+function utf.utf8_to_utf8_t(t)
+ return type(t) == "string" and lpegmatch(utflinesplitter,t) or t
+end
+
+function utf.utf16_to_utf8_t(t,endian)
+ return endian and utf16_to_utf8_be_t(t) or utf16_to_utf8_le_t(t) or t
+end
+
+function utf.utf32_to_utf8_t(t,endian)
+ return endian and utf32_to_utf8_be_t(t) or utf32_to_utf8_le_t(t) or t
+end
+
+local function little(b)
+ if b < 0x10000 then
+ return char(b%256,rshift(b,8))
+ else
+ b = b - 0x10000
+ local b1 = rshift(b,10) + 0xD800
+ local b2 = b%1024 + 0xDC00
+ return char(b1%256,rshift(b1,8),b2%256,rshift(b2,8))
+ end
+end
+
+local function big(b)
+ if b < 0x10000 then
+ return char(rshift(b,8),b%256)
+ else
+ b = b - 0x10000
+ local b1 = rshift(b,10) + 0xD800
+ local b2 = b%1024 + 0xDC00
+ return char(rshift(b1,8),b1%256,rshift(b2,8),b2%256)
+ end
+end
+
+local l_remap = Cs((p_utf8byte/little+P(1)/"")^0)
+local b_remap = Cs((p_utf8byte/big +P(1)/"")^0)
+
+local function utf8_to_utf16_be(str,nobom)
+ if nobom then
+ return lpegmatch(b_remap,str)
+ else
+ return char(254,255) .. lpegmatch(b_remap,str)
+ end
+end
+
+local function utf8_to_utf16_le(str,nobom)
+ if nobom then
+ return lpegmatch(l_remap,str)
+ else
+ return char(255,254) .. lpegmatch(l_remap,str)
+ end
+end
+
+utf.utf8_to_utf16_be = utf8_to_utf16_be
+utf.utf8_to_utf16_le = utf8_to_utf16_le
+
+function utf.utf8_to_utf16(str,littleendian,nobom)
+ if littleendian then
+ return utf8_to_utf16_le(str,nobom)
+ else
+ return utf8_to_utf16_be(str,nobom)
+ end
+end
+
+local pattern = Cs (
+ (p_utf8byte / function(unicode ) return format( "0x%04X", unicode) end) *
+ (p_utf8byte * Carg(1) / function(unicode,separator) return format("%s0x%04X",separator,unicode) end)^0
+)
+
+function utf.tocodes(str,separator)
+ return lpegmatch(pattern,str,1,separator or " ")
+end
+
+function utf.ustring(s)
+ return format("U+%05X",type(s) == "number" and s or utfbyte(s))
+end
+
+function utf.xstring(s)
+ return format("0x%05X",type(s) == "number" and s or utfbyte(s))
+end
+
+function utf.toeight(str)
+ if not str or str == "" then
+ return nil
+ end
+ local utftype = lpegmatch(p_utfstricttype,str)
+ if utftype == "utf-8" then
+ return sub(str,4) -- remove the bom
+ elseif utftype == "utf-16-be" then
+ return utf16_to_utf8_be(str) -- bom gets removed
+ elseif utftype == "utf-16-le" then
+ return utf16_to_utf8_le(str) -- bom gets removed
+ else
+ return str
+ end
+end
+
+--
+
+do
+
+ local p_nany = p_utf8character / ""
+ local cache = { }
+
+ function utf.count(str,what)
+ if type(what) == "string" then
+ local p = cache[what]
+ if not p then
+ p = Cs((P(what)/" " + p_nany)^0)
+ cache[p] = p
+ end
+ return #lpegmatch(p,str)
+ else -- 4 times slower but still faster than / function
+ return #lpegmatch(Cs((P(what)/" " + p_nany)^0),str)
+ end
+ end
+
+end
+
+if not string.utfvalues then
+
+ -- So, a logical next step is to check for the values variant. It over five times
+ -- slower than the built-in string.utfvalues. I optimized it a bit for n=0,1.
+
+ ----- wrap, yield, gmatch = coroutine.wrap, coroutine.yield, string.gmatch
+ local find = string.find
+
+ local dummy = function()
+ -- we share this one
+ end
+
+ -- function string.utfvalues(str)
+ -- local n = #str
+ -- if n == 0 then
+ -- return wrap(dummy)
+ -- elseif n == 1 then
+ -- return wrap(function() yield(utfbyte(str)) end)
+ -- else
+ -- return wrap(function() for s in gmatch(str,".[\128-\191]*") do
+ -- yield(utfbyte(s))
+ -- end end)
+ -- end
+ -- end
+ --
+ -- faster:
+
+ function string.utfvalues(str)
+ local n = #str
+ if n == 0 then
+ return dummy
+ elseif n == 1 then
+ return function() return utfbyte(str) end
+ else
+ local p = 1
+ -- local n = #str
+ return function()
+ -- if p <= n then -- slower than the last find
+ local b, e = find(str,".[\128-\191]*",p)
+ if b then
+ p = e + 1
+ return utfbyte(sub(str,b,e))
+ end
+ -- end
+ end
+ end
+ end
+
+ -- slower:
+ --
+ -- local pattern = C(p_utf8character) * Cp()
+ -- ----- pattern = p_utf8character/utfbyte * Cp()
+ -- ----- pattern = p_utf8byte * Cp()
+ --
+ -- function string.utfvalues(str) -- one of the cases where a find is faster than an lpeg
+ -- local n = #str
+ -- if n == 0 then
+ -- return dummy
+ -- elseif n == 1 then
+ -- return function() return utfbyte(str) end
+ -- else
+ -- local p = 1
+ -- return function()
+ -- local s, e = lpegmatch(pattern,str,p)
+ -- if e then
+ -- p = e
+ -- return utfbyte(s)
+ -- -- return s
+ -- end
+ -- end
+ -- end
+ -- end
+
+end
+
+utf.values = string.utfvalues
+
+function utf.chrlen(u) -- u is number
+ return
+ (u < 0x80 and 1) or
+ (u < 0xE0 and 2) or
+ (u < 0xF0 and 3) or
+ (u < 0xF8 and 4) or
+ (u < 0xFC and 5) or
+ (u < 0xFE and 6) or 0
+end
+
+-- hashing saves a little but not that much in practice
+--
+-- local utf32 = table.setmetatableindex(function(t,k) local v = toutf32(k) t[k] = v return v end)
+
+if bit32 then
+
+ local extract = bit32.extract
+ local char = string.char
+
+ function utf.toutf32string(n)
+ if n <= 0xFF then
+ return
+ char(n) ..
+ "\000\000\000"
+ elseif n <= 0xFFFF then
+ return
+ char(extract(n, 0,8)) ..
+ char(extract(n, 8,8)) ..
+ "\000\000"
+ elseif n <= 0xFFFFFF then
+ return
+ char(extract(n, 0,8)) ..
+ char(extract(n, 8,8)) ..
+ char(extract(n,16,8)) ..
+ "\000"
+ else
+ return
+ char(extract(n, 0,8)) ..
+ char(extract(n, 8,8)) ..
+ char(extract(n,16,8)) ..
+ char(extract(n,24,8))
+ end
+ end
+
+end
+
+-- goodie:
+
+local len = utf.len
+local rep = rep
+
+function string.utfpadd(s,n)
+ if n and n ~= 0 then
+ local l = len(s)
+ if n > 0 then
+ local d = n - l
+ if d > 0 then
+ return rep(c or " ",d) .. s
+ end
+ else
+ local d = - n - l
+ if d > 0 then
+ return s .. rep(c or " ",d)
+ end
+ end
+ end
+ return s
+end
+
+-- goodies
+
+do
+
+ local utfcharacters = utf.characters or string.utfcharacters
+ local utfchar = utf.char or string.utfcharacter
+
+ lpeg.UP = P
+
+ if utfcharacters then
+
+ function lpeg.US(str)
+ local p = P(false)
+ for uc in utfcharacters(str) do
+ p = p + P(uc)
+ end
+ return p
+ end
+
+ else
+
+ function lpeg.US(str)
+ local p = P(false)
+ local f = function(uc)
+ p = p + P(uc)
+ end
+ lpegmatch((p_utf8char/f)^0,str)
+ return p
+ end
+
+ end
+
+ local range = p_utf8byte * p_utf8byte + Cc(false) -- utf8byte is already a capture
+
+ function lpeg.UR(str,more)
+ local first, last
+ if type(str) == "number" then
+ first = str
+ last = more or first
+ else
+ first, last = lpegmatch(range,str)
+ if not last then
+ return P(str)
+ end
+ end
+ if first == last then
+ return P(str)
+ end
+ if not utfchar then
+ utfchar = utf.char -- maybe delayed
+ end
+ if utfchar and (last - first < 8) then -- a somewhat arbitrary criterium
+ local p = P(false)
+ for i=first,last do
+ p = p + P(utfchar(i))
+ end
+ return p -- nil when invalid range
+ else
+ local f = function(b)
+ return b >= first and b <= last
+ end
+ -- tricky, these nested captures
+ return p_utf8byte / f -- nil when invalid range
+ end
+ end
+
+ -- print(lpeg.match(lpeg.Cs((C(lpeg.UR("αω"))/{ ["χ"] = "OEPS" })^0),"αωχαω"))
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-reference-load-order.lua b/macros/luatex/generic/luaotfload/fontloader-reference-load-order.lua
new file mode 100644
index 0000000000..85fe1ae975
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-reference-load-order.lua
@@ -0,0 +1,349 @@
+if not modules then modules = { } end modules ['luatex-fonts'] = {
+ version = 1.001,
+ comment = "companion to luatex-fonts.tex",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+-- A merged file is generated with:
+--
+-- mtxrun --script package --merge --stripcontext luatex-fonts.lua
+--
+-- A needed resource file is made by:
+--
+-- mtxrun --script context luatex-basics-prepare.tex
+--
+-- A font (generic) database is created with:
+--
+-- mtxrun --script font --reload --simple
+
+-- The following code isolates the generic context code from already defined or to be defined
+-- namespaces. This is the reference loader for plain tex. This generic code is also used in
+-- luaotfload which is a low level lualatex opentype font loader but somehow has gotten a bit
+-- too generic name / prefix, originally set up and maintained by Khaled Hosny. Currently that
+-- set of derived files is maintained by a larger team lead by Philipp Gesang so when there are
+-- issues with this code in latex, you can best contact him. It might make sense then to first
+-- check if context has the same issue. We do our best to keep the interface as clean as possible.
+--
+-- The code base is rather stable now, especially if you stay away from the non generic code. All
+-- relevant data is organized in tables within the main table of a font instance. There are a few
+-- places where in context other code is plugged in, but this does not affect the core code. Users
+-- can (given that their macro package provides this option) access the font data (characters,
+-- descriptions, properties, parameters, etc) of this main table. The documentation is part of
+-- context. There is also a manual for the helper libraries (maintained as part of the cld manuals).
+--
+-- Future versions will probably have some more specific context code removed, like tracing and
+-- obscure hooks, so that we have a more efficient version (and less files too). So, don't depend
+-- too much on low level code that is meant for context as it can change without notice. We might
+-- also add more helper code here, but that depends to what extend metatex (sidetrack of context)
+-- evolves into a low level layer (depends on time, as usual).
+
+-- The code here is the same as in context version 2015.09.11 but the rendering in context can be
+-- different from generic. This can be a side effect of additional callbacks, additional features
+-- and interferences between mechanisms between macro packages. We use the rendering in context
+-- and luatex-plain as reference for issues.
+
+utf = utf or (unicode and unicode.utf8) or { }
+
+-- We have some (global) hooks (for latex):
+
+if not non_generic_context then
+ non_generic_context = { }
+end
+
+if not non_generic_context.luatex_fonts then
+ non_generic_context.luatex_fonts = {
+ -- load_before = nil,
+ -- load_after = nil,
+ -- skip_loading = nil,
+ }
+end
+
+if not generic_context then
+ generic_context = { }
+end
+
+if not generic_context.push_namespaces then
+
+ function generic_context.push_namespaces()
+ -- logs.report("system","push namespace")
+ local normalglobal = { }
+ for k, v in next, _G do
+ normalglobal[k] = v
+ end
+ return normalglobal
+ end
+
+ function generic_context.pop_namespaces(normalglobal,isolate)
+ if normalglobal then
+ -- logs.report("system","pop namespace")
+ for k, v in next, _G do
+ if not normalglobal[k] then
+ generic_context[k] = v
+ if isolate then
+ _G[k] = nil
+ end
+ end
+ end
+ for k, v in next, normalglobal do
+ _G[k] = v
+ end
+ -- just to be sure:
+ setmetatable(generic_context,_G)
+ else
+ logs.report("system","fatal error: invalid pop of generic_context")
+ os.exit()
+ end
+ end
+
+end
+
+local whatever = generic_context.push_namespaces()
+
+-- We keep track of load time by storing the current time. That way we cannot be accused
+-- of slowing down loading too much. Anyhow, there is no reason for this library to perform
+-- slower in any other package as it does in context.
+--
+-- Please don't update to this version without proper testing. It might be that this version
+-- lags behind stock context and the only formal release takes place around tex live code
+-- freeze.
+
+local starttime = os.gettimeofday()
+
+-- As we don't use the context file searching, we need to initialize the kpse library. As the
+-- progname can be anything we will temporary switch to the context namespace if needed. Just
+-- adding the context paths to the path specification is somewhat faster.
+--
+-- Now, with lua 5.2 being used we might create a special ENV for this.
+
+-- kpse.set_program_name("luatex")
+
+-- One can define texio.reporter as alternative terminal/log writer. That's as far
+-- as I want to go with this.
+
+local ctxkpse = nil
+local verbose = true
+
+if not logs or not logs.report then
+ if not logs then
+ logs = { }
+ end
+ function logs.report(c,f,...)
+ local r = texio.reporter or texio.write_nl
+ if f then
+ r(c .. " : " .. string.format(f,...))
+ else
+ r("")
+ end
+ end
+end
+
+local function loadmodule(name,continue)
+ local foundname = kpse.find_file(name,"tex") or ""
+ if not foundname then
+ if not ctxkpse then
+ ctxkpse = kpse.new("luatex","context")
+ end
+ foundname = ctxkpse:find_file(name,"tex") or ""
+ end
+ if foundname == "" then
+ if not continue then
+ logs.report("system","unable to locate file '%s'",name)
+ os.exit()
+ end
+ else
+ if verbose then
+ logs.report("system","loading '%s'",foundname) -- no file.basename yet
+ end
+ dofile(foundname)
+ end
+end
+
+if non_generic_context.luatex_fonts.load_before then
+ loadmodule(non_generic_context.luatex_fonts.load_before,true)
+end
+
+if non_generic_context.luatex_fonts.skip_loading ~= true then
+
+ loadmodule('luatex-fonts-merged.lua',true)
+
+ if fonts then
+
+ if not fonts._merge_loaded_message_done_ then
+ texio.write_nl("log", "!")
+ texio.write_nl("log", "! I am using the merged version of 'luatex-fonts.lua' here. If")
+ texio.write_nl("log", "! you run into problems or experience unexpected behaviour, and")
+ texio.write_nl("log", "! if you have ConTeXt installed you can try to delete the file")
+ texio.write_nl("log", "! 'luatex-font-merged.lua' as I might then use the possibly")
+ texio.write_nl("log", "! updated libraries. The merged version is not supported as it")
+ texio.write_nl("log", "! is a frozen instance. Problems can be reported to the ConTeXt")
+ texio.write_nl("log", "! mailing list.")
+ texio.write_nl("log", "!")
+ end
+
+ fonts._merge_loaded_message_done_ = true
+
+ else
+
+ -- The following helpers are a bit overkill but I don't want to mess up
+ -- context code for the sake of general generality. Around version 1.0
+ -- there will be an official api defined.
+ --
+ -- So, I will strip these libraries and see what is really needed so that
+ -- we don't have this overhead in the generic modules. The next section
+ -- is only there for the packager, so stick to using luatex-fonts with
+ -- luatex-fonts-merged.lua and forget about the rest. The following list
+ -- might change without prior notice (for instance because we shuffled
+ -- code around).
+
+ loadmodule("l-lua.lua")
+ loadmodule("l-lpeg.lua")
+ loadmodule("l-function.lua")
+ loadmodule("l-string.lua")
+ loadmodule("l-table.lua")
+ loadmodule("l-io.lua")
+ loadmodule("l-file.lua")
+ loadmodule("l-boolean.lua")
+ loadmodule("l-math.lua")
+
+ -- A few slightly higher level support modules:
+
+ loadmodule("util-str.lua") -- future versions can ship without this one
+ loadmodule("util-fil.lua") -- future versions can ship without this one
+
+ -- The following modules contain code that is either not used at all
+ -- outside context or will fail when enabled due to lack of other
+ -- modules.
+
+ -- First we load a few helper modules. This is about the miminum needed
+ -- to let the font modules do their work. Don't depend on their functions
+ -- as we might strip them in future versions of this generic variant.
+
+ loadmodule('luatex-basics-gen.lua')
+ loadmodule('data-con.lua')
+
+ -- We do need some basic node support. The code in there is not for
+ -- general use as it might change.
+
+ loadmodule('luatex-basics-nod.lua')
+
+ -- We ship a resources needed for font handling (more might end up here).
+
+ loadmodule('luatex-basics-chr.lua')
+
+ -- Now come the font modules that deal with traditional tex fonts as well
+ -- as open type fonts.
+ --
+ -- The font database file (if used at all) must be put someplace visible
+ -- for kpse and is not shared with context. The mtx-fonts script can be
+ -- used to generate this file (using the --reload --force --simple option).
+
+ loadmodule('font-ini.lua')
+ loadmodule('luatex-fonts-mis.lua')
+ loadmodule('font-con.lua')
+ loadmodule('luatex-fonts-enc.lua')
+ loadmodule('font-cid.lua')
+ loadmodule('font-map.lua')
+
+ -- We use a bit simpler database because using the context one demands
+ -- loading more helper code and although it is more flexible (more ways
+ -- to resolve and so) it will never be uses in plain/latex anyway, so
+ -- let's stick to a simple approach.
+
+ loadmodule('luatex-fonts-syn.lua')
+
+ -- We need some helpers.
+
+ loadmodule('font-vfc.lua')
+
+ -- This is the bulk of opentype code.
+
+ loadmodule('font-otr.lua')
+ loadmodule('font-oti.lua')
+ loadmodule('font-ott.lua')
+ loadmodule('font-cff.lua')
+ loadmodule('font-ttf.lua')
+ loadmodule('font-dsp.lua')
+ loadmodule('font-oup.lua')
+ loadmodule('font-otl.lua')
+ loadmodule('font-oto.lua')
+ loadmodule('font-otj.lua')
+ loadmodule('font-ota.lua')
+ loadmodule('font-ots.lua')
+ loadmodule('font-osd.lua')
+ loadmodule('font-ocl.lua')
+ loadmodule('font-otc.lua')
+
+ -- The code for type one fonts.
+
+ loadmodule('font-onr.lua')
+ loadmodule('font-one.lua')
+ loadmodule('font-afk.lua')
+
+ -- And for traditional TeX fonts.
+
+ loadmodule('luatex-fonts-tfm.lua')
+
+ -- Some common code.
+
+ loadmodule('font-lua.lua')
+ loadmodule('font-def.lua')
+
+ -- We support xetex compatible specifiers (plain/latex only).
+
+ loadmodule('luatex-fonts-def.lua') -- was font-xtx.lua
+
+ -- Here come some additional features.
+
+ loadmodule('luatex-fonts-ext.lua')
+ loadmodule('font-imp-tex.lua')
+ loadmodule('font-imp-ligatures.lua')
+ loadmodule('font-imp-italics.lua')
+ loadmodule('font-imp-effects.lua')
+ loadmodule('luatex-fonts-lig.lua')
+
+ -- We need to plug into a callback and the following module implements the
+ -- handlers. Actual plugging in happens later.
+
+ loadmodule('luatex-fonts-gbn.lua')
+
+ end
+
+end
+
+if non_generic_context.luatex_fonts.load_after then
+ loadmodule(non_generic_context.luatex_fonts.load_after,true)
+end
+
+resolvers.loadmodule = loadmodule
+
+-- In order to deal with the fonts we need to initialize some callbacks. One can overload them later
+-- on if needed. First a bit of abstraction.
+
+generic_context.callback_ligaturing = false
+generic_context.callback_kerning = false
+generic_context.callback_pre_linebreak_filter = nodes.simple_font_handler
+generic_context.callback_hpack_filter = nodes.simple_font_handler
+generic_context.callback_define_font = fonts.definers.read
+
+-- The next ones can be done at a different moment if needed. You can create a generic_context namespace
+-- and set no_callbacks_yet to true, load this module, and enable the callbacks later. So, there is really
+-- *no* need to create a alternative for luatex-fonts.lua and luatex-fonts-merged.lua: just load this one
+-- and overload if needed.
+
+if not generic_context.no_callbacks_yet then
+
+ callback.register('ligaturing', generic_context.callback_ligaturing)
+ callback.register('kerning', generic_context.callback_kerning)
+ callback.register('pre_linebreak_filter', generic_context.callback_pre_linebreak_filter)
+ callback.register('hpack_filter', generic_context.callback_hpack_filter)
+ callback.register('define_font' , generic_context.callback_define_font)
+
+end
+
+-- We're done.
+
+logs.report("system","luatex-fonts.lua loaded in %0.3f seconds", os.gettimeofday()-starttime)
+
+generic_context.pop_namespaces(whatever)
diff --git a/macros/luatex/generic/luaotfload/fontloader-reference-load-order.tex b/macros/luatex/generic/luaotfload/fontloader-reference-load-order.tex
new file mode 100644
index 0000000000..7b457e9b4f
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-reference-load-order.tex
@@ -0,0 +1,140 @@
+%D \module
+%D [ file=luatex-fonts,
+%D version=2009.12.01,
+%D title=\LUATEX\ Support Macros,
+%D subtitle=Generic \OPENTYPE\ Font Handler,
+%D author=Hans Hagen,
+%D copyright={PRAGMA ADE \& \CONTEXT\ Development Team}]
+
+%D \subject{Welcome}
+%D
+%D This file is one of a set of basic functionality enhancements
+%D for \LUATEX\ derived from the \CONTEXT\ \MKIV\ code base. Please
+%D don't polute the \type {luatex-*} namespace with code not coming
+%D from the \CONTEXT\ development team as we may add more files.
+%D
+%D As this is an experimental setup, it might not always work out as
+%D expected. Around \LUATEX\ version 0.50 we expect the code to be
+%D more or less okay.
+%D
+%D This file implements a basic font system for a bare \LUATEX\
+%D system. By default \LUATEX\ only knows about the classic \TFM\
+%D fonts but it can read other font formats and pass them to \LUA.
+%D With some glue code one can then construct a suitable \TFM\
+%D representation that \LUATEX\ can work with. For more advanced font
+%D support a bit more code is needed that needs to be hooked
+%D into the callback mechanism.
+%D
+%D This file is currently rather simple: it just loads the \LUA\ file
+%D with the same name. An example of a \type {luatex.tex} file that is
+%D just plain \TEX:
+%D
+%D \starttyping
+%D \catcode`\{=1 % left brace is begin-group character
+%D \catcode`\}=2 % right brace is end-group character
+%D
+%D \input plain
+%D
+%D \everyjob\expandafter{\the\everyjob\input luatex-fonts\relax}
+%D
+%D \dump
+%D \stoptyping
+%D
+%D We could load the \LUA\ file in \type {\everyjob} but maybe some
+%D day we need more here.
+%D
+%D When defining a font you can use two prefixes. A \type {file:}
+%D prefix forced a file search, while a \type {name:} prefix will
+%D result in consulting the names database. Such a database can be
+%D generated with:
+%D
+%D \starttyping
+%D mtxrun --usekpse --script fonts --names
+%D \stoptyping
+%D
+%D This will generate a file \type {luatex-fonts-names.lua} that has
+%D to be placed in a location where it can be found by \KPSE. Beware:
+%D the \type {--kpseonly} flag is only used outside \CONTEXT\ and
+%D provides very limited functionality, just enough for this task.
+%D
+%D The code loaded here does not come out of thin air, but is mostly
+%D shared with \CONTEXT, however, in that macropackage we go beyond
+%D what is provided here. When you use the code packaged here you
+%D need to keep a few things in mind:
+%D
+%D \startitemize
+%D
+%D \item This subsystem will be extended, improved etc. in about the
+%D same pace as \CONTEXT\ \MKIV. However, because \CONTEXT\ provides a
+%D rather high level of integration not all features will be supported
+%D in the same quality. Use \CONTEXT\ if you want more goodies.
+%D
+%D \item There is no official \API\ yet, which means that using
+%D functions implemented here is at your own risk, in the sense that
+%D names and namespaces might change. There will be a minimal \API\
+%D defined once \LUATEX\ version 1.0 is out. Instead of patching the
+%D files it's better to overload functions if needed.
+%D
+%D \item The modules are not stripped too much, which makes it
+%D possible to benefit from improvements in the code that take place
+%D in the perspective of \CONTEXT\ development. They might be split a
+%D bit more in due time so the baseline might become smaller.
+%D
+%D \item The code is maintained and tested by the \CONTEXT\
+%D development team. As such it might be better suited for this macro
+%D package and integration in other systems might demand some
+%D additional wrapping. Problems can be reported to the team but as we
+%D use \CONTEXT\ \MKIV\ as baseline, you'd better check if the problem
+%D is a general \CONTEXT\ problem too.
+%D
+%D \item The more high level support for features that is provided in
+%D \CONTEXT\ is not part of the code loaded here as it makes no sense
+%D elsewhere. Some experimental features are not part of this code
+%D either but some might show up later.
+%D
+%D \item Math font support will be added but only in its basic form
+%D once that the Latin Modern and \TEX\ Gyre math fonts are
+%D available.
+%D
+%D \item At this moment the more nifty speed-ups are not enabled
+%D because they work in tandem with the alternative file handling
+%D that \CONTEXT\ uses. Maybe around \LUATEX\ 1.0 we will bring some
+%D speedup into this code too (if it pays off at all).
+%D
+%D \item The code defines a few global tables. If this code is used
+%D in a larger perspective then you can best make sure that no
+%D conflicts occur. The \CONTEXT\ package expects users to work in
+%D their own namespace (\type {userdata}, \type {thirddata}, \type
+%D {moduledata} or \type {document}. The team takes all freedom to
+%D use any table at the global level but will not use tables that are
+%D named after macro packages. Later the \CONTEXT\ might operate in
+%D a more controlled namespace but it has a low priority.
+%D
+%D \item There is some tracing code present but this is not enabled
+%D and not supported outside \CONTEXT\ either as it integrates quite
+%D tightly into \CONTEXT. In case of problems you can use \CONTEXT\
+%D for tracking down problems.
+%D
+%D \item Patching the code in distributions is dangerous as it might
+%D fix your problem but introduce new ones for \CONTEXT. So, best keep
+%D the original code as it is.
+%D
+%D \item Attributes are (automatically) taken from the range 127-255 so
+%D you'd best not use these yourself.
+%D
+%D \stopitemize
+%D
+%D If this all sounds a bit tricky, keep in mind that it makes no sense
+%D for us to maintain multiple code bases and we happen to use \CONTEXT.
+%D
+%D For more details about how the font subsystem works we refer to
+%D publications in \TEX\ related journals, the \CONTEXT\ documentation,
+%D and the \CONTEXT\ wiki.
+
+\directlua {
+ if not fonts then
+ dofile(kpse.find_file("luatex-fonts.lua","tex"))
+ end
+}
+
+\endinput
diff --git a/macros/luatex/generic/luaotfload/fontloader-reference.lua b/macros/luatex/generic/luaotfload/fontloader-reference.lua
new file mode 100644
index 0000000000..3120f45135
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-reference.lua
@@ -0,0 +1,38728 @@
+-- merged file : c:/data/develop/context/sources/luatex-fonts-merged.lua
+-- parent file : c:/data/develop/context/sources/luatex-fonts.lua
+-- merge date : 08/11/19 20:03:46
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-lua']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+LUAMAJORVERSION,LUAMINORVERSION=string.match(_VERSION,"^[^%d]+(%d+)%.(%d+).*$")
+LUAMAJORVERSION=tonumber(LUAMAJORVERSION) or 5
+LUAMINORVERSION=tonumber(LUAMINORVERSION) or 1
+LUAVERSION=LUAMAJORVERSION+LUAMINORVERSION/10
+if LUAVERSION<5.2 and jit then
+ MINORVERSION=2
+ LUAVERSION=5.2
+end
+if not lpeg then
+ lpeg=require("lpeg")
+end
+if loadstring then
+ local loadnormal=load
+ function load(first,...)
+ if type(first)=="string" then
+ return loadstring(first,...)
+ else
+ return loadnormal(first,...)
+ end
+ end
+else
+ loadstring=load
+end
+if not ipairs then
+ local function iterate(a,i)
+ i=i+1
+ local v=a[i]
+ if v~=nil then
+ return i,v
+ end
+ end
+ function ipairs(a)
+ return iterate,a,0
+ end
+end
+if not pairs then
+ function pairs(t)
+ return next,t
+ end
+end
+if not table.unpack then
+ table.unpack=_G.unpack
+elseif not unpack then
+ _G.unpack=table.unpack
+end
+if not package.loaders then
+ package.loaders=package.searchers
+end
+local print,select,tostring=print,select,tostring
+local inspectors={}
+function setinspector(kind,inspector)
+ inspectors[kind]=inspector
+end
+function inspect(...)
+ for s=1,select("#",...) do
+ local value=select(s,...)
+ if value==nil then
+ print("nil")
+ else
+ local done=false
+ local kind=type(value)
+ local inspector=inspectors[kind]
+ if inspector then
+ done=inspector(value)
+ if done then
+ break
+ end
+ end
+ for kind,inspector in next,inspectors do
+ done=inspector(value)
+ if done then
+ break
+ end
+ end
+ if not done then
+ print(tostring(value))
+ end
+ end
+ end
+end
+local dummy=function() end
+function optionalrequire(...)
+ local ok,result=xpcall(require,dummy,...)
+ if ok then
+ return result
+ end
+end
+if lua then
+ lua.mask=load([[τεχ = 1]]) and "utf" or "ascii"
+end
+local flush=io.flush
+if flush then
+ local execute=os.execute if execute then function os.execute(...) flush() return execute(...) end end
+ local exec=os.exec if exec then function os.exec (...) flush() return exec (...) end end
+ local spawn=os.spawn if spawn then function os.spawn (...) flush() return spawn (...) end end
+ local popen=io.popen if popen then function io.popen (...) flush() return popen (...) end end
+end
+FFISUPPORTED=type(ffi)=="table" and ffi.os~="" and ffi.arch~="" and ffi.load
+if not FFISUPPORTED then
+ local okay;okay,ffi=pcall(require,"ffi")
+ FFISUPPORTED=type(ffi)=="table" and ffi.os~="" and ffi.arch~="" and ffi.load
+end
+if not FFISUPPORTED then
+ ffi=nil
+elseif not ffi.number then
+ ffi.number=tonumber
+end
+if LUAVERSION>5.3 then
+end
+if status and os.setenv then
+ os.setenv("engine",string.lower(status.luatex_engine or "unknown"))
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-lpeg']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+lpeg=require("lpeg")
+local lpeg=lpeg
+if not lpeg.print then function lpeg.print(...) print(lpeg.pcode(...)) end end
+local type,next,tostring=type,next,tostring
+local byte,char,gmatch,format=string.byte,string.char,string.gmatch,string.format
+local floor=math.floor
+local P,R,S,V,Ct,C,Cs,Cc,Cp,Cmt=lpeg.P,lpeg.R,lpeg.S,lpeg.V,lpeg.Ct,lpeg.C,lpeg.Cs,lpeg.Cc,lpeg.Cp,lpeg.Cmt
+local lpegtype,lpegmatch,lpegprint=lpeg.type,lpeg.match,lpeg.print
+if setinspector then
+ setinspector("lpeg",function(v) if lpegtype(v) then lpegprint(v) return true end end)
+end
+lpeg.patterns=lpeg.patterns or {}
+local patterns=lpeg.patterns
+local anything=P(1)
+local endofstring=P(-1)
+local alwaysmatched=P(true)
+patterns.anything=anything
+patterns.endofstring=endofstring
+patterns.beginofstring=alwaysmatched
+patterns.alwaysmatched=alwaysmatched
+local sign=S('+-')
+local zero=P('0')
+local digit=R('09')
+local digits=digit^1
+local octdigit=R("07")
+local octdigits=octdigit^1
+local lowercase=R("az")
+local uppercase=R("AZ")
+local underscore=P("_")
+local hexdigit=digit+lowercase+uppercase
+local hexdigits=hexdigit^1
+local cr,lf,crlf=P("\r"),P("\n"),P("\r\n")
+local newline=P("\r")*(P("\n")+P(true))+P("\n")
+local escaped=P("\\")*anything
+local squote=P("'")
+local dquote=P('"')
+local space=P(" ")
+local period=P(".")
+local comma=P(",")
+local utfbom_32_be=P('\000\000\254\255')
+local utfbom_32_le=P('\255\254\000\000')
+local utfbom_16_be=P('\254\255')
+local utfbom_16_le=P('\255\254')
+local utfbom_8=P('\239\187\191')
+local utfbom=utfbom_32_be+utfbom_32_le+utfbom_16_be+utfbom_16_le+utfbom_8
+local utftype=utfbom_32_be*Cc("utf-32-be")+utfbom_32_le*Cc("utf-32-le")+utfbom_16_be*Cc("utf-16-be")+utfbom_16_le*Cc("utf-16-le")+utfbom_8*Cc("utf-8")+alwaysmatched*Cc("utf-8")
+local utfstricttype=utfbom_32_be*Cc("utf-32-be")+utfbom_32_le*Cc("utf-32-le")+utfbom_16_be*Cc("utf-16-be")+utfbom_16_le*Cc("utf-16-le")+utfbom_8*Cc("utf-8")
+local utfoffset=utfbom_32_be*Cc(4)+utfbom_32_le*Cc(4)+utfbom_16_be*Cc(2)+utfbom_16_le*Cc(2)+utfbom_8*Cc(3)+Cc(0)
+local utf8next=R("\128\191")
+patterns.utfbom_32_be=utfbom_32_be
+patterns.utfbom_32_le=utfbom_32_le
+patterns.utfbom_16_be=utfbom_16_be
+patterns.utfbom_16_le=utfbom_16_le
+patterns.utfbom_8=utfbom_8
+patterns.utf_16_be_nl=P("\000\r\000\n")+P("\000\r")+P("\000\n")
+patterns.utf_16_le_nl=P("\r\000\n\000")+P("\r\000")+P("\n\000")
+patterns.utf_32_be_nl=P("\000\000\000\r\000\000\000\n")+P("\000\000\000\r")+P("\000\000\000\n")
+patterns.utf_32_le_nl=P("\r\000\000\000\n\000\000\000")+P("\r\000\000\000")+P("\n\000\000\000")
+patterns.utf8one=R("\000\127")
+patterns.utf8two=R("\194\223")*utf8next
+patterns.utf8three=R("\224\239")*utf8next*utf8next
+patterns.utf8four=R("\240\244")*utf8next*utf8next*utf8next
+patterns.utfbom=utfbom
+patterns.utftype=utftype
+patterns.utfstricttype=utfstricttype
+patterns.utfoffset=utfoffset
+local utf8char=patterns.utf8one+patterns.utf8two+patterns.utf8three+patterns.utf8four
+local validutf8char=utf8char^0*endofstring*Cc(true)+Cc(false)
+local utf8character=P(1)*R("\128\191")^0
+patterns.utf8=utf8char
+patterns.utf8char=utf8char
+patterns.utf8character=utf8character
+patterns.validutf8=validutf8char
+patterns.validutf8char=validutf8char
+local eol=S("\n\r")
+local spacer=S(" \t\f\v")
+local whitespace=eol+spacer
+local nonspacer=1-spacer
+local nonwhitespace=1-whitespace
+patterns.eol=eol
+patterns.spacer=spacer
+patterns.whitespace=whitespace
+patterns.nonspacer=nonspacer
+patterns.nonwhitespace=nonwhitespace
+local stripper=spacer^0*C((spacer^0*nonspacer^1)^0)
+local fullstripper=whitespace^0*C((whitespace^0*nonwhitespace^1)^0)
+local collapser=Cs(spacer^0/""*nonspacer^0*((spacer^0/" "*nonspacer^1)^0))
+local nospacer=Cs((whitespace^1/""+nonwhitespace^1)^0)
+local b_collapser=Cs(whitespace^0/""*(nonwhitespace^1+whitespace^1/" ")^0)
+local e_collapser=Cs((whitespace^1*endofstring/""+nonwhitespace^1+whitespace^1/" ")^0)
+local m_collapser=Cs((nonwhitespace^1+whitespace^1/" ")^0)
+local b_stripper=Cs(spacer^0/""*(nonspacer^1+spacer^1/" ")^0)
+local e_stripper=Cs((spacer^1*endofstring/""+nonspacer^1+spacer^1/" ")^0)
+local m_stripper=Cs((nonspacer^1+spacer^1/" ")^0)
+patterns.stripper=stripper
+patterns.fullstripper=fullstripper
+patterns.collapser=collapser
+patterns.nospacer=nospacer
+patterns.b_collapser=b_collapser
+patterns.m_collapser=m_collapser
+patterns.e_collapser=e_collapser
+patterns.b_stripper=b_stripper
+patterns.m_stripper=m_stripper
+patterns.e_stripper=e_stripper
+patterns.lowercase=lowercase
+patterns.uppercase=uppercase
+patterns.letter=patterns.lowercase+patterns.uppercase
+patterns.space=space
+patterns.tab=P("\t")
+patterns.spaceortab=patterns.space+patterns.tab
+patterns.newline=newline
+patterns.emptyline=newline^1
+patterns.equal=P("=")
+patterns.comma=comma
+patterns.commaspacer=comma*spacer^0
+patterns.period=period
+patterns.colon=P(":")
+patterns.semicolon=P(";")
+patterns.underscore=underscore
+patterns.escaped=escaped
+patterns.squote=squote
+patterns.dquote=dquote
+patterns.nosquote=(escaped+(1-squote))^0
+patterns.nodquote=(escaped+(1-dquote))^0
+patterns.unsingle=(squote/"")*patterns.nosquote*(squote/"")
+patterns.undouble=(dquote/"")*patterns.nodquote*(dquote/"")
+patterns.unquoted=patterns.undouble+patterns.unsingle
+patterns.unspacer=((patterns.spacer^1)/"")^0
+patterns.singlequoted=squote*patterns.nosquote*squote
+patterns.doublequoted=dquote*patterns.nodquote*dquote
+patterns.quoted=patterns.doublequoted+patterns.singlequoted
+patterns.digit=digit
+patterns.digits=digits
+patterns.octdigit=octdigit
+patterns.octdigits=octdigits
+patterns.hexdigit=hexdigit
+patterns.hexdigits=hexdigits
+patterns.sign=sign
+patterns.cardinal=digits
+patterns.integer=sign^-1*digits
+patterns.unsigned=digit^0*period*digits
+patterns.float=sign^-1*patterns.unsigned
+patterns.cunsigned=digit^0*comma*digits
+patterns.cpunsigned=digit^0*(period+comma)*digits
+patterns.cfloat=sign^-1*patterns.cunsigned
+patterns.cpfloat=sign^-1*patterns.cpunsigned
+patterns.number=patterns.float+patterns.integer
+patterns.cnumber=patterns.cfloat+patterns.integer
+patterns.cpnumber=patterns.cpfloat+patterns.integer
+patterns.oct=zero*octdigits
+patterns.octal=patterns.oct
+patterns.HEX=zero*P("X")*(digit+uppercase)^1
+patterns.hex=zero*P("x")*(digit+lowercase)^1
+patterns.hexadecimal=zero*S("xX")*hexdigits
+patterns.hexafloat=sign^-1*zero*S("xX")*(hexdigit^0*period*hexdigits+hexdigits*period*hexdigit^0+hexdigits)*(S("pP")*sign^-1*hexdigits)^-1
+patterns.decafloat=sign^-1*(digit^0*period*digits+digits*period*digit^0+digits)*S("eE")*sign^-1*digits
+patterns.propername=(uppercase+lowercase+underscore)*(uppercase+lowercase+underscore+digit)^0*endofstring
+patterns.somecontent=(anything-newline-space)^1
+patterns.beginline=#(1-newline)
+patterns.longtostring=Cs(whitespace^0/""*((patterns.quoted+nonwhitespace^1+whitespace^1/""*(endofstring+Cc(" ")))^0))
+function anywhere(pattern)
+ return (1-P(pattern))^0*P(pattern)
+end
+lpeg.anywhere=anywhere
+function lpeg.instringchecker(p)
+ p=anywhere(p)
+ return function(str)
+ return lpegmatch(p,str) and true or false
+ end
+end
+function lpeg.splitter(pattern,action)
+ if action then
+ return (((1-P(pattern))^1)/action+1)^0
+ else
+ return (Cs((1-P(pattern))^1)+1)^0
+ end
+end
+function lpeg.tsplitter(pattern,action)
+ if action then
+ return Ct((((1-P(pattern))^1)/action+1)^0)
+ else
+ return Ct((Cs((1-P(pattern))^1)+1)^0)
+ end
+end
+local splitters_s,splitters_m,splitters_t={},{},{}
+local function splitat(separator,single)
+ local splitter=(single and splitters_s[separator]) or splitters_m[separator]
+ if not splitter then
+ separator=P(separator)
+ local other=C((1-separator)^0)
+ if single then
+ local any=anything
+ splitter=other*(separator*C(any^0)+"")
+ splitters_s[separator]=splitter
+ else
+ splitter=other*(separator*other)^0
+ splitters_m[separator]=splitter
+ end
+ end
+ return splitter
+end
+local function tsplitat(separator)
+ local splitter=splitters_t[separator]
+ if not splitter then
+ splitter=Ct(splitat(separator))
+ splitters_t[separator]=splitter
+ end
+ return splitter
+end
+lpeg.splitat=splitat
+lpeg.tsplitat=tsplitat
+function string.splitup(str,separator)
+ if not separator then
+ separator=","
+ end
+ return lpegmatch(splitters_m[separator] or splitat(separator),str)
+end
+local cache={}
+function lpeg.split(separator,str)
+ local c=cache[separator]
+ if not c then
+ c=tsplitat(separator)
+ cache[separator]=c
+ end
+ return lpegmatch(c,str)
+end
+function string.split(str,separator)
+ if separator then
+ local c=cache[separator]
+ if not c then
+ c=tsplitat(separator)
+ cache[separator]=c
+ end
+ return lpegmatch(c,str)
+ else
+ return { str }
+ end
+end
+local spacing=patterns.spacer^0*newline
+local empty=spacing*Cc("")
+local nonempty=Cs((1-spacing)^1)*spacing^-1
+local content=(empty+nonempty)^1
+patterns.textline=content
+local linesplitter=tsplitat(newline)
+patterns.linesplitter=linesplitter
+function string.splitlines(str)
+ return lpegmatch(linesplitter,str)
+end
+local cache={}
+function lpeg.checkedsplit(separator,str)
+ local c=cache[separator]
+ if not c then
+ separator=P(separator)
+ local other=C((1-separator)^1)
+ c=Ct(separator^0*other*(separator^1*other)^0)
+ cache[separator]=c
+ end
+ return lpegmatch(c,str)
+end
+function string.checkedsplit(str,separator)
+ local c=cache[separator]
+ if not c then
+ separator=P(separator)
+ local other=C((1-separator)^1)
+ c=Ct(separator^0*other*(separator^1*other)^0)
+ cache[separator]=c
+ end
+ return lpegmatch(c,str)
+end
+local function f2(s) local c1,c2=byte(s,1,2) return c1*64+c2-12416 end
+local function f3(s) local c1,c2,c3=byte(s,1,3) return (c1*64+c2)*64+c3-925824 end
+local function f4(s) local c1,c2,c3,c4=byte(s,1,4) return ((c1*64+c2)*64+c3)*64+c4-63447168 end
+local utf8byte=patterns.utf8one/byte+patterns.utf8two/f2+patterns.utf8three/f3+patterns.utf8four/f4
+patterns.utf8byte=utf8byte
+local cache={}
+function lpeg.stripper(str)
+ if type(str)=="string" then
+ local s=cache[str]
+ if not s then
+ s=Cs(((S(str)^1)/""+1)^0)
+ cache[str]=s
+ end
+ return s
+ else
+ return Cs(((str^1)/""+1)^0)
+ end
+end
+local cache={}
+function lpeg.keeper(str)
+ if type(str)=="string" then
+ local s=cache[str]
+ if not s then
+ s=Cs((((1-S(str))^1)/""+1)^0)
+ cache[str]=s
+ end
+ return s
+ else
+ return Cs((((1-str)^1)/""+1)^0)
+ end
+end
+function lpeg.frontstripper(str)
+ return (P(str)+P(true))*Cs(anything^0)
+end
+function lpeg.endstripper(str)
+ return Cs((1-P(str)*endofstring)^0)
+end
+function lpeg.replacer(one,two,makefunction,isutf)
+ local pattern
+ local u=isutf and utf8char or 1
+ if type(one)=="table" then
+ local no=#one
+ local p=P(false)
+ if no==0 then
+ for k,v in next,one do
+ p=p+P(k)/v
+ end
+ pattern=Cs((p+u)^0)
+ elseif no==1 then
+ local o=one[1]
+ one,two=P(o[1]),o[2]
+ pattern=Cs((one/two+u)^0)
+ else
+ for i=1,no do
+ local o=one[i]
+ p=p+P(o[1])/o[2]
+ end
+ pattern=Cs((p+u)^0)
+ end
+ else
+ pattern=Cs((P(one)/(two or "")+u)^0)
+ end
+ if makefunction then
+ return function(str)
+ return lpegmatch(pattern,str)
+ end
+ else
+ return pattern
+ end
+end
+function lpeg.finder(lst,makefunction,isutf)
+ local pattern
+ if type(lst)=="table" then
+ pattern=P(false)
+ if #lst==0 then
+ for k,v in next,lst do
+ pattern=pattern+P(k)
+ end
+ else
+ for i=1,#lst do
+ pattern=pattern+P(lst[i])
+ end
+ end
+ else
+ pattern=P(lst)
+ end
+ if isutf then
+ pattern=((utf8char or 1)-pattern)^0*pattern
+ else
+ pattern=(1-pattern)^0*pattern
+ end
+ if makefunction then
+ return function(str)
+ return lpegmatch(pattern,str)
+ end
+ else
+ return pattern
+ end
+end
+local splitters_f,splitters_s={},{}
+function lpeg.firstofsplit(separator)
+ local splitter=splitters_f[separator]
+ if not splitter then
+ local pattern=P(separator)
+ splitter=C((1-pattern)^0)
+ splitters_f[separator]=splitter
+ end
+ return splitter
+end
+function lpeg.secondofsplit(separator)
+ local splitter=splitters_s[separator]
+ if not splitter then
+ local pattern=P(separator)
+ splitter=(1-pattern)^0*pattern*C(anything^0)
+ splitters_s[separator]=splitter
+ end
+ return splitter
+end
+local splitters_s,splitters_p={},{}
+function lpeg.beforesuffix(separator)
+ local splitter=splitters_s[separator]
+ if not splitter then
+ local pattern=P(separator)
+ splitter=C((1-pattern)^0)*pattern*endofstring
+ splitters_s[separator]=splitter
+ end
+ return splitter
+end
+function lpeg.afterprefix(separator)
+ local splitter=splitters_p[separator]
+ if not splitter then
+ local pattern=P(separator)
+ splitter=pattern*C(anything^0)
+ splitters_p[separator]=splitter
+ end
+ return splitter
+end
+function lpeg.balancer(left,right)
+ left,right=P(left),P(right)
+ return P { left*((1-left-right)+V(1))^0*right }
+end
+function lpeg.counter(pattern,action)
+ local n=0
+ local pattern=(P(pattern)/function() n=n+1 end+anything)^0
+ if action then
+ return function(str) n=0;lpegmatch(pattern,str);action(n) end
+ else
+ return function(str) n=0;lpegmatch(pattern,str);return n end
+ end
+end
+function lpeg.is_lpeg(p)
+ return p and lpegtype(p)=="pattern"
+end
+function lpeg.oneof(list,...)
+ if type(list)~="table" then
+ list={ list,... }
+ end
+ local p=P(list[1])
+ for l=2,#list do
+ p=p+P(list[l])
+ end
+ return p
+end
+local sort=table.sort
+local function copyindexed(old)
+ local new={}
+ for i=1,#old do
+ new[i]=old
+ end
+ return new
+end
+local function sortedkeys(tab)
+ local keys,s={},0
+ for key,_ in next,tab do
+ s=s+1
+ keys[s]=key
+ end
+ sort(keys)
+ return keys
+end
+function lpeg.append(list,pp,delayed,checked)
+ local p=pp
+ if #list>0 then
+ local keys=copyindexed(list)
+ sort(keys)
+ for i=#keys,1,-1 do
+ local k=keys[i]
+ if p then
+ p=P(k)+p
+ else
+ p=P(k)
+ end
+ end
+ elseif delayed then
+ local keys=sortedkeys(list)
+ if p then
+ for i=1,#keys,1 do
+ local k=keys[i]
+ local v=list[k]
+ p=P(k)/list+p
+ end
+ else
+ for i=1,#keys do
+ local k=keys[i]
+ local v=list[k]
+ if p then
+ p=P(k)+p
+ else
+ p=P(k)
+ end
+ end
+ if p then
+ p=p/list
+ end
+ end
+ elseif checked then
+ local keys=sortedkeys(list)
+ for i=1,#keys do
+ local k=keys[i]
+ local v=list[k]
+ if p then
+ if k==v then
+ p=P(k)+p
+ else
+ p=P(k)/v+p
+ end
+ else
+ if k==v then
+ p=P(k)
+ else
+ p=P(k)/v
+ end
+ end
+ end
+ else
+ local keys=sortedkeys(list)
+ for i=1,#keys do
+ local k=keys[i]
+ local v=list[k]
+ if p then
+ p=P(k)/v+p
+ else
+ p=P(k)/v
+ end
+ end
+ end
+ return p
+end
+local p_false=P(false)
+local p_true=P(true)
+local lower=utf and utf.lower or string.lower
+local upper=utf and utf.upper or string.upper
+function lpeg.setutfcasers(l,u)
+ lower=l or lower
+ upper=u or upper
+end
+local function make1(t,rest)
+ local p=p_false
+ local keys=sortedkeys(t)
+ for i=1,#keys do
+ local k=keys[i]
+ if k~="" then
+ local v=t[k]
+ if v==true then
+ p=p+P(k)*p_true
+ elseif v==false then
+ else
+ p=p+P(k)*make1(v,v[""])
+ end
+ end
+ end
+ if rest then
+ p=p+p_true
+ end
+ return p
+end
+local function make2(t,rest)
+ local p=p_false
+ local keys=sortedkeys(t)
+ for i=1,#keys do
+ local k=keys[i]
+ if k~="" then
+ local v=t[k]
+ if v==true then
+ p=p+(P(lower(k))+P(upper(k)))*p_true
+ elseif v==false then
+ else
+ p=p+(P(lower(k))+P(upper(k)))*make2(v,v[""])
+ end
+ end
+ end
+ if rest then
+ p=p+p_true
+ end
+ return p
+end
+local function utfchartabletopattern(list,insensitive)
+ local tree={}
+ local n=#list
+ if n==0 then
+ for s in next,list do
+ local t=tree
+ local p,pk
+ for c in gmatch(s,".") do
+ if t==true then
+ t={ [c]=true,[""]=true }
+ p[pk]=t
+ p=t
+ t=false
+ elseif t==false then
+ t={ [c]=false }
+ p[pk]=t
+ p=t
+ t=false
+ else
+ local tc=t[c]
+ if not tc then
+ tc=false
+ t[c]=false
+ end
+ p=t
+ t=tc
+ end
+ pk=c
+ end
+ if t==false then
+ p[pk]=true
+ elseif t==true then
+ else
+ t[""]=true
+ end
+ end
+ else
+ for i=1,n do
+ local s=list[i]
+ local t=tree
+ local p,pk
+ for c in gmatch(s,".") do
+ if t==true then
+ t={ [c]=true,[""]=true }
+ p[pk]=t
+ p=t
+ t=false
+ elseif t==false then
+ t={ [c]=false }
+ p[pk]=t
+ p=t
+ t=false
+ else
+ local tc=t[c]
+ if not tc then
+ tc=false
+ t[c]=false
+ end
+ p=t
+ t=tc
+ end
+ pk=c
+ end
+ if t==false then
+ p[pk]=true
+ elseif t==true then
+ else
+ t[""]=true
+ end
+ end
+ end
+ return (insensitive and make2 or make1)(tree)
+end
+lpeg.utfchartabletopattern=utfchartabletopattern
+function lpeg.utfreplacer(list,insensitive)
+ local pattern=Cs((utfchartabletopattern(list,insensitive)/list+utf8character)^0)
+ return function(str)
+ return lpegmatch(pattern,str) or str
+ end
+end
+patterns.containseol=lpeg.finder(eol)
+local function nextstep(n,step,result)
+ local m=n%step
+ local d=floor(n/step)
+ if d>0 then
+ local v=V(tostring(step))
+ local s=result.start
+ for i=1,d do
+ if s then
+ s=v*s
+ else
+ s=v
+ end
+ end
+ result.start=s
+ end
+ if step>1 and result.start then
+ local v=V(tostring(step/2))
+ result[tostring(step)]=v*v
+ end
+ if step>0 then
+ return nextstep(m,step/2,result)
+ else
+ return result
+ end
+end
+function lpeg.times(pattern,n)
+ return P(nextstep(n,2^16,{ "start",["1"]=pattern }))
+end
+do
+ local trailingzeros=zero^0*-digit
+ local stripper=Cs((
+ digits*(
+ period*trailingzeros/""+period*(digit-trailingzeros)^1*(trailingzeros/"")
+ )+1
+ )^0)
+ lpeg.patterns.stripzeros=stripper
+ local nonzero=digit-zero
+ local trailingzeros=zero^1*endofstring
+ local stripper=Cs((1-period)^0*(
+ period*trailingzeros/""+period*(nonzero^1+(trailingzeros/"")+zero^1)^0+endofstring
+ ))
+ lpeg.patterns.stripzero=stripper
+end
+local byte_to_HEX={}
+local byte_to_hex={}
+local byte_to_dec={}
+local hex_to_byte={}
+for i=0,255 do
+ local H=format("%02X",i)
+ local h=format("%02x",i)
+ local d=format("%03i",i)
+ local c=char(i)
+ byte_to_HEX[c]=H
+ byte_to_hex[c]=h
+ byte_to_dec[c]=d
+ hex_to_byte[h]=c
+ hex_to_byte[H]=c
+end
+local hextobyte=P(2)/hex_to_byte
+local bytetoHEX=P(1)/byte_to_HEX
+local bytetohex=P(1)/byte_to_hex
+local bytetodec=P(1)/byte_to_dec
+local hextobytes=Cs(hextobyte^0)
+local bytestoHEX=Cs(bytetoHEX^0)
+local bytestohex=Cs(bytetohex^0)
+local bytestodec=Cs(bytetodec^0)
+patterns.hextobyte=hextobyte
+patterns.bytetoHEX=bytetoHEX
+patterns.bytetohex=bytetohex
+patterns.bytetodec=bytetodec
+patterns.hextobytes=hextobytes
+patterns.bytestoHEX=bytestoHEX
+patterns.bytestohex=bytestohex
+patterns.bytestodec=bytestodec
+function string.toHEX(s)
+ if not s or s=="" then
+ return s
+ else
+ return lpegmatch(bytestoHEX,s)
+ end
+end
+function string.tohex(s)
+ if not s or s=="" then
+ return s
+ else
+ return lpegmatch(bytestohex,s)
+ end
+end
+function string.todec(s)
+ if not s or s=="" then
+ return s
+ else
+ return lpegmatch(bytestodec,s)
+ end
+end
+function string.tobytes(s)
+ if not s or s=="" then
+ return s
+ else
+ return lpegmatch(hextobytes,s)
+ end
+end
+local patterns={}
+local function containsws(what)
+ local p=patterns[what]
+ if not p then
+ local p1=P(what)*(whitespace+endofstring)*Cc(true)
+ local p2=whitespace*P(p1)
+ p=P(p1)+P(1-p2)^0*p2+Cc(false)
+ patterns[what]=p
+ end
+ return p
+end
+lpeg.containsws=containsws
+function string.containsws(str,what)
+ return lpegmatch(patterns[what] or containsws(what),str)
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-functions']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+functions=functions or {}
+function functions.dummy() end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-string']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local string=string
+local sub,gmatch,format,char,byte,rep,lower=string.sub,string.gmatch,string.format,string.char,string.byte,string.rep,string.lower
+local lpegmatch,patterns=lpeg.match,lpeg.patterns
+local P,S,C,Ct,Cc,Cs=lpeg.P,lpeg.S,lpeg.C,lpeg.Ct,lpeg.Cc,lpeg.Cs
+local unquoted=patterns.squote*C(patterns.nosquote)*patterns.squote+patterns.dquote*C(patterns.nodquote)*patterns.dquote
+function string.unquoted(str)
+ return lpegmatch(unquoted,str) or str
+end
+function string.quoted(str)
+ return format("%q",str)
+end
+function string.count(str,pattern)
+ local n=0
+ for _ in gmatch(str,pattern) do
+ n=n+1
+ end
+ return n
+end
+function string.limit(str,n,sentinel)
+ if #str>n then
+ sentinel=sentinel or "..."
+ return sub(str,1,(n-#sentinel))..sentinel
+ else
+ return str
+ end
+end
+local stripper=patterns.stripper
+local fullstripper=patterns.fullstripper
+local collapser=patterns.collapser
+local nospacer=patterns.nospacer
+local longtostring=patterns.longtostring
+function string.strip(str)
+ return str and lpegmatch(stripper,str) or ""
+end
+function string.fullstrip(str)
+ return str and lpegmatch(fullstripper,str) or ""
+end
+function string.collapsespaces(str)
+ return str and lpegmatch(collapser,str) or ""
+end
+function string.nospaces(str)
+ return str and lpegmatch(nospacer,str) or ""
+end
+function string.longtostring(str)
+ return str and lpegmatch(longtostring,str) or ""
+end
+local pattern=P(" ")^0*P(-1)
+function string.is_empty(str)
+ if not str or str=="" then
+ return true
+ else
+ return lpegmatch(pattern,str) and true or false
+ end
+end
+local anything=patterns.anything
+local moreescapes=Cc("%")*S(".-+%?()[]*$^{}")
+local allescapes=Cc("%")*S(".-+%?()[]*")
+local someescapes=Cc("%")*S(".-+%()[]")
+local matchescapes=Cc(".")*S("*?")
+local pattern_m=Cs ((moreescapes+anything )^0 )
+local pattern_a=Cs ((allescapes+anything )^0 )
+local pattern_b=Cs ((someescapes+matchescapes+anything )^0 )
+local pattern_c=Cs (Cc("^")*(someescapes+matchescapes+anything )^0*Cc("$") )
+function string.escapedpattern(str,simple)
+ return lpegmatch(simple and pattern_b or pattern_a,str)
+end
+function string.topattern(str,lowercase,strict)
+ if str=="" or type(str)~="string" then
+ return ".*"
+ elseif strict=="all" then
+ str=lpegmatch(pattern_m,str)
+ elseif strict then
+ str=lpegmatch(pattern_c,str)
+ else
+ str=lpegmatch(pattern_b,str)
+ end
+ if lowercase then
+ return lower(str)
+ else
+ return str
+ end
+end
+function string.valid(str,default)
+ return (type(str)=="string" and str~="" and str) or default or nil
+end
+string.itself=function(s) return s end
+local pattern_c=Ct(C(1)^0)
+local pattern_b=Ct((C(1)/byte)^0)
+function string.totable(str,bytes)
+ return lpegmatch(bytes and pattern_b or pattern_c,str)
+end
+local replacer=lpeg.replacer("@","%%")
+function string.tformat(fmt,...)
+ return format(lpegmatch(replacer,fmt),...)
+end
+string.quote=string.quoted
+string.unquote=string.unquoted
+if not string.bytetable then
+ local limit=5000
+ function string.bytetable(str)
+ local n=#str
+ if n>limit then
+ local t={ byte(str,1,limit) }
+ for i=limit+1,n do
+ t[i]=byte(str,i)
+ end
+ return t
+ else
+ return { byte(str,1,n) }
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-table']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local type,next,tostring,tonumber,select=type,next,tostring,tonumber,select
+local table,string=table,string
+local concat,sort=table.concat,table.sort
+local format,lower,dump=string.format,string.lower,string.dump
+local getmetatable,setmetatable=getmetatable,setmetatable
+local lpegmatch,patterns=lpeg.match,lpeg.patterns
+local floor=math.floor
+local stripper=patterns.stripper
+function table.getn(t)
+ return t and #t
+end
+function table.strip(tab)
+ local lst={}
+ local l=0
+ for i=1,#tab do
+ local s=lpegmatch(stripper,tab[i]) or ""
+ if s=="" then
+ else
+ l=l+1
+ lst[l]=s
+ end
+ end
+ return lst
+end
+function table.keys(t)
+ if t then
+ local keys={}
+ local k=0
+ for key in next,t do
+ k=k+1
+ keys[k]=key
+ end
+ return keys
+ else
+ return {}
+ end
+end
+local function compare(a,b)
+ local ta=type(a)
+ if ta=="number" then
+ local tb=type(b)
+ if ta==tb then
+ return a<b
+ elseif tb=="string" then
+ return tostring(a)<b
+ end
+ elseif ta=="string" then
+ local tb=type(b)
+ if ta==tb then
+ return a<b
+ else
+ return a<tostring(b)
+ end
+ end
+ return tostring(a)<tostring(b)
+end
+local function sortedkeys(tab)
+ if tab then
+ local srt={}
+ local category=0
+ local s=0
+ for key in next,tab do
+ s=s+1
+ srt[s]=key
+ if category~=3 then
+ local tkey=type(key)
+ if category==1 then
+ if tkey~="string" then
+ category=3
+ end
+ elseif category==2 then
+ if tkey~="number" then
+ category=3
+ end
+ else
+ if tkey=="string" then
+ category=1
+ elseif tkey=="number" then
+ category=2
+ else
+ category=3
+ end
+ end
+ end
+ end
+ if s<2 then
+ elseif category==3 then
+ sort(srt,compare)
+ else
+ sort(srt)
+ end
+ return srt
+ else
+ return {}
+ end
+end
+local function sortedhashonly(tab)
+ if tab then
+ local srt={}
+ local s=0
+ for key in next,tab do
+ if type(key)=="string" then
+ s=s+1
+ srt[s]=key
+ end
+ end
+ if s>1 then
+ sort(srt)
+ end
+ return srt
+ else
+ return {}
+ end
+end
+local function sortedindexonly(tab)
+ if tab then
+ local srt={}
+ local s=0
+ for key in next,tab do
+ if type(key)=="number" then
+ s=s+1
+ srt[s]=key
+ end
+ end
+ if s>1 then
+ sort(srt)
+ end
+ return srt
+ else
+ return {}
+ end
+end
+local function sortedhashkeys(tab,cmp)
+ if tab then
+ local srt={}
+ local s=0
+ for key in next,tab do
+ if key then
+ s=s+1
+ srt[s]=key
+ end
+ end
+ if s>1 then
+ sort(srt,cmp)
+ end
+ return srt
+ else
+ return {}
+ end
+end
+function table.allkeys(t)
+ local keys={}
+ for k,v in next,t do
+ for k in next,v do
+ keys[k]=true
+ end
+ end
+ return sortedkeys(keys)
+end
+table.sortedkeys=sortedkeys
+table.sortedhashonly=sortedhashonly
+table.sortedindexonly=sortedindexonly
+table.sortedhashkeys=sortedhashkeys
+local function nothing() end
+local function sortedhash(t,cmp)
+ if t then
+ local s
+ if cmp then
+ s=sortedhashkeys(t,function(a,b) return cmp(t,a,b) end)
+ else
+ s=sortedkeys(t)
+ end
+ local m=#s
+ if m==1 then
+ return next,t
+ elseif m>0 then
+ local n=0
+ return function()
+ if n<m then
+ n=n+1
+ local k=s[n]
+ return k,t[k]
+ end
+ end
+ end
+ end
+ return nothing
+end
+table.sortedhash=sortedhash
+table.sortedpairs=sortedhash
+function table.append(t,list)
+ local n=#t
+ for i=1,#list do
+ n=n+1
+ t[n]=list[i]
+ end
+ return t
+end
+function table.prepend(t,list)
+ local nl=#list
+ local nt=nl+#t
+ for i=#t,1,-1 do
+ t[nt]=t[i]
+ nt=nt-1
+ end
+ for i=1,#list do
+ t[i]=list[i]
+ end
+ return t
+end
+function table.merge(t,...)
+ if not t then
+ t={}
+ end
+ for i=1,select("#",...) do
+ for k,v in next,(select(i,...)) do
+ t[k]=v
+ end
+ end
+ return t
+end
+function table.merged(...)
+ local t={}
+ for i=1,select("#",...) do
+ for k,v in next,(select(i,...)) do
+ t[k]=v
+ end
+ end
+ return t
+end
+function table.imerge(t,...)
+ local nt=#t
+ for i=1,select("#",...) do
+ local nst=select(i,...)
+ for j=1,#nst do
+ nt=nt+1
+ t[nt]=nst[j]
+ end
+ end
+ return t
+end
+function table.imerged(...)
+ local tmp={}
+ local ntmp=0
+ for i=1,select("#",...) do
+ local nst=select(i,...)
+ for j=1,#nst do
+ ntmp=ntmp+1
+ tmp[ntmp]=nst[j]
+ end
+ end
+ return tmp
+end
+local function fastcopy(old,metatabletoo)
+ if old then
+ local new={}
+ for k,v in next,old do
+ if type(v)=="table" then
+ new[k]=fastcopy(v,metatabletoo)
+ else
+ new[k]=v
+ end
+ end
+ if metatabletoo then
+ local mt=getmetatable(old)
+ if mt then
+ setmetatable(new,mt)
+ end
+ end
+ return new
+ else
+ return {}
+ end
+end
+local function copy(t,tables)
+ if not tables then
+ tables={}
+ end
+ local tcopy={}
+ if not tables[t] then
+ tables[t]=tcopy
+ end
+ for i,v in next,t do
+ if type(i)=="table" then
+ if tables[i] then
+ i=tables[i]
+ else
+ i=copy(i,tables)
+ end
+ end
+ if type(v)~="table" then
+ tcopy[i]=v
+ elseif tables[v] then
+ tcopy[i]=tables[v]
+ else
+ tcopy[i]=copy(v,tables)
+ end
+ end
+ local mt=getmetatable(t)
+ if mt then
+ setmetatable(tcopy,mt)
+ end
+ return tcopy
+end
+table.fastcopy=fastcopy
+table.copy=copy
+function table.derive(parent)
+ local child={}
+ if parent then
+ setmetatable(child,{ __index=parent })
+ end
+ return child
+end
+function table.tohash(t,value)
+ local h={}
+ if t then
+ if value==nil then value=true end
+ for _,v in next,t do
+ h[v]=value
+ end
+ end
+ return h
+end
+function table.fromhash(t)
+ local hsh={}
+ local h=0
+ for k,v in next,t do
+ if v then
+ h=h+1
+ hsh[h]=k
+ end
+ end
+ return hsh
+end
+local noquotes,hexify,handle,compact,inline,functions,metacheck
+local reserved=table.tohash {
+ 'and','break','do','else','elseif','end','false','for','function','if',
+ 'in','local','nil','not','or','repeat','return','then','true','until','while',
+ 'NaN','goto',
+}
+local function is_simple_table(t,hexify)
+ local nt=#t
+ if nt>0 then
+ local n=0
+ for _,v in next,t do
+ n=n+1
+ if type(v)=="table" then
+ return nil
+ end
+ end
+ local haszero=rawget(t,0)
+ if n==nt then
+ local tt={}
+ for i=1,nt do
+ local v=t[i]
+ local tv=type(v)
+ if tv=="number" then
+ if hexify then
+ tt[i]=format("0x%X",v)
+ else
+ tt[i]=v
+ end
+ elseif tv=="string" then
+ tt[i]=format("%q",v)
+ elseif tv=="boolean" then
+ tt[i]=v and "true" or "false"
+ else
+ return nil
+ end
+ end
+ return tt
+ elseif haszero and (n==nt+1) then
+ local tt={}
+ for i=0,nt do
+ local v=t[i]
+ local tv=type(v)
+ if tv=="number" then
+ if hexify then
+ tt[i+1]=format("0x%X",v)
+ else
+ tt[i+1]=v
+ end
+ elseif tv=="string" then
+ tt[i+1]=format("%q",v)
+ elseif tv=="boolean" then
+ tt[i+1]=v and "true" or "false"
+ else
+ return nil
+ end
+ end
+ tt[1]="[0] = "..tt[1]
+ return tt
+ end
+ end
+ return nil
+end
+table.is_simple_table=is_simple_table
+local propername=patterns.propername
+local function dummy() end
+local function do_serialize(root,name,depth,level,indexed)
+ if level>0 then
+ depth=depth.." "
+ if indexed then
+ handle(format("%s{",depth))
+ else
+ local tn=type(name)
+ if tn=="number" then
+ if hexify then
+ handle(format("%s[0x%X]={",depth,name))
+ else
+ handle(format("%s[%s]={",depth,name))
+ end
+ elseif tn=="string" then
+ if noquotes and not reserved[name] and lpegmatch(propername,name) then
+ handle(format("%s%s={",depth,name))
+ else
+ handle(format("%s[%q]={",depth,name))
+ end
+ elseif tn=="boolean" then
+ handle(format("%s[%s]={",depth,name and "true" or "false"))
+ else
+ handle(format("%s{",depth))
+ end
+ end
+ end
+ if root and next(root)~=nil then
+ local first=nil
+ local last=0
+ if compact then
+ last=#root
+ for k=1,last do
+ if rawget(root,k)==nil then
+ last=k-1
+ break
+ end
+ end
+ if last>0 then
+ first=1
+ end
+ end
+ local sk=sortedkeys(root)
+ for i=1,#sk do
+ local k=sk[i]
+ local v=root[k]
+ local tv=type(v)
+ local tk=type(k)
+ if compact and first and tk=="number" and k>=first and k<=last then
+ if tv=="number" then
+ if hexify then
+ handle(format("%s 0x%X,",depth,v))
+ else
+ handle(format("%s %s,",depth,v))
+ end
+ elseif tv=="string" then
+ handle(format("%s %q,",depth,v))
+ elseif tv=="table" then
+ if next(v)==nil then
+ handle(format("%s {},",depth))
+ elseif inline then
+ local st=is_simple_table(v,hexify)
+ if st then
+ handle(format("%s { %s },",depth,concat(st,", ")))
+ else
+ do_serialize(v,k,depth,level+1,true)
+ end
+ else
+ do_serialize(v,k,depth,level+1,true)
+ end
+ elseif tv=="boolean" then
+ handle(format("%s %s,",depth,v and "true" or "false"))
+ elseif tv=="function" then
+ if functions then
+ handle(format('%s load(%q),',depth,dump(v)))
+ else
+ handle(format('%s "function",',depth))
+ end
+ else
+ handle(format("%s %q,",depth,tostring(v)))
+ end
+ elseif k=="__p__" then
+ if false then
+ handle(format("%s __p__=nil,",depth))
+ end
+ elseif tv=="number" then
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]=0x%X,",depth,k,v))
+ else
+ handle(format("%s [%s]=%s,",depth,k,v))
+ end
+ elseif tk=="boolean" then
+ if hexify then
+ handle(format("%s [%s]=0x%X,",depth,k and "true" or "false",v))
+ else
+ handle(format("%s [%s]=%s,",depth,k and "true" or "false",v))
+ end
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ if hexify then
+ handle(format("%s %s=0x%X,",depth,k,v))
+ else
+ handle(format("%s %s=%s,",depth,k,v))
+ end
+ else
+ if hexify then
+ handle(format("%s [%q]=0x%X,",depth,k,v))
+ else
+ handle(format("%s [%q]=%s,",depth,k,v))
+ end
+ end
+ elseif tv=="string" then
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]=%q,",depth,k,v))
+ else
+ handle(format("%s [%s]=%q,",depth,k,v))
+ end
+ elseif tk=="boolean" then
+ handle(format("%s [%s]=%q,",depth,k and "true" or "false",v))
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=%q,",depth,k,v))
+ else
+ handle(format("%s [%q]=%q,",depth,k,v))
+ end
+ elseif tv=="table" then
+ if next(v)==nil then
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]={},",depth,k))
+ else
+ handle(format("%s [%s]={},",depth,k))
+ end
+ elseif tk=="boolean" then
+ handle(format("%s [%s]={},",depth,k and "true" or "false"))
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s={},",depth,k))
+ else
+ handle(format("%s [%q]={},",depth,k))
+ end
+ elseif inline then
+ local st=is_simple_table(v,hexify)
+ if st then
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]={ %s },",depth,k,concat(st,", ")))
+ else
+ handle(format("%s [%s]={ %s },",depth,k,concat(st,", ")))
+ end
+ elseif tk=="boolean" then
+ handle(format("%s [%s]={ %s },",depth,k and "true" or "false",concat(st,", ")))
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s={ %s },",depth,k,concat(st,", ")))
+ else
+ handle(format("%s [%q]={ %s },",depth,k,concat(st,", ")))
+ end
+ else
+ do_serialize(v,k,depth,level+1)
+ end
+ else
+ do_serialize(v,k,depth,level+1)
+ end
+ elseif tv=="boolean" then
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]=%s,",depth,k,v and "true" or "false"))
+ else
+ handle(format("%s [%s]=%s,",depth,k,v and "true" or "false"))
+ end
+ elseif tk=="boolean" then
+ handle(format("%s [%s]=%s,",depth,tostring(k),v and "true" or "false"))
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=%s,",depth,k,v and "true" or "false"))
+ else
+ handle(format("%s [%q]=%s,",depth,k,v and "true" or "false"))
+ end
+ elseif tv=="function" then
+ if functions then
+ local getinfo=debug and debug.getinfo
+ if getinfo then
+ local f=getinfo(v).what=="C" and dump(dummy) or dump(v)
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]=load(%q),",depth,k,f))
+ else
+ handle(format("%s [%s]=load(%q),",depth,k,f))
+ end
+ elseif tk=="boolean" then
+ handle(format("%s [%s]=load(%q),",depth,k and "true" or "false",f))
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=load(%q),",depth,k,f))
+ else
+ handle(format("%s [%q]=load(%q),",depth,k,f))
+ end
+ end
+ end
+ else
+ if tk=="number" then
+ if hexify then
+ handle(format("%s [0x%X]=%q,",depth,k,tostring(v)))
+ else
+ handle(format("%s [%s]=%q,",depth,k,tostring(v)))
+ end
+ elseif tk=="boolean" then
+ handle(format("%s [%s]=%q,",depth,k and "true" or "false",tostring(v)))
+ elseif tk~="string" then
+ elseif noquotes and not reserved[k] and lpegmatch(propername,k) then
+ handle(format("%s %s=%q,",depth,k,tostring(v)))
+ else
+ handle(format("%s [%q]=%q,",depth,k,tostring(v)))
+ end
+ end
+ end
+ end
+ if level>0 then
+ handle(format("%s},",depth))
+ end
+end
+local function serialize(_handle,root,name,specification)
+ local tname=type(name)
+ if type(specification)=="table" then
+ noquotes=specification.noquotes
+ hexify=specification.hexify
+ handle=_handle or specification.handle or print
+ functions=specification.functions
+ compact=specification.compact
+ inline=specification.inline and compact
+ metacheck=specification.metacheck
+ if functions==nil then
+ functions=true
+ end
+ if compact==nil then
+ compact=true
+ end
+ if inline==nil then
+ inline=compact
+ end
+ if metacheck==nil then
+ metacheck=true
+ end
+ else
+ noquotes=false
+ hexify=false
+ handle=_handle or print
+ compact=true
+ inline=true
+ functions=true
+ metacheck=true
+ end
+ if tname=="string" then
+ if name=="return" then
+ handle("return {")
+ else
+ handle(name.."={")
+ end
+ elseif tname=="number" then
+ if hexify then
+ handle(format("[0x%X]={",name))
+ else
+ handle("["..name.."]={")
+ end
+ elseif tname=="boolean" then
+ if name then
+ handle("return {")
+ else
+ handle("{")
+ end
+ else
+ handle("t={")
+ end
+ if root then
+ if metacheck and getmetatable(root) then
+ local dummy=root._w_h_a_t_e_v_e_r_
+ root._w_h_a_t_e_v_e_r_=nil
+ end
+ if next(root)~=nil then
+ do_serialize(root,name,"",0)
+ end
+ end
+ handle("}")
+end
+function table.serialize(root,name,specification)
+ local t={}
+ local n=0
+ local function flush(s)
+ n=n+1
+ t[n]=s
+ end
+ serialize(flush,root,name,specification)
+ return concat(t,"\n")
+end
+table.tohandle=serialize
+local maxtab=2*1024
+function table.tofile(filename,root,name,specification)
+ local f=io.open(filename,'w')
+ if f then
+ if maxtab>1 then
+ local t={}
+ local n=0
+ local function flush(s)
+ n=n+1
+ t[n]=s
+ if n>maxtab then
+ f:write(concat(t,"\n"),"\n")
+ t={}
+ n=0
+ end
+ end
+ serialize(flush,root,name,specification)
+ f:write(concat(t,"\n"),"\n")
+ else
+ local function flush(s)
+ f:write(s,"\n")
+ end
+ serialize(flush,root,name,specification)
+ end
+ f:close()
+ io.flush()
+ end
+end
+local function flattened(t,f,depth)
+ if f==nil then
+ f={}
+ depth=0xFFFF
+ elseif tonumber(f) then
+ depth=f
+ f={}
+ elseif not depth then
+ depth=0xFFFF
+ end
+ for k,v in next,t do
+ if type(k)~="number" then
+ if depth>0 and type(v)=="table" then
+ flattened(v,f,depth-1)
+ else
+ f[#f+1]=v
+ end
+ end
+ end
+ for k=1,#t do
+ local v=t[k]
+ if depth>0 and type(v)=="table" then
+ flattened(v,f,depth-1)
+ else
+ f[#f+1]=v
+ end
+ end
+ return f
+end
+table.flattened=flattened
+local function collapsed(t,f,h)
+ if f==nil then
+ f={}
+ h={}
+ end
+ for k=1,#t do
+ local v=t[k]
+ if type(v)=="table" then
+ collapsed(v,f,h)
+ elseif not h[v] then
+ f[#f+1]=v
+ h[v]=true
+ end
+ end
+ return f
+end
+local function collapsedhash(t,h)
+ if h==nil then
+ h={}
+ end
+ for k=1,#t do
+ local v=t[k]
+ if type(v)=="table" then
+ collapsedhash(v,h)
+ else
+ h[v]=true
+ end
+ end
+ return h
+end
+table.collapsed=collapsed
+table.collapsedhash=collapsedhash
+local function unnest(t,f)
+ if not f then
+ f={}
+ end
+ for i=1,#t do
+ local v=t[i]
+ if type(v)=="table" then
+ if type(v[1])=="table" then
+ unnest(v,f)
+ else
+ f[#f+1]=v
+ end
+ else
+ f[#f+1]=v
+ end
+ end
+ return f
+end
+function table.unnest(t)
+ return unnest(t)
+end
+local function are_equal(a,b,n,m)
+ if a==b then
+ return true
+ elseif a and b and #a==#b then
+ if not n then
+ n=1
+ end
+ if not m then
+ m=#a
+ end
+ for i=n,m do
+ local ai,bi=a[i],b[i]
+ if ai==bi then
+ elseif type(ai)=="table" and type(bi)=="table" then
+ if not are_equal(ai,bi) then
+ return false
+ end
+ else
+ return false
+ end
+ end
+ return true
+ else
+ return false
+ end
+end
+local function identical(a,b)
+ if a~=b then
+ for ka,va in next,a do
+ local vb=b[ka]
+ if va==vb then
+ elseif type(va)=="table" and type(vb)=="table" then
+ if not identical(va,vb) then
+ return false
+ end
+ else
+ return false
+ end
+ end
+ end
+ return true
+end
+table.identical=identical
+table.are_equal=are_equal
+local function sparse(old,nest,keeptables)
+ local new={}
+ for k,v in next,old do
+ if not (v=="" or v==false) then
+ if nest and type(v)=="table" then
+ v=sparse(v,nest)
+ if keeptables or next(v)~=nil then
+ new[k]=v
+ end
+ else
+ new[k]=v
+ end
+ end
+ end
+ return new
+end
+table.sparse=sparse
+function table.compact(t)
+ return sparse(t,true,true)
+end
+function table.contains(t,v)
+ if t then
+ for i=1,#t do
+ if t[i]==v then
+ return i
+ end
+ end
+ end
+ return false
+end
+function table.count(t)
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ end
+ return n
+end
+function table.swapped(t,s)
+ local n={}
+ if s then
+ for k,v in next,s do
+ n[k]=v
+ end
+ end
+ for k,v in next,t do
+ n[v]=k
+ end
+ return n
+end
+function table.hashed(t)
+ for i=1,#t do
+ t[t[i]]=i
+ end
+ return t
+end
+function table.mirrored(t)
+ local n={}
+ for k,v in next,t do
+ n[v]=k
+ n[k]=v
+ end
+ return n
+end
+function table.reversed(t)
+ if t then
+ local tt={}
+ local tn=#t
+ if tn>0 then
+ local ttn=0
+ for i=tn,1,-1 do
+ ttn=ttn+1
+ tt[ttn]=t[i]
+ end
+ end
+ return tt
+ end
+end
+function table.reverse(t)
+ if t then
+ local n=#t
+ local m=n+1
+ for i=1,floor(n/2) do
+ local j=m-i
+ t[i],t[j]=t[j],t[i]
+ end
+ return t
+ end
+end
+local function sequenced(t,sep,simple)
+ if not t then
+ return ""
+ elseif type(t)~="table" then
+ return t
+ end
+ local n=#t
+ local s={}
+ if n>0 then
+ for i=1,n do
+ local v=t[i]
+ if type(v)=="table" then
+ s[i]="{"..sequenced(v,sep,simple).."}"
+ else
+ s[i]=tostring(t[i])
+ end
+ end
+ else
+ n=0
+ for k,v in sortedhash(t) do
+ if simple then
+ if v==true then
+ n=n+1
+ s[n]=k
+ elseif v and v~="" then
+ n=n+1
+ if type(v)=="table" then
+ s[n]=k.."={"..sequenced(v,sep,simple).."}"
+ else
+ s[n]=k.."="..tostring(v)
+ end
+ end
+ else
+ n=n+1
+ if type(v)=="table" then
+ s[n]=k.."={"..sequenced(v,sep,simple).."}"
+ else
+ s[n]=k.."="..tostring(v)
+ end
+ end
+ end
+ end
+ if sep==true then
+ return "{ "..concat(s,", ").." }"
+ else
+ return concat(s,sep or " | ")
+ end
+end
+table.sequenced=sequenced
+function table.print(t,...)
+ if type(t)~="table" then
+ print(tostring(t))
+ else
+ serialize(print,t,...)
+ end
+end
+if setinspector then
+ setinspector("table",function(v) if type(v)=="table" then serialize(print,v,"table") return true end end)
+end
+function table.sub(t,i,j)
+ return { unpack(t,i,j) }
+end
+function table.is_empty(t)
+ return not t or next(t)==nil
+end
+function table.has_one_entry(t)
+ return t and next(t,next(t))==nil
+end
+function table.loweredkeys(t)
+ local l={}
+ for k,v in next,t do
+ l[lower(k)]=v
+ end
+ return l
+end
+function table.unique(old)
+ local hash={}
+ local new={}
+ local n=0
+ for i=1,#old do
+ local oi=old[i]
+ if not hash[oi] then
+ n=n+1
+ new[n]=oi
+ hash[oi]=true
+ end
+ end
+ return new
+end
+function table.sorted(t,...)
+ sort(t,...)
+ return t
+end
+function table.values(t,s)
+ if t then
+ local values={}
+ local keys={}
+ local v=0
+ for key,value in next,t do
+ if not keys[value] then
+ v=v+1
+ values[v]=value
+ keys[k]=key
+ end
+ end
+ if s then
+ sort(values)
+ end
+ return values
+ else
+ return {}
+ end
+end
+function table.filtered(t,pattern,sort,cmp)
+ if t and type(pattern)=="string" then
+ if sort then
+ local s
+ if cmp then
+ s=sortedhashkeys(t,function(a,b) return cmp(t,a,b) end)
+ else
+ s=sortedkeys(t)
+ end
+ local n=0
+ local m=#s
+ local function kv(s)
+ while n<m do
+ n=n+1
+ local k=s[n]
+ if find(k,pattern) then
+ return k,t[k]
+ end
+ end
+ end
+ return kv,s
+ else
+ local n=next(t)
+ local function iterator()
+ while n~=nil do
+ local k=n
+ n=next(t,k)
+ if find(k,pattern) then
+ return k,t[k]
+ end
+ end
+ end
+ return iterator,t
+ end
+ else
+ return nothing
+ end
+end
+if not table.move then
+ function table.move(a1,f,e,t,a2)
+ if a2 and a1~=a2 then
+ for i=f,e do
+ a2[t]=a1[i]
+ t=t+1
+ end
+ return a2
+ else
+ t=t+e-f
+ for i=e,f,-1 do
+ a1[t]=a1[i]
+ t=t-1
+ end
+ return a1
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-io']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local io=io
+local open,flush,write,read=io.open,io.flush,io.write,io.read
+local byte,find,gsub,format=string.byte,string.find,string.gsub,string.format
+local concat=table.concat
+local type=type
+if string.find(os.getenv("PATH"),";",1,true) then
+ io.fileseparator,io.pathseparator="\\",";"
+else
+ io.fileseparator,io.pathseparator="/",":"
+end
+local large=0x01000000
+local medium=0x00100000
+local small=0x00020000
+local function readall(f)
+ local size=f:seek("end")
+ if size>0 then
+ f:seek("set",0)
+ return f:read(size)
+ else
+ return ""
+ end
+end
+io.readall=readall
+function io.loaddata(filename,textmode)
+ local f=open(filename,(textmode and 'r') or 'rb')
+ if f then
+ local size=f:seek("end")
+ local data=nil
+ if size>0 then
+ f:seek("set",0)
+ data=f:read(size)
+ end
+ f:close()
+ return data
+ end
+end
+function io.copydata(source,target,action)
+ local f=open(source,"rb")
+ if f then
+ local g=open(target,"wb")
+ if g then
+ local size=f:seek("end")
+ if size>0 then
+ f:seek("set",0)
+ local data=f:read(size)
+ if action then
+ data=action(data)
+ end
+ if data then
+ g:write(data)
+ end
+ end
+ g:close()
+ end
+ f:close()
+ flush()
+ end
+end
+function io.savedata(filename,data,joiner)
+ local f=open(filename,"wb")
+ if f then
+ if type(data)=="table" then
+ f:write(concat(data,joiner or ""))
+ elseif type(data)=="function" then
+ data(f)
+ else
+ f:write(data or "")
+ end
+ f:close()
+ flush()
+ return true
+ else
+ return false
+ end
+end
+if fio and fio.readline then
+ local readline=fio.readline
+ function io.loadlines(filename,n)
+ local f=open(filename,'r')
+ if not f then
+ elseif n then
+ local lines={}
+ for i=1,n do
+ local line=readline(f)
+ if line then
+ lines[i]=line
+ else
+ break
+ end
+ end
+ f:close()
+ lines=concat(lines,"\n")
+ if #lines>0 then
+ return lines
+ end
+ else
+ local line=readline(f)
+ f:close()
+ if line and #line>0 then
+ return line
+ end
+ end
+ end
+else
+ function io.loadlines(filename,n)
+ local f=open(filename,'r')
+ if not f then
+ elseif n then
+ local lines={}
+ for i=1,n do
+ local line=f:read("*lines")
+ if line then
+ lines[i]=line
+ else
+ break
+ end
+ end
+ f:close()
+ lines=concat(lines,"\n")
+ if #lines>0 then
+ return lines
+ end
+ else
+ local line=f:read("*line") or ""
+ f:close()
+ if #line>0 then
+ return line
+ end
+ end
+ end
+end
+function io.loadchunk(filename,n)
+ local f=open(filename,'rb')
+ if f then
+ local data=f:read(n or 1024)
+ f:close()
+ if #data>0 then
+ return data
+ end
+ end
+end
+function io.exists(filename)
+ local f=open(filename)
+ if f==nil then
+ return false
+ else
+ f:close()
+ return true
+ end
+end
+function io.size(filename)
+ local f=open(filename)
+ if f==nil then
+ return 0
+ else
+ local s=f:seek("end")
+ f:close()
+ return s
+ end
+end
+local function noflines(f)
+ if type(f)=="string" then
+ local f=open(filename)
+ if f then
+ local n=f and noflines(f) or 0
+ f:close()
+ return n
+ else
+ return 0
+ end
+ else
+ local n=0
+ for _ in f:lines() do
+ n=n+1
+ end
+ f:seek('set',0)
+ return n
+ end
+end
+io.noflines=noflines
+local nextchar={
+ [ 4]=function(f)
+ return f:read(1,1,1,1)
+ end,
+ [ 2]=function(f)
+ return f:read(1,1)
+ end,
+ [ 1]=function(f)
+ return f:read(1)
+ end,
+ [-2]=function(f)
+ local a,b=f:read(1,1)
+ return b,a
+ end,
+ [-4]=function(f)
+ local a,b,c,d=f:read(1,1,1,1)
+ return d,c,b,a
+ end
+}
+function io.characters(f,n)
+ if f then
+ return nextchar[n or 1],f
+ end
+end
+local nextbyte={
+ [4]=function(f)
+ local a,b,c,d=f:read(1,1,1,1)
+ if d then
+ return byte(a),byte(b),byte(c),byte(d)
+ end
+ end,
+ [3]=function(f)
+ local a,b,c=f:read(1,1,1)
+ if b then
+ return byte(a),byte(b),byte(c)
+ end
+ end,
+ [2]=function(f)
+ local a,b=f:read(1,1)
+ if b then
+ return byte(a),byte(b)
+ end
+ end,
+ [1]=function (f)
+ local a=f:read(1)
+ if a then
+ return byte(a)
+ end
+ end,
+ [-2]=function (f)
+ local a,b=f:read(1,1)
+ if b then
+ return byte(b),byte(a)
+ end
+ end,
+ [-3]=function(f)
+ local a,b,c=f:read(1,1,1)
+ if b then
+ return byte(c),byte(b),byte(a)
+ end
+ end,
+ [-4]=function(f)
+ local a,b,c,d=f:read(1,1,1,1)
+ if d then
+ return byte(d),byte(c),byte(b),byte(a)
+ end
+ end
+}
+function io.bytes(f,n)
+ if f then
+ return nextbyte[n or 1],f
+ else
+ return nil,nil
+ end
+end
+function io.ask(question,default,options)
+ while true do
+ write(question)
+ if options then
+ write(format(" [%s]",concat(options,"|")))
+ end
+ if default then
+ write(format(" [%s]",default))
+ end
+ write(format(" "))
+ flush()
+ local answer=read()
+ answer=gsub(answer,"^%s*(.*)%s*$","%1")
+ if answer=="" and default then
+ return default
+ elseif not options then
+ return answer
+ else
+ for k=1,#options do
+ if options[k]==answer then
+ return answer
+ end
+ end
+ local pattern="^"..answer
+ for k=1,#options do
+ local v=options[k]
+ if find(v,pattern) then
+ return v
+ end
+ end
+ end
+ end
+end
+local function readnumber(f,n,m)
+ if m then
+ f:seek("set",n)
+ n=m
+ end
+ if n==1 then
+ return byte(f:read(1))
+ elseif n==2 then
+ local a,b=byte(f:read(2),1,2)
+ return 0x100*a+b
+ elseif n==3 then
+ local a,b,c=byte(f:read(3),1,3)
+ return 0x10000*a+0x100*b+c
+ elseif n==4 then
+ local a,b,c,d=byte(f:read(4),1,4)
+ return 0x1000000*a+0x10000*b+0x100*c+d
+ elseif n==8 then
+ local a,b=readnumber(f,4),readnumber(f,4)
+ return 0x100*a+b
+ elseif n==12 then
+ local a,b,c=readnumber(f,4),readnumber(f,4),readnumber(f,4)
+ return 0x10000*a+0x100*b+c
+ elseif n==-2 then
+ local b,a=byte(f:read(2),1,2)
+ return 0x100*a+b
+ elseif n==-3 then
+ local c,b,a=byte(f:read(3),1,3)
+ return 0x10000*a+0x100*b+c
+ elseif n==-4 then
+ local d,c,b,a=byte(f:read(4),1,4)
+ return 0x1000000*a+0x10000*b+0x100*c+d
+ elseif n==-8 then
+ local h,g,f,e,d,c,b,a=byte(f:read(8),1,8)
+ return 0x100000000000000*a+0x1000000000000*b+0x10000000000*c+0x100000000*d+0x1000000*e+0x10000*f+0x100*g+h
+ else
+ return 0
+ end
+end
+io.readnumber=readnumber
+function io.readstring(f,n,m)
+ if m then
+ f:seek("set",n)
+ n=m
+ end
+ local str=gsub(f:read(n),"\000","")
+ return str
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-file']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+file=file or {}
+local file=file
+if not lfs then
+ lfs=optionalrequire("lfs")
+end
+local insert,concat=table.insert,table.concat
+local match,find,gmatch=string.match,string.find,string.gmatch
+local lpegmatch=lpeg.match
+local getcurrentdir,attributes=lfs.currentdir,lfs.attributes
+local checkedsplit=string.checkedsplit
+local P,R,S,C,Cs,Cp,Cc,Ct=lpeg.P,lpeg.R,lpeg.S,lpeg.C,lpeg.Cs,lpeg.Cp,lpeg.Cc,lpeg.Ct
+local attributes=lfs.attributes
+function lfs.isdir(name)
+ return attributes(name,"mode")=="directory"
+end
+function lfs.isfile(name)
+ local a=attributes(name,"mode")
+ return a=="file" or a=="link" or nil
+end
+function lfs.isfound(name)
+ local a=attributes(name,"mode")
+ return (a=="file" or a=="link") and name or nil
+end
+if sandbox then
+ sandbox.redefine(lfs.isfile,"lfs.isfile")
+ sandbox.redefine(lfs.isdir,"lfs.isdir")
+ sandbox.redefine(lfs.isfound,"lfs.isfound")
+end
+local colon=P(":")
+local period=P(".")
+local periods=P("..")
+local fwslash=P("/")
+local bwslash=P("\\")
+local slashes=S("\\/")
+local noperiod=1-period
+local noslashes=1-slashes
+local name=noperiod^1
+local suffix=period/""*(1-period-slashes)^1*-1
+local pattern=C((1-(slashes^1*noslashes^1*-1))^1)*P(1)
+local function pathpart(name,default)
+ return name and lpegmatch(pattern,name) or default or ""
+end
+local pattern=(noslashes^0*slashes)^1*C(noslashes^1)*-1
+local function basename(name)
+ return name and lpegmatch(pattern,name) or name
+end
+local pattern=(noslashes^0*slashes^1)^0*Cs((1-suffix)^1)*suffix^0
+local function nameonly(name)
+ return name and lpegmatch(pattern,name) or name
+end
+local pattern=(noslashes^0*slashes)^0*(noperiod^1*period)^1*C(noperiod^1)*-1
+local function suffixonly(name)
+ return name and lpegmatch(pattern,name) or ""
+end
+local pattern=(noslashes^0*slashes)^0*noperiod^1*((period*C(noperiod^1))^1)*-1+Cc("")
+local function suffixesonly(name)
+ if name then
+ return lpegmatch(pattern,name)
+ else
+ return ""
+ end
+end
+file.pathpart=pathpart
+file.basename=basename
+file.nameonly=nameonly
+file.suffixonly=suffixonly
+file.suffix=suffixonly
+file.suffixesonly=suffixesonly
+file.suffixes=suffixesonly
+file.dirname=pathpart
+file.extname=suffixonly
+local drive=C(R("az","AZ"))*colon
+local path=C((noslashes^0*slashes)^0)
+local suffix=period*C(P(1-period)^0*P(-1))
+local base=C((1-suffix)^0)
+local rest=C(P(1)^0)
+drive=drive+Cc("")
+path=path+Cc("")
+base=base+Cc("")
+suffix=suffix+Cc("")
+local pattern_a=drive*path*base*suffix
+local pattern_b=path*base*suffix
+local pattern_c=C(drive*path)*C(base*suffix)
+local pattern_d=path*rest
+function file.splitname(str,splitdrive)
+ if not str then
+ elseif splitdrive then
+ return lpegmatch(pattern_a,str)
+ else
+ return lpegmatch(pattern_b,str)
+ end
+end
+function file.splitbase(str)
+ if str then
+ return lpegmatch(pattern_d,str)
+ else
+ return "",str
+ end
+end
+function file.nametotable(str,splitdrive)
+ if str then
+ local path,drive,subpath,name,base,suffix=lpegmatch(pattern_c,str)
+ if splitdrive then
+ return {
+ path=path,
+ drive=drive,
+ subpath=subpath,
+ name=name,
+ base=base,
+ suffix=suffix,
+ }
+ else
+ return {
+ path=path,
+ name=name,
+ base=base,
+ suffix=suffix,
+ }
+ end
+ end
+end
+local pattern=Cs(((period*(1-period-slashes)^1*-1)/""+1)^1)
+function file.removesuffix(name)
+ return name and lpegmatch(pattern,name)
+end
+local suffix=period/""*(1-period-slashes)^1*-1
+local pattern=Cs((noslashes^0*slashes^1)^0*((1-suffix)^1))*Cs(suffix)
+function file.addsuffix(filename,suffix,criterium)
+ if not filename or not suffix or suffix=="" then
+ return filename
+ elseif criterium==true then
+ return filename.."."..suffix
+ elseif not criterium then
+ local n,s=lpegmatch(pattern,filename)
+ if not s or s=="" then
+ return filename.."."..suffix
+ else
+ return filename
+ end
+ else
+ local n,s=lpegmatch(pattern,filename)
+ if s and s~="" then
+ local t=type(criterium)
+ if t=="table" then
+ for i=1,#criterium do
+ if s==criterium[i] then
+ return filename
+ end
+ end
+ elseif t=="string" then
+ if s==criterium then
+ return filename
+ end
+ end
+ end
+ return (n or filename).."."..suffix
+ end
+end
+local suffix=period*(1-period-slashes)^1*-1
+local pattern=Cs((1-suffix)^0)
+function file.replacesuffix(name,suffix)
+ if name and suffix and suffix~="" then
+ return lpegmatch(pattern,name).."."..suffix
+ else
+ return name
+ end
+end
+local reslasher=lpeg.replacer(P("\\"),"/")
+function file.reslash(str)
+ return str and lpegmatch(reslasher,str)
+end
+if lfs.isreadablefile and lfs.iswritablefile then
+ file.is_readable=lfs.isreadablefile
+ file.is_writable=lfs.iswritablefile
+else
+ function file.is_writable(name)
+ if not name then
+ elseif lfs.isdir(name) then
+ name=name.."/m_t_x_t_e_s_t.tmp"
+ local f=io.open(name,"wb")
+ if f then
+ f:close()
+ os.remove(name)
+ return true
+ end
+ elseif lfs.isfile(name) then
+ local f=io.open(name,"ab")
+ if f then
+ f:close()
+ return true
+ end
+ else
+ local f=io.open(name,"ab")
+ if f then
+ f:close()
+ os.remove(name)
+ return true
+ end
+ end
+ return false
+ end
+ local readable=P("r")*Cc(true)
+ function file.is_readable(name)
+ if name then
+ local a=attributes(name)
+ return a and lpegmatch(readable,a.permissions) or false
+ else
+ return false
+ end
+ end
+end
+file.isreadable=file.is_readable
+file.iswritable=file.is_writable
+function file.size(name)
+ if name then
+ local a=attributes(name)
+ return a and a.size or 0
+ else
+ return 0
+ end
+end
+function file.splitpath(str,separator)
+ return str and checkedsplit(lpegmatch(reslasher,str),separator or io.pathseparator)
+end
+function file.joinpath(tab,separator)
+ return tab and concat(tab,separator or io.pathseparator)
+end
+local someslash=S("\\/")
+local stripper=Cs(P(fwslash)^0/""*reslasher)
+local isnetwork=someslash*someslash*(1-someslash)+(1-fwslash-colon)^1*colon
+local isroot=fwslash^1*-1
+local hasroot=fwslash^1
+local reslasher=lpeg.replacer(S("\\/"),"/")
+local deslasher=lpeg.replacer(S("\\/")^1,"/")
+function file.join(one,two,three,...)
+ if not two then
+ return one=="" and one or lpegmatch(reslasher,one)
+ end
+ if one=="" then
+ return lpegmatch(stripper,three and concat({ two,three,... },"/") or two)
+ end
+ if lpegmatch(isnetwork,one) then
+ local one=lpegmatch(reslasher,one)
+ local two=lpegmatch(deslasher,three and concat({ two,three,... },"/") or two)
+ if lpegmatch(hasroot,two) then
+ return one..two
+ else
+ return one.."/"..two
+ end
+ elseif lpegmatch(isroot,one) then
+ local two=lpegmatch(deslasher,three and concat({ two,three,... },"/") or two)
+ if lpegmatch(hasroot,two) then
+ return two
+ else
+ return "/"..two
+ end
+ else
+ return lpegmatch(deslasher,concat({ one,two,three,... },"/"))
+ end
+end
+local drivespec=R("az","AZ")^1*colon
+local anchors=fwslash+drivespec
+local untouched=periods+(1-period)^1*P(-1)
+local mswindrive=Cs(drivespec*(bwslash/"/"+fwslash)^0)
+local mswinuncpath=(bwslash+fwslash)*(bwslash+fwslash)*Cc("//")
+local splitstarter=(mswindrive+mswinuncpath+Cc(false))*Ct(lpeg.splitat(S("/\\")^1))
+local absolute=fwslash
+function file.collapsepath(str,anchor)
+ if not str then
+ return
+ end
+ if anchor==true and not lpegmatch(anchors,str) then
+ str=getcurrentdir().."/"..str
+ end
+ if str=="" or str=="." then
+ return "."
+ elseif lpegmatch(untouched,str) then
+ return lpegmatch(reslasher,str)
+ end
+ local starter,oldelements=lpegmatch(splitstarter,str)
+ local newelements={}
+ local i=#oldelements
+ while i>0 do
+ local element=oldelements[i]
+ if element=='.' then
+ elseif element=='..' then
+ local n=i-1
+ while n>0 do
+ local element=oldelements[n]
+ if element~='..' and element~='.' then
+ oldelements[n]='.'
+ break
+ else
+ n=n-1
+ end
+ end
+ if n<1 then
+ insert(newelements,1,'..')
+ end
+ elseif element~="" then
+ insert(newelements,1,element)
+ end
+ i=i-1
+ end
+ if #newelements==0 then
+ return starter or "."
+ elseif starter then
+ return starter..concat(newelements,'/')
+ elseif lpegmatch(absolute,str) then
+ return "/"..concat(newelements,'/')
+ else
+ newelements=concat(newelements,'/')
+ if anchor=="." and find(str,"^%./") then
+ return "./"..newelements
+ else
+ return newelements
+ end
+ end
+end
+local validchars=R("az","09","AZ","--","..")
+local pattern_a=lpeg.replacer(1-validchars)
+local pattern_a=Cs((validchars+P(1)/"-")^1)
+local whatever=P("-")^0/""
+local pattern_b=Cs(whatever*(1-whatever*-1)^1)
+function file.robustname(str,strict)
+ if str then
+ str=lpegmatch(pattern_a,str) or str
+ if strict then
+ return lpegmatch(pattern_b,str) or str
+ else
+ return str
+ end
+ end
+end
+local loaddata=io.loaddata
+local savedata=io.savedata
+file.readdata=loaddata
+file.savedata=savedata
+function file.copy(oldname,newname)
+ if oldname and newname then
+ local data=loaddata(oldname)
+ if data and data~="" then
+ savedata(newname,data)
+ end
+ end
+end
+local letter=R("az","AZ")+S("_-+")
+local separator=P("://")
+local qualified=period^0*fwslash+letter*colon+letter^1*separator+letter^1*fwslash
+local rootbased=fwslash+letter*colon
+lpeg.patterns.qualified=qualified
+lpeg.patterns.rootbased=rootbased
+function file.is_qualified_path(filename)
+ return filename and lpegmatch(qualified,filename)~=nil
+end
+function file.is_rootbased_path(filename)
+ return filename and lpegmatch(rootbased,filename)~=nil
+end
+function file.strip(name,dir)
+ if name then
+ local b,a=match(name,"^(.-)"..dir.."(.*)$")
+ return a~="" and a or name
+ end
+end
+function lfs.mkdirs(path)
+ local full=""
+ for sub in gmatch(path,"(/*[^\\/]+)") do
+ full=full..sub
+ lfs.mkdir(full)
+ end
+end
+function file.withinbase(path)
+ local l=0
+ if not find(path,"^/") then
+ path="/"..path
+ end
+ for dir in gmatch(path,"/([^/]+)") do
+ if dir==".." then
+ l=l-1
+ elseif dir~="." then
+ l=l+1
+ end
+ if l<0 then
+ return false
+ end
+ end
+ return true
+end
+local symlinkattributes=lfs.symlinkattributes
+function lfs.readlink(name)
+ return symlinkattributes(name,"target") or nil
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-boolean']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local type,tonumber=type,tonumber
+boolean=boolean or {}
+local boolean=boolean
+function boolean.tonumber(b)
+ if b then return 1 else return 0 end
+end
+function toboolean(str,tolerant)
+ if str==nil then
+ return false
+ elseif str==false then
+ return false
+ elseif str==true then
+ return true
+ elseif str=="true" then
+ return true
+ elseif str=="false" then
+ return false
+ elseif not tolerant then
+ return false
+ elseif str==0 then
+ return false
+ elseif (tonumber(str) or 0)>0 then
+ return true
+ else
+ return str=="yes" or str=="on" or str=="t"
+ end
+end
+string.toboolean=toboolean
+function string.booleanstring(str)
+ if str=="0" then
+ return false
+ elseif str=="1" then
+ return true
+ elseif str=="" then
+ return false
+ elseif str=="false" then
+ return false
+ elseif str=="true" then
+ return true
+ elseif (tonumber(str) or 0)>0 then
+ return true
+ else
+ return str=="yes" or str=="on" or str=="t"
+ end
+end
+function string.is_boolean(str,default,strict)
+ if type(str)=="string" then
+ if str=="true" or str=="yes" or str=="on" or str=="t" or (not strict and str=="1") then
+ return true
+ elseif str=="false" or str=="no" or str=="off" or str=="f" or (not strict and str=="0") then
+ return false
+ end
+ end
+ return default
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['l-math']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if not math.ceiling then
+ math.ceiling=math.ceil
+end
+if not math.round then
+ local floor=math.floor
+ function math.round(x) return floor(x+0.5) end
+end
+if not math.div then
+ local floor=math.floor
+ function math.div(n,m) return floor(n/m) end
+end
+if not math.mod then
+ function math.mod(n,m) return n%m end
+end
+if not math.sind then
+ local sin,cos,tan=math.sin,math.cos,math.tan
+ local pipi=2*math.pi/360
+ function math.sind(d) return sin(d*pipi) end
+ function math.cosd(d) return cos(d*pipi) end
+ function math.tand(d) return tan(d*pipi) end
+end
+if not math.odd then
+ function math.odd (n) return n%2~=0 end
+ function math.even(n) return n%2==0 end
+end
+if not math.cosh then
+ local exp=math.exp
+ function math.cosh(x)
+ local xx=exp(x)
+ return (xx+1/xx)/2
+ end
+ function math.sinh(x)
+ local xx=exp(x)
+ return (xx-1/xx)/2
+ end
+ function math.tanh(x)
+ local xx=exp(x)
+ return (xx-1/xx)/(xx+1/xx)
+ end
+end
+if not math.pow then
+ function math.pow(x,y)
+ return x^y
+ end
+end
+if not math.atan2 then
+ math.atan2=math.atan
+end
+if not math.ldexp then
+ function math.ldexp(x,e)
+ return x*2.0^e
+ end
+end
+if not math.log10 then
+ local log=math.log
+ function math.log10(x)
+ return log(x,10)
+ end
+end
+if not math.type then
+ function math.type()
+ return "float"
+ end
+end
+if not math.tointeger then
+ math.mininteger=-0x4FFFFFFFFFFF
+ math.maxinteger=0x4FFFFFFFFFFF
+ local floor=math.floor
+ function math.tointeger(n)
+ local f=floor(n)
+ return f==n and f or nil
+ end
+end
+if not math.ult then
+ local floor=math.floor
+ function math.tointeger(m,n)
+ return floor(m)<floor(n)
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['util-str']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+utilities=utilities or {}
+utilities.strings=utilities.strings or {}
+local strings=utilities.strings
+local format,gsub,rep,sub,find=string.format,string.gsub,string.rep,string.sub,string.find
+local load,dump=load,string.dump
+local tonumber,type,tostring,next,setmetatable=tonumber,type,tostring,next,setmetatable
+local unpack,concat=table.unpack,table.concat
+local P,V,C,S,R,Ct,Cs,Cp,Carg,Cc=lpeg.P,lpeg.V,lpeg.C,lpeg.S,lpeg.R,lpeg.Ct,lpeg.Cs,lpeg.Cp,lpeg.Carg,lpeg.Cc
+local patterns,lpegmatch=lpeg.patterns,lpeg.match
+local utfchar,utfbyte,utflen=utf.char,utf.byte,utf.len
+local loadstripped=function(str,shortcuts)
+ if shortcuts then
+ return load(dump(load(str),true),nil,nil,shortcuts)
+ else
+ return load(dump(load(str),true))
+ end
+end
+if not number then number={} end
+local stripzero=patterns.stripzero
+local stripzeros=patterns.stripzeros
+local newline=patterns.newline
+local endofstring=patterns.endofstring
+local anything=patterns.anything
+local whitespace=patterns.whitespace
+local space=patterns.space
+local spacer=patterns.spacer
+local spaceortab=patterns.spaceortab
+local digit=patterns.digit
+local sign=patterns.sign
+local period=patterns.period
+local ptf=1/65536
+local bpf=(7200/7227)/65536
+local function points(n)
+ if n==0 then
+ return "0pt"
+ end
+ n=tonumber(n)
+ if not n or n==0 then
+ return "0pt"
+ end
+ n=n*ptf
+ if n%1==0 then
+ return format("%ipt",n)
+ end
+ return lpegmatch(stripzeros,format("%.5fpt",n))
+end
+local function basepoints(n)
+ if n==0 then
+ return "0pt"
+ end
+ n=tonumber(n)
+ if not n or n==0 then
+ return "0pt"
+ end
+ n=n*bpf
+ if n%1==0 then
+ return format("%ibp",n)
+ end
+ return lpegmatch(stripzeros,format("%.5fbp",n))
+end
+number.points=points
+number.basepoints=basepoints
+local rubish=spaceortab^0*newline
+local anyrubish=spaceortab+newline
+local stripped=(spaceortab^1/"")*newline
+local leading=rubish^0/""
+local trailing=(anyrubish^1*endofstring)/""
+local redundant=rubish^3/"\n"
+local pattern=Cs(leading*(trailing+redundant+stripped+anything)^0)
+function strings.collapsecrlf(str)
+ return lpegmatch(pattern,str)
+end
+local repeaters={}
+function strings.newrepeater(str,offset)
+ offset=offset or 0
+ local s=repeaters[str]
+ if not s then
+ s={}
+ repeaters[str]=s
+ end
+ local t=s[offset]
+ if t then
+ return t
+ end
+ t={}
+ setmetatable(t,{ __index=function(t,k)
+ if not k then
+ return ""
+ end
+ local n=k+offset
+ local s=n>0 and rep(str,n) or ""
+ t[k]=s
+ return s
+ end })
+ s[offset]=t
+ return t
+end
+local extra,tab,start=0,0,4,0
+local nspaces=strings.newrepeater(" ")
+string.nspaces=nspaces
+local pattern=Carg(1)/function(t)
+ extra,tab,start=0,t or 7,1
+ end*Cs((
+ Cp()*patterns.tab/function(position)
+ local current=(position-start+1)+extra
+ local spaces=tab-(current-1)%tab
+ if spaces>0 then
+ extra=extra+spaces-1
+ return nspaces[spaces]
+ else
+ return ""
+ end
+ end+newline*Cp()/function(position)
+ extra,start=0,position
+ end+anything
+ )^1)
+function strings.tabtospace(str,tab)
+ return lpegmatch(pattern,str,1,tab or 7)
+end
+function string.utfpadding(s,n)
+ if not n or n==0 then
+ return ""
+ end
+ local l=utflen(s)
+ if n>0 then
+ return nspaces[n-l]
+ else
+ return nspaces[-n-l]
+ end
+end
+local optionalspace=spacer^0
+local nospace=optionalspace/""
+local endofline=nospace*newline
+local stripend=(whitespace^1*endofstring)/""
+local normalline=(nospace*((1-optionalspace*(newline+endofstring))^1)*nospace)
+local stripempty=endofline^1/""
+local normalempty=endofline^1
+local singleempty=endofline*(endofline^0/"")
+local doubleempty=endofline*endofline^-1*(endofline^0/"")
+local stripstart=stripempty^0
+local intospace=whitespace^1/" "
+local noleading=whitespace^1/""
+local notrailing=noleading*endofstring
+local p_prune_normal=Cs (stripstart*(stripend+normalline+normalempty )^0 )
+local p_prune_collapse=Cs (stripstart*(stripend+normalline+doubleempty )^0 )
+local p_prune_noempty=Cs (stripstart*(stripend+normalline+singleempty )^0 )
+local p_prune_intospace=Cs (noleading*(notrailing+intospace+1 )^0 )
+local p_retain_normal=Cs ((normalline+normalempty )^0 )
+local p_retain_collapse=Cs ((normalline+doubleempty )^0 )
+local p_retain_noempty=Cs ((normalline+singleempty )^0 )
+local striplinepatterns={
+ ["prune"]=p_prune_normal,
+ ["prune and collapse"]=p_prune_collapse,
+ ["prune and no empty"]=p_prune_noempty,
+ ["prune and to space"]=p_prune_intospace,
+ ["retain"]=p_retain_normal,
+ ["retain and collapse"]=p_retain_collapse,
+ ["retain and no empty"]=p_retain_noempty,
+ ["collapse"]=patterns.collapser,
+}
+setmetatable(striplinepatterns,{ __index=function(t,k) return p_prune_collapse end })
+strings.striplinepatterns=striplinepatterns
+function strings.striplines(str,how)
+ return str and lpegmatch(striplinepatterns[how],str) or str
+end
+function strings.collapse(str)
+ return str and lpegmatch(p_prune_intospace,str) or str
+end
+strings.striplong=strings.striplines
+function strings.nice(str)
+ str=gsub(str,"[:%-+_]+"," ")
+ return str
+end
+local n=0
+local sequenced=table.sequenced
+function string.autodouble(s,sep)
+ if s==nil then
+ return '""'
+ end
+ local t=type(s)
+ if t=="number" then
+ return tostring(s)
+ end
+ if t=="table" then
+ return ('"'..sequenced(s,sep or ",")..'"')
+ end
+ return ('"'..tostring(s)..'"')
+end
+function string.autosingle(s,sep)
+ if s==nil then
+ return "''"
+ end
+ local t=type(s)
+ if t=="number" then
+ return tostring(s)
+ end
+ if t=="table" then
+ return ("'"..sequenced(s,sep or ",").."'")
+ end
+ return ("'"..tostring(s).."'")
+end
+local tracedchars={ [0]=
+ "[null]","[soh]","[stx]","[etx]","[eot]","[enq]","[ack]","[bel]",
+ "[bs]","[ht]","[lf]","[vt]","[ff]","[cr]","[so]","[si]",
+ "[dle]","[dc1]","[dc2]","[dc3]","[dc4]","[nak]","[syn]","[etb]",
+ "[can]","[em]","[sub]","[esc]","[fs]","[gs]","[rs]","[us]",
+ "[space]",
+}
+string.tracedchars=tracedchars
+strings.tracers=tracedchars
+function string.tracedchar(b)
+ if type(b)=="number" then
+ return tracedchars[b] or (utfchar(b).." (U+"..format("%05X",b)..")")
+ else
+ local c=utfbyte(b)
+ return tracedchars[c] or (b.." (U+"..(c and format("%05X",c) or "?????")..")")
+ end
+end
+function number.signed(i)
+ if i>0 then
+ return "+",i
+ else
+ return "-",-i
+ end
+end
+local two=digit*digit
+local three=two*digit
+local prefix=(Carg(1)*three)^1
+local splitter=Cs (
+ (((1-(three^1*period))^1+C(three))*prefix+C((1-period)^1))*(anything/""*Carg(2))*C(2)
+)
+local splitter3=Cs (
+ three*prefix*endofstring+two*prefix*endofstring+digit*prefix*endofstring+three+two+digit
+)
+patterns.formattednumber=splitter
+function number.formatted(n,sep1,sep2)
+ if sep1==false then
+ if type(n)=="number" then
+ n=tostring(n)
+ end
+ return lpegmatch(splitter3,n,1,sep2 or ".")
+ else
+ if type(n)=="number" then
+ n=format("%0.2f",n)
+ end
+ if sep1==true then
+ return lpegmatch(splitter,n,1,".",",")
+ elseif sep1=="." then
+ return lpegmatch(splitter,n,1,sep1,sep2 or ",")
+ elseif sep1=="," then
+ return lpegmatch(splitter,n,1,sep1,sep2 or ".")
+ else
+ return lpegmatch(splitter,n,1,sep1 or ",",sep2 or ".")
+ end
+ end
+end
+local p=Cs(
+ P("-")^0*(P("0")^1/"")^0*(1-period)^0*(period*P("0")^1*endofstring/""+period^0)*P(1-P("0")^1*endofstring)^0
+ )
+function number.compactfloat(n,fmt)
+ if n==0 then
+ return "0"
+ elseif n==1 then
+ return "1"
+ end
+ n=lpegmatch(p,format(fmt or "%0.3f",n))
+ if n=="." or n=="" or n=="-" then
+ return "0"
+ end
+ return n
+end
+local zero=P("0")^1/""
+local plus=P("+")/""
+local minus=P("-")
+local separator=period
+local trailing=zero^1*#S("eE")
+local exponent=(S("eE")*(plus+Cs((minus*zero^0*endofstring)/"")+minus)*zero^0*(endofstring*Cc("0")+anything^1))
+local pattern_a=Cs(minus^0*digit^1*(separator/""*trailing+separator*(trailing+digit)^0)*exponent)
+local pattern_b=Cs((exponent+anything)^0)
+function number.sparseexponent(f,n)
+ if not n then
+ n=f
+ f="%e"
+ end
+ local tn=type(n)
+ if tn=="string" then
+ local m=tonumber(n)
+ if m then
+ return lpegmatch((f=="%e" or f=="%E") and pattern_a or pattern_b,format(f,m))
+ end
+ elseif tn=="number" then
+ return lpegmatch((f=="%e" or f=="%E") and pattern_a or pattern_b,format(f,n))
+ end
+ return tostring(n)
+end
+local hf={}
+local hs={}
+setmetatable(hf,{ __index=function(t,k)
+ local v="%."..k.."f"
+ t[k]=v
+ return v
+end } )
+setmetatable(hs,{ __index=function(t,k)
+ local v="%"..k.."s"
+ t[k]=v
+ return v
+end } )
+function number.formattedfloat(n,b,a)
+ local s=format(hf[a],n)
+ local l=(b or 0)+(a or 0)+1
+ if #s<l then
+ return format(hs[l],s)
+ else
+ return s
+ end
+end
+local template=[[
+%s
+%s
+return function(%s) return %s end
+]]
+local pattern=Cs(Cc('"')*(
+ (1-S('"\\\n\r'))^1+P('"')/'\\"'+P('\\')/'\\\\'+P('\n')/'\\n'+P('\r')/'\\r'
+)^0*Cc('"'))
+patterns.escapedquotes=pattern
+function string.escapedquotes(s)
+ return lpegmatch(pattern,s)
+end
+local preamble=""
+local environment={
+ global=global or _G,
+ lpeg=lpeg,
+ type=type,
+ tostring=tostring,
+ tonumber=tonumber,
+ format=string.format,
+ concat=table.concat,
+ signed=number.signed,
+ points=number.points,
+ basepoints=number.basepoints,
+ utfchar=utf.char,
+ utfbyte=utf.byte,
+ lpegmatch=lpeg.match,
+ nspaces=string.nspaces,
+ utfpadding=string.utfpadding,
+ tracedchar=string.tracedchar,
+ autosingle=string.autosingle,
+ autodouble=string.autodouble,
+ sequenced=table.sequenced,
+ formattednumber=number.formatted,
+ sparseexponent=number.sparseexponent,
+ formattedfloat=number.formattedfloat,
+ stripzero=patterns.stripzero,
+ stripzeros=patterns.stripzeros,
+ escapedquotes=string.escapedquotes,
+ FORMAT=string.f9,
+}
+local arguments={ "a1" }
+setmetatable(arguments,{ __index=function(t,k)
+ local v=t[k-1]..",a"..k
+ t[k]=v
+ return v
+ end
+})
+local prefix_any=C((sign+space+period+digit)^0)
+local prefix_sub=(C((sign+digit)^0)+Cc(0))*period*(C((sign+digit)^0)+Cc(0))
+local prefix_tab=P("{")*C((1-P("}"))^0)*P("}")+C((1-R("az","AZ","09","%%"))^0)
+local format_s=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("format('%%%ss',a%s)",f,n)
+ else
+ return format("(a%s or '')",n)
+ end
+end
+local format_S=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("format('%%%ss',tostring(a%s))",f,n)
+ else
+ return format("tostring(a%s)",n)
+ end
+end
+local format_right=function(f)
+ n=n+1
+ f=tonumber(f)
+ if not f or f==0 then
+ return format("(a%s or '')",n)
+ elseif f>0 then
+ return format("utfpadding(a%s,%i)..a%s",n,f,n)
+ else
+ return format("a%s..utfpadding(a%s,%i)",n,n,f)
+ end
+end
+local format_left=function(f)
+ n=n+1
+ f=tonumber(f)
+ if not f or f==0 then
+ return format("(a%s or '')",n)
+ end
+ if f<0 then
+ return format("utfpadding(a%s,%i)..a%s",n,-f,n)
+ else
+ return format("a%s..utfpadding(a%s,%i)",n,n,-f)
+ end
+end
+local format_q=function()
+ n=n+1
+ return format("(a%s ~= nil and format('%%q',tostring(a%s)) or '')",n,n)
+end
+local format_Q=function()
+ n=n+1
+ return format("escapedquotes(tostring(a%s))",n)
+end
+local format_i=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("format('%%%si',a%s)",f,n)
+ else
+ return format("format('%%i',a%s)",n)
+ end
+end
+local format_d=format_i
+local format_I=function(f)
+ n=n+1
+ return format("format('%%s%%%si',signed(a%s))",f,n)
+end
+local format_f=function(f)
+ n=n+1
+ return format("format('%%%sf',a%s)",f,n)
+end
+local format_F=function(f)
+ n=n+1
+ if not f or f=="" then
+ return format("(((a%s > -0.0000000005 and a%s < 0.0000000005) and '0') or format((a%s %% 1 == 0) and '%%i' or '%%.9f',a%s))",n,n,n,n)
+ else
+ return format("format((a%s %% 1 == 0) and '%%i' or '%%%sf',a%s)",n,f,n)
+ end
+end
+local format_k=function(b,a)
+ n=n+1
+ return format("formattedfloat(a%s,%s,%s)",n,b or 0,a or 0)
+end
+local format_g=function(f)
+ n=n+1
+ return format("format('%%%sg',a%s)",f,n)
+end
+local format_G=function(f)
+ n=n+1
+ return format("format('%%%sG',a%s)",f,n)
+end
+local format_e=function(f)
+ n=n+1
+ return format("format('%%%se',a%s)",f,n)
+end
+local format_E=function(f)
+ n=n+1
+ return format("format('%%%sE',a%s)",f,n)
+end
+local format_j=function(f)
+ n=n+1
+ return format("sparseexponent('%%%se',a%s)",f,n)
+end
+local format_J=function(f)
+ n=n+1
+ return format("sparseexponent('%%%sE',a%s)",f,n)
+end
+local format_x=function(f)
+ n=n+1
+ return format("format('%%%sx',a%s)",f,n)
+end
+local format_X=function(f)
+ n=n+1
+ return format("format('%%%sX',a%s)",f,n)
+end
+local format_o=function(f)
+ n=n+1
+ return format("format('%%%so',a%s)",f,n)
+end
+local format_c=function()
+ n=n+1
+ return format("utfchar(a%s)",n)
+end
+local format_C=function()
+ n=n+1
+ return format("tracedchar(a%s)",n)
+end
+local format_r=function(f)
+ n=n+1
+ return format("format('%%%s.0f',a%s)",f,n)
+end
+local format_h=function(f)
+ n=n+1
+ if f=="-" then
+ f=sub(f,2)
+ return format("format('%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ else
+ return format("format('0x%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ end
+end
+local format_H=function(f)
+ n=n+1
+ if f=="-" then
+ f=sub(f,2)
+ return format("format('%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ else
+ return format("format('0x%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ end
+end
+local format_u=function(f)
+ n=n+1
+ if f=="-" then
+ f=sub(f,2)
+ return format("format('%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ else
+ return format("format('u+%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ end
+end
+local format_U=function(f)
+ n=n+1
+ if f=="-" then
+ f=sub(f,2)
+ return format("format('%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ else
+ return format("format('U+%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f=="" and "05" or f,n,n,n)
+ end
+end
+local format_p=function()
+ n=n+1
+ return format("points(a%s)",n)
+end
+local format_b=function()
+ n=n+1
+ return format("basepoints(a%s)",n)
+end
+local format_t=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("concat(a%s,%q)",n,f)
+ else
+ return format("concat(a%s)",n)
+ end
+end
+local format_T=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("sequenced(a%s,%q)",n,f)
+ else
+ return format("sequenced(a%s)",n)
+ end
+end
+local format_l=function()
+ n=n+1
+ return format("(a%s and 'true' or 'false')",n)
+end
+local format_L=function()
+ n=n+1
+ return format("(a%s and 'TRUE' or 'FALSE')",n)
+end
+local format_n=function()
+ n=n+1
+ return format("((a%s %% 1 == 0) and format('%%i',a%s) or tostring(a%s))",n,n,n)
+end
+local format_N=function(f)
+ n=n+1
+ if not f or f=="" then
+ f=".9"
+ end
+ return format("(((a%s %% 1 == 0) and format('%%i',a%s)) or lpegmatch(stripzero,format('%%%sf',a%s)))",n,n,f,n)
+end
+local format_a=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("autosingle(a%s,%q)",n,f)
+ else
+ return format("autosingle(a%s)",n)
+ end
+end
+local format_A=function(f)
+ n=n+1
+ if f and f~="" then
+ return format("autodouble(a%s,%q)",n,f)
+ else
+ return format("autodouble(a%s)",n)
+ end
+end
+local format_w=function(f)
+ n=n+1
+ f=tonumber(f)
+ if f then
+ return format("nspaces[%s+a%s]",f,n)
+ else
+ return format("nspaces[a%s]",n)
+ end
+end
+local format_W=function(f)
+ return format("nspaces[%s]",tonumber(f) or 0)
+end
+local format_m=function(f)
+ n=n+1
+ if not f or f=="" then
+ f=","
+ end
+ if f=="0" then
+ return format([[formattednumber(a%s,false)]],n)
+ else
+ return format([[formattednumber(a%s,%q,".")]],n,f)
+ end
+end
+local format_M=function(f)
+ n=n+1
+ if not f or f=="" then
+ f="."
+ end
+ if f=="0" then
+ return format([[formattednumber(a%s,false)]],n)
+ else
+ return format([[formattednumber(a%s,%q,",")]],n,f)
+ end
+end
+local format_z=function(f)
+ n=n+(tonumber(f) or 1)
+ return "''"
+end
+local format_rest=function(s)
+ return format("%q",s)
+end
+local format_extension=function(extensions,f,name)
+ local extension=extensions[name] or "tostring(%s)"
+ local f=tonumber(f) or 1
+ local w=find(extension,"%.%.%.")
+ if w then
+ if f==0 then
+ extension=gsub(extension,"%.%.%.","")
+ return extension
+ elseif f==1 then
+ extension=gsub(extension,"%.%.%.","%%s")
+ n=n+1
+ local a="a"..n
+ return format(extension,a,a)
+ elseif f<0 then
+ local a="a"..(n+f+1)
+ return format(extension,a,a)
+ else
+ extension=gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
+ local t={}
+ for i=1,f do
+ n=n+1
+ t[i]="a"..n
+ end
+ return format(extension,unpack(t))
+ end
+ else
+ extension=gsub(extension,"%%s",function()
+ n=n+1
+ return "a"..n
+ end)
+ return extension
+ end
+end
+local builder=Cs { "start",
+ start=(
+ (
+ P("%")/""*(
+ V("!")
++V("s")+V("q")+V("i")+V("d")+V("f")+V("F")+V("g")+V("G")+V("e")+V("E")+V("x")+V("X")+V("o")
++V("c")+V("C")+V("S")
++V("Q")
++V("n")
++V("N")
++V("k")
++V("r")+V("h")+V("H")+V("u")+V("U")+V("p")+V("b")+V("t")+V("T")+V("l")+V("L")+V("I")+V("w")
++V("W")
++V("a")
++V("A")
++V("j")+V("J")
++V("m")+V("M")
++V("z")
++V(">")
++V("<")
+ )+V("*")
+ )*(endofstring+Carg(1))
+ )^0,
+ ["s"]=(prefix_any*P("s"))/format_s,
+ ["q"]=(prefix_any*P("q"))/format_q,
+ ["i"]=(prefix_any*P("i"))/format_i,
+ ["d"]=(prefix_any*P("d"))/format_d,
+ ["f"]=(prefix_any*P("f"))/format_f,
+ ["F"]=(prefix_any*P("F"))/format_F,
+ ["g"]=(prefix_any*P("g"))/format_g,
+ ["G"]=(prefix_any*P("G"))/format_G,
+ ["e"]=(prefix_any*P("e"))/format_e,
+ ["E"]=(prefix_any*P("E"))/format_E,
+ ["x"]=(prefix_any*P("x"))/format_x,
+ ["X"]=(prefix_any*P("X"))/format_X,
+ ["o"]=(prefix_any*P("o"))/format_o,
+ ["S"]=(prefix_any*P("S"))/format_S,
+ ["Q"]=(prefix_any*P("Q"))/format_Q,
+ ["n"]=(prefix_any*P("n"))/format_n,
+ ["N"]=(prefix_any*P("N"))/format_N,
+ ["k"]=(prefix_sub*P("k"))/format_k,
+ ["c"]=(prefix_any*P("c"))/format_c,
+ ["C"]=(prefix_any*P("C"))/format_C,
+ ["r"]=(prefix_any*P("r"))/format_r,
+ ["h"]=(prefix_any*P("h"))/format_h,
+ ["H"]=(prefix_any*P("H"))/format_H,
+ ["u"]=(prefix_any*P("u"))/format_u,
+ ["U"]=(prefix_any*P("U"))/format_U,
+ ["p"]=(prefix_any*P("p"))/format_p,
+ ["b"]=(prefix_any*P("b"))/format_b,
+ ["t"]=(prefix_tab*P("t"))/format_t,
+ ["T"]=(prefix_tab*P("T"))/format_T,
+ ["l"]=(prefix_any*P("l"))/format_l,
+ ["L"]=(prefix_any*P("L"))/format_L,
+ ["I"]=(prefix_any*P("I"))/format_I,
+ ["w"]=(prefix_any*P("w"))/format_w,
+ ["W"]=(prefix_any*P("W"))/format_W,
+ ["j"]=(prefix_any*P("j"))/format_j,
+ ["J"]=(prefix_any*P("J"))/format_J,
+ ["m"]=(prefix_any*P("m"))/format_m,
+ ["M"]=(prefix_any*P("M"))/format_M,
+ ["z"]=(prefix_any*P("z"))/format_z,
+ ["a"]=(prefix_any*P("a"))/format_a,
+ ["A"]=(prefix_any*P("A"))/format_A,
+ ["<"]=(prefix_any*P("<"))/format_left,
+ [">"]=(prefix_any*P(">"))/format_right,
+ ["*"]=Cs(((1-P("%"))^1+P("%%")/"%%")^1)/format_rest,
+ ["?"]=Cs(((1-P("%"))^1 )^1)/format_rest,
+ ["!"]=Carg(2)*prefix_any*P("!")*C((1-P("!"))^1)*P("!")/format_extension,
+}
+local xx=setmetatable({},{ __index=function(t,k) local v=format("%02x",k) t[k]=v return v end })
+local XX=setmetatable({},{ __index=function(t,k) local v=format("%02X",k) t[k]=v return v end })
+local preset={
+ ["%02x"]=function(n) return xx[n] end,
+ ["%02X"]=function(n) return XX[n] end,
+}
+local direct=P("%")*(sign+space+period+digit)^0*S("sqidfgGeExXo")*endofstring/[[local format = string.format return function(str) return format("%0",str) end]]
+local function make(t,str)
+ local f=preset[str]
+ if f then
+ return f
+ end
+ local p=lpegmatch(direct,str)
+ if p then
+ f=loadstripped(p)()
+ else
+ n=0
+ p=lpegmatch(builder,str,1,t._connector_,t._extensions_)
+ if n>0 then
+ p=format(template,preamble,t._preamble_,arguments[n],p)
+ f=loadstripped(p,t._environment_)()
+ else
+ f=function() return str end
+ end
+ end
+ t[str]=f
+ return f
+end
+local function use(t,fmt,...)
+ return t[fmt](...)
+end
+strings.formatters={}
+function strings.formatters.new(noconcat)
+ local e={}
+ for k,v in next,environment do
+ e[k]=v
+ end
+ local t={
+ _type_="formatter",
+ _connector_=noconcat and "," or "..",
+ _extensions_={},
+ _preamble_="",
+ _environment_=e,
+ }
+ setmetatable(t,{ __index=make,__call=use })
+ return t
+end
+local formatters=strings.formatters.new()
+string.formatters=formatters
+string.formatter=function(str,...) return formatters[str](...) end
+local function add(t,name,template,preamble)
+ if type(t)=="table" and t._type_=="formatter" then
+ t._extensions_[name]=template or "%s"
+ if type(preamble)=="string" then
+ t._preamble_=preamble.."\n"..t._preamble_
+ elseif type(preamble)=="table" then
+ for k,v in next,preamble do
+ t._environment_[k]=v
+ end
+ end
+ end
+end
+strings.formatters.add=add
+patterns.xmlescape=Cs((P("<")/"&lt;"+P(">")/"&gt;"+P("&")/"&amp;"+P('"')/"&quot;"+anything)^0)
+patterns.texescape=Cs((C(S("#$%\\{}"))/"\\%1"+anything)^0)
+patterns.luaescape=Cs(((1-S('"\n'))^1+P('"')/'\\"'+P('\n')/'\\n"')^0)
+patterns.luaquoted=Cs(Cc('"')*((1-S('"\n'))^1+P('"')/'\\"'+P('\n')/'\\n"')^0*Cc('"'))
+add(formatters,"xml",[[lpegmatch(xmlescape,%s)]],{ xmlescape=patterns.xmlescape })
+add(formatters,"tex",[[lpegmatch(texescape,%s)]],{ texescape=patterns.texescape })
+add(formatters,"lua",[[lpegmatch(luaescape,%s)]],{ luaescape=patterns.luaescape })
+local dquote=patterns.dquote
+local equote=patterns.escaped+dquote/'\\"'+1
+local cquote=Cc('"')
+local pattern=Cs(dquote*(equote-P(-2))^0*dquote)
++Cs(cquote*(equote-space)^0*space*equote^0*cquote)
+function string.optionalquoted(str)
+ return lpegmatch(pattern,str) or str
+end
+local pattern=Cs((newline/(os.newline or "\r")+1)^0)
+function string.replacenewlines(str)
+ return lpegmatch(pattern,str)
+end
+function strings.newcollector()
+ local result,r={},0
+ return
+ function(fmt,str,...)
+ r=r+1
+ result[r]=str==nil and fmt or formatters[fmt](str,...)
+ end,
+ function(connector)
+ if result then
+ local str=concat(result,connector)
+ result,r={},0
+ return str
+ end
+ end
+end
+local f_16_16=formatters["%0.5N"]
+function number.to16dot16(n)
+ return f_16_16(n/65536.0)
+end
+if not string.explode then
+ local tsplitat=lpeg.tsplitat
+ local p_utf=patterns.utf8character
+ local p_check=C(p_utf)*(P("+")*Cc(true))^0
+ local p_split=Ct(C(p_utf)^0)
+ local p_space=Ct((C(1-P(" ")^1)+P(" ")^1)^0)
+ function string.explode(str,symbol)
+ if symbol=="" then
+ return lpegmatch(p_split,str)
+ elseif symbol then
+ local a,b=lpegmatch(p_check,symbol)
+ if b then
+ return lpegmatch(tsplitat(P(a)^1),str)
+ else
+ return lpegmatch(tsplitat(a),str)
+ end
+ else
+ return lpegmatch(p_space,str)
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['util-fil']={
+ version=1.001,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local tonumber=tonumber
+local byte=string.byte
+local char=string.char
+utilities=utilities or {}
+local files={}
+utilities.files=files
+local zerobased={}
+function files.open(filename,zb)
+ local f=io.open(filename,"rb")
+ if f then
+ zerobased[f]=zb or false
+ end
+ return f
+end
+function files.close(f)
+ zerobased[f]=nil
+ f:close()
+end
+function files.size(f)
+ local current=f:seek()
+ local size=f:seek("end")
+ f:seek("set",current)
+ return size
+end
+files.getsize=files.size
+function files.setposition(f,n)
+ if zerobased[f] then
+ f:seek("set",n)
+ else
+ f:seek("set",n-1)
+ end
+end
+function files.getposition(f)
+ if zerobased[f] then
+ return f:seek()
+ else
+ return f:seek()+1
+ end
+end
+function files.look(f,n,chars)
+ local p=f:seek()
+ local s=f:read(n)
+ f:seek("set",p)
+ if chars then
+ return s
+ else
+ return byte(s,1,#s)
+ end
+end
+function files.skip(f,n)
+ if n==1 then
+ f:read(n)
+ else
+ f:seek("set",f:seek()+n)
+ end
+end
+function files.readbyte(f)
+ return byte(f:read(1))
+end
+function files.readbytes(f,n)
+ return byte(f:read(n),1,n)
+end
+function files.readbytetable(f,n)
+ local s=f:read(n or 1)
+ return { byte(s,1,#s) }
+end
+function files.readchar(f)
+ return f:read(1)
+end
+function files.readstring(f,n)
+ return f:read(n or 1)
+end
+function files.readinteger1(f)
+ local n=byte(f:read(1))
+ if n>=0x80 then
+ return n-0x100
+ else
+ return n
+ end
+end
+files.readcardinal1=files.readbyte
+files.readcardinal=files.readcardinal1
+files.readinteger=files.readinteger1
+files.readsignedbyte=files.readinteger1
+function files.readcardinal2(f)
+ local a,b=byte(f:read(2),1,2)
+ return 0x100*a+b
+end
+function files.readcardinal2le(f)
+ local b,a=byte(f:read(2),1,2)
+ return 0x100*a+b
+end
+function files.readinteger2(f)
+ local a,b=byte(f:read(2),1,2)
+ if a>=0x80 then
+ return 0x100*a+b-0x10000
+ else
+ return 0x100*a+b
+ end
+end
+function files.readinteger2le(f)
+ local b,a=byte(f:read(2),1,2)
+ if a>=0x80 then
+ return 0x100*a+b-0x10000
+ else
+ return 0x100*a+b
+ end
+end
+function files.readcardinal3(f)
+ local a,b,c=byte(f:read(3),1,3)
+ return 0x10000*a+0x100*b+c
+end
+function files.readcardinal3le(f)
+ local c,b,a=byte(f:read(3),1,3)
+ return 0x10000*a+0x100*b+c
+end
+function files.readinteger3(f)
+ local a,b,c=byte(f:read(3),1,3)
+ if a>=0x80 then
+ return 0x10000*a+0x100*b+c-0x1000000
+ else
+ return 0x10000*a+0x100*b+c
+ end
+end
+function files.readinteger3le(f)
+ local c,b,a=byte(f:read(3),1,3)
+ if a>=0x80 then
+ return 0x10000*a+0x100*b+c-0x1000000
+ else
+ return 0x10000*a+0x100*b+c
+ end
+end
+function files.readcardinal4(f)
+ local a,b,c,d=byte(f:read(4),1,4)
+ return 0x1000000*a+0x10000*b+0x100*c+d
+end
+function files.readcardinal4le(f)
+ local d,c,b,a=byte(f:read(4),1,4)
+ return 0x1000000*a+0x10000*b+0x100*c+d
+end
+function files.readinteger4(f)
+ local a,b,c,d=byte(f:read(4),1,4)
+ if a>=0x80 then
+ return 0x1000000*a+0x10000*b+0x100*c+d-0x100000000
+ else
+ return 0x1000000*a+0x10000*b+0x100*c+d
+ end
+end
+function files.readinteger4le(f)
+ local d,c,b,a=byte(f:read(4),1,4)
+ if a>=0x80 then
+ return 0x1000000*a+0x10000*b+0x100*c+d-0x100000000
+ else
+ return 0x1000000*a+0x10000*b+0x100*c+d
+ end
+end
+function files.readfixed2(f)
+ local a,b=byte(f:read(2),1,2)
+ if a>=0x80 then
+ tonumber((a-0x100).."."..b)
+ else
+ tonumber((a ).."."..b)
+ end
+end
+function files.readfixed4(f)
+ local a,b,c,d=byte(f:read(4),1,4)
+ if a>=0x80 then
+ tonumber((0x100*a+b-0x10000).."."..(0x100*c+d))
+ else
+ tonumber((0x100*a+b ).."."..(0x100*c+d))
+ end
+end
+if bit32 then
+ local extract=bit32.extract
+ local band=bit32.band
+ function files.read2dot14(f)
+ local a,b=byte(f:read(2),1,2)
+ if a>=0x80 then
+ local n=-(0x100*a+b)
+ return-(extract(n,14,2)+(band(n,0x3FFF)/16384.0))
+ else
+ local n=0x100*a+b
+ return (extract(n,14,2)+(band(n,0x3FFF)/16384.0))
+ end
+ end
+end
+function files.skipshort(f,n)
+ f:read(2*(n or 1))
+end
+function files.skiplong(f,n)
+ f:read(4*(n or 1))
+end
+if bit32 then
+ local rshift=bit32.rshift
+ function files.writecardinal2(f,n)
+ local a=char(n%256)
+ n=rshift(n,8)
+ local b=char(n%256)
+ f:write(b,a)
+ end
+ function files.writecardinal4(f,n)
+ local a=char(n%256)
+ n=rshift(n,8)
+ local b=char(n%256)
+ n=rshift(n,8)
+ local c=char(n%256)
+ n=rshift(n,8)
+ local d=char(n%256)
+ f:write(d,c,b,a)
+ end
+ function files.writecardinal2le(f,n)
+ local a=char(n%256)
+ n=rshift(n,8)
+ local b=char(n%256)
+ f:write(a,b)
+ end
+ function files.writecardinal4le(f,n)
+ local a=char(n%256)
+ n=rshift(n,8)
+ local b=char(n%256)
+ n=rshift(n,8)
+ local c=char(n%256)
+ n=rshift(n,8)
+ local d=char(n%256)
+ f:write(a,b,c,d)
+ end
+else
+ local floor=math.floor
+ function files.writecardinal2(f,n)
+ local a=char(n%256)
+ n=floor(n/256)
+ local b=char(n%256)
+ f:write(b,a)
+ end
+ function files.writecardinal4(f,n)
+ local a=char(n%256)
+ n=floor(n/256)
+ local b=char(n%256)
+ n=floor(n/256)
+ local c=char(n%256)
+ n=floor(n/256)
+ local d=char(n%256)
+ f:write(d,c,b,a)
+ end
+ function files.writecardinal2le(f,n)
+ local a=char(n%256)
+ n=floor(n/256)
+ local b=char(n%256)
+ f:write(a,b)
+ end
+ function files.writecardinal4le(f,n)
+ local a=char(n%256)
+ n=floor(n/256)
+ local b=char(n%256)
+ n=floor(n/256)
+ local c=char(n%256)
+ n=floor(n/256)
+ local d=char(n%256)
+ f:write(a,b,c,d)
+ end
+end
+function files.writestring(f,s)
+ f:write(char(byte(s,1,#s)))
+end
+function files.writebyte(f,b)
+ f:write(char(b))
+end
+if fio and fio.readcardinal1 then
+ files.readcardinal1=fio.readcardinal1
+ files.readcardinal2=fio.readcardinal2
+ files.readcardinal3=fio.readcardinal3
+ files.readcardinal4=fio.readcardinal4
+ files.readcardinal1le=fio.readcardinal1le or files.readcardinal1le
+ files.readcardinal2le=fio.readcardinal2le or files.readcardinal2le
+ files.readcardinal3le=fio.readcardinal3le or files.readcardinal3le
+ files.readcardinal4le=fio.readcardinal4le or files.readcardinal4le
+ files.readinteger1=fio.readinteger1
+ files.readinteger2=fio.readinteger2
+ files.readinteger3=fio.readinteger3
+ files.readinteger4=fio.readinteger4
+ files.readinteger1le=fio.readinteger1le or files.readinteger1le
+ files.readinteger2le=fio.readinteger2le or files.readinteger2le
+ files.readinteger3le=fio.readinteger3le or files.readinteger3le
+ files.readinteger4le=fio.readinteger4le or files.readinteger4le
+ files.readfixed2=fio.readfixed2
+ files.readfixed4=fio.readfixed4
+ files.read2dot14=fio.read2dot14
+ files.setposition=fio.setposition
+ files.getposition=fio.getposition
+ files.readbyte=files.readcardinal1
+ files.readsignedbyte=files.readinteger1
+ files.readcardinal=files.readcardinal1
+ files.readinteger=files.readinteger1
+ local skipposition=fio.skipposition
+ files.skipposition=skipposition
+ files.readbytes=fio.readbytes
+ files.readbytetable=fio.readbytetable
+ function files.skipshort(f,n)
+ skipposition(f,2*(n or 1))
+ end
+ function files.skiplong(f,n)
+ skipposition(f,4*(n or 1))
+ end
+end
+if fio and fio.writecardinal1 then
+ files.writecardinal1=fio.writecardinal1
+ files.writecardinal2=fio.writecardinal2
+ files.writecardinal3=fio.writecardinal3
+ files.writecardinal4=fio.writecardinal4
+ files.writecardinal1le=fio.writecardinal1le
+ files.writecardinal2le=fio.writecardinal2le
+ files.writecardinal3le=fio.writecardinal3le
+ files.writecardinal4le=fio.writecardinal4le
+ files.writeinteger1=fio.writeinteger1 or fio.writecardinal1
+ files.writeinteger2=fio.writeinteger2 or fio.writecardinal2
+ files.writeinteger3=fio.writeinteger3 or fio.writecardinal3
+ files.writeinteger4=fio.writeinteger4 or fio.writecardinal4
+ files.writeinteger1le=files.writeinteger1le or fio.writecardinal1le
+ files.writeinteger2le=files.writeinteger2le or fio.writecardinal2le
+ files.writeinteger3le=files.writeinteger3le or fio.writecardinal3le
+ files.writeinteger4le=files.writeinteger4le or fio.writecardinal4le
+end
+if fio and fio.readcardinaltable then
+ files.readcardinaltable=fio.readcardinaltable
+ files.readintegertable=fio.readintegertable
+else
+ local readcardinal1=files.readcardinal1
+ local readcardinal2=files.readcardinal2
+ local readcardinal3=files.readcardinal3
+ local readcardinal4=files.readcardinal4
+ function files.readcardinaltable(f,n,b)
+ local t={}
+ if b==1 then for i=1,n do t[i]=readcardinal1(f) end
+ elseif b==2 then for i=1,n do t[i]=readcardinal2(f) end
+ elseif b==3 then for i=1,n do t[i]=readcardinal3(f) end
+ elseif b==4 then for i=1,n do t[i]=readcardinal4(f) end end
+ return t
+ end
+ local readinteger1=files.readinteger1
+ local readinteger2=files.readinteger2
+ local readinteger3=files.readinteger3
+ local readinteger4=files.readinteger4
+ function files.readintegertable(f,n,b)
+ local t={}
+ if b==1 then for i=1,n do t[i]=readinteger1(f) end
+ elseif b==2 then for i=1,n do t[i]=readinteger2(f) end
+ elseif b==3 then for i=1,n do t[i]=readinteger3(f) end
+ elseif b==4 then for i=1,n do t[i]=readinteger4(f) end end
+ return t
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luat-basics-gen']={
+ version=1.100,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local match,gmatch,gsub,lower=string.match,string.gmatch,string.gsub,string.lower
+local formatters,split,format,dump=string.formatters,string.split,string.format,string.dump
+local loadfile,type=loadfile,type
+local setmetatable,getmetatable,collectgarbage=setmetatable,getmetatable,collectgarbage
+local floor=math.floor
+local dummyfunction=function()
+end
+local dummyreporter=function(c)
+ return function(f,...)
+ local r=texio.reporter or texio.write_nl
+ if f then
+ r(c.." : "..(formatters or format)(f,...))
+ else
+ r("")
+ end
+ end
+end
+local dummyreport=function(c,f,...)
+ local r=texio.reporter or texio.write_nl
+ if f then
+ r(c.." : "..(formatters or format)(f,...))
+ else
+ r("")
+ end
+end
+statistics={
+ register=dummyfunction,
+ starttiming=dummyfunction,
+ stoptiming=dummyfunction,
+ elapsedtime=nil,
+}
+directives={
+ register=dummyfunction,
+ enable=dummyfunction,
+ disable=dummyfunction,
+}
+trackers={
+ register=dummyfunction,
+ enable=dummyfunction,
+ disable=dummyfunction,
+}
+experiments={
+ register=dummyfunction,
+ enable=dummyfunction,
+ disable=dummyfunction,
+}
+storage={
+ register=dummyfunction,
+ shared={},
+}
+logs={
+ new=dummyreporter,
+ reporter=dummyreporter,
+ messenger=dummyreporter,
+ report=dummyreport,
+}
+callbacks={
+ register=function(n,f)
+ return callback.register(n,f)
+ end,
+}
+utilities=utilities or {}
+utilities.storage=utilities.storage or {
+ allocate=function(t)
+ return t or {}
+ end,
+ mark=function(t)
+ return t or {}
+ end,
+}
+utilities.parsers=utilities.parsers or {
+ settings_to_array=function(s)
+ return split(s,",")
+ end,
+ settings_to_hash=function(s)
+ local t={}
+ for k,v in gmatch(s,"([^%s,=]+)=([^%s,]+)") do
+ t[k]=v
+ end
+ return t
+ end,
+ settings_to_hash_colon_too=function(s)
+ local t={}
+ for k,v in gmatch(s,"([^%s,=:]+)[=:]([^%s,]+)") do
+ t[k]=v
+ end
+ return t
+ end,
+}
+characters=characters or {
+ data={}
+}
+texconfig.kpse_init=true
+resolvers=resolvers or {}
+local remapper={
+ otf="opentype fonts",
+ ttf="truetype fonts",
+ ttc="truetype fonts",
+ cid="cid maps",
+ cidmap="cid maps",
+ pfb="type1 fonts",
+ afm="afm",
+ enc="enc files",
+ lua="tex",
+}
+function resolvers.findfile(name,fileformat)
+ name=gsub(name,"\\","/")
+ if not fileformat or fileformat=="" then
+ fileformat=file.suffix(name)
+ if fileformat=="" then
+ fileformat="tex"
+ end
+ end
+ fileformat=lower(fileformat)
+ fileformat=remapper[fileformat] or fileformat
+ local found=kpse.find_file(name,fileformat)
+ if not found or found=="" then
+ found=kpse.find_file(name,"other text files")
+ end
+ return found
+end
+resolvers.findbinfile=resolvers.findfile
+function resolvers.loadbinfile(filename,filetype)
+ local data=io.loaddata(filename)
+ return true,data,#data
+end
+function resolvers.resolve(s)
+ return s
+end
+function resolvers.unresolve(s)
+ return s
+end
+caches={}
+local writable=nil
+local readables={}
+local usingjit=jit
+if not caches.namespace or caches.namespace=="" or caches.namespace=="context" then
+ caches.namespace='generic'
+end
+do
+ local cachepaths=kpse.expand_var('$TEXMFCACHE') or ""
+ if cachepaths=="" or cachepaths=="$TEXMFCACHE" then
+ cachepaths=kpse.expand_var('$TEXMFVAR') or ""
+ end
+ if cachepaths=="" or cachepaths=="$TEXMFVAR" then
+ cachepaths=kpse.expand_var('$VARTEXMF') or ""
+ end
+ if cachepaths=="" then
+ local fallbacks={ "TMPDIR","TEMPDIR","TMP","TEMP","HOME","HOMEPATH" }
+ for i=1,#fallbacks do
+ cachepaths=os.getenv(fallbacks[i]) or ""
+ if cachepath~="" and lfs.isdir(cachepath) then
+ break
+ end
+ end
+ end
+ if cachepaths=="" then
+ cachepaths="."
+ end
+ cachepaths=split(cachepaths,os.type=="windows" and ";" or ":")
+ for i=1,#cachepaths do
+ local cachepath=cachepaths[i]
+ if not lfs.isdir(cachepath) then
+ lfs.mkdirs(cachepath)
+ if lfs.isdir(cachepath) then
+ logs.report("system","creating cache path '%s'",cachepath)
+ end
+ end
+ if file.is_writable(cachepath) then
+ writable=file.join(cachepath,"luatex-cache")
+ lfs.mkdir(writable)
+ writable=file.join(writable,caches.namespace)
+ lfs.mkdir(writable)
+ break
+ end
+ end
+ for i=1,#cachepaths do
+ if file.is_readable(cachepaths[i]) then
+ readables[#readables+1]=file.join(cachepaths[i],"luatex-cache",caches.namespace)
+ end
+ end
+ if not writable then
+ logs.report("system","no writeable cache path, quiting")
+ os.exit()
+ elseif #readables==0 then
+ logs.report("system","no readable cache path, quiting")
+ os.exit()
+ elseif #readables==1 and readables[1]==writable then
+ logs.report("system","using cache '%s'",writable)
+ else
+ logs.report("system","using write cache '%s'",writable)
+ logs.report("system","using read cache '%s'",table.concat(readables," "))
+ end
+end
+function caches.getwritablepath(category,subcategory)
+ local path=file.join(writable,category)
+ lfs.mkdir(path)
+ path=file.join(path,subcategory)
+ lfs.mkdir(path)
+ return path
+end
+function caches.getreadablepaths(category,subcategory)
+ local t={}
+ for i=1,#readables do
+ t[i]=file.join(readables[i],category,subcategory)
+ end
+ return t
+end
+local function makefullname(path,name)
+ if path and path~="" then
+ return file.addsuffix(file.join(path,name),"lua"),file.addsuffix(file.join(path,name),usingjit and "lub" or "luc")
+ end
+end
+function caches.is_writable(path,name)
+ local fullname=makefullname(path,name)
+ return fullname and file.is_writable(fullname)
+end
+function caches.loaddata(readables,name,writable)
+ for i=1,#readables do
+ local path=readables[i]
+ local loader=false
+ local luaname,lucname=makefullname(path,name)
+ if lfs.isfile(lucname) then
+ logs.report("system","loading luc file '%s'",lucname)
+ loader=loadfile(lucname)
+ end
+ if not loader and lfs.isfile(luaname) then
+ local luacrap,lucname=makefullname(writable,name)
+ logs.report("system","compiling luc file '%s'",lucname)
+ if lfs.isfile(lucname) then
+ loader=loadfile(lucname)
+ end
+ caches.compile(data,luaname,lucname)
+ if lfs.isfile(lucname) then
+ logs.report("system","loading luc file '%s'",lucname)
+ loader=loadfile(lucname)
+ else
+ logs.report("system","error in loading luc file '%s'",lucname)
+ end
+ if not loader then
+ logs.report("system","loading lua file '%s'",luaname)
+ loader=loadfile(luaname)
+ else
+ logs.report("system","error in loading lua file '%s'",luaname)
+ end
+ end
+ if loader then
+ loader=loader()
+ collectgarbage("step")
+ return loader
+ end
+ end
+ return false
+end
+function caches.savedata(path,name,data)
+ local luaname,lucname=makefullname(path,name)
+ if luaname then
+ logs.report("system","saving lua file '%s'",luaname)
+ table.tofile(luaname,data,true)
+ if lucname and type(caches.compile)=="function" then
+ os.remove(lucname)
+ logs.report("system","saving luc file '%s'",lucname)
+ caches.compile(data,luaname,lucname)
+ end
+ end
+end
+function caches.compile(data,luaname,lucname)
+ local d=io.loaddata(luaname)
+ if not d or d=="" then
+ d=table.serialize(data,true)
+ end
+ if d and d~="" then
+ local f=io.open(lucname,'wb')
+ if f then
+ local s=loadstring(d)
+ if s then
+ f:write(dump(s,true))
+ end
+ f:close()
+ end
+ end
+end
+function table.setmetatableindex(t,f)
+ if type(t)~="table" then
+ f,t=t,{}
+ end
+ local m=getmetatable(t)
+ if f=="table" then
+ f=function(t,k) local v={} t[k]=v return v end
+ end
+ if m then
+ m.__index=f
+ else
+ setmetatable(t,{ __index=f })
+ end
+ return t
+end
+function table.makeweak(t)
+ local m=getmetatable(t)
+ if m then
+ m.__mode="v"
+ else
+ setmetatable(t,{ __mode="v" })
+ end
+ return t
+end
+arguments={}
+if arg then
+ for i=1,#arg do
+ local k,v=match(arg[i],"^%-%-([^=]+)=?(.-)$")
+ if k and v then
+ arguments[k]=v
+ end
+ end
+end
+if not number.idiv then
+ function number.idiv(i,d)
+ return floor(i/d)
+ end
+end
+local u=unicode and unicode.utf8
+if u then
+ utf.lower=u.lower
+ utf.upper=u.upper
+ utf.char=u.char
+ utf.byte=u.byte
+ utf.len=u.len
+ if lpeg.setutfcasers then
+ lpeg.setutfcasers(u.lower,u.upper)
+ end
+ local bytepairs=string.bytepairs
+ local utfchar=utf.char
+ local concat=table.concat
+ function utf.utf16_to_utf8_be(s)
+ if not s then
+ return nil
+ elseif s=="" then
+ return ""
+ end
+ local result,r,more={},0,0
+ for left,right in bytepairs(s) do
+ if right then
+ local now=256*left+right
+ if more>0 then
+ now=(more-0xD800)*0x400+(now-0xDC00)+0x10000
+ more=0
+ r=r+1
+ result[r]=utfchar(now)
+ elseif now>=0xD800 and now<=0xDBFF then
+ more=now
+ else
+ r=r+1
+ result[r]=utfchar(now)
+ end
+ end
+ end
+ return concat(result)
+ end
+ local characters=string.utfcharacters
+ function utf.split(str)
+ local t,n={},0
+ for s in characters(str) do
+ n=n+1
+ t[n]=s
+ end
+ return t
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['data-con']={
+ version=1.100,
+ comment="companion to luat-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local format,lower,gsub=string.format,string.lower,string.gsub
+local trace_cache=false trackers.register("resolvers.cache",function(v) trace_cache=v end)
+local trace_containers=false trackers.register("resolvers.containers",function(v) trace_containers=v end)
+local trace_storage=false trackers.register("resolvers.storage",function(v) trace_storage=v end)
+containers=containers or {}
+local containers=containers
+containers.usecache=true
+local report_containers=logs.reporter("resolvers","containers")
+local allocated={}
+local mt={
+ __index=function(t,k)
+ if k=="writable" then
+ local writable=caches.getwritablepath(t.category,t.subcategory) or { "." }
+ t.writable=writable
+ return writable
+ elseif k=="readables" then
+ local readables=caches.getreadablepaths(t.category,t.subcategory) or { "." }
+ t.readables=readables
+ return readables
+ end
+ end,
+ __storage__=true
+}
+function containers.define(category,subcategory,version,enabled)
+ if category and subcategory then
+ local c=allocated[category]
+ if not c then
+ c={}
+ allocated[category]=c
+ end
+ local s=c[subcategory]
+ if not s then
+ s={
+ category=category,
+ subcategory=subcategory,
+ storage={},
+ enabled=enabled,
+ version=version or math.pi,
+ trace=false,
+ }
+ setmetatable(s,mt)
+ c[subcategory]=s
+ end
+ return s
+ end
+end
+function containers.is_usable(container,name)
+ return container.enabled and caches and caches.is_writable(container.writable,name)
+end
+function containers.is_valid(container,name)
+ if name and name~="" then
+ local storage=container.storage[name]
+ return storage and storage.cache_version==container.version
+ else
+ return false
+ end
+end
+function containers.read(container,name)
+ local storage=container.storage
+ local stored=storage[name]
+ if not stored and container.enabled and caches and containers.usecache then
+ stored=caches.loaddata(container.readables,name,container.writable)
+ if stored and stored.cache_version==container.version then
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","load",container.subcategory,name)
+ end
+ else
+ stored=nil
+ end
+ storage[name]=stored
+ elseif stored then
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","reuse",container.subcategory,name)
+ end
+ end
+ return stored
+end
+function containers.write(container,name,data)
+ if data then
+ data.cache_version=container.version
+ if container.enabled and caches then
+ local unique,shared=data.unique,data.shared
+ data.unique,data.shared=nil,nil
+ caches.savedata(container.writable,name,data)
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","save",container.subcategory,name)
+ end
+ data.unique,data.shared=unique,shared
+ end
+ if trace_cache or trace_containers then
+ report_containers("action %a, category %a, name %a","store",container.subcategory,name)
+ end
+ container.storage[name]=data
+ end
+ return data
+end
+function containers.content(container,name)
+ return container.storage[name]
+end
+function containers.cleanname(name)
+ return (gsub(lower(name),"[^%w\128-\255]+","-"))
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-fonts-nod']={
+ version=1.001,
+ comment="companion to luatex-fonts.lua",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+if tex.attribute[0]~=0 then
+ texio.write_nl("log","!")
+ texio.write_nl("log","! Attribute 0 is reserved for ConTeXt's font feature management and has to be")
+ texio.write_nl("log","! set to zero. Also, some attributes in the range 1-255 are used for special")
+ texio.write_nl("log","! purposes so setting them at the TeX end might break the font handler.")
+ texio.write_nl("log","!")
+ tex.attribute[0]=0
+end
+attributes=attributes or {}
+attributes.unsetvalue=-0x7FFFFFFF
+local numbers,last={},127
+attributes.private=attributes.private or function(name)
+ local number=numbers[name]
+ if not number then
+ if last<255 then
+ last=last+1
+ end
+ number=last
+ numbers[name]=number
+ end
+ return number
+end
+nodes={}
+nodes.handlers={}
+local nodecodes={}
+local glyphcodes=node.subtypes("glyph")
+local disccodes=node.subtypes("disc")
+for k,v in next,node.types() do
+ v=string.gsub(v,"_","")
+ nodecodes[k]=v
+ nodecodes[v]=k
+end
+for k,v in next,glyphcodes do
+ glyphcodes[v]=k
+end
+for k,v in next,disccodes do
+ disccodes[v]=k
+end
+nodes.nodecodes=nodecodes
+nodes.glyphcodes=glyphcodes
+nodes.disccodes=disccodes
+nodes.handlers.protectglyphs=node.protect_glyphs
+nodes.handlers.unprotectglyphs=node.unprotect_glyphs
+local direct=node.direct
+local nuts={}
+nodes.nuts=nuts
+local tonode=direct.tonode
+local tonut=direct.todirect
+nodes.tonode=tonode
+nodes.tonut=tonut
+nuts.tonode=tonode
+nuts.tonut=tonut
+nuts.getattr=direct.get_attribute
+nuts.getboth=direct.getboth
+nuts.getchar=direct.getchar
+nuts.getcomponents=direct.getcomponents
+nuts.getdirection=direct.getdirection
+nuts.getdisc=direct.getdisc
+nuts.getfield=direct.getfield
+nuts.getfont=direct.getfont
+nuts.getid=direct.getid
+nuts.getkern=direct.getkern
+nuts.getlist=direct.getlist
+nuts.getnext=direct.getnext
+nuts.getoffsets=direct.getoffsets
+nuts.getprev=direct.getprev
+nuts.getsubtype=direct.getsubtype
+nuts.getwidth=direct.getwidth
+nuts.setattr=direct.setfield
+nuts.setboth=direct.setboth
+nuts.setchar=direct.setchar
+nuts.setcomponents=direct.setcomponents
+nuts.setdirection=direct.setdirection
+nuts.setdisc=direct.setdisc
+nuts.setfield=setfield
+nuts.setkern=direct.setkern
+nuts.setlink=direct.setlink
+nuts.setlist=direct.setlist
+nuts.setnext=direct.setnext
+nuts.setoffsets=direct.setoffsets
+nuts.setprev=direct.setprev
+nuts.setsplit=direct.setsplit
+nuts.setsubtype=direct.setsubtype
+nuts.setwidth=direct.setwidth
+nuts.getglyphdata=nuts.getattr
+nuts.setglyphdata=nuts.setattr
+nuts.ischar=direct.is_char
+nuts.isglyph=direct.is_glyph
+nuts.copy=direct.copy
+nuts.copy_list=direct.copy_list
+nuts.copy_node=direct.copy
+nuts.delete=direct.delete
+nuts.end_of_math=direct.end_of_math
+nuts.flush=direct.flush
+nuts.flush_list=direct.flush_list
+nuts.flush_node=direct.flush_node
+nuts.free=direct.free
+nuts.insert_after=direct.insert_after
+nuts.insert_before=direct.insert_before
+nuts.is_node=direct.is_node
+nuts.kerning=direct.kerning
+nuts.ligaturing=direct.ligaturing
+nuts.new=direct.new
+nuts.remove=direct.remove
+nuts.tail=direct.tail
+nuts.traverse=direct.traverse
+nuts.traverse_char=direct.traverse_char
+nuts.traverse_glyph=direct.traverse_glyph
+nuts.traverse_id=direct.traverse_id
+local propertydata=direct.get_properties_table()
+nodes.properties={ data=propertydata }
+if direct.set_properties_mode then
+ direct.set_properties_mode(true,true)
+ function direct.set_properties_mode() end
+end
+nuts.getprop=function(n,k)
+ local p=propertydata[n]
+ if p then
+ return p[k]
+ end
+end
+nuts.setprop=function(n,k,v)
+ if v then
+ local p=propertydata[n]
+ if p then
+ p[k]=v
+ else
+ propertydata[n]={ [k]=v }
+ end
+ end
+end
+nodes.setprop=nodes.setproperty
+nodes.getprop=nodes.getproperty
+local setprev=nuts.setprev
+local setnext=nuts.setnext
+local getnext=nuts.getnext
+local setlink=nuts.setlink
+local getfield=nuts.getfield
+local setfield=nuts.setfield
+local getcomponents=nuts.getcomponents
+local setcomponents=nuts.setcomponents
+local find_tail=nuts.tail
+local flush_list=nuts.flush_list
+local flush_node=nuts.flush_node
+local traverse_id=nuts.traverse_id
+local copy_node=nuts.copy_node
+local glyph_code=nodes.nodecodes.glyph
+function nuts.copy_no_components(g,copyinjection)
+ local components=getcomponents(g)
+ if components then
+ setcomponents(g)
+ local n=copy_node(g)
+ if copyinjection then
+ copyinjection(n,g)
+ end
+ setcomponents(g,components)
+ return n
+ else
+ local n=copy_node(g)
+ if copyinjection then
+ copyinjection(n,g)
+ end
+ return n
+ end
+end
+function nuts.copy_only_glyphs(current)
+ local head=nil
+ local previous=nil
+ for n in traverse_id(glyph_code,current) do
+ n=copy_node(n)
+ if head then
+ setlink(previous,n)
+ else
+ head=n
+ end
+ previous=n
+ end
+ return head
+end
+nuts.uses_font=direct.uses_font
+do
+ local dummy=tonut(node.new("glyph"))
+ nuts.traversers={
+ glyph=nuts.traverse_id(nodecodes.glyph,dummy),
+ glue=nuts.traverse_id(nodecodes.glue,dummy),
+ disc=nuts.traverse_id(nodecodes.disc,dummy),
+ boundary=nuts.traverse_id(nodecodes.boundary,dummy),
+ char=nuts.traverse_char(dummy),
+ node=nuts.traverse(dummy),
+ }
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+
+characters=characters or {}
+characters.blockrange={}
+characters.classifiers={
+ [768]=5,
+ [769]=5,
+ [770]=5,
+ [771]=5,
+ [772]=5,
+ [773]=5,
+ [774]=5,
+ [775]=5,
+ [776]=5,
+ [777]=5,
+ [778]=5,
+ [779]=5,
+ [780]=5,
+ [781]=5,
+ [782]=5,
+ [783]=5,
+ [784]=5,
+ [785]=5,
+ [786]=5,
+ [787]=5,
+ [788]=5,
+ [789]=5,
+ [790]=5,
+ [791]=5,
+ [792]=5,
+ [793]=5,
+ [794]=5,
+ [795]=5,
+ [796]=5,
+ [797]=5,
+ [798]=5,
+ [799]=5,
+ [800]=5,
+ [801]=5,
+ [802]=5,
+ [803]=5,
+ [804]=5,
+ [805]=5,
+ [806]=5,
+ [807]=5,
+ [808]=5,
+ [809]=5,
+ [810]=5,
+ [811]=5,
+ [812]=5,
+ [813]=5,
+ [814]=5,
+ [815]=5,
+ [816]=5,
+ [817]=5,
+ [818]=5,
+ [819]=5,
+ [820]=5,
+ [821]=5,
+ [822]=5,
+ [823]=5,
+ [824]=5,
+ [825]=5,
+ [826]=5,
+ [827]=5,
+ [828]=5,
+ [829]=5,
+ [830]=5,
+ [831]=5,
+ [832]=5,
+ [833]=5,
+ [834]=5,
+ [835]=5,
+ [836]=5,
+ [837]=5,
+ [838]=5,
+ [839]=5,
+ [840]=5,
+ [841]=5,
+ [842]=5,
+ [843]=5,
+ [844]=5,
+ [845]=5,
+ [846]=5,
+ [847]=5,
+ [848]=5,
+ [849]=5,
+ [850]=5,
+ [851]=5,
+ [852]=5,
+ [853]=5,
+ [854]=5,
+ [855]=5,
+ [856]=5,
+ [857]=5,
+ [858]=5,
+ [859]=5,
+ [860]=5,
+ [861]=5,
+ [862]=5,
+ [863]=5,
+ [864]=5,
+ [865]=5,
+ [866]=5,
+ [867]=5,
+ [868]=5,
+ [869]=5,
+ [870]=5,
+ [871]=5,
+ [872]=5,
+ [873]=5,
+ [874]=5,
+ [875]=5,
+ [876]=5,
+ [877]=5,
+ [878]=5,
+ [879]=5,
+ [1155]=5,
+ [1156]=5,
+ [1157]=5,
+ [1158]=5,
+ [1159]=5,
+ [1425]=5,
+ [1426]=5,
+ [1427]=5,
+ [1428]=5,
+ [1429]=5,
+ [1430]=5,
+ [1431]=5,
+ [1432]=5,
+ [1433]=5,
+ [1434]=5,
+ [1435]=5,
+ [1436]=5,
+ [1437]=5,
+ [1438]=5,
+ [1439]=5,
+ [1440]=5,
+ [1441]=5,
+ [1442]=5,
+ [1443]=5,
+ [1444]=5,
+ [1445]=5,
+ [1446]=5,
+ [1447]=5,
+ [1448]=5,
+ [1449]=5,
+ [1450]=5,
+ [1451]=5,
+ [1452]=5,
+ [1453]=5,
+ [1454]=5,
+ [1455]=5,
+ [1456]=5,
+ [1457]=5,
+ [1458]=5,
+ [1459]=5,
+ [1460]=5,
+ [1461]=5,
+ [1462]=5,
+ [1463]=5,
+ [1464]=5,
+ [1465]=5,
+ [1466]=5,
+ [1467]=5,
+ [1468]=5,
+ [1469]=5,
+ [1471]=5,
+ [1473]=5,
+ [1474]=5,
+ [1476]=5,
+ [1477]=5,
+ [1479]=5,
+ [1536]=4,
+ [1537]=4,
+ [1538]=4,
+ [1539]=4,
+ [1540]=4,
+ [1541]=4,
+ [1542]=6,
+ [1543]=6,
+ [1544]=4,
+ [1545]=6,
+ [1546]=6,
+ [1547]=4,
+ [1548]=6,
+ [1549]=6,
+ [1550]=6,
+ [1551]=6,
+ [1552]=5,
+ [1553]=5,
+ [1554]=5,
+ [1555]=5,
+ [1556]=5,
+ [1557]=5,
+ [1558]=5,
+ [1559]=5,
+ [1560]=5,
+ [1561]=5,
+ [1562]=5,
+ [1563]=6,
+ [1564]=6,
+ [1566]=6,
+ [1567]=6,
+ [1568]=2,
+ [1569]=4,
+ [1570]=3,
+ [1571]=3,
+ [1572]=3,
+ [1573]=3,
+ [1574]=2,
+ [1575]=3,
+ [1576]=2,
+ [1577]=3,
+ [1578]=2,
+ [1579]=2,
+ [1580]=2,
+ [1581]=2,
+ [1582]=2,
+ [1583]=3,
+ [1584]=3,
+ [1585]=3,
+ [1586]=3,
+ [1587]=2,
+ [1588]=2,
+ [1589]=2,
+ [1590]=2,
+ [1591]=2,
+ [1592]=2,
+ [1593]=2,
+ [1594]=2,
+ [1595]=2,
+ [1596]=2,
+ [1597]=2,
+ [1598]=2,
+ [1599]=2,
+ [1600]=2,
+ [1601]=2,
+ [1602]=2,
+ [1603]=2,
+ [1604]=2,
+ [1605]=2,
+ [1606]=2,
+ [1607]=2,
+ [1608]=3,
+ [1609]=2,
+ [1610]=2,
+ [1611]=5,
+ [1612]=5,
+ [1613]=5,
+ [1614]=5,
+ [1615]=5,
+ [1616]=5,
+ [1617]=5,
+ [1618]=5,
+ [1619]=5,
+ [1620]=5,
+ [1621]=5,
+ [1622]=5,
+ [1623]=5,
+ [1624]=5,
+ [1625]=5,
+ [1626]=5,
+ [1627]=5,
+ [1628]=5,
+ [1629]=5,
+ [1630]=5,
+ [1631]=5,
+ [1632]=6,
+ [1633]=6,
+ [1634]=6,
+ [1635]=6,
+ [1636]=6,
+ [1637]=6,
+ [1638]=6,
+ [1639]=6,
+ [1640]=6,
+ [1641]=6,
+ [1642]=6,
+ [1643]=6,
+ [1644]=6,
+ [1645]=6,
+ [1646]=2,
+ [1647]=2,
+ [1648]=5,
+ [1649]=3,
+ [1650]=3,
+ [1651]=3,
+ [1652]=4,
+ [1653]=3,
+ [1654]=3,
+ [1655]=3,
+ [1656]=2,
+ [1657]=2,
+ [1658]=2,
+ [1659]=2,
+ [1660]=2,
+ [1661]=2,
+ [1662]=2,
+ [1663]=2,
+ [1664]=2,
+ [1665]=2,
+ [1666]=2,
+ [1667]=2,
+ [1668]=2,
+ [1669]=2,
+ [1670]=2,
+ [1671]=2,
+ [1672]=3,
+ [1673]=3,
+ [1674]=3,
+ [1675]=3,
+ [1676]=3,
+ [1677]=3,
+ [1678]=3,
+ [1679]=3,
+ [1680]=3,
+ [1681]=3,
+ [1682]=3,
+ [1683]=3,
+ [1684]=3,
+ [1685]=3,
+ [1686]=3,
+ [1687]=3,
+ [1688]=3,
+ [1689]=3,
+ [1690]=2,
+ [1691]=2,
+ [1692]=2,
+ [1693]=2,
+ [1694]=2,
+ [1695]=2,
+ [1696]=2,
+ [1697]=2,
+ [1698]=2,
+ [1699]=2,
+ [1700]=2,
+ [1701]=2,
+ [1702]=2,
+ [1703]=2,
+ [1704]=2,
+ [1705]=2,
+ [1706]=2,
+ [1707]=2,
+ [1708]=2,
+ [1709]=2,
+ [1710]=2,
+ [1711]=2,
+ [1712]=2,
+ [1713]=2,
+ [1714]=2,
+ [1715]=2,
+ [1716]=2,
+ [1717]=2,
+ [1718]=2,
+ [1719]=2,
+ [1720]=2,
+ [1721]=2,
+ [1722]=2,
+ [1723]=2,
+ [1724]=2,
+ [1725]=2,
+ [1726]=2,
+ [1727]=2,
+ [1728]=3,
+ [1729]=2,
+ [1730]=2,
+ [1731]=3,
+ [1732]=3,
+ [1733]=3,
+ [1734]=3,
+ [1735]=3,
+ [1736]=3,
+ [1737]=3,
+ [1738]=3,
+ [1739]=3,
+ [1740]=2,
+ [1741]=3,
+ [1742]=2,
+ [1743]=3,
+ [1744]=2,
+ [1745]=2,
+ [1746]=3,
+ [1747]=3,
+ [1748]=6,
+ [1749]=3,
+ [1750]=5,
+ [1751]=5,
+ [1752]=5,
+ [1753]=5,
+ [1754]=5,
+ [1755]=5,
+ [1756]=5,
+ [1757]=4,
+ [1758]=6,
+ [1759]=5,
+ [1760]=5,
+ [1761]=5,
+ [1762]=5,
+ [1763]=5,
+ [1764]=5,
+ [1765]=6,
+ [1766]=6,
+ [1767]=5,
+ [1768]=5,
+ [1769]=6,
+ [1770]=5,
+ [1771]=5,
+ [1772]=5,
+ [1773]=5,
+ [1774]=3,
+ [1775]=3,
+ [1776]=6,
+ [1777]=6,
+ [1778]=6,
+ [1779]=6,
+ [1780]=6,
+ [1781]=6,
+ [1782]=6,
+ [1783]=6,
+ [1784]=6,
+ [1785]=6,
+ [1786]=2,
+ [1787]=2,
+ [1788]=2,
+ [1789]=6,
+ [1790]=6,
+ [1791]=2,
+ [1792]=6,
+ [1793]=6,
+ [1794]=6,
+ [1795]=6,
+ [1796]=6,
+ [1797]=6,
+ [1798]=6,
+ [1799]=6,
+ [1800]=6,
+ [1801]=6,
+ [1802]=6,
+ [1803]=6,
+ [1804]=6,
+ [1805]=6,
+ [1808]=3,
+ [1809]=5,
+ [1810]=2,
+ [1811]=2,
+ [1812]=2,
+ [1813]=3,
+ [1814]=3,
+ [1815]=3,
+ [1816]=3,
+ [1817]=3,
+ [1818]=2,
+ [1819]=2,
+ [1820]=2,
+ [1821]=2,
+ [1822]=3,
+ [1823]=2,
+ [1824]=2,
+ [1825]=2,
+ [1826]=2,
+ [1827]=2,
+ [1828]=2,
+ [1829]=2,
+ [1830]=2,
+ [1831]=2,
+ [1832]=3,
+ [1833]=2,
+ [1834]=3,
+ [1835]=2,
+ [1836]=3,
+ [1837]=2,
+ [1838]=2,
+ [1839]=3,
+ [1840]=5,
+ [1841]=5,
+ [1842]=5,
+ [1843]=5,
+ [1844]=5,
+ [1845]=5,
+ [1846]=5,
+ [1847]=5,
+ [1848]=5,
+ [1849]=5,
+ [1850]=5,
+ [1851]=5,
+ [1852]=5,
+ [1853]=5,
+ [1854]=5,
+ [1855]=5,
+ [1856]=5,
+ [1857]=5,
+ [1858]=5,
+ [1859]=5,
+ [1860]=5,
+ [1861]=5,
+ [1862]=5,
+ [1863]=5,
+ [1864]=5,
+ [1865]=5,
+ [1866]=5,
+ [1869]=3,
+ [1870]=2,
+ [1871]=2,
+ [1872]=2,
+ [1873]=2,
+ [1874]=2,
+ [1875]=2,
+ [1876]=2,
+ [1877]=2,
+ [1878]=2,
+ [1879]=2,
+ [1880]=2,
+ [1881]=3,
+ [1882]=3,
+ [1883]=3,
+ [1884]=2,
+ [1885]=2,
+ [1886]=2,
+ [1887]=2,
+ [1888]=2,
+ [1889]=2,
+ [1890]=2,
+ [1891]=2,
+ [1892]=2,
+ [1893]=2,
+ [1894]=2,
+ [1895]=2,
+ [1896]=2,
+ [1897]=2,
+ [1898]=2,
+ [1899]=3,
+ [1900]=3,
+ [1901]=2,
+ [1902]=2,
+ [1903]=2,
+ [1904]=2,
+ [1905]=3,
+ [1906]=2,
+ [1907]=3,
+ [1908]=3,
+ [1909]=2,
+ [1910]=2,
+ [1911]=2,
+ [1912]=3,
+ [1913]=3,
+ [1914]=2,
+ [1915]=2,
+ [1916]=2,
+ [1917]=2,
+ [1918]=2,
+ [1919]=2,
+ [1958]=5,
+ [1959]=5,
+ [1960]=5,
+ [1961]=5,
+ [1962]=5,
+ [1963]=5,
+ [1964]=5,
+ [1965]=5,
+ [1966]=5,
+ [1967]=5,
+ [1968]=5,
+ [1984]=6,
+ [1985]=6,
+ [1986]=6,
+ [1987]=6,
+ [1988]=6,
+ [1989]=6,
+ [1990]=6,
+ [1991]=6,
+ [1992]=6,
+ [1993]=6,
+ [1994]=2,
+ [1995]=2,
+ [1996]=2,
+ [1997]=2,
+ [1998]=2,
+ [1999]=2,
+ [2000]=2,
+ [2001]=2,
+ [2002]=2,
+ [2003]=2,
+ [2004]=2,
+ [2005]=2,
+ [2006]=2,
+ [2007]=2,
+ [2008]=2,
+ [2009]=2,
+ [2010]=2,
+ [2011]=2,
+ [2012]=2,
+ [2013]=2,
+ [2014]=2,
+ [2015]=2,
+ [2016]=2,
+ [2017]=2,
+ [2018]=2,
+ [2019]=2,
+ [2020]=2,
+ [2021]=2,
+ [2022]=2,
+ [2023]=2,
+ [2024]=2,
+ [2025]=2,
+ [2026]=2,
+ [2027]=5,
+ [2028]=5,
+ [2029]=5,
+ [2030]=5,
+ [2031]=5,
+ [2032]=5,
+ [2033]=5,
+ [2034]=5,
+ [2035]=5,
+ [2036]=6,
+ [2037]=6,
+ [2038]=6,
+ [2039]=6,
+ [2040]=6,
+ [2041]=6,
+ [2042]=2,
+ [2045]=5,
+ [2046]=6,
+ [2047]=6,
+ [2070]=5,
+ [2071]=5,
+ [2072]=5,
+ [2073]=5,
+ [2075]=5,
+ [2076]=5,
+ [2077]=5,
+ [2078]=5,
+ [2079]=5,
+ [2080]=5,
+ [2081]=5,
+ [2082]=5,
+ [2083]=5,
+ [2085]=5,
+ [2086]=5,
+ [2087]=5,
+ [2089]=5,
+ [2090]=5,
+ [2091]=5,
+ [2092]=5,
+ [2093]=5,
+ [2112]=3,
+ [2113]=2,
+ [2114]=2,
+ [2115]=2,
+ [2116]=2,
+ [2117]=2,
+ [2118]=3,
+ [2119]=3,
+ [2120]=2,
+ [2121]=3,
+ [2122]=2,
+ [2123]=2,
+ [2124]=2,
+ [2125]=2,
+ [2126]=2,
+ [2127]=2,
+ [2128]=2,
+ [2129]=2,
+ [2130]=2,
+ [2131]=2,
+ [2132]=3,
+ [2133]=2,
+ [2134]=4,
+ [2135]=4,
+ [2136]=4,
+ [2137]=5,
+ [2138]=5,
+ [2139]=5,
+ [2144]=2,
+ [2145]=4,
+ [2146]=2,
+ [2147]=2,
+ [2148]=2,
+ [2149]=2,
+ [2150]=4,
+ [2151]=3,
+ [2152]=2,
+ [2153]=3,
+ [2154]=3,
+ [2208]=2,
+ [2209]=2,
+ [2210]=2,
+ [2211]=2,
+ [2212]=2,
+ [2213]=2,
+ [2214]=2,
+ [2215]=2,
+ [2216]=2,
+ [2217]=2,
+ [2218]=3,
+ [2219]=3,
+ [2220]=3,
+ [2221]=4,
+ [2222]=3,
+ [2223]=2,
+ [2224]=2,
+ [2225]=3,
+ [2226]=3,
+ [2227]=2,
+ [2228]=2,
+ [2230]=2,
+ [2231]=2,
+ [2232]=2,
+ [2233]=3,
+ [2234]=2,
+ [2235]=2,
+ [2236]=2,
+ [2237]=2,
+ [2259]=5,
+ [2260]=5,
+ [2261]=5,
+ [2262]=5,
+ [2263]=5,
+ [2264]=5,
+ [2265]=5,
+ [2266]=5,
+ [2267]=5,
+ [2268]=5,
+ [2269]=5,
+ [2270]=5,
+ [2271]=5,
+ [2272]=5,
+ [2273]=5,
+ [2274]=4,
+ [2275]=5,
+ [2276]=5,
+ [2277]=5,
+ [2278]=5,
+ [2279]=5,
+ [2280]=5,
+ [2281]=5,
+ [2282]=5,
+ [2283]=5,
+ [2284]=5,
+ [2285]=5,
+ [2286]=5,
+ [2287]=5,
+ [2288]=5,
+ [2289]=5,
+ [2290]=5,
+ [2291]=5,
+ [2292]=5,
+ [2293]=5,
+ [2294]=5,
+ [2295]=5,
+ [2296]=5,
+ [2297]=5,
+ [2298]=5,
+ [2299]=5,
+ [2300]=5,
+ [2301]=5,
+ [2302]=5,
+ [2303]=5,
+ [2304]=5,
+ [2305]=5,
+ [2306]=5,
+ [2362]=5,
+ [2364]=5,
+ [2369]=5,
+ [2370]=5,
+ [2371]=5,
+ [2372]=5,
+ [2373]=5,
+ [2374]=5,
+ [2375]=5,
+ [2376]=5,
+ [2381]=5,
+ [2385]=5,
+ [2386]=5,
+ [2387]=5,
+ [2388]=5,
+ [2389]=5,
+ [2390]=5,
+ [2391]=5,
+ [2402]=5,
+ [2403]=5,
+ [2433]=5,
+ [2492]=5,
+ [2497]=5,
+ [2498]=5,
+ [2499]=5,
+ [2500]=5,
+ [2509]=5,
+ [2530]=5,
+ [2531]=5,
+ [2558]=5,
+ [2561]=5,
+ [2562]=5,
+ [2620]=5,
+ [2625]=5,
+ [2626]=5,
+ [2631]=5,
+ [2632]=5,
+ [2635]=5,
+ [2636]=5,
+ [2637]=5,
+ [2641]=5,
+ [2672]=5,
+ [2673]=5,
+ [2677]=5,
+ [2689]=5,
+ [2690]=5,
+ [2748]=5,
+ [2753]=5,
+ [2754]=5,
+ [2755]=5,
+ [2756]=5,
+ [2757]=5,
+ [2759]=5,
+ [2760]=5,
+ [2765]=5,
+ [2786]=5,
+ [2787]=5,
+ [2810]=5,
+ [2811]=5,
+ [2812]=5,
+ [2813]=5,
+ [2814]=5,
+ [2815]=5,
+ [2817]=5,
+ [2876]=5,
+ [2879]=5,
+ [2881]=5,
+ [2882]=5,
+ [2883]=5,
+ [2884]=5,
+ [2893]=5,
+ [2902]=5,
+ [2914]=5,
+ [2915]=5,
+ [2946]=5,
+ [3008]=5,
+ [3021]=5,
+ [3072]=5,
+ [3076]=5,
+ [3134]=5,
+ [3135]=5,
+ [3136]=5,
+ [3142]=5,
+ [3143]=5,
+ [3144]=5,
+ [3146]=5,
+ [3147]=5,
+ [3148]=5,
+ [3149]=5,
+ [3157]=5,
+ [3158]=5,
+ [3170]=5,
+ [3171]=5,
+ [3201]=5,
+ [3260]=5,
+ [3263]=5,
+ [3270]=5,
+ [3276]=5,
+ [3277]=5,
+ [3298]=5,
+ [3299]=5,
+ [3328]=5,
+ [3329]=5,
+ [3387]=5,
+ [3388]=5,
+ [3393]=5,
+ [3394]=5,
+ [3395]=5,
+ [3396]=5,
+ [3405]=5,
+ [3426]=5,
+ [3427]=5,
+ [3530]=5,
+ [3538]=5,
+ [3539]=5,
+ [3540]=5,
+ [3542]=5,
+ [3633]=5,
+ [3636]=5,
+ [3637]=5,
+ [3638]=5,
+ [3639]=5,
+ [3640]=5,
+ [3641]=5,
+ [3642]=5,
+ [3655]=5,
+ [3656]=5,
+ [3657]=5,
+ [3658]=5,
+ [3659]=5,
+ [3660]=5,
+ [3661]=5,
+ [3662]=5,
+ [3761]=5,
+ [3764]=5,
+ [3765]=5,
+ [3766]=5,
+ [3767]=5,
+ [3768]=5,
+ [3769]=5,
+ [3770]=5,
+ [3771]=5,
+ [3772]=5,
+ [3784]=5,
+ [3785]=5,
+ [3786]=5,
+ [3787]=5,
+ [3788]=5,
+ [3789]=5,
+ [3864]=5,
+ [3865]=5,
+ [3893]=5,
+ [3895]=5,
+ [3897]=5,
+ [3953]=5,
+ [3954]=5,
+ [3955]=5,
+ [3956]=5,
+ [3957]=5,
+ [3958]=5,
+ [3959]=5,
+ [3960]=5,
+ [3961]=5,
+ [3962]=5,
+ [3963]=5,
+ [3964]=5,
+ [3965]=5,
+ [3966]=5,
+ [3968]=5,
+ [3969]=5,
+ [3970]=5,
+ [3971]=5,
+ [3972]=5,
+ [3974]=5,
+ [3975]=5,
+ [3981]=5,
+ [3982]=5,
+ [3983]=5,
+ [3984]=5,
+ [3985]=5,
+ [3986]=5,
+ [3987]=5,
+ [3988]=5,
+ [3989]=5,
+ [3990]=5,
+ [3991]=5,
+ [3993]=5,
+ [3994]=5,
+ [3995]=5,
+ [3996]=5,
+ [3997]=5,
+ [3998]=5,
+ [3999]=5,
+ [4000]=5,
+ [4001]=5,
+ [4002]=5,
+ [4003]=5,
+ [4004]=5,
+ [4005]=5,
+ [4006]=5,
+ [4007]=5,
+ [4008]=5,
+ [4009]=5,
+ [4010]=5,
+ [4011]=5,
+ [4012]=5,
+ [4013]=5,
+ [4014]=5,
+ [4015]=5,
+ [4016]=5,
+ [4017]=5,
+ [4018]=5,
+ [4019]=5,
+ [4020]=5,
+ [4021]=5,
+ [4022]=5,
+ [4023]=5,
+ [4024]=5,
+ [4025]=5,
+ [4026]=5,
+ [4027]=5,
+ [4028]=5,
+ [4038]=5,
+ [4141]=5,
+ [4142]=5,
+ [4143]=5,
+ [4144]=5,
+ [4146]=5,
+ [4147]=5,
+ [4148]=5,
+ [4149]=5,
+ [4150]=5,
+ [4151]=5,
+ [4153]=5,
+ [4154]=5,
+ [4157]=5,
+ [4158]=5,
+ [4184]=5,
+ [4185]=5,
+ [4190]=5,
+ [4191]=5,
+ [4192]=5,
+ [4209]=5,
+ [4210]=5,
+ [4211]=5,
+ [4212]=5,
+ [4226]=5,
+ [4229]=5,
+ [4230]=5,
+ [4237]=5,
+ [4253]=5,
+ [4957]=5,
+ [4958]=5,
+ [4959]=5,
+ [5906]=5,
+ [5907]=5,
+ [5908]=5,
+ [5938]=5,
+ [5939]=5,
+ [5940]=5,
+ [5970]=5,
+ [5971]=5,
+ [6002]=5,
+ [6003]=5,
+ [6071]=5,
+ [6072]=5,
+ [6073]=5,
+ [6074]=5,
+ [6075]=5,
+ [6076]=5,
+ [6077]=5,
+ [6086]=5,
+ [6089]=5,
+ [6090]=5,
+ [6091]=5,
+ [6092]=5,
+ [6093]=5,
+ [6094]=5,
+ [6095]=5,
+ [6096]=5,
+ [6097]=5,
+ [6098]=5,
+ [6099]=5,
+ [6109]=5,
+ [6150]=4,
+ [6151]=2,
+ [6154]=2,
+ [6155]=5,
+ [6156]=5,
+ [6157]=5,
+ [6158]=4,
+ [6176]=2,
+ [6177]=2,
+ [6178]=2,
+ [6179]=2,
+ [6180]=2,
+ [6181]=2,
+ [6182]=2,
+ [6183]=2,
+ [6184]=2,
+ [6185]=2,
+ [6186]=2,
+ [6187]=2,
+ [6188]=2,
+ [6189]=2,
+ [6190]=2,
+ [6191]=2,
+ [6192]=2,
+ [6193]=2,
+ [6194]=2,
+ [6195]=2,
+ [6196]=2,
+ [6197]=2,
+ [6198]=2,
+ [6199]=2,
+ [6200]=2,
+ [6201]=2,
+ [6202]=2,
+ [6203]=2,
+ [6204]=2,
+ [6205]=2,
+ [6206]=2,
+ [6207]=2,
+ [6208]=2,
+ [6209]=2,
+ [6210]=2,
+ [6211]=2,
+ [6212]=2,
+ [6213]=2,
+ [6214]=2,
+ [6215]=2,
+ [6216]=2,
+ [6217]=2,
+ [6218]=2,
+ [6219]=2,
+ [6220]=2,
+ [6221]=2,
+ [6222]=2,
+ [6223]=2,
+ [6224]=2,
+ [6225]=2,
+ [6226]=2,
+ [6227]=2,
+ [6228]=2,
+ [6229]=2,
+ [6230]=2,
+ [6231]=2,
+ [6232]=2,
+ [6233]=2,
+ [6234]=2,
+ [6235]=2,
+ [6236]=2,
+ [6237]=2,
+ [6238]=2,
+ [6239]=2,
+ [6240]=2,
+ [6241]=2,
+ [6242]=2,
+ [6243]=2,
+ [6244]=2,
+ [6245]=2,
+ [6246]=2,
+ [6247]=2,
+ [6248]=2,
+ [6249]=2,
+ [6250]=2,
+ [6251]=2,
+ [6252]=2,
+ [6253]=2,
+ [6254]=2,
+ [6255]=2,
+ [6256]=2,
+ [6257]=2,
+ [6258]=2,
+ [6259]=2,
+ [6260]=2,
+ [6261]=2,
+ [6262]=2,
+ [6263]=2,
+ [6264]=2,
+ [6272]=4,
+ [6273]=4,
+ [6274]=4,
+ [6275]=4,
+ [6276]=4,
+ [6279]=2,
+ [6280]=2,
+ [6281]=2,
+ [6282]=2,
+ [6283]=2,
+ [6284]=2,
+ [6285]=2,
+ [6286]=2,
+ [6287]=2,
+ [6288]=2,
+ [6289]=2,
+ [6290]=2,
+ [6291]=2,
+ [6292]=2,
+ [6293]=2,
+ [6294]=2,
+ [6295]=2,
+ [6296]=2,
+ [6297]=2,
+ [6298]=2,
+ [6299]=2,
+ [6300]=2,
+ [6301]=2,
+ [6302]=2,
+ [6303]=2,
+ [6304]=2,
+ [6305]=2,
+ [6306]=2,
+ [6307]=2,
+ [6308]=2,
+ [6309]=2,
+ [6310]=2,
+ [6311]=2,
+ [6312]=2,
+ [6313]=5,
+ [6314]=2,
+ [6432]=5,
+ [6433]=5,
+ [6434]=5,
+ [6439]=5,
+ [6440]=5,
+ [6450]=5,
+ [6457]=5,
+ [6458]=5,
+ [6459]=5,
+ [6679]=5,
+ [6680]=5,
+ [6742]=5,
+ [6744]=5,
+ [6745]=5,
+ [6746]=5,
+ [6747]=5,
+ [6748]=5,
+ [6749]=5,
+ [6750]=5,
+ [6752]=5,
+ [6754]=5,
+ [6757]=5,
+ [6758]=5,
+ [6759]=5,
+ [6760]=5,
+ [6761]=5,
+ [6762]=5,
+ [6763]=5,
+ [6764]=5,
+ [6771]=5,
+ [6772]=5,
+ [6773]=5,
+ [6774]=5,
+ [6775]=5,
+ [6776]=5,
+ [6777]=5,
+ [6778]=5,
+ [6779]=5,
+ [6780]=5,
+ [6783]=5,
+ [6832]=5,
+ [6833]=5,
+ [6834]=5,
+ [6835]=5,
+ [6836]=5,
+ [6837]=5,
+ [6838]=5,
+ [6839]=5,
+ [6840]=5,
+ [6841]=5,
+ [6842]=5,
+ [6843]=5,
+ [6844]=5,
+ [6845]=5,
+ [6912]=5,
+ [6913]=5,
+ [6914]=5,
+ [6915]=5,
+ [6964]=5,
+ [6966]=5,
+ [6967]=5,
+ [6968]=5,
+ [6969]=5,
+ [6970]=5,
+ [6972]=5,
+ [6978]=5,
+ [7019]=5,
+ [7020]=5,
+ [7021]=5,
+ [7022]=5,
+ [7023]=5,
+ [7024]=5,
+ [7025]=5,
+ [7026]=5,
+ [7027]=5,
+ [7040]=5,
+ [7041]=5,
+ [7074]=5,
+ [7075]=5,
+ [7076]=5,
+ [7077]=5,
+ [7080]=5,
+ [7081]=5,
+ [7083]=5,
+ [7142]=5,
+ [7144]=5,
+ [7145]=5,
+ [7149]=5,
+ [7151]=5,
+ [7152]=5,
+ [7153]=5,
+ [7212]=5,
+ [7213]=5,
+ [7214]=5,
+ [7215]=5,
+ [7216]=5,
+ [7217]=5,
+ [7218]=5,
+ [7219]=5,
+ [7222]=5,
+ [7223]=5,
+ [7376]=5,
+ [7377]=5,
+ [7378]=5,
+ [7380]=5,
+ [7381]=5,
+ [7382]=5,
+ [7383]=5,
+ [7384]=5,
+ [7385]=5,
+ [7386]=5,
+ [7387]=5,
+ [7388]=5,
+ [7389]=5,
+ [7390]=5,
+ [7391]=5,
+ [7392]=5,
+ [7394]=5,
+ [7395]=5,
+ [7396]=5,
+ [7397]=5,
+ [7398]=5,
+ [7399]=5,
+ [7400]=5,
+ [7405]=5,
+ [7412]=5,
+ [7416]=5,
+ [7417]=5,
+ [7616]=5,
+ [7617]=5,
+ [7618]=5,
+ [7619]=5,
+ [7620]=5,
+ [7621]=5,
+ [7622]=5,
+ [7623]=5,
+ [7624]=5,
+ [7625]=5,
+ [7626]=5,
+ [7627]=5,
+ [7628]=5,
+ [7629]=5,
+ [7630]=5,
+ [7631]=5,
+ [7632]=5,
+ [7633]=5,
+ [7634]=5,
+ [7635]=5,
+ [7636]=5,
+ [7637]=5,
+ [7638]=5,
+ [7639]=5,
+ [7640]=5,
+ [7641]=5,
+ [7642]=5,
+ [7643]=5,
+ [7644]=5,
+ [7645]=5,
+ [7646]=5,
+ [7647]=5,
+ [7648]=5,
+ [7649]=5,
+ [7650]=5,
+ [7651]=5,
+ [7652]=5,
+ [7653]=5,
+ [7654]=5,
+ [7655]=5,
+ [7656]=5,
+ [7657]=5,
+ [7658]=5,
+ [7659]=5,
+ [7660]=5,
+ [7661]=5,
+ [7662]=5,
+ [7663]=5,
+ [7664]=5,
+ [7665]=5,
+ [7666]=5,
+ [7667]=5,
+ [7668]=5,
+ [7669]=5,
+ [7670]=5,
+ [7671]=5,
+ [7672]=5,
+ [7673]=5,
+ [7675]=5,
+ [7676]=5,
+ [7677]=5,
+ [7678]=5,
+ [7679]=5,
+ [8204]=4,
+ [8205]=2,
+ [8239]=4,
+ [8294]=4,
+ [8295]=4,
+ [8296]=4,
+ [8297]=4,
+ [8400]=5,
+ [8401]=5,
+ [8402]=5,
+ [8403]=5,
+ [8404]=5,
+ [8405]=5,
+ [8406]=5,
+ [8407]=5,
+ [8408]=5,
+ [8409]=5,
+ [8410]=5,
+ [8411]=5,
+ [8412]=5,
+ [8417]=5,
+ [8421]=5,
+ [8422]=5,
+ [8423]=5,
+ [8424]=5,
+ [8425]=5,
+ [8426]=5,
+ [8427]=5,
+ [8428]=5,
+ [8429]=5,
+ [8430]=5,
+ [8431]=5,
+ [8432]=5,
+ [11503]=5,
+ [11504]=5,
+ [11505]=5,
+ [11647]=5,
+ [11744]=5,
+ [11745]=5,
+ [11746]=5,
+ [11747]=5,
+ [11748]=5,
+ [11749]=5,
+ [11750]=5,
+ [11751]=5,
+ [11752]=5,
+ [11753]=5,
+ [11754]=5,
+ [11755]=5,
+ [11756]=5,
+ [11757]=5,
+ [11758]=5,
+ [11759]=5,
+ [11760]=5,
+ [11761]=5,
+ [11762]=5,
+ [11763]=5,
+ [11764]=5,
+ [11765]=5,
+ [11766]=5,
+ [11767]=5,
+ [11768]=5,
+ [11769]=5,
+ [11770]=5,
+ [11771]=5,
+ [11772]=5,
+ [11773]=5,
+ [11774]=5,
+ [11775]=5,
+ [12330]=5,
+ [12331]=5,
+ [12332]=5,
+ [12333]=5,
+ [12334]=5,
+ [12335]=5,
+ [12441]=5,
+ [12442]=5,
+ [42607]=5,
+ [42612]=5,
+ [42613]=5,
+ [42614]=5,
+ [42615]=5,
+ [42616]=5,
+ [42617]=5,
+ [42618]=5,
+ [42619]=5,
+ [42620]=5,
+ [42621]=5,
+ [42654]=5,
+ [42655]=5,
+ [42736]=5,
+ [42737]=5,
+ [43014]=5,
+ [43019]=5,
+ [43045]=5,
+ [43046]=5,
+ [43072]=2,
+ [43073]=2,
+ [43074]=2,
+ [43075]=2,
+ [43076]=2,
+ [43077]=2,
+ [43078]=2,
+ [43079]=2,
+ [43080]=2,
+ [43081]=2,
+ [43082]=2,
+ [43083]=2,
+ [43084]=2,
+ [43085]=2,
+ [43086]=2,
+ [43087]=2,
+ [43088]=2,
+ [43089]=2,
+ [43090]=2,
+ [43091]=2,
+ [43092]=2,
+ [43093]=2,
+ [43094]=2,
+ [43095]=2,
+ [43096]=2,
+ [43097]=2,
+ [43098]=2,
+ [43099]=2,
+ [43100]=2,
+ [43101]=2,
+ [43102]=2,
+ [43103]=2,
+ [43104]=2,
+ [43105]=2,
+ [43106]=2,
+ [43107]=2,
+ [43108]=2,
+ [43109]=2,
+ [43110]=2,
+ [43111]=2,
+ [43112]=2,
+ [43113]=2,
+ [43114]=2,
+ [43115]=2,
+ [43116]=2,
+ [43117]=2,
+ [43118]=2,
+ [43119]=2,
+ [43120]=2,
+ [43121]=2,
+ [43122]=1,
+ [43123]=4,
+ [43204]=5,
+ [43205]=5,
+ [43232]=5,
+ [43233]=5,
+ [43234]=5,
+ [43235]=5,
+ [43236]=5,
+ [43237]=5,
+ [43238]=5,
+ [43239]=5,
+ [43240]=5,
+ [43241]=5,
+ [43242]=5,
+ [43243]=5,
+ [43244]=5,
+ [43245]=5,
+ [43246]=5,
+ [43247]=5,
+ [43248]=5,
+ [43249]=5,
+ [43263]=5,
+ [43302]=5,
+ [43303]=5,
+ [43304]=5,
+ [43305]=5,
+ [43306]=5,
+ [43307]=5,
+ [43308]=5,
+ [43309]=5,
+ [43335]=5,
+ [43336]=5,
+ [43337]=5,
+ [43338]=5,
+ [43339]=5,
+ [43340]=5,
+ [43341]=5,
+ [43342]=5,
+ [43343]=5,
+ [43344]=5,
+ [43345]=5,
+ [43392]=5,
+ [43393]=5,
+ [43394]=5,
+ [43443]=5,
+ [43446]=5,
+ [43447]=5,
+ [43448]=5,
+ [43449]=5,
+ [43452]=5,
+ [43493]=5,
+ [43561]=5,
+ [43562]=5,
+ [43563]=5,
+ [43564]=5,
+ [43565]=5,
+ [43566]=5,
+ [43569]=5,
+ [43570]=5,
+ [43573]=5,
+ [43574]=5,
+ [43587]=5,
+ [43596]=5,
+ [43644]=5,
+ [43696]=5,
+ [43698]=5,
+ [43699]=5,
+ [43700]=5,
+ [43703]=5,
+ [43704]=5,
+ [43710]=5,
+ [43711]=5,
+ [43713]=5,
+ [43756]=5,
+ [43757]=5,
+ [43766]=5,
+ [44005]=5,
+ [44008]=5,
+ [44013]=5,
+ [64286]=5,
+ [65056]=5,
+ [65057]=5,
+ [65058]=5,
+ [65059]=5,
+ [65060]=5,
+ [65061]=5,
+ [65062]=5,
+ [65063]=5,
+ [65064]=5,
+ [65065]=5,
+ [65066]=5,
+ [65067]=5,
+ [65068]=5,
+ [65069]=5,
+ [65070]=5,
+ [65071]=5,
+ [66045]=5,
+ [66272]=5,
+ [66422]=5,
+ [66423]=5,
+ [66424]=5,
+ [66425]=5,
+ [66426]=5,
+ [68097]=5,
+ [68098]=5,
+ [68099]=5,
+ [68101]=5,
+ [68102]=5,
+ [68108]=5,
+ [68109]=5,
+ [68110]=5,
+ [68111]=5,
+ [68152]=5,
+ [68153]=5,
+ [68154]=5,
+ [68159]=5,
+ [68288]=2,
+ [68289]=2,
+ [68290]=2,
+ [68291]=2,
+ [68292]=2,
+ [68293]=3,
+ [68294]=4,
+ [68295]=3,
+ [68296]=4,
+ [68297]=3,
+ [68298]=3,
+ [68299]=4,
+ [68300]=4,
+ [68301]=1,
+ [68302]=3,
+ [68303]=3,
+ [68304]=3,
+ [68305]=3,
+ [68306]=3,
+ [68307]=2,
+ [68308]=2,
+ [68309]=2,
+ [68310]=2,
+ [68311]=1,
+ [68312]=2,
+ [68313]=2,
+ [68314]=2,
+ [68315]=2,
+ [68316]=2,
+ [68317]=3,
+ [68318]=2,
+ [68319]=2,
+ [68320]=2,
+ [68321]=3,
+ [68322]=4,
+ [68323]=4,
+ [68324]=3,
+ [68325]=5,
+ [68326]=5,
+ [68331]=2,
+ [68332]=2,
+ [68333]=2,
+ [68334]=2,
+ [68335]=3,
+ [68480]=2,
+ [68481]=3,
+ [68482]=2,
+ [68483]=3,
+ [68484]=3,
+ [68485]=3,
+ [68486]=2,
+ [68487]=2,
+ [68488]=2,
+ [68489]=3,
+ [68490]=2,
+ [68491]=2,
+ [68492]=3,
+ [68493]=2,
+ [68494]=3,
+ [68495]=3,
+ [68496]=2,
+ [68497]=3,
+ [68521]=3,
+ [68522]=3,
+ [68523]=3,
+ [68524]=3,
+ [68525]=2,
+ [68526]=2,
+ [68527]=4,
+ [68864]=1,
+ [68865]=2,
+ [68866]=2,
+ [68867]=2,
+ [68868]=2,
+ [68869]=2,
+ [68870]=2,
+ [68871]=2,
+ [68872]=2,
+ [68873]=2,
+ [68874]=2,
+ [68875]=2,
+ [68876]=2,
+ [68877]=2,
+ [68878]=2,
+ [68879]=2,
+ [68880]=2,
+ [68881]=2,
+ [68882]=2,
+ [68883]=2,
+ [68884]=2,
+ [68885]=2,
+ [68886]=2,
+ [68887]=2,
+ [68888]=2,
+ [68889]=2,
+ [68890]=2,
+ [68891]=2,
+ [68892]=2,
+ [68893]=2,
+ [68894]=2,
+ [68895]=2,
+ [68896]=2,
+ [68897]=2,
+ [68898]=3,
+ [68899]=2,
+ [68900]=5,
+ [68901]=5,
+ [68902]=5,
+ [68903]=5,
+ [69424]=2,
+ [69425]=2,
+ [69426]=2,
+ [69427]=3,
+ [69428]=2,
+ [69429]=2,
+ [69430]=2,
+ [69431]=2,
+ [69432]=2,
+ [69433]=2,
+ [69434]=2,
+ [69435]=2,
+ [69436]=2,
+ [69437]=2,
+ [69438]=2,
+ [69439]=2,
+ [69440]=2,
+ [69441]=2,
+ [69442]=2,
+ [69443]=2,
+ [69444]=2,
+ [69445]=4,
+ [69446]=5,
+ [69447]=5,
+ [69448]=5,
+ [69449]=5,
+ [69450]=5,
+ [69451]=5,
+ [69452]=5,
+ [69453]=5,
+ [69454]=5,
+ [69455]=5,
+ [69456]=5,
+ [69457]=2,
+ [69458]=2,
+ [69459]=2,
+ [69460]=3,
+ [69633]=5,
+ [69688]=5,
+ [69689]=5,
+ [69690]=5,
+ [69691]=5,
+ [69692]=5,
+ [69693]=5,
+ [69694]=5,
+ [69695]=5,
+ [69696]=5,
+ [69697]=5,
+ [69698]=5,
+ [69699]=5,
+ [69700]=5,
+ [69701]=5,
+ [69702]=5,
+ [69759]=5,
+ [69760]=5,
+ [69761]=5,
+ [69811]=5,
+ [69812]=5,
+ [69813]=5,
+ [69814]=5,
+ [69817]=5,
+ [69818]=5,
+ [69821]=4,
+ [69837]=4,
+ [69888]=5,
+ [69889]=5,
+ [69890]=5,
+ [69927]=5,
+ [69928]=5,
+ [69929]=5,
+ [69930]=5,
+ [69931]=5,
+ [69933]=5,
+ [69934]=5,
+ [69935]=5,
+ [69936]=5,
+ [69937]=5,
+ [69938]=5,
+ [69939]=5,
+ [69940]=5,
+ [70003]=5,
+ [70016]=5,
+ [70017]=5,
+ [70070]=5,
+ [70071]=5,
+ [70072]=5,
+ [70073]=5,
+ [70074]=5,
+ [70075]=5,
+ [70076]=5,
+ [70077]=5,
+ [70078]=5,
+ [70090]=5,
+ [70091]=5,
+ [70092]=5,
+ [70191]=5,
+ [70192]=5,
+ [70193]=5,
+ [70196]=5,
+ [70198]=5,
+ [70199]=5,
+ [70206]=5,
+ [70367]=5,
+ [70371]=5,
+ [70372]=5,
+ [70373]=5,
+ [70374]=5,
+ [70375]=5,
+ [70376]=5,
+ [70377]=5,
+ [70378]=5,
+ [70400]=5,
+ [70401]=5,
+ [70459]=5,
+ [70460]=5,
+ [70464]=5,
+ [70502]=5,
+ [70503]=5,
+ [70504]=5,
+ [70505]=5,
+ [70506]=5,
+ [70507]=5,
+ [70508]=5,
+ [70512]=5,
+ [70513]=5,
+ [70514]=5,
+ [70515]=5,
+ [70516]=5,
+ [70712]=5,
+ [70713]=5,
+ [70714]=5,
+ [70715]=5,
+ [70716]=5,
+ [70717]=5,
+ [70718]=5,
+ [70719]=5,
+ [70722]=5,
+ [70723]=5,
+ [70724]=5,
+ [70726]=5,
+ [70750]=5,
+ [70835]=5,
+ [70836]=5,
+ [70837]=5,
+ [70838]=5,
+ [70839]=5,
+ [70840]=5,
+ [70842]=5,
+ [70847]=5,
+ [70848]=5,
+ [70850]=5,
+ [70851]=5,
+ [71090]=5,
+ [71091]=5,
+ [71092]=5,
+ [71093]=5,
+ [71100]=5,
+ [71101]=5,
+ [71103]=5,
+ [71104]=5,
+ [71132]=5,
+ [71133]=5,
+ [71219]=5,
+ [71220]=5,
+ [71221]=5,
+ [71222]=5,
+ [71223]=5,
+ [71224]=5,
+ [71225]=5,
+ [71226]=5,
+ [71229]=5,
+ [71231]=5,
+ [71232]=5,
+ [71339]=5,
+ [71341]=5,
+ [71344]=5,
+ [71345]=5,
+ [71346]=5,
+ [71347]=5,
+ [71348]=5,
+ [71349]=5,
+ [71351]=5,
+ [71453]=5,
+ [71454]=5,
+ [71455]=5,
+ [71458]=5,
+ [71459]=5,
+ [71460]=5,
+ [71461]=5,
+ [71463]=5,
+ [71464]=5,
+ [71465]=5,
+ [71466]=5,
+ [71467]=5,
+ [71727]=5,
+ [71728]=5,
+ [71729]=5,
+ [71730]=5,
+ [71731]=5,
+ [71732]=5,
+ [71733]=5,
+ [71734]=5,
+ [71735]=5,
+ [71737]=5,
+ [71738]=5,
+ [72148]=5,
+ [72149]=5,
+ [72150]=5,
+ [72151]=5,
+ [72154]=5,
+ [72155]=5,
+ [72160]=5,
+ [72193]=5,
+ [72194]=5,
+ [72195]=5,
+ [72196]=5,
+ [72197]=5,
+ [72198]=5,
+ [72201]=5,
+ [72202]=5,
+ [72243]=5,
+ [72244]=5,
+ [72245]=5,
+ [72246]=5,
+ [72247]=5,
+ [72248]=5,
+ [72251]=5,
+ [72252]=5,
+ [72253]=5,
+ [72254]=5,
+ [72263]=5,
+ [72273]=5,
+ [72274]=5,
+ [72275]=5,
+ [72276]=5,
+ [72277]=5,
+ [72278]=5,
+ [72281]=5,
+ [72282]=5,
+ [72283]=5,
+ [72330]=5,
+ [72331]=5,
+ [72332]=5,
+ [72333]=5,
+ [72334]=5,
+ [72335]=5,
+ [72336]=5,
+ [72337]=5,
+ [72338]=5,
+ [72339]=5,
+ [72340]=5,
+ [72341]=5,
+ [72342]=5,
+ [72344]=5,
+ [72345]=5,
+ [72752]=5,
+ [72753]=5,
+ [72754]=5,
+ [72755]=5,
+ [72756]=5,
+ [72757]=5,
+ [72758]=5,
+ [72760]=5,
+ [72761]=5,
+ [72762]=5,
+ [72763]=5,
+ [72764]=5,
+ [72765]=5,
+ [72767]=5,
+ [72850]=5,
+ [72851]=5,
+ [72852]=5,
+ [72853]=5,
+ [72854]=5,
+ [72855]=5,
+ [72856]=5,
+ [72857]=5,
+ [72858]=5,
+ [72859]=5,
+ [72860]=5,
+ [72861]=5,
+ [72862]=5,
+ [72863]=5,
+ [72864]=5,
+ [72865]=5,
+ [72866]=5,
+ [72867]=5,
+ [72868]=5,
+ [72869]=5,
+ [72870]=5,
+ [72871]=5,
+ [72874]=5,
+ [72875]=5,
+ [72876]=5,
+ [72877]=5,
+ [72878]=5,
+ [72879]=5,
+ [72880]=5,
+ [72882]=5,
+ [72883]=5,
+ [72885]=5,
+ [72886]=5,
+ [73009]=5,
+ [73010]=5,
+ [73011]=5,
+ [73012]=5,
+ [73013]=5,
+ [73014]=5,
+ [73018]=5,
+ [73020]=5,
+ [73021]=5,
+ [73023]=5,
+ [73024]=5,
+ [73025]=5,
+ [73026]=5,
+ [73027]=5,
+ [73028]=5,
+ [73029]=5,
+ [73031]=5,
+ [73104]=5,
+ [73105]=5,
+ [73109]=5,
+ [73111]=5,
+ [73459]=5,
+ [73460]=5,
+ [92912]=5,
+ [92913]=5,
+ [92914]=5,
+ [92915]=5,
+ [92916]=5,
+ [92976]=5,
+ [92977]=5,
+ [92978]=5,
+ [92979]=5,
+ [92980]=5,
+ [92981]=5,
+ [92982]=5,
+ [94031]=5,
+ [94095]=5,
+ [94096]=5,
+ [94097]=5,
+ [94098]=5,
+ [113821]=5,
+ [113822]=5,
+ [119143]=5,
+ [119144]=5,
+ [119145]=5,
+ [119163]=5,
+ [119164]=5,
+ [119165]=5,
+ [119166]=5,
+ [119167]=5,
+ [119168]=5,
+ [119169]=5,
+ [119170]=5,
+ [119173]=5,
+ [119174]=5,
+ [119175]=5,
+ [119176]=5,
+ [119177]=5,
+ [119178]=5,
+ [119179]=5,
+ [119210]=5,
+ [119211]=5,
+ [119212]=5,
+ [119213]=5,
+ [119362]=5,
+ [119363]=5,
+ [119364]=5,
+ [121344]=5,
+ [121345]=5,
+ [121346]=5,
+ [121347]=5,
+ [121348]=5,
+ [121349]=5,
+ [121350]=5,
+ [121351]=5,
+ [121352]=5,
+ [121353]=5,
+ [121354]=5,
+ [121355]=5,
+ [121356]=5,
+ [121357]=5,
+ [121358]=5,
+ [121359]=5,
+ [121360]=5,
+ [121361]=5,
+ [121362]=5,
+ [121363]=5,
+ [121364]=5,
+ [121365]=5,
+ [121366]=5,
+ [121367]=5,
+ [121368]=5,
+ [121369]=5,
+ [121370]=5,
+ [121371]=5,
+ [121372]=5,
+ [121373]=5,
+ [121374]=5,
+ [121375]=5,
+ [121376]=5,
+ [121377]=5,
+ [121378]=5,
+ [121379]=5,
+ [121380]=5,
+ [121381]=5,
+ [121382]=5,
+ [121383]=5,
+ [121384]=5,
+ [121385]=5,
+ [121386]=5,
+ [121387]=5,
+ [121388]=5,
+ [121389]=5,
+ [121390]=5,
+ [121391]=5,
+ [121392]=5,
+ [121393]=5,
+ [121394]=5,
+ [121395]=5,
+ [121396]=5,
+ [121397]=5,
+ [121398]=5,
+ [121403]=5,
+ [121404]=5,
+ [121405]=5,
+ [121406]=5,
+ [121407]=5,
+ [121408]=5,
+ [121409]=5,
+ [121410]=5,
+ [121411]=5,
+ [121412]=5,
+ [121413]=5,
+ [121414]=5,
+ [121415]=5,
+ [121416]=5,
+ [121417]=5,
+ [121418]=5,
+ [121419]=5,
+ [121420]=5,
+ [121421]=5,
+ [121422]=5,
+ [121423]=5,
+ [121424]=5,
+ [121425]=5,
+ [121426]=5,
+ [121427]=5,
+ [121428]=5,
+ [121429]=5,
+ [121430]=5,
+ [121431]=5,
+ [121432]=5,
+ [121433]=5,
+ [121434]=5,
+ [121435]=5,
+ [121436]=5,
+ [121437]=5,
+ [121438]=5,
+ [121439]=5,
+ [121440]=5,
+ [121441]=5,
+ [121442]=5,
+ [121443]=5,
+ [121444]=5,
+ [121445]=5,
+ [121446]=5,
+ [121447]=5,
+ [121448]=5,
+ [121449]=5,
+ [121450]=5,
+ [121451]=5,
+ [121452]=5,
+ [121461]=5,
+ [121476]=5,
+ [121499]=5,
+ [121500]=5,
+ [121501]=5,
+ [121502]=5,
+ [121503]=5,
+ [121505]=5,
+ [121506]=5,
+ [121507]=5,
+ [121508]=5,
+ [121509]=5,
+ [121510]=5,
+ [121511]=5,
+ [121512]=5,
+ [121513]=5,
+ [121514]=5,
+ [121515]=5,
+ [121516]=5,
+ [121517]=5,
+ [121518]=5,
+ [121519]=5,
+ [122880]=5,
+ [122881]=5,
+ [122882]=5,
+ [122883]=5,
+ [122884]=5,
+ [122885]=5,
+ [122886]=5,
+ [122888]=5,
+ [122889]=5,
+ [122890]=5,
+ [122891]=5,
+ [122892]=5,
+ [122893]=5,
+ [122894]=5,
+ [122895]=5,
+ [122896]=5,
+ [122897]=5,
+ [122898]=5,
+ [122899]=5,
+ [122900]=5,
+ [122901]=5,
+ [122902]=5,
+ [122903]=5,
+ [122904]=5,
+ [122907]=5,
+ [122908]=5,
+ [122909]=5,
+ [122910]=5,
+ [122911]=5,
+ [122912]=5,
+ [122913]=5,
+ [122915]=5,
+ [122916]=5,
+ [122918]=5,
+ [122919]=5,
+ [122920]=5,
+ [122921]=5,
+ [122922]=5,
+ [123184]=5,
+ [123185]=5,
+ [123186]=5,
+ [123187]=5,
+ [123188]=5,
+ [123189]=5,
+ [123190]=5,
+ [123628]=5,
+ [123629]=5,
+ [123630]=5,
+ [123631]=5,
+ [125136]=5,
+ [125137]=5,
+ [125138]=5,
+ [125139]=5,
+ [125140]=5,
+ [125141]=5,
+ [125142]=5,
+ [125184]=2,
+ [125185]=2,
+ [125186]=2,
+ [125187]=2,
+ [125188]=2,
+ [125189]=2,
+ [125190]=2,
+ [125191]=2,
+ [125192]=2,
+ [125193]=2,
+ [125194]=2,
+ [125195]=2,
+ [125196]=2,
+ [125197]=2,
+ [125198]=2,
+ [125199]=2,
+ [125200]=2,
+ [125201]=2,
+ [125202]=2,
+ [125203]=2,
+ [125204]=2,
+ [125205]=2,
+ [125206]=2,
+ [125207]=2,
+ [125208]=2,
+ [125209]=2,
+ [125210]=2,
+ [125211]=2,
+ [125212]=2,
+ [125213]=2,
+ [125214]=2,
+ [125215]=2,
+ [125216]=2,
+ [125217]=2,
+ [125218]=2,
+ [125219]=2,
+ [125220]=2,
+ [125221]=2,
+ [125222]=2,
+ [125223]=2,
+ [125224]=2,
+ [125225]=2,
+ [125226]=2,
+ [125227]=2,
+ [125228]=2,
+ [125229]=2,
+ [125230]=2,
+ [125231]=2,
+ [125232]=2,
+ [125233]=2,
+ [125234]=2,
+ [125235]=2,
+ [125236]=2,
+ [125237]=2,
+ [125238]=2,
+ [125239]=2,
+ [125240]=2,
+ [125241]=2,
+ [125242]=2,
+ [125243]=2,
+ [125244]=2,
+ [125245]=2,
+ [125246]=2,
+ [125247]=2,
+ [125248]=2,
+ [125249]=2,
+ [125250]=2,
+ [125251]=2,
+ [125252]=5,
+ [125253]=5,
+ [125254]=5,
+ [125255]=5,
+ [125256]=5,
+ [125257]=5,
+ [125258]=5,
+ [1042752]=5,
+}
+characters.indicgroups={
+ ["above_mark"]={
+ [2304]=true,
+ [2305]=true,
+ [2306]=true,
+ [2362]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2385]=true,
+ [2387]=true,
+ [2388]=true,
+ [2389]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2690]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2879]=true,
+ [3008]=true,
+ [3021]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3142]=true,
+ [3143]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3149]=true,
+ [3263]=true,
+ [3270]=true,
+ [3406]=true,
+ [4141]=true,
+ [4142]=true,
+ [4146]=true,
+ [4147]=true,
+ [4148]=true,
+ [4149]=true,
+ [4150]=true,
+ [4154]=true,
+ [4209]=true,
+ [4210]=true,
+ [4211]=true,
+ [4212]=true,
+ [4229]=true,
+ [4230]=true,
+ [4253]=true,
+ [43232]=true,
+ [43233]=true,
+ [43234]=true,
+ [43235]=true,
+ [43236]=true,
+ [43237]=true,
+ [43238]=true,
+ [43239]=true,
+ [43240]=true,
+ [43241]=true,
+ [43242]=true,
+ [43243]=true,
+ [43244]=true,
+ [43245]=true,
+ [43246]=true,
+ [43247]=true,
+ [43248]=true,
+ [43249]=true,
+ [43493]=true,
+ [43644]=true,
+ },
+ ["after_half"]={},
+ ["after_main"]={
+ [2864]=true,
+ [2879]=true,
+ [2902]=true,
+ [3376]=true,
+ },
+ ["after_postscript"]={
+ [2433]=true,
+ [2494]=true,
+ [2496]=true,
+ [2519]=true,
+ [2561]=true,
+ [2562]=true,
+ [2622]=true,
+ [2624]=true,
+ [2625]=true,
+ [2626]=true,
+ [2672]=true,
+ [2673]=true,
+ [2735]=true,
+ [2750]=true,
+ [2752]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2786]=true,
+ [2787]=true,
+ [2878]=true,
+ [2880]=true,
+ [2903]=true,
+ [2992]=true,
+ [3006]=true,
+ [3007]=true,
+ [3009]=true,
+ [3010]=true,
+ [3031]=true,
+ [3120]=true,
+ [3248]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3415]=true,
+ },
+ ["after_subscript"]={
+ [2366]=true,
+ [2368]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2402]=true,
+ [2403]=true,
+ [2480]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2530]=true,
+ [2531]=true,
+ [2544]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [3008]=true,
+ [3139]=true,
+ [3140]=true,
+ [3267]=true,
+ [3268]=true,
+ [3285]=true,
+ [3286]=true,
+ },
+ ["anudatta"]={
+ [2386]=true,
+ },
+ ["before_half"]={
+ [2367]=true,
+ [2382]=true,
+ [2495]=true,
+ [2503]=true,
+ [2504]=true,
+ [2623]=true,
+ [2751]=true,
+ [2887]=true,
+ },
+ ["before_main"]={
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ },
+ ["before_postscript"]={
+ [2352]=true,
+ [2736]=true,
+ },
+ ["before_subscript"]={
+ [2608]=true,
+ [2817]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3137]=true,
+ [3138]=true,
+ [3142]=true,
+ [3143]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3157]=true,
+ [3158]=true,
+ [3262]=true,
+ [3263]=true,
+ [3265]=true,
+ [3266]=true,
+ [3270]=true,
+ [3276]=true,
+ [3298]=true,
+ [3299]=true,
+ },
+ ["below_mark"]={
+ [2364]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2381]=true,
+ [2386]=true,
+ [2390]=true,
+ [2391]=true,
+ [2402]=true,
+ [2403]=true,
+ [2492]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2509]=true,
+ [2620]=true,
+ [2625]=true,
+ [2626]=true,
+ [2637]=true,
+ [2748]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2765]=true,
+ [2876]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [2884]=true,
+ [2893]=true,
+ [2914]=true,
+ [2915]=true,
+ [3009]=true,
+ [3010]=true,
+ [3170]=true,
+ [3171]=true,
+ [3260]=true,
+ [3286]=true,
+ [3298]=true,
+ [3299]=true,
+ [3426]=true,
+ [3427]=true,
+ [4143]=true,
+ [4144]=true,
+ [4151]=true,
+ [4153]=true,
+ [4157]=true,
+ [4158]=true,
+ [4184]=true,
+ [4185]=true,
+ [4190]=true,
+ [4191]=true,
+ [4192]=true,
+ [4226]=true,
+ [4237]=true,
+ },
+ ["consonant"]={
+ [2325]=true,
+ [2326]=true,
+ [2327]=true,
+ [2328]=true,
+ [2329]=true,
+ [2330]=true,
+ [2331]=true,
+ [2332]=true,
+ [2333]=true,
+ [2334]=true,
+ [2335]=true,
+ [2336]=true,
+ [2337]=true,
+ [2338]=true,
+ [2339]=true,
+ [2340]=true,
+ [2341]=true,
+ [2342]=true,
+ [2343]=true,
+ [2344]=true,
+ [2345]=true,
+ [2346]=true,
+ [2347]=true,
+ [2348]=true,
+ [2349]=true,
+ [2350]=true,
+ [2351]=true,
+ [2352]=true,
+ [2353]=true,
+ [2354]=true,
+ [2355]=true,
+ [2356]=true,
+ [2357]=true,
+ [2358]=true,
+ [2359]=true,
+ [2360]=true,
+ [2361]=true,
+ [2392]=true,
+ [2393]=true,
+ [2394]=true,
+ [2395]=true,
+ [2396]=true,
+ [2397]=true,
+ [2398]=true,
+ [2399]=true,
+ [2424]=true,
+ [2425]=true,
+ [2426]=true,
+ [2453]=true,
+ [2454]=true,
+ [2455]=true,
+ [2456]=true,
+ [2457]=true,
+ [2458]=true,
+ [2459]=true,
+ [2460]=true,
+ [2461]=true,
+ [2462]=true,
+ [2463]=true,
+ [2464]=true,
+ [2465]=true,
+ [2466]=true,
+ [2467]=true,
+ [2468]=true,
+ [2469]=true,
+ [2470]=true,
+ [2471]=true,
+ [2472]=true,
+ [2474]=true,
+ [2475]=true,
+ [2476]=true,
+ [2477]=true,
+ [2478]=true,
+ [2479]=true,
+ [2480]=true,
+ [2482]=true,
+ [2486]=true,
+ [2487]=true,
+ [2488]=true,
+ [2489]=true,
+ [2510]=true,
+ [2524]=true,
+ [2525]=true,
+ [2527]=true,
+ [2581]=true,
+ [2582]=true,
+ [2583]=true,
+ [2584]=true,
+ [2585]=true,
+ [2586]=true,
+ [2587]=true,
+ [2588]=true,
+ [2589]=true,
+ [2590]=true,
+ [2591]=true,
+ [2592]=true,
+ [2593]=true,
+ [2594]=true,
+ [2595]=true,
+ [2596]=true,
+ [2597]=true,
+ [2598]=true,
+ [2599]=true,
+ [2600]=true,
+ [2602]=true,
+ [2603]=true,
+ [2604]=true,
+ [2605]=true,
+ [2606]=true,
+ [2607]=true,
+ [2608]=true,
+ [2610]=true,
+ [2611]=true,
+ [2613]=true,
+ [2614]=true,
+ [2616]=true,
+ [2617]=true,
+ [2649]=true,
+ [2650]=true,
+ [2651]=true,
+ [2652]=true,
+ [2654]=true,
+ [2709]=true,
+ [2710]=true,
+ [2711]=true,
+ [2712]=true,
+ [2713]=true,
+ [2714]=true,
+ [2715]=true,
+ [2716]=true,
+ [2717]=true,
+ [2718]=true,
+ [2719]=true,
+ [2720]=true,
+ [2721]=true,
+ [2722]=true,
+ [2723]=true,
+ [2724]=true,
+ [2725]=true,
+ [2726]=true,
+ [2727]=true,
+ [2728]=true,
+ [2730]=true,
+ [2731]=true,
+ [2732]=true,
+ [2733]=true,
+ [2734]=true,
+ [2735]=true,
+ [2736]=true,
+ [2738]=true,
+ [2739]=true,
+ [2741]=true,
+ [2742]=true,
+ [2743]=true,
+ [2744]=true,
+ [2745]=true,
+ [2837]=true,
+ [2838]=true,
+ [2839]=true,
+ [2840]=true,
+ [2841]=true,
+ [2842]=true,
+ [2843]=true,
+ [2844]=true,
+ [2845]=true,
+ [2846]=true,
+ [2847]=true,
+ [2848]=true,
+ [2849]=true,
+ [2850]=true,
+ [2851]=true,
+ [2852]=true,
+ [2853]=true,
+ [2854]=true,
+ [2855]=true,
+ [2856]=true,
+ [2858]=true,
+ [2859]=true,
+ [2860]=true,
+ [2861]=true,
+ [2862]=true,
+ [2863]=true,
+ [2864]=true,
+ [2866]=true,
+ [2867]=true,
+ [2869]=true,
+ [2870]=true,
+ [2871]=true,
+ [2872]=true,
+ [2873]=true,
+ [2908]=true,
+ [2909]=true,
+ [2929]=true,
+ [2965]=true,
+ [2969]=true,
+ [2970]=true,
+ [2972]=true,
+ [2974]=true,
+ [2975]=true,
+ [2979]=true,
+ [2980]=true,
+ [2984]=true,
+ [2985]=true,
+ [2986]=true,
+ [2990]=true,
+ [2991]=true,
+ [2992]=true,
+ [2993]=true,
+ [2994]=true,
+ [2995]=true,
+ [2996]=true,
+ [2997]=true,
+ [2998]=true,
+ [2999]=true,
+ [3000]=true,
+ [3001]=true,
+ [3093]=true,
+ [3094]=true,
+ [3095]=true,
+ [3096]=true,
+ [3097]=true,
+ [3098]=true,
+ [3099]=true,
+ [3100]=true,
+ [3101]=true,
+ [3102]=true,
+ [3103]=true,
+ [3104]=true,
+ [3105]=true,
+ [3106]=true,
+ [3107]=true,
+ [3108]=true,
+ [3109]=true,
+ [3110]=true,
+ [3111]=true,
+ [3112]=true,
+ [3114]=true,
+ [3115]=true,
+ [3116]=true,
+ [3117]=true,
+ [3118]=true,
+ [3119]=true,
+ [3120]=true,
+ [3121]=true,
+ [3122]=true,
+ [3123]=true,
+ [3124]=true,
+ [3125]=true,
+ [3126]=true,
+ [3127]=true,
+ [3128]=true,
+ [3129]=true,
+ [3133]=true,
+ [3221]=true,
+ [3222]=true,
+ [3223]=true,
+ [3224]=true,
+ [3225]=true,
+ [3226]=true,
+ [3227]=true,
+ [3228]=true,
+ [3229]=true,
+ [3230]=true,
+ [3231]=true,
+ [3232]=true,
+ [3233]=true,
+ [3234]=true,
+ [3235]=true,
+ [3236]=true,
+ [3237]=true,
+ [3238]=true,
+ [3239]=true,
+ [3240]=true,
+ [3242]=true,
+ [3243]=true,
+ [3244]=true,
+ [3245]=true,
+ [3246]=true,
+ [3247]=true,
+ [3248]=true,
+ [3249]=true,
+ [3250]=true,
+ [3251]=true,
+ [3253]=true,
+ [3254]=true,
+ [3255]=true,
+ [3256]=true,
+ [3257]=true,
+ [3294]=true,
+ [3349]=true,
+ [3350]=true,
+ [3351]=true,
+ [3352]=true,
+ [3353]=true,
+ [3354]=true,
+ [3355]=true,
+ [3356]=true,
+ [3357]=true,
+ [3358]=true,
+ [3359]=true,
+ [3360]=true,
+ [3361]=true,
+ [3362]=true,
+ [3363]=true,
+ [3364]=true,
+ [3365]=true,
+ [3366]=true,
+ [3367]=true,
+ [3368]=true,
+ [3369]=true,
+ [3370]=true,
+ [3371]=true,
+ [3372]=true,
+ [3373]=true,
+ [3374]=true,
+ [3375]=true,
+ [3376]=true,
+ [3377]=true,
+ [3378]=true,
+ [3379]=true,
+ [3380]=true,
+ [3381]=true,
+ [3382]=true,
+ [3383]=true,
+ [3384]=true,
+ [3385]=true,
+ [3386]=true,
+ [4096]=true,
+ [4097]=true,
+ [4098]=true,
+ [4099]=true,
+ [4100]=true,
+ [4101]=true,
+ [4102]=true,
+ [4103]=true,
+ [4104]=true,
+ [4105]=true,
+ [4106]=true,
+ [4107]=true,
+ [4108]=true,
+ [4109]=true,
+ [4110]=true,
+ [4111]=true,
+ [4112]=true,
+ [4113]=true,
+ [4114]=true,
+ [4115]=true,
+ [4116]=true,
+ [4117]=true,
+ [4118]=true,
+ [4119]=true,
+ [4120]=true,
+ [4121]=true,
+ [4122]=true,
+ [4123]=true,
+ [4124]=true,
+ [4125]=true,
+ [4126]=true,
+ [4127]=true,
+ [4128]=true,
+ [4155]=true,
+ [4156]=true,
+ [4157]=true,
+ [4158]=true,
+ [4159]=true,
+ [4176]=true,
+ [4177]=true,
+ [4186]=true,
+ [4187]=true,
+ [4188]=true,
+ [4189]=true,
+ [4190]=true,
+ [4191]=true,
+ [4192]=true,
+ [4193]=true,
+ [4197]=true,
+ [4198]=true,
+ [4206]=true,
+ [4207]=true,
+ [4208]=true,
+ [4213]=true,
+ [4214]=true,
+ [4215]=true,
+ [4216]=true,
+ [4217]=true,
+ [4218]=true,
+ [4219]=true,
+ [4220]=true,
+ [4221]=true,
+ [4222]=true,
+ [4223]=true,
+ [4224]=true,
+ [4225]=true,
+ [4226]=true,
+ [4238]=true,
+ [43488]=true,
+ [43489]=true,
+ [43490]=true,
+ [43491]=true,
+ [43492]=true,
+ [43495]=true,
+ [43496]=true,
+ [43497]=true,
+ [43498]=true,
+ [43499]=true,
+ [43500]=true,
+ [43501]=true,
+ [43502]=true,
+ [43503]=true,
+ [43514]=true,
+ [43515]=true,
+ [43516]=true,
+ [43517]=true,
+ [43518]=true,
+ [43616]=true,
+ [43617]=true,
+ [43618]=true,
+ [43619]=true,
+ [43620]=true,
+ [43621]=true,
+ [43622]=true,
+ [43623]=true,
+ [43624]=true,
+ [43625]=true,
+ [43626]=true,
+ [43628]=true,
+ [43629]=true,
+ [43630]=true,
+ [43631]=true,
+ [43633]=true,
+ [43634]=true,
+ [43635]=true,
+ [43636]=true,
+ [43637]=true,
+ [43638]=true,
+ [43642]=true,
+ [43646]=true,
+ [43647]=true,
+ },
+ ["dependent_vowel"]={
+ [2362]=true,
+ [2363]=true,
+ [2366]=true,
+ [2367]=true,
+ [2368]=true,
+ [2369]=true,
+ [2370]=true,
+ [2371]=true,
+ [2372]=true,
+ [2373]=true,
+ [2374]=true,
+ [2375]=true,
+ [2376]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2382]=true,
+ [2383]=true,
+ [2389]=true,
+ [2390]=true,
+ [2391]=true,
+ [2402]=true,
+ [2403]=true,
+ [2494]=true,
+ [2495]=true,
+ [2497]=true,
+ [2498]=true,
+ [2499]=true,
+ [2500]=true,
+ [2503]=true,
+ [2504]=true,
+ [2507]=true,
+ [2508]=true,
+ [2622]=true,
+ [2623]=true,
+ [2624]=true,
+ [2625]=true,
+ [2626]=true,
+ [2631]=true,
+ [2632]=true,
+ [2635]=true,
+ [2636]=true,
+ [2750]=true,
+ [2751]=true,
+ [2752]=true,
+ [2753]=true,
+ [2754]=true,
+ [2755]=true,
+ [2756]=true,
+ [2757]=true,
+ [2759]=true,
+ [2760]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2878]=true,
+ [2879]=true,
+ [2880]=true,
+ [2881]=true,
+ [2882]=true,
+ [2883]=true,
+ [2884]=true,
+ [2887]=true,
+ [2888]=true,
+ [2891]=true,
+ [2892]=true,
+ [2914]=true,
+ [2915]=true,
+ [3006]=true,
+ [3007]=true,
+ [3008]=true,
+ [3009]=true,
+ [3010]=true,
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3018]=true,
+ [3019]=true,
+ [3020]=true,
+ [3134]=true,
+ [3135]=true,
+ [3136]=true,
+ [3137]=true,
+ [3138]=true,
+ [3139]=true,
+ [3140]=true,
+ [3142]=true,
+ [3143]=true,
+ [3144]=true,
+ [3146]=true,
+ [3147]=true,
+ [3148]=true,
+ [3170]=true,
+ [3171]=true,
+ [3262]=true,
+ [3263]=true,
+ [3264]=true,
+ [3265]=true,
+ [3266]=true,
+ [3267]=true,
+ [3268]=true,
+ [3270]=true,
+ [3271]=true,
+ [3272]=true,
+ [3274]=true,
+ [3275]=true,
+ [3276]=true,
+ [3285]=true,
+ [3286]=true,
+ [3298]=true,
+ [3299]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3396]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ [3402]=true,
+ [3403]=true,
+ [3404]=true,
+ [3415]=true,
+ [3426]=true,
+ [3427]=true,
+ [4139]=true,
+ [4140]=true,
+ [4141]=true,
+ [4142]=true,
+ [4143]=true,
+ [4144]=true,
+ [4145]=true,
+ [4146]=true,
+ [4147]=true,
+ [4148]=true,
+ [4149]=true,
+ [4182]=true,
+ [4183]=true,
+ [4184]=true,
+ [4185]=true,
+ [4194]=true,
+ [4199]=true,
+ [4200]=true,
+ [4209]=true,
+ [4210]=true,
+ [4211]=true,
+ [4212]=true,
+ [4227]=true,
+ [4228]=true,
+ [4229]=true,
+ [4230]=true,
+ [4252]=true,
+ [4253]=true,
+ [43493]=true,
+ },
+ ["halant"]={
+ [2381]=true,
+ [2509]=true,
+ [2637]=true,
+ [2765]=true,
+ [2893]=true,
+ [3021]=true,
+ [3149]=true,
+ [3277]=true,
+ [3405]=true,
+ },
+ ["independent_vowel"]={
+ [2308]=true,
+ [2309]=true,
+ [2310]=true,
+ [2311]=true,
+ [2312]=true,
+ [2313]=true,
+ [2314]=true,
+ [2315]=true,
+ [2316]=true,
+ [2317]=true,
+ [2318]=true,
+ [2319]=true,
+ [2320]=true,
+ [2321]=true,
+ [2322]=true,
+ [2323]=true,
+ [2324]=true,
+ [2400]=true,
+ [2401]=true,
+ [2418]=true,
+ [2419]=true,
+ [2420]=true,
+ [2421]=true,
+ [2422]=true,
+ [2423]=true,
+ [2437]=true,
+ [2438]=true,
+ [2439]=true,
+ [2440]=true,
+ [2441]=true,
+ [2442]=true,
+ [2443]=true,
+ [2444]=true,
+ [2447]=true,
+ [2448]=true,
+ [2451]=true,
+ [2452]=true,
+ [2528]=true,
+ [2529]=true,
+ [2530]=true,
+ [2531]=true,
+ [2565]=true,
+ [2566]=true,
+ [2567]=true,
+ [2568]=true,
+ [2569]=true,
+ [2570]=true,
+ [2575]=true,
+ [2576]=true,
+ [2579]=true,
+ [2580]=true,
+ [2693]=true,
+ [2694]=true,
+ [2695]=true,
+ [2696]=true,
+ [2697]=true,
+ [2698]=true,
+ [2699]=true,
+ [2700]=true,
+ [2701]=true,
+ [2703]=true,
+ [2704]=true,
+ [2705]=true,
+ [2707]=true,
+ [2708]=true,
+ [2784]=true,
+ [2785]=true,
+ [2786]=true,
+ [2787]=true,
+ [2821]=true,
+ [2822]=true,
+ [2823]=true,
+ [2824]=true,
+ [2825]=true,
+ [2826]=true,
+ [2827]=true,
+ [2828]=true,
+ [2831]=true,
+ [2832]=true,
+ [2835]=true,
+ [2836]=true,
+ [2912]=true,
+ [2913]=true,
+ [2949]=true,
+ [2950]=true,
+ [2951]=true,
+ [2952]=true,
+ [2953]=true,
+ [2954]=true,
+ [2958]=true,
+ [2959]=true,
+ [2960]=true,
+ [2962]=true,
+ [2963]=true,
+ [2964]=true,
+ [3077]=true,
+ [3078]=true,
+ [3079]=true,
+ [3080]=true,
+ [3081]=true,
+ [3082]=true,
+ [3083]=true,
+ [3084]=true,
+ [3086]=true,
+ [3087]=true,
+ [3088]=true,
+ [3090]=true,
+ [3091]=true,
+ [3092]=true,
+ [3168]=true,
+ [3169]=true,
+ [3205]=true,
+ [3206]=true,
+ [3207]=true,
+ [3208]=true,
+ [3209]=true,
+ [3210]=true,
+ [3211]=true,
+ [3212]=true,
+ [3214]=true,
+ [3215]=true,
+ [3216]=true,
+ [3218]=true,
+ [3219]=true,
+ [3220]=true,
+ [3296]=true,
+ [3297]=true,
+ [3333]=true,
+ [3334]=true,
+ [3335]=true,
+ [3336]=true,
+ [3337]=true,
+ [3338]=true,
+ [3339]=true,
+ [3340]=true,
+ [3342]=true,
+ [3343]=true,
+ [3344]=true,
+ [3346]=true,
+ [3347]=true,
+ [3348]=true,
+ [3423]=true,
+ [3424]=true,
+ [3425]=true,
+ [4129]=true,
+ [4130]=true,
+ [4131]=true,
+ [4132]=true,
+ [4133]=true,
+ [4134]=true,
+ [4135]=true,
+ [4136]=true,
+ [4137]=true,
+ [4138]=true,
+ [4178]=true,
+ [4179]=true,
+ [4180]=true,
+ [4181]=true,
+ },
+ ["nukta"]={
+ [2364]=true,
+ [2492]=true,
+ [2620]=true,
+ [2748]=true,
+ [2876]=true,
+ [3260]=true,
+ },
+ ["post_mark"]={
+ [2307]=true,
+ [2363]=true,
+ [2366]=true,
+ [2368]=true,
+ [2377]=true,
+ [2378]=true,
+ [2379]=true,
+ [2380]=true,
+ [2383]=true,
+ [2494]=true,
+ [2496]=true,
+ [2622]=true,
+ [2624]=true,
+ [2750]=true,
+ [2752]=true,
+ [2761]=true,
+ [2763]=true,
+ [2764]=true,
+ [2878]=true,
+ [2880]=true,
+ [3006]=true,
+ [3007]=true,
+ [3137]=true,
+ [3138]=true,
+ [3139]=true,
+ [3140]=true,
+ [3262]=true,
+ [3265]=true,
+ [3266]=true,
+ [3267]=true,
+ [3268]=true,
+ [3276]=true,
+ [3285]=true,
+ [3390]=true,
+ [3391]=true,
+ [3392]=true,
+ [3393]=true,
+ [3394]=true,
+ [3395]=true,
+ [3396]=true,
+ [3415]=true,
+ [4139]=true,
+ [4140]=true,
+ [4152]=true,
+ [4155]=true,
+ [4182]=true,
+ [4183]=true,
+ [4194]=true,
+ [4195]=true,
+ [4196]=true,
+ [4199]=true,
+ [4200]=true,
+ [4201]=true,
+ [4202]=true,
+ [4203]=true,
+ [4204]=true,
+ [4205]=true,
+ [4227]=true,
+ [4231]=true,
+ [4232]=true,
+ [4233]=true,
+ [4234]=true,
+ [4235]=true,
+ [4236]=true,
+ [4239]=true,
+ [4250]=true,
+ [4251]=true,
+ [4252]=true,
+ [43643]=true,
+ [43645]=true,
+ },
+ ["pre_mark"]={
+ [2367]=true,
+ [2382]=true,
+ [2495]=true,
+ [2503]=true,
+ [2504]=true,
+ [2623]=true,
+ [2751]=true,
+ [2887]=true,
+ [3014]=true,
+ [3015]=true,
+ [3016]=true,
+ [3398]=true,
+ [3399]=true,
+ [3400]=true,
+ [4145]=true,
+ [4228]=true,
+ },
+ ["ra"]={
+ [2352]=true,
+ [2480]=true,
+ [2544]=true,
+ [2608]=true,
+ [2736]=true,
+ [2864]=true,
+ [2992]=true,
+ [3120]=true,
+ [3248]=true,
+ [3376]=true,
+ },
+ ["stress_tone_mark"]={
+ [2385]=true,
+ [2386]=true,
+ [2387]=true,
+ [2388]=true,
+ [4151]=true,
+ [4195]=true,
+ [4196]=true,
+ [4201]=true,
+ [4202]=true,
+ [4203]=true,
+ [4204]=true,
+ [4205]=true,
+ [4231]=true,
+ [4232]=true,
+ [4233]=true,
+ [4234]=true,
+ [4235]=true,
+ [4236]=true,
+ [4237]=true,
+ [4239]=true,
+ [4250]=true,
+ [4251]=true,
+ [43643]=true,
+ [43644]=true,
+ [43645]=true,
+ },
+ ["twopart_mark"]={
+ [2507]={ 2503,2494 },
+ [2508]={ 2503,2519 },
+ [2888]={ 2887,2902 },
+ [2891]={ 2887,2878 },
+ [2892]={ 2887,2903 },
+ [3018]={ 3014,3006 },
+ [3019]={ 3015,3006 },
+ [3020]={ 3014,3031 },
+ [3144]={ 3142,3158 },
+ [3264]={ 3263,3285 },
+ [3271]={ 3270,3285 },
+ [3272]={ 3270,3286 },
+ [3274]={ 3270,3266 },
+ [3275]={ 3274,3285 },
+ [3402]={ 3398,3390 },
+ [3403]={ 3399,3390 },
+ [3404]={ 3398,3415 },
+ },
+ ["vowel_modifier"]={
+ [2304]=true,
+ [2305]=true,
+ [2306]=true,
+ [2307]=true,
+ [2433]=true,
+ [3330]=true,
+ [3331]=true,
+ [4150]=true,
+ [4152]=true,
+ [4153]=true,
+ [4154]=true,
+ [43232]=true,
+ [43233]=true,
+ [43234]=true,
+ [43235]=true,
+ [43236]=true,
+ [43237]=true,
+ [43238]=true,
+ [43239]=true,
+ [43240]=true,
+ [43241]=true,
+ [43242]=true,
+ [43243]=true,
+ [43244]=true,
+ [43245]=true,
+ [43246]=true,
+ [43247]=true,
+ [43249]=true,
+ },
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-ini']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local allocate=utilities.storage.allocate
+local sortedhash=table.sortedhash
+fonts=fonts or {}
+local fonts=fonts
+local identifiers=allocate()
+fonts.hashes=fonts.hashes or { identifiers=identifiers }
+fonts.tables=fonts.tables or {}
+fonts.helpers=fonts.helpers or {}
+fonts.tracers=fonts.tracers or {}
+fonts.specifiers=fonts.specifiers or {}
+fonts.analyzers={}
+fonts.readers={}
+fonts.definers={ methods={} }
+fonts.loggers={ register=function() end }
+if context then
+
+--removed
+
+end
+fonts.privateoffsets={
+ textbase=0xF0000,
+ textextrabase=0xFD000,
+ mathextrabase=0xFE000,
+ mathbase=0xFF000,
+ keepnames=false,
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-font-mis']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local currentfont=font.current
+local hashes=fonts.hashes
+local identifiers=hashes.identifiers or {}
+local marks=hashes.marks or {}
+hashes.identifiers=identifiers
+hashes.marks=marks
+table.setmetatableindex(marks,function(t,k)
+ if k==true then
+ return marks[currentfont()]
+ else
+ local resources=identifiers[k].resources or {}
+ local marks=resources.marks or {}
+ t[k]=marks
+ return marks
+ end
+end)
+function font.each()
+ return table.sortedhash(fonts.hashes.identifiers)
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-con']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,tostring,tonumber,rawget=next,tostring,tonumber,rawget
+local format,match,lower,gsub,find=string.format,string.match,string.lower,string.gsub,string.find
+local sort,insert,concat=table.sort,table.insert,table.concat
+local sortedkeys,sortedhash,serialize,fastcopy=table.sortedkeys,table.sortedhash,table.serialize,table.fastcopy
+local derivetable=table.derive
+local ioflush=io.flush
+local round=math.round
+local setmetatable,getmetatable,rawget,rawset=setmetatable,getmetatable,rawget,rawset
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local trace_scaling=false trackers.register("fonts.scaling",function(v) trace_scaling=v end)
+local report_defining=logs.reporter("fonts","defining")
+local fonts=fonts
+local constructors=fonts.constructors or {}
+fonts.constructors=constructors
+local handlers=fonts.handlers or {}
+fonts.handlers=handlers
+local allocate=utilities.storage.allocate
+local setmetatableindex=table.setmetatableindex
+constructors.dontembed=allocate()
+constructors.autocleanup=true
+constructors.namemode="fullpath"
+constructors.version=1.01
+constructors.cache=containers.define("fonts","constructors",constructors.version,false)
+constructors.privateoffset=fonts.privateoffsets.textbase or 0xF0000
+constructors.cacheintex=true
+constructors.addtounicode=true
+local designsizes=allocate()
+constructors.designsizes=designsizes
+local loadedfonts=allocate()
+constructors.loadedfonts=loadedfonts
+local factors={
+ pt=65536.0,
+ bp=65781.8,
+}
+function constructors.setfactor(f)
+ constructors.factor=factors[f or 'pt'] or factors.pt
+end
+constructors.setfactor()
+function constructors.scaled(scaledpoints,designsize)
+ if scaledpoints<0 then
+ local factor=constructors.factor
+ if designsize then
+ if designsize>factor then
+ return (- scaledpoints/1000)*designsize
+ else
+ return (- scaledpoints/1000)*designsize*factor
+ end
+ else
+ return (- scaledpoints/1000)*10*factor
+ end
+ else
+ return scaledpoints
+ end
+end
+function constructors.getprivate(tfmdata)
+ local properties=tfmdata.properties
+ local private=properties.private
+ properties.private=private+1
+ return private
+end
+function constructors.setmathparameter(tfmdata,name,value)
+ local m=tfmdata.mathparameters
+ local c=tfmdata.MathConstants
+ if m then
+ m[name]=value
+ end
+ if c and c~=m then
+ c[name]=value
+ end
+end
+function constructors.getmathparameter(tfmdata,name)
+ local p=tfmdata.mathparameters or tfmdata.MathConstants
+ if p then
+ return p[name]
+ end
+end
+function constructors.cleanuptable(tfmdata)
+ if constructors.autocleanup and tfmdata.properties.virtualized then
+ for k,v in next,tfmdata.characters do
+ if v.commands then v.commands=nil end
+ end
+ end
+end
+function constructors.calculatescale(tfmdata,scaledpoints)
+ local parameters=tfmdata.parameters
+ if scaledpoints<0 then
+ scaledpoints=(- scaledpoints/1000)*(tfmdata.designsize or parameters.designsize)
+ end
+ return scaledpoints,scaledpoints/(parameters.units or 1000)
+end
+local unscaled={
+ ScriptPercentScaleDown=true,
+ ScriptScriptPercentScaleDown=true,
+ RadicalDegreeBottomRaisePercent=true,
+ NoLimitSupFactor=true,
+ NoLimitSubFactor=true,
+}
+function constructors.assignmathparameters(target,original)
+ local mathparameters=original.mathparameters
+ if mathparameters and next(mathparameters) then
+ local targetparameters=target.parameters
+ local targetproperties=target.properties
+ local targetmathparameters={}
+ local factor=targetproperties.math_is_scaled and 1 or targetparameters.factor
+ for name,value in next,mathparameters do
+ if unscaled[name] then
+ targetmathparameters[name]=value
+ else
+ targetmathparameters[name]=value*factor
+ end
+ end
+ if not targetmathparameters.FractionDelimiterSize then
+ targetmathparameters.FractionDelimiterSize=1.01*targetparameters.size
+ end
+ if not mathparameters.FractionDelimiterDisplayStyleSize then
+ targetmathparameters.FractionDelimiterDisplayStyleSize=2.40*targetparameters.size
+ end
+ target.mathparameters=targetmathparameters
+ end
+end
+function constructors.beforecopyingcharacters(target,original)
+end
+function constructors.aftercopyingcharacters(target,original)
+end
+constructors.sharefonts=false
+constructors.nofsharedfonts=0
+local sharednames={}
+function constructors.trytosharefont(target,tfmdata)
+ if constructors.sharefonts then
+ local characters=target.characters
+ local n=1
+ local t={ target.psname }
+ local u=sortedkeys(characters)
+ for i=1,#u do
+ local k=u[i]
+ n=n+1;t[n]=k
+ n=n+1;t[n]=characters[k].index or k
+ end
+ local h=md5.HEX(concat(t," "))
+ local s=sharednames[h]
+ if s then
+ if trace_defining then
+ report_defining("font %a uses backend resources of font %a",target.fullname,s)
+ end
+ target.fullname=s
+ constructors.nofsharedfonts=constructors.nofsharedfonts+1
+ target.properties.sharedwith=s
+ else
+ sharednames[h]=target.fullname
+ end
+ end
+end
+local synonyms={
+ exheight="x_height",
+ xheight="x_height",
+ ex="x_height",
+ emwidth="quad",
+ em="quad",
+ spacestretch="space_stretch",
+ stretch="space_stretch",
+ spaceshrink="space_shrink",
+ shrink="space_shrink",
+ extraspace="extra_space",
+ xspace="extra_space",
+ slantperpoint="slant",
+}
+function constructors.enhanceparameters(parameters)
+ local mt=getmetatable(parameters)
+ local getter=function(t,k)
+ if not k then
+ return nil
+ end
+ local s=synonyms[k]
+ if s then
+ return rawget(t,s) or (mt and mt[s]) or nil
+ end
+ if k=="spacing" then
+ return {
+ width=t.space,
+ stretch=t.space_stretch,
+ shrink=t.space_shrink,
+ extra=t.extra_space,
+ }
+ end
+ return mt and mt[k] or nil
+ end
+ local setter=function(t,k,v)
+ if not k then
+ return 0
+ end
+ local s=synonyms[k]
+ if s then
+ rawset(t,s,v)
+ elseif k=="spacing" then
+ if type(v)=="table" then
+ rawset(t,"space",v.width or 0)
+ rawset(t,"space_stretch",v.stretch or 0)
+ rawset(t,"space_shrink",v.shrink or 0)
+ rawset(t,"extra_space",v.extra or 0)
+ end
+ else
+ rawset(t,k,v)
+ end
+ end
+ setmetatable(parameters,{
+ __index=getter,
+ __newindex=setter,
+ })
+end
+local function mathkerns(v,vdelta)
+ local k={}
+ for i=1,#v do
+ local entry=v[i]
+ local height=entry.height
+ local kern=entry.kern
+ k[i]={
+ height=height and vdelta*height or 0,
+ kern=kern and vdelta*kern or 0,
+ }
+ end
+ return k
+end
+local psfake=0
+local function fixedpsname(psname,fallback)
+ local usedname=psname
+ if psname and psname~="" then
+ if find(psname," ",1,true) then
+ usedname=gsub(psname,"[%s]+","-")
+ else
+ end
+ elseif not fallback or fallback=="" then
+ psfake=psfake+1
+ psname="fakename-"..psfake
+ else
+ psname=fallback
+ usedname=gsub(psname,"[^a-zA-Z0-9]+","-")
+ end
+ return usedname,psname~=usedname
+end
+function constructors.scale(tfmdata,specification)
+ local target={}
+ if tonumber(specification) then
+ specification={ size=specification }
+ end
+ target.specification=specification
+ local scaledpoints=specification.size
+ local relativeid=specification.relativeid
+ local properties=tfmdata.properties or {}
+ local goodies=tfmdata.goodies or {}
+ local resources=tfmdata.resources or {}
+ local descriptions=tfmdata.descriptions or {}
+ local characters=tfmdata.characters or {}
+ local changed=tfmdata.changed or {}
+ local shared=tfmdata.shared or {}
+ local parameters=tfmdata.parameters or {}
+ local mathparameters=tfmdata.mathparameters or {}
+ local targetcharacters={}
+ local targetdescriptions=derivetable(descriptions)
+ local targetparameters=derivetable(parameters)
+ local targetproperties=derivetable(properties)
+ local targetgoodies=goodies
+ target.characters=targetcharacters
+ target.descriptions=targetdescriptions
+ target.parameters=targetparameters
+ target.properties=targetproperties
+ target.goodies=targetgoodies
+ target.shared=shared
+ target.resources=resources
+ target.unscaled=tfmdata
+ local mathsize=tonumber(specification.mathsize) or 0
+ local textsize=tonumber(specification.textsize) or scaledpoints
+ local forcedsize=tonumber(parameters.mathsize ) or 0
+ local extrafactor=tonumber(specification.factor ) or 1
+ if (mathsize==2 or forcedsize==2) and parameters.scriptpercentage then
+ scaledpoints=parameters.scriptpercentage*textsize/100
+ elseif (mathsize==3 or forcedsize==3) and parameters.scriptscriptpercentage then
+ scaledpoints=parameters.scriptscriptpercentage*textsize/100
+ elseif forcedsize>1000 then
+ scaledpoints=forcedsize
+ else
+ end
+ targetparameters.mathsize=mathsize
+ targetparameters.textsize=textsize
+ targetparameters.forcedsize=forcedsize
+ targetparameters.extrafactor=extrafactor
+ local addtounicode=constructors.addtounicode
+ local tounicode=fonts.mappings.tounicode
+ local unknowncode=tounicode(0xFFFD)
+ local defaultwidth=resources.defaultwidth or 0
+ local defaultheight=resources.defaultheight or 0
+ local defaultdepth=resources.defaultdepth or 0
+ local units=parameters.units or 1000
+ targetproperties.language=properties.language or "dflt"
+ targetproperties.script=properties.script or "dflt"
+ targetproperties.mode=properties.mode or "base"
+ local askedscaledpoints=scaledpoints
+ local scaledpoints,delta=constructors.calculatescale(tfmdata,scaledpoints,nil,specification)
+ local hdelta=delta
+ local vdelta=delta
+ target.designsize=parameters.designsize
+ target.units=units
+ target.units_per_em=units
+ local direction=properties.direction or tfmdata.direction or 0
+ target.direction=direction
+ properties.direction=direction
+ target.size=scaledpoints
+ target.encodingbytes=properties.encodingbytes or 1
+ target.embedding=properties.embedding or "subset"
+ target.tounicode=1
+ target.cidinfo=properties.cidinfo
+ target.format=properties.format
+ target.cache=constructors.cacheintex and "yes" or "renew"
+ local fontname=properties.fontname or tfmdata.fontname
+ local fullname=properties.fullname or tfmdata.fullname
+ local filename=properties.filename or tfmdata.filename
+ local psname=properties.psname or tfmdata.psname
+ local name=properties.name or tfmdata.name
+ local psname,psfixed=fixedpsname(psname,fontname or fullname or file.nameonly(filename))
+ target.fontname=fontname
+ target.fullname=fullname
+ target.filename=filename
+ target.psname=psname
+ target.name=name
+ properties.fontname=fontname
+ properties.fullname=fullname
+ properties.filename=filename
+ properties.psname=psname
+ properties.name=name
+ local expansion=parameters.expansion
+ if expansion then
+ target.stretch=expansion.stretch
+ target.shrink=expansion.shrink
+ target.step=expansion.step
+ end
+ local slantfactor=parameters.slantfactor or 0
+ if slantfactor~=0 then
+ target.slant=slantfactor*1000
+ else
+ target.slant=0
+ end
+ local extendfactor=parameters.extendfactor or 0
+ if extendfactor~=0 and extendfactor~=1 then
+ hdelta=hdelta*extendfactor
+ target.extend=extendfactor*1000
+ else
+ target.extend=1000
+ end
+ local squeezefactor=parameters.squeezefactor or 0
+ if squeezefactor~=0 and squeezefactor~=1 then
+ vdelta=vdelta*squeezefactor
+ target.squeeze=squeezefactor*1000
+ else
+ target.squeeze=1000
+ end
+ local mode=parameters.mode or 0
+ if mode~=0 then
+ target.mode=mode
+ end
+ local width=parameters.width or 0
+ if width~=0 then
+ target.width=width*delta*1000/655360
+ end
+ targetparameters.factor=delta
+ targetparameters.hfactor=hdelta
+ targetparameters.vfactor=vdelta
+ targetparameters.size=scaledpoints
+ targetparameters.units=units
+ targetparameters.scaledpoints=askedscaledpoints
+ targetparameters.mode=mode
+ targetparameters.width=width
+ local isvirtual=properties.virtualized or tfmdata.type=="virtual"
+ local hasquality=parameters.expansion or parameters.protrusion
+ local hasitalics=properties.hasitalics
+ local autoitalicamount=properties.autoitalicamount
+ local stackmath=not properties.nostackmath
+ local haskerns=properties.haskerns or properties.mode=="base"
+ local hasligatures=properties.hasligatures or properties.mode=="base"
+ local realdimensions=properties.realdimensions
+ local writingmode=properties.writingmode or "horizontal"
+ local identity=properties.identity or "horizontal"
+ local vfonts=target.fonts
+ if vfonts and #vfonts>0 then
+ target.fonts=fastcopy(vfonts)
+ elseif isvirtual then
+ target.fonts={ { id=0 } }
+ end
+ if changed and not next(changed) then
+ changed=false
+ end
+ target.type=isvirtual and "virtual" or "real"
+ target.writingmode=writingmode=="vertical" and "vertical" or "horizontal"
+ target.identity=identity=="vertical" and "vertical" or "horizontal"
+ target.postprocessors=tfmdata.postprocessors
+ local targetslant=(parameters.slant or parameters[1] or 0)*factors.pt
+ local targetspace=(parameters.space or parameters[2] or 0)*hdelta
+ local targetspace_stretch=(parameters.space_stretch or parameters[3] or 0)*hdelta
+ local targetspace_shrink=(parameters.space_shrink or parameters[4] or 0)*hdelta
+ local targetx_height=(parameters.x_height or parameters[5] or 0)*vdelta
+ local targetquad=(parameters.quad or parameters[6] or 0)*hdelta
+ local targetextra_space=(parameters.extra_space or parameters[7] or 0)*hdelta
+ targetparameters.slant=targetslant
+ targetparameters.space=targetspace
+ targetparameters.space_stretch=targetspace_stretch
+ targetparameters.space_shrink=targetspace_shrink
+ targetparameters.x_height=targetx_height
+ targetparameters.quad=targetquad
+ targetparameters.extra_space=targetextra_space
+ local ascender=parameters.ascender
+ if ascender then
+ targetparameters.ascender=delta*ascender
+ end
+ local descender=parameters.descender
+ if descender then
+ targetparameters.descender=delta*descender
+ end
+ constructors.enhanceparameters(targetparameters)
+ local protrusionfactor=(targetquad~=0 and 1000/targetquad) or 0
+ local scaledwidth=defaultwidth*hdelta
+ local scaledheight=defaultheight*vdelta
+ local scaleddepth=defaultdepth*vdelta
+ local hasmath=(properties.hasmath or next(mathparameters)) and true
+ if hasmath then
+ constructors.assignmathparameters(target,tfmdata)
+ properties.hasmath=true
+ target.nomath=false
+ target.MathConstants=target.mathparameters
+ else
+ properties.hasmath=false
+ target.nomath=true
+ target.mathparameters=nil
+ end
+ if hasmath then
+ local mathitalics=properties.mathitalics
+ if mathitalics==false then
+ if trace_defining then
+ report_defining("%s italics %s for font %a, fullname %a, filename %a","math",hasitalics and "ignored" or "disabled",name,fullname,filename)
+ end
+ hasitalics=false
+ autoitalicamount=false
+ end
+ else
+ local textitalics=properties.textitalics
+ if textitalics==false then
+ if trace_defining then
+ report_defining("%s italics %s for font %a, fullname %a, filename %a","text",hasitalics and "ignored" or "disabled",name,fullname,filename)
+ end
+ hasitalics=false
+ autoitalicamount=false
+ end
+ end
+ if trace_defining then
+ report_defining("defining tfm, name %a, fullname %a, filename %a, %spsname %a, hscale %a, vscale %a, math %a, italics %a",
+ name,fullname,filename,psfixed and "(fixed) " or "",psname,hdelta,vdelta,
+ hasmath and "enabled" or "disabled",hasitalics and "enabled" or "disabled")
+ end
+ constructors.beforecopyingcharacters(target,tfmdata)
+ local sharedkerns={}
+ for unicode,character in next,characters do
+ local chr,description,index
+ if changed then
+ local c=changed[unicode]
+ if c and c~=unicode then
+ if c then
+ description=descriptions[c] or descriptions[unicode] or character
+ character=characters[c] or character
+ index=description.index or c
+ else
+ description=descriptions[unicode] or character
+ index=description.index or unicode
+ end
+ else
+ description=descriptions[unicode] or character
+ index=description.index or unicode
+ end
+ else
+ description=descriptions[unicode] or character
+ index=description.index or unicode
+ end
+ local width=description.width
+ local height=description.height
+ local depth=description.depth
+ local isunicode=description.unicode
+ if realdimensions then
+ if not height or height==0 then
+ local bb=description.boundingbox
+ local ht=bb[4]
+ if ht~=0 then
+ height=ht
+ end
+ if not depth or depth==0 then
+ local dp=-bb[2]
+ if dp~=0 then
+ depth=dp
+ end
+ end
+ elseif not depth or depth==0 then
+ local dp=-description.boundingbox[2]
+ if dp~=0 then
+ depth=dp
+ end
+ end
+ end
+ if width then width=hdelta*width else width=scaledwidth end
+ if height then height=vdelta*height else height=scaledheight end
+ if depth and depth~=0 then
+ depth=delta*depth
+ if isunicode then
+ chr={
+ index=index,
+ height=height,
+ depth=depth,
+ width=width,
+ unicode=isunicode,
+ }
+ else
+ chr={
+ index=index,
+ height=height,
+ depth=depth,
+ width=width,
+ }
+ end
+ else
+ if isunicode then
+ chr={
+ index=index,
+ height=height,
+ width=width,
+ unicode=isunicode,
+ }
+ else
+ chr={
+ index=index,
+ height=height,
+ width=width,
+ }
+ end
+ end
+ if addtounicode then
+ chr.tounicode=isunicode and tounicode(isunicode) or unknowncode
+ end
+ if hasquality then
+ local ve=character.expansion_factor
+ if ve then
+ chr.expansion_factor=ve*1000
+ end
+ local vl=character.left_protruding
+ if vl then
+ chr.left_protruding=protrusionfactor*width*vl
+ end
+ local vr=character.right_protruding
+ if vr then
+ chr.right_protruding=protrusionfactor*width*vr
+ end
+ end
+ if hasmath then
+ local vn=character.next
+ if vn then
+ chr.next=vn
+ else
+ local vv=character.vert_variants
+ if vv then
+ local t={}
+ for i=1,#vv do
+ local vvi=vv[i]
+ local s=vvi["start"] or 0
+ local e=vvi["end"] or 0
+ local a=vvi["advance"] or 0
+ t[i]={
+ ["start"]=s==0 and 0 or s*vdelta,
+ ["end"]=e==0 and 0 or e*vdelta,
+ ["advance"]=a==0 and 0 or a*vdelta,
+ ["extender"]=vvi["extender"],
+ ["glyph"]=vvi["glyph"],
+ }
+ end
+ chr.vert_variants=t
+ else
+ local hv=character.horiz_variants
+ if hv then
+ local t={}
+ for i=1,#hv do
+ local hvi=hv[i]
+ local s=hvi["start"] or 0
+ local e=hvi["end"] or 0
+ local a=hvi["advance"] or 0
+ t[i]={
+ ["start"]=s==0 and 0 or s*hdelta,
+ ["end"]=e==0 and 0 or e*hdelta,
+ ["advance"]=a==0 and 0 or a*hdelta,
+ ["extender"]=hvi["extender"],
+ ["glyph"]=hvi["glyph"],
+ }
+ end
+ chr.horiz_variants=t
+ end
+ end
+ end
+ local vi=character.vert_italic
+ if vi and vi~=0 then
+ chr.vert_italic=vi*hdelta
+ end
+ local va=character.accent
+ if va then
+ chr.top_accent=vdelta*va
+ end
+ if stackmath then
+ local mk=character.mathkerns
+ if mk then
+ local tr=mk.topright
+ local tl=mk.topleft
+ local br=mk.bottomright
+ local bl=mk.bottomleft
+ chr.mathkern={
+ top_right=tr and mathkerns(tr,vdelta) or nil,
+ top_left=tl and mathkerns(tl,vdelta) or nil,
+ bottom_right=br and mathkerns(br,vdelta) or nil,
+ bottom_left=bl and mathkerns(bl,vdelta) or nil,
+ }
+ end
+ end
+ if hasitalics then
+ local vi=character.italic
+ if vi and vi~=0 then
+ chr.italic=vi*hdelta
+ end
+ end
+ elseif autoitalicamount then
+ local vi=description.italic
+ if not vi then
+ local bb=description.boundingbox
+ if bb then
+ local vi=bb[3]-description.width+autoitalicamount
+ if vi>0 then
+ chr.italic=vi*hdelta
+ end
+ else
+ end
+ elseif vi~=0 then
+ chr.italic=vi*hdelta
+ end
+ elseif hasitalics then
+ local vi=character.italic
+ if vi and vi~=0 then
+ chr.italic=vi*hdelta
+ end
+ end
+ if haskerns then
+ local vk=character.kerns
+ if vk then
+ local s=sharedkerns[vk]
+ if not s then
+ s={}
+ for k,v in next,vk do s[k]=v*hdelta end
+ sharedkerns[vk]=s
+ end
+ chr.kerns=s
+ end
+ end
+ if hasligatures then
+ local vl=character.ligatures
+ if vl then
+ if true then
+ chr.ligatures=vl
+ else
+ local tt={}
+ for i,l in next,vl do
+ tt[i]=l
+ end
+ chr.ligatures=tt
+ end
+ end
+ end
+ if isvirtual then
+ local vc=character.commands
+ if vc then
+ local ok=false
+ for i=1,#vc do
+ local key=vc[i][1]
+ if key=="right" or key=="down" or key=="rule" then
+ ok=true
+ break
+ end
+ end
+ if ok then
+ local tt={}
+ for i=1,#vc do
+ local ivc=vc[i]
+ local key=ivc[1]
+ if key=="right" then
+ tt[i]={ key,ivc[2]*hdelta }
+ elseif key=="down" then
+ tt[i]={ key,ivc[2]*vdelta }
+ elseif key=="rule" then
+ tt[i]={ key,ivc[2]*vdelta,ivc[3]*hdelta }
+ else
+ tt[i]=ivc
+ end
+ end
+ chr.commands=tt
+ else
+ chr.commands=vc
+ end
+ end
+ end
+ targetcharacters[unicode]=chr
+ end
+ properties.setitalics=hasitalics
+ constructors.aftercopyingcharacters(target,tfmdata)
+ constructors.trytosharefont(target,tfmdata)
+ local vfonts=target.fonts
+ if isvirtual or target.type=="virtual" or properties.virtualized then
+ properties.virtualized=true
+ target.type="virtual"
+ if not vfonts or #vfonts==0 then
+ target.fonts={ { id=0 } }
+ end
+ elseif vfonts then
+ properties.virtualized=true
+ target.type="virtual"
+ if #vfonts==0 then
+ target.fonts={ { id=0 } }
+ end
+ end
+ return target
+end
+function constructors.finalize(tfmdata)
+ if tfmdata.properties and tfmdata.properties.finalized then
+ return
+ end
+ if not tfmdata.characters then
+ return nil
+ end
+ if not tfmdata.goodies then
+ tfmdata.goodies={}
+ end
+ local parameters=tfmdata.parameters
+ if not parameters then
+ return nil
+ end
+ if not parameters.expansion then
+ parameters.expansion={
+ stretch=tfmdata.stretch or 0,
+ shrink=tfmdata.shrink or 0,
+ step=tfmdata.step or 0,
+ }
+ end
+ if not parameters.size then
+ parameters.size=tfmdata.size
+ end
+ if not parameters.mode then
+ parameters.mode=0
+ end
+ if not parameters.width then
+ parameters.width=0
+ end
+ if not parameters.slantfactor then
+ parameters.slantfactor=(tfmdata.slant or 0)/1000
+ end
+ if not parameters.extendfactor then
+ parameters.extendfactor=(tfmdata.extend or 1000)/1000
+ end
+ if not parameters.squeezefactor then
+ parameters.squeezefactor=(tfmdata.squeeze or 1000)/1000
+ end
+ local designsize=parameters.designsize
+ if designsize then
+ parameters.minsize=tfmdata.minsize or designsize
+ parameters.maxsize=tfmdata.maxsize or designsize
+ else
+ designsize=factors.pt*10
+ parameters.designsize=designsize
+ parameters.minsize=designsize
+ parameters.maxsize=designsize
+ end
+ parameters.minsize=tfmdata.minsize or parameters.designsize
+ parameters.maxsize=tfmdata.maxsize or parameters.designsize
+ if not parameters.units then
+ parameters.units=tfmdata.units or tfmdata.units_per_em or 1000
+ end
+ if not tfmdata.descriptions then
+ local descriptions={}
+ setmetatableindex(descriptions,function(t,k) local v={} t[k]=v return v end)
+ tfmdata.descriptions=descriptions
+ end
+ local properties=tfmdata.properties
+ if not properties then
+ properties={}
+ tfmdata.properties=properties
+ end
+ if not properties.virtualized then
+ properties.virtualized=tfmdata.type=="virtual"
+ end
+ properties.fontname=properties.fontname or tfmdata.fontname
+ properties.filename=properties.filename or tfmdata.filename
+ properties.fullname=properties.fullname or tfmdata.fullname
+ properties.name=properties.name or tfmdata.name
+ properties.psname=properties.psname or tfmdata.psname
+ properties.encodingbytes=tfmdata.encodingbytes or 1
+ properties.embedding=tfmdata.embedding or "subset"
+ properties.tounicode=tfmdata.tounicode or 1
+ properties.cidinfo=tfmdata.cidinfo or nil
+ properties.format=tfmdata.format or "type1"
+ properties.direction=tfmdata.direction or 0
+ properties.writingmode=tfmdata.writingmode or "horizontal"
+ properties.identity=tfmdata.identity or "horizontal"
+ properties.usedbitmap=tfmdata.usedbitmap
+ if not tfmdata.resources then
+ tfmdata.resources={}
+ end
+ if not tfmdata.shared then
+ tfmdata.shared={}
+ end
+ if not properties.hasmath then
+ properties.hasmath=not tfmdata.nomath
+ end
+ tfmdata.MathConstants=nil
+ tfmdata.postprocessors=nil
+ tfmdata.fontname=nil
+ tfmdata.filename=nil
+ tfmdata.fullname=nil
+ tfmdata.name=nil
+ tfmdata.psname=nil
+ tfmdata.encodingbytes=nil
+ tfmdata.embedding=nil
+ tfmdata.tounicode=nil
+ tfmdata.cidinfo=nil
+ tfmdata.format=nil
+ tfmdata.direction=nil
+ tfmdata.type=nil
+ tfmdata.nomath=nil
+ tfmdata.designsize=nil
+ tfmdata.size=nil
+ tfmdata.stretch=nil
+ tfmdata.shrink=nil
+ tfmdata.step=nil
+ tfmdata.slant=nil
+ tfmdata.extend=nil
+ tfmdata.squeeze=nil
+ tfmdata.mode=nil
+ tfmdata.width=nil
+ tfmdata.units=nil
+ tfmdata.units_per_em=nil
+ tfmdata.cache=nil
+ properties.finalized=true
+ return tfmdata
+end
+local hashmethods={}
+constructors.hashmethods=hashmethods
+function constructors.hashfeatures(specification)
+ local features=specification.features
+ if features then
+ local t,n={},0
+ for category,list in sortedhash(features) do
+ if next(list) then
+ local hasher=hashmethods[category]
+ if hasher then
+ local hash=hasher(list)
+ if hash then
+ n=n+1
+ t[n]=category..":"..hash
+ end
+ end
+ end
+ end
+ if n>0 then
+ return concat(t," & ")
+ end
+ end
+ return "unknown"
+end
+hashmethods.normal=function(list)
+ local s={}
+ local n=0
+ for k,v in next,list do
+ if not k then
+ elseif k=="number" or k=="features" then
+ else
+ n=n+1
+ if type(v)=="table" then
+ local t={}
+ local m=0
+ for k,v in next,v do
+ m=m+1
+ t[m]=k..'='..tostring(v)
+ end
+ s[n]=k..'={'..concat(t,",").."}"
+ else
+ s[n]=k..'='..tostring(v)
+ end
+ end
+ end
+ if n>0 then
+ sort(s)
+ return concat(s,"+")
+ end
+end
+function constructors.hashinstance(specification,force)
+ local hash=specification.hash
+ local size=specification.size
+ local fallbacks=specification.fallbacks
+ if force or not hash then
+ hash=constructors.hashfeatures(specification)
+ specification.hash=hash
+ end
+ if size<1000 and designsizes[hash] then
+ size=round(constructors.scaled(size,designsizes[hash]))
+ else
+ size=round(size)
+ end
+ specification.size=size
+ if fallbacks then
+ return hash..' @ '..size..' @ '..fallbacks
+ else
+ return hash..' @ '..size
+ end
+end
+function constructors.setname(tfmdata,specification)
+ if constructors.namemode=="specification" then
+ local specname=specification.specification
+ if specname then
+ tfmdata.properties.name=specname
+ if trace_defining then
+ report_otf("overloaded fontname %a",specname)
+ end
+ end
+ end
+end
+function constructors.checkedfilename(data)
+ local foundfilename=data.foundfilename
+ if not foundfilename then
+ local askedfilename=data.filename or ""
+ if askedfilename~="" then
+ askedfilename=resolvers.resolve(askedfilename)
+ foundfilename=resolvers.findbinfile(askedfilename,"") or ""
+ if foundfilename=="" then
+ report_defining("source file %a is not found",askedfilename)
+ foundfilename=resolvers.findbinfile(file.basename(askedfilename),"") or ""
+ if foundfilename~="" then
+ report_defining("using source file %a due to cache mismatch",foundfilename)
+ end
+ end
+ end
+ data.foundfilename=foundfilename
+ end
+ return foundfilename
+end
+local formats=allocate()
+fonts.formats=formats
+setmetatableindex(formats,function(t,k)
+ local l=lower(k)
+ if rawget(t,k) then
+ t[k]=l
+ return l
+ end
+ return rawget(t,file.suffix(l))
+end)
+do
+ local function setindeed(mode,source,target,group,name,position)
+ local action=source[mode]
+ if not action then
+ return
+ end
+ local t=target[mode]
+ if not t then
+ report_defining("fatal error in setting feature %a, group %a, mode %a",name,group,mode)
+ os.exit()
+ elseif position then
+ insert(t,position,{ name=name,action=action })
+ else
+ for i=1,#t do
+ local ti=t[i]
+ if ti.name==name then
+ ti.action=action
+ return
+ end
+ end
+ insert(t,{ name=name,action=action })
+ end
+ end
+ local function set(group,name,target,source)
+ target=target[group]
+ if not target then
+ report_defining("fatal target error in setting feature %a, group %a",name,group)
+ os.exit()
+ end
+ local source=source[group]
+ if not source then
+ report_defining("fatal source error in setting feature %a, group %a",name,group)
+ os.exit()
+ end
+ local position=source.position
+ setindeed("node",source,target,group,name,position)
+ setindeed("base",source,target,group,name,position)
+ setindeed("plug",source,target,group,name,position)
+ end
+ local function register(where,specification)
+ local name=specification.name
+ if name and name~="" then
+ local default=specification.default
+ local description=specification.description
+ local initializers=specification.initializers
+ local processors=specification.processors
+ local manipulators=specification.manipulators
+ local modechecker=specification.modechecker
+ if default then
+ where.defaults[name]=default
+ end
+ if description and description~="" then
+ where.descriptions[name]=description
+ end
+ if initializers then
+ set('initializers',name,where,specification)
+ end
+ if processors then
+ set('processors',name,where,specification)
+ end
+ if manipulators then
+ set('manipulators',name,where,specification)
+ end
+ if modechecker then
+ where.modechecker=modechecker
+ end
+ end
+ end
+ constructors.registerfeature=register
+ function constructors.getfeatureaction(what,where,mode,name)
+ what=handlers[what].features
+ if what then
+ where=what[where]
+ if where then
+ mode=where[mode]
+ if mode then
+ for i=1,#mode do
+ local m=mode[i]
+ if m.name==name then
+ return m.action
+ end
+ end
+ end
+ end
+ end
+ end
+ local newfeatures={}
+ constructors.newfeatures=newfeatures
+ constructors.features=newfeatures
+ local function setnewfeatures(what)
+ local handler=handlers[what]
+ local features=handler.features
+ if not features then
+ local tables=handler.tables
+ local statistics=handler.statistics
+ features=allocate {
+ defaults={},
+ descriptions=tables and tables.features or {},
+ used=statistics and statistics.usedfeatures or {},
+ initializers={ base={},node={},plug={} },
+ processors={ base={},node={},plug={} },
+ manipulators={ base={},node={},plug={} },
+ }
+ features.register=function(specification) return register(features,specification) end
+ handler.features=features
+ end
+ return features
+ end
+ setmetatable(newfeatures,{
+ __call=function(t,k) local v=t[k] return v end,
+ __index=function(t,k) local v=setnewfeatures(k) t[k]=v return v end,
+ })
+end
+do
+ local newhandler={}
+ constructors.handlers=newhandler
+ constructors.newhandler=newhandler
+ local function setnewhandler(what)
+ local handler=handlers[what]
+ if not handler then
+ handler={}
+ handlers[what]=handler
+ end
+ return handler
+ end
+ setmetatable(newhandler,{
+ __call=function(t,k) local v=t[k] return v end,
+ __index=function(t,k) local v=setnewhandler(k) t[k]=v return v end,
+ })
+end
+do
+ local newenhancer={}
+ constructors.enhancers=newenhancer
+ constructors.newenhancer=newenhancer
+ local function setnewenhancer(format)
+ local handler=handlers[format]
+ local enhancers=handler.enhancers
+ if not enhancers then
+ local actions=allocate()
+ local before=allocate()
+ local after=allocate()
+ local order=allocate()
+ local known={}
+ local nofsteps=0
+ local patches={ before=before,after=after }
+ local trace=false
+ local report=logs.reporter("fonts",format.." enhancing")
+ trackers.register(format..".loading",function(v) trace=v end)
+ local function enhance(name,data,filename,raw)
+ local enhancer=actions[name]
+ if enhancer then
+ if trace then
+ report("apply enhancement %a to file %a",name,filename)
+ ioflush()
+ end
+ enhancer(data,filename,raw)
+ else
+ end
+ end
+ local function apply(data,filename,raw)
+ local basename=file.basename(lower(filename))
+ if trace then
+ report("%s enhancing file %a","start",filename)
+ end
+ ioflush()
+ for e=1,nofsteps do
+ local enhancer=order[e]
+ local b=before[enhancer]
+ if b then
+ for pattern,action in next,b do
+ if find(basename,pattern) then
+ action(data,filename,raw)
+ end
+ end
+ end
+ enhance(enhancer,data,filename,raw)
+ local a=after[enhancer]
+ if a then
+ for pattern,action in next,a do
+ if find(basename,pattern) then
+ action(data,filename,raw)
+ end
+ end
+ end
+ ioflush()
+ end
+ if trace then
+ report("%s enhancing file %a","stop",filename)
+ end
+ ioflush()
+ end
+ local function register(what,action)
+ if action then
+ if actions[what] then
+ else
+ nofsteps=nofsteps+1
+ order[nofsteps]=what
+ known[what]=nofsteps
+ end
+ actions[what]=action
+ else
+ report("bad enhancer %a",what)
+ end
+ end
+ local function patch(what,where,pattern,action)
+ local pw=patches[what]
+ if pw then
+ local ww=pw[where]
+ if ww then
+ ww[pattern]=action
+ else
+ pw[where]={ [pattern]=action }
+ if not known[where] then
+ nofsteps=nofsteps+1
+ order[nofsteps]=where
+ known[where]=nofsteps
+ end
+ end
+ end
+ end
+ enhancers={
+ register=register,
+ apply=apply,
+ patch=patch,
+ report=report,
+ patches={
+ register=patch,
+ report=report,
+ },
+ }
+ handler.enhancers=enhancers
+ end
+ return enhancers
+ end
+ setmetatable(newenhancer,{
+ __call=function(t,k) local v=t[k] return v end,
+ __index=function(t,k) local v=setnewenhancer(k) t[k]=v return v end,
+ })
+end
+function constructors.checkedfeatures(what,features)
+ local defaults=handlers[what].features.defaults
+ if features and next(features) then
+ features=fastcopy(features)
+ for key,value in next,defaults do
+ if features[key]==nil then
+ features[key]=value
+ end
+ end
+ return features
+ else
+ return fastcopy(defaults)
+ end
+end
+function constructors.initializefeatures(what,tfmdata,features,trace,report)
+ if features and next(features) then
+ local properties=tfmdata.properties or {}
+ local whathandler=handlers[what]
+ local whatfeatures=whathandler.features
+ local whatmodechecker=whatfeatures.modechecker
+ local mode=properties.mode or (whatmodechecker and whatmodechecker(tfmdata,features,features.mode)) or features.mode or "base"
+ properties.mode=mode
+ features.mode=mode
+ local done={}
+ while true do
+ local redo=false
+ local initializers=whatfeatures.initializers[mode]
+ if initializers then
+ for i=1,#initializers do
+ local step=initializers[i]
+ local feature=step.name
+ local value=features[feature]
+ if not value then
+ elseif done[feature] then
+ else
+ local action=step.action
+ if trace then
+ report("initializing feature %a to %a for mode %a for font %a",feature,
+ value,mode,tfmdata.properties.fullname)
+ end
+ action(tfmdata,value,features)
+ if mode~=properties.mode or mode~=features.mode then
+ if whatmodechecker then
+ properties.mode=whatmodechecker(tfmdata,features,properties.mode)
+ features.mode=properties.mode
+ end
+ if mode~=properties.mode then
+ mode=properties.mode
+ redo=true
+ end
+ end
+ done[feature]=true
+ end
+ if redo then
+ break
+ end
+ end
+ if not redo then
+ break
+ end
+ else
+ break
+ end
+ end
+ properties.mode=mode
+ return true
+ else
+ return false
+ end
+end
+function constructors.collectprocessors(what,tfmdata,features,trace,report)
+ local processes={}
+ local nofprocesses=0
+ if features and next(features) then
+ local properties=tfmdata.properties
+ local whathandler=handlers[what]
+ local whatfeatures=whathandler.features
+ local whatprocessors=whatfeatures.processors
+ local mode=properties.mode
+ local processors=whatprocessors[mode]
+ if processors then
+ for i=1,#processors do
+ local step=processors[i]
+ local feature=step.name
+ if features[feature] then
+ local action=step.action
+ if trace then
+ report("installing feature processor %a for mode %a for font %a",feature,mode,tfmdata.properties.fullname)
+ end
+ if action then
+ nofprocesses=nofprocesses+1
+ processes[nofprocesses]=action
+ end
+ end
+ end
+ elseif trace then
+ report("no feature processors for mode %a for font %a",mode,properties.fullname)
+ end
+ end
+ return processes
+end
+function constructors.applymanipulators(what,tfmdata,features,trace,report)
+ if features and next(features) then
+ local properties=tfmdata.properties
+ local whathandler=handlers[what]
+ local whatfeatures=whathandler.features
+ local whatmanipulators=whatfeatures.manipulators
+ local mode=properties.mode
+ local manipulators=whatmanipulators[mode]
+ if manipulators then
+ for i=1,#manipulators do
+ local step=manipulators[i]
+ local feature=step.name
+ local value=features[feature]
+ if value then
+ local action=step.action
+ if trace then
+ report("applying feature manipulator %a for mode %a for font %a",feature,mode,properties.fullname)
+ end
+ if action then
+ action(tfmdata,feature,value)
+ end
+ end
+ end
+ end
+ end
+end
+function constructors.addcoreunicodes(unicodes)
+ if not unicodes then
+ unicodes={}
+ end
+ unicodes.space=0x0020
+ unicodes.hyphen=0x002D
+ unicodes.zwj=0x200D
+ unicodes.zwnj=0x200C
+ return unicodes
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-font-enc']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local fonts=fonts
+local encodings={}
+fonts.encodings=encodings
+encodings.agl={}
+encodings.known={}
+setmetatable(encodings.agl,{ __index=function(t,k)
+ if k=="unicodes" then
+ logs.report("fonts","loading (extended) adobe glyph list")
+ local unicodes=dofile(resolvers.findfile("font-age.lua"))
+ encodings.agl={ unicodes=unicodes }
+ return unicodes
+ else
+ return nil
+ end
+end })
+encodings.cache=containers.define("fonts","enc",encodings.version,true)
+function encodings.load(filename)
+ local name=file.removesuffix(filename)
+ local data=containers.read(encodings.cache,name)
+ if data then
+ return data
+ end
+ local vector,tag,hash,unicodes={},"",{},{}
+ local foundname=resolvers.findfile(filename,'enc')
+ if foundname and foundname~="" then
+ local ok,encoding,size=resolvers.loadbinfile(foundname)
+ if ok and encoding then
+ encoding=string.gsub(encoding,"%%(.-)\n","")
+ local unicoding=encodings.agl.unicodes
+ local tag,vec=string.match(encoding,"/(%w+)%s*%[(.*)%]%s*def")
+ local i=0
+ for ch in string.gmatch(vec,"/([%a%d%.]+)") do
+ if ch~=".notdef" then
+ vector[i]=ch
+ if not hash[ch] then
+ hash[ch]=i
+ else
+ end
+ local u=unicoding[ch]
+ if u then
+ unicodes[u]=i
+ end
+ end
+ i=i+1
+ end
+ end
+ end
+ local data={
+ name=name,
+ tag=tag,
+ vector=vector,
+ hash=hash,
+ unicodes=unicodes
+ }
+ return containers.write(encodings.cache,name,data)
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-cid']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local format,match,lower=string.format,string.match,string.lower
+local tonumber=tonumber
+local P,S,R,C,V,lpegmatch=lpeg.P,lpeg.S,lpeg.R,lpeg.C,lpeg.V,lpeg.match
+local fonts,logs,trackers=fonts,logs,trackers
+local trace_loading=false trackers.register("otf.loading",function(v) trace_loading=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local cid={}
+fonts.cid=cid
+local cidmap={}
+local cidmax=10
+local number=C(R("09","af","AF")^1)
+local space=S(" \n\r\t")
+local spaces=space^0
+local period=P(".")
+local periods=period*period
+local name=P("/")*C((1-space)^1)
+local unicodes,names={},{}
+local function do_one(a,b)
+ unicodes[tonumber(a)]=tonumber(b,16)
+end
+local function do_range(a,b,c)
+ c=tonumber(c,16)
+ for i=tonumber(a),tonumber(b) do
+ unicodes[i]=c
+ c=c+1
+ end
+end
+local function do_name(a,b)
+ names[tonumber(a)]=b
+end
+local grammar=P { "start",
+ start=number*spaces*number*V("series"),
+ series=(spaces*(V("one")+V("range")+V("named")))^1,
+ one=(number*spaces*number)/do_one,
+ range=(number*periods*number*spaces*number)/do_range,
+ named=(number*spaces*name)/do_name
+}
+local function loadcidfile(filename)
+ local data=io.loaddata(filename)
+ if data then
+ unicodes,names={},{}
+ lpegmatch(grammar,data)
+ local supplement,registry,ordering=match(filename,"^(.-)%-(.-)%-()%.(.-)$")
+ return {
+ supplement=supplement,
+ registry=registry,
+ ordering=ordering,
+ filename=filename,
+ unicodes=unicodes,
+ names=names,
+ }
+ end
+end
+cid.loadfile=loadcidfile
+local template="%s-%s-%s.cidmap"
+local function locate(registry,ordering,supplement)
+ local filename=format(template,registry,ordering,supplement)
+ local hashname=lower(filename)
+ local found=cidmap[hashname]
+ if not found then
+ if trace_loading then
+ report_otf("checking cidmap, registry %a, ordering %a, supplement %a, filename %a",registry,ordering,supplement,filename)
+ end
+ local fullname=resolvers.findfile(filename,'cid') or ""
+ if fullname~="" then
+ found=loadcidfile(fullname)
+ if found then
+ if trace_loading then
+ report_otf("using cidmap file %a",filename)
+ end
+ cidmap[hashname]=found
+ found.usedname=file.basename(filename)
+ end
+ end
+ end
+ return found
+end
+function cid.getmap(specification)
+ if not specification then
+ report_otf("invalid cidinfo specification, table expected")
+ return
+ end
+ local registry=specification.registry
+ local ordering=specification.ordering
+ local supplement=specification.supplement
+ local filename=format(registry,ordering,supplement)
+ local lowername=lower(filename)
+ local found=cidmap[lowername]
+ if found then
+ return found
+ end
+ if ordering=="Identity" then
+ local found={
+ supplement=supplement,
+ registry=registry,
+ ordering=ordering,
+ filename=filename,
+ unicodes={},
+ names={},
+ }
+ cidmap[lowername]=found
+ return found
+ end
+ if trace_loading then
+ report_otf("cidmap needed, registry %a, ordering %a, supplement %a",registry,ordering,supplement)
+ end
+ found=locate(registry,ordering,supplement)
+ if not found then
+ local supnum=tonumber(supplement)
+ local cidnum=nil
+ if supnum<cidmax then
+ for s=supnum+1,cidmax do
+ local c=locate(registry,ordering,s)
+ if c then
+ found,cidnum=c,s
+ break
+ end
+ end
+ end
+ if not found and supnum>0 then
+ for s=supnum-1,0,-1 do
+ local c=locate(registry,ordering,s)
+ if c then
+ found,cidnum=c,s
+ break
+ end
+ end
+ end
+ registry=lower(registry)
+ ordering=lower(ordering)
+ if found and cidnum>0 then
+ for s=0,cidnum-1 do
+ local filename=format(template,registry,ordering,s)
+ if not cidmap[filename] then
+ cidmap[filename]=found
+ end
+ end
+ end
+ end
+ return found
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-map']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local tonumber,next,type=tonumber,next,type
+local match,format,find,concat,gsub,lower=string.match,string.format,string.find,table.concat,string.gsub,string.lower
+local P,R,S,C,Ct,Cc,lpegmatch=lpeg.P,lpeg.R,lpeg.S,lpeg.C,lpeg.Ct,lpeg.Cc,lpeg.match
+local formatters=string.formatters
+local sortedhash,sortedkeys=table.sortedhash,table.sortedkeys
+local rshift=bit32.rshift
+local trace_loading=false trackers.register("fonts.loading",function(v) trace_loading=v end)
+local trace_mapping=false trackers.register("fonts.mapping",function(v) trace_mapping=v end)
+local report_fonts=logs.reporter("fonts","loading")
+local force_ligatures=false directives.register("fonts.mapping.forceligatures",function(v) force_ligatures=v end)
+local fonts=fonts or {}
+local mappings=fonts.mappings or {}
+fonts.mappings=mappings
+local allocate=utilities.storage.allocate
+local hex=R("AF","af","09")
+local hexfour=(hex*hex*hex^-2)/function(s) return tonumber(s,16) end
+local hexsix=(hex*hex*hex^-4)/function(s) return tonumber(s,16) end
+local dec=(R("09")^1)/tonumber
+local period=P(".")
+local unicode=(P("uni")+P("UNI"))*(hexfour*(period+P(-1))*Cc(false)+Ct(hexfour^1)*Cc(true))
+local ucode=(P("u")+P("U") )*(hexsix*(period+P(-1))*Cc(false)+Ct(hexsix^1)*Cc(true))
+local index=P("index")*dec*Cc(false)
+local parser=unicode+ucode+index
+local parsers={}
+local function makenameparser(str)
+ if not str or str=="" then
+ return parser
+ else
+ local p=parsers[str]
+ if not p then
+ p=P(str)*period*dec*Cc(false)
+ parsers[str]=p
+ end
+ return p
+ end
+end
+local f_single=formatters["%04X"]
+local f_double=formatters["%04X%04X"]
+local function tounicode16(unicode)
+ if unicode<0xD7FF or (unicode>0xDFFF and unicode<=0xFFFF) then
+ return f_single(unicode)
+ else
+ unicode=unicode-0x10000
+ return f_double(rshift(unicode,10)+0xD800,unicode%1024+0xDC00)
+ end
+end
+local function tounicode16sequence(unicodes)
+ local t={}
+ for l=1,#unicodes do
+ local u=unicodes[l]
+ if u<0xD7FF or (u>0xDFFF and u<=0xFFFF) then
+ t[l]=f_single(u)
+ else
+ u=u-0x10000
+ t[l]=f_double(rshift(u,10)+0xD800,u%1024+0xDC00)
+ end
+ end
+ return concat(t)
+end
+local unknown=f_single(0xFFFD)
+local hash={}
+local conc={}
+table.setmetatableindex(hash,function(t,k)
+ if k<0xD7FF or (k>0xDFFF and k<=0xFFFF) then
+ v=f_single(k)
+ else
+ local k=k-0x10000
+ v=f_double(rshift(k,10)+0xD800,k%1024+0xDC00)
+ end
+ t[k]=v
+ return v
+end)
+local function tounicode(k)
+ if type(k)=="table" then
+ local n=#k
+ for l=1,n do
+ conc[l]=hash[k[l]]
+ end
+ return concat(conc,"",1,n)
+ elseif k>=0x00E000 and k<=0x00F8FF then
+ return unknown
+ elseif k>=0x0F0000 and k<=0x0FFFFF then
+ return unknown
+ elseif k>=0x100000 and k<=0x10FFFF then
+ return unknown
+ else
+ return hash[k]
+ end
+end
+local function fromunicode16(str)
+ if #str==4 then
+ return tonumber(str,16)
+ else
+ local l,r=match(str,"(....)(....)")
+ return 0x10000+(tonumber(l,16)-0xD800)*0x400+tonumber(r,16)-0xDC00
+ end
+end
+mappings.makenameparser=makenameparser
+mappings.tounicode=tounicode
+mappings.tounicode16=tounicode16
+mappings.tounicode16sequence=tounicode16sequence
+mappings.fromunicode16=fromunicode16
+local ligseparator=P("_")
+local varseparator=P(".")
+local namesplitter=Ct(C((1-ligseparator-varseparator)^1)*(ligseparator*C((1-ligseparator-varseparator)^1))^0)
+do
+ local overloads={
+ IJ={ name="I_J",unicode={ 0x49,0x4A },mess=0x0132 },
+ ij={ name="i_j",unicode={ 0x69,0x6A },mess=0x0133 },
+ ff={ name="f_f",unicode={ 0x66,0x66 },mess=0xFB00 },
+ fi={ name="f_i",unicode={ 0x66,0x69 },mess=0xFB01 },
+ fl={ name="f_l",unicode={ 0x66,0x6C },mess=0xFB02 },
+ ffi={ name="f_f_i",unicode={ 0x66,0x66,0x69 },mess=0xFB03 },
+ ffl={ name="f_f_l",unicode={ 0x66,0x66,0x6C },mess=0xFB04 },
+ fj={ name="f_j",unicode={ 0x66,0x6A } },
+ fk={ name="f_k",unicode={ 0x66,0x6B } },
+ }
+ local o=allocate {}
+ for k,v in next,overloads do
+ local name=v.name
+ local mess=v.mess
+ if name then
+ o[name]=v
+ end
+ if mess then
+ o[mess]=v
+ end
+ o[k]=v
+ end
+ mappings.overloads=o
+end
+function mappings.addtounicode(data,filename,checklookups,forceligatures)
+ local resources=data.resources
+ local unicodes=resources.unicodes
+ if not unicodes then
+ if trace_mapping then
+ report_fonts("no unicode list, quitting tounicode for %a",filename)
+ end
+ return
+ end
+ local properties=data.properties
+ local descriptions=data.descriptions
+ local overloads=mappings.overloads
+ unicodes['space']=unicodes['space'] or 32
+ unicodes['hyphen']=unicodes['hyphen'] or 45
+ unicodes['zwj']=unicodes['zwj'] or 0x200D
+ unicodes['zwnj']=unicodes['zwnj'] or 0x200C
+ local private=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+ local unicodevector=fonts.encodings.agl.unicodes or {}
+ local contextvector=fonts.encodings.agl.ctxcodes or {}
+ local missing={}
+ local nofmissing=0
+ local oparser=nil
+ local cidnames=nil
+ local cidcodes=nil
+ local cidinfo=properties.cidinfo
+ local usedmap=cidinfo and fonts.cid.getmap(cidinfo)
+ local uparser=makenameparser()
+ if usedmap then
+ oparser=usedmap and makenameparser(cidinfo.ordering)
+ cidnames=usedmap.names
+ cidcodes=usedmap.unicodes
+ end
+ local ns=0
+ local nl=0
+ local dlist=sortedkeys(descriptions)
+ for i=1,#dlist do
+ local du=dlist[i]
+ local glyph=descriptions[du]
+ local name=glyph.name
+ if name then
+ local overload=overloads[name] or overloads[du]
+ if overload then
+ glyph.unicode=overload.unicode
+ else
+ local gu=glyph.unicode
+ if not gu or gu==-1 or du>=private or (du>=0xE000 and du<=0xF8FF) or du==0xFFFE or du==0xFFFF then
+ local unicode=unicodevector[name] or contextvector[name]
+ if unicode then
+ glyph.unicode=unicode
+ ns=ns+1
+ end
+ if (not unicode) and usedmap then
+ local foundindex=lpegmatch(oparser,name)
+ if foundindex then
+ unicode=cidcodes[foundindex]
+ if unicode then
+ glyph.unicode=unicode
+ ns=ns+1
+ else
+ local reference=cidnames[foundindex]
+ if reference then
+ local foundindex=lpegmatch(oparser,reference)
+ if foundindex then
+ unicode=cidcodes[foundindex]
+ if unicode then
+ glyph.unicode=unicode
+ ns=ns+1
+ end
+ end
+ if not unicode or unicode=="" then
+ local foundcodes,multiple=lpegmatch(uparser,reference)
+ if foundcodes then
+ glyph.unicode=foundcodes
+ if multiple then
+ nl=nl+1
+ unicode=true
+ else
+ ns=ns+1
+ unicode=foundcodes
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if not unicode or unicode=="" then
+ local split=lpegmatch(namesplitter,name)
+ local nsplit=split and #split or 0
+ if nsplit==0 then
+ elseif nsplit==1 then
+ local base=split[1]
+ local u=unicodes[base] or unicodevector[base] or contextvector[name]
+ if not u then
+ elseif type(u)=="table" then
+ if u[1]<private then
+ unicode=u
+ glyph.unicode=unicode
+ end
+ elseif u<private then
+ unicode=u
+ glyph.unicode=unicode
+ end
+ else
+ local t={}
+ local n=0
+ for l=1,nsplit do
+ local base=split[l]
+ local u=unicodes[base] or unicodevector[base] or contextvector[name]
+ if not u then
+ break
+ elseif type(u)=="table" then
+ if u[1]>=private then
+ break
+ end
+ n=n+1
+ t[n]=u[1]
+ else
+ if u>=private then
+ break
+ end
+ n=n+1
+ t[n]=u
+ end
+ end
+ if n>0 then
+ if n==1 then
+ unicode=t[1]
+ else
+ unicode=t
+ end
+ glyph.unicode=unicode
+ end
+ end
+ nl=nl+1
+ end
+ if not unicode or unicode=="" then
+ local foundcodes,multiple=lpegmatch(uparser,name)
+ if foundcodes then
+ glyph.unicode=foundcodes
+ if multiple then
+ nl=nl+1
+ unicode=true
+ else
+ ns=ns+1
+ unicode=foundcodes
+ end
+ end
+ end
+ local r=overloads[unicode]
+ if r then
+ unicode=r.unicode
+ glyph.unicode=unicode
+ end
+ if not unicode then
+ missing[du]=true
+ nofmissing=nofmissing+1
+ end
+ else
+ end
+ end
+ else
+ local overload=overloads[du]
+ if overload then
+ glyph.unicode=overload.unicode
+ elseif not glyph.unicode then
+ missing[du]=true
+ nofmissing=nofmissing+1
+ end
+ end
+ end
+ if type(checklookups)=="function" then
+ checklookups(data,missing,nofmissing)
+ end
+ local unicoded=0
+ local collected=fonts.handlers.otf.readers.getcomponents(data)
+ local function resolve(glyph,u)
+ local n=#u
+ for i=1,n do
+ if u[i]>private then
+ n=0
+ break
+ end
+ end
+ if n>0 then
+ if n>1 then
+ glyph.unicode=u
+ else
+ glyph.unicode=u[1]
+ end
+ unicoded=unicoded+1
+ end
+ end
+ if not collected then
+ elseif forceligatures or force_ligatures then
+ for i=1,#dlist do
+ local du=dlist[i]
+ if du>=private or (du>=0xE000 and du<=0xF8FF) then
+ local u=collected[du]
+ if u then
+ resolve(descriptions[du],u)
+ end
+ end
+ end
+ else
+ for i=1,#dlist do
+ local du=dlist[i]
+ if du>=private or (du>=0xE000 and du<=0xF8FF) then
+ local glyph=descriptions[du]
+ if glyph.class=="ligature" and not glyph.unicode then
+ local u=collected[du]
+ if u then
+ resolve(glyph,u)
+ end
+ end
+ end
+ end
+ end
+ if trace_mapping and unicoded>0 then
+ report_fonts("%n ligature tounicode mappings deduced from gsub ligature features",unicoded)
+ end
+ if trace_mapping then
+ for i=1,#dlist do
+ local du=dlist[i]
+ local glyph=descriptions[du]
+ local name=glyph.name or "-"
+ local index=glyph.index or 0
+ local unicode=glyph.unicode
+ if unicode then
+ if type(unicode)=="table" then
+ local unicodes={}
+ for i=1,#unicode do
+ unicodes[i]=formatters("%U",unicode[i])
+ end
+ report_fonts("internal slot %U, name %a, unicode %U, tounicode % t",index,name,du,unicodes)
+ else
+ report_fonts("internal slot %U, name %a, unicode %U, tounicode %U",index,name,du,unicode)
+ end
+ else
+ report_fonts("internal slot %U, name %a, unicode %U",index,name,du)
+ end
+ end
+ end
+ if trace_loading and (ns>0 or nl>0) then
+ report_fonts("%s tounicode entries added, ligatures %s",nl+ns,ns)
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-fonts-syn']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local fonts=fonts
+fonts.names=fonts.names or {}
+fonts.names.version=1.001
+fonts.names.basename="luatex-fonts-names"
+fonts.names.cache=containers.define("fonts","data",fonts.names.version,true)
+local data=nil
+local loaded=false
+local fileformats={ "lua","tex","other text files" }
+function fonts.names.reportmissingbase()
+ logs.report("fonts","missing font database, run: mtxrun --script fonts --reload --simple")
+ fonts.names.reportmissingbase=nil
+end
+function fonts.names.reportmissingname()
+ logs.report("fonts","unknown font in font database, run: mtxrun --script fonts --reload --simple")
+ fonts.names.reportmissingname=nil
+end
+function fonts.names.resolve(name,sub)
+ if not loaded then
+ local basename=fonts.names.basename
+ if basename and basename~="" then
+ data=containers.read(fonts.names.cache,basename)
+ if not data then
+ basename=file.addsuffix(basename,"lua")
+ for i=1,#fileformats do
+ local format=fileformats[i]
+ local foundname=resolvers.findfile(basename,format) or ""
+ if foundname~="" then
+ data=dofile(foundname)
+ logs.report("fonts","font database '%s' loaded",foundname)
+ break
+ end
+ end
+ end
+ end
+ loaded=true
+ end
+ if type(data)=="table" and data.version==fonts.names.version then
+ local condensed=string.gsub(string.lower(name),"[^%a%d]","")
+ local found=data.mappings and data.mappings[condensed]
+ if found then
+ local fontname,filename,subfont=found[1],found[2],found[3]
+ if subfont then
+ return filename,fontname
+ else
+ return filename,false
+ end
+ elseif fonts.names.reportmissingname then
+ fonts.names.reportmissingname()
+ return name,false
+ end
+ elseif fonts.names.reportmissingbase then
+ fonts.names.reportmissingbase()
+ end
+end
+fonts.names.resolvespec=fonts.names.resolve
+function fonts.names.getfilename(askedname,suffix)
+ return ""
+end
+function fonts.names.ignoredfile(filename)
+ return false
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-vfc']={
+ version=1.001,
+ comment="companion to font-ini.mkiv and hand-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local select,type=select,type
+local insert=table.insert
+local fonts=fonts
+local helpers=fonts.helpers
+local setmetatableindex=table.setmetatableindex
+local makeweak=table.makeweak
+local push={ "push" }
+local pop={ "pop" }
+local dummy={ "comment" }
+function helpers.prependcommands(commands,...)
+ insert(commands,1,push)
+ for i=select("#",...),1,-1 do
+ local s=(select(i,...))
+ if s then
+ insert(commands,1,s)
+ end
+ end
+ insert(commands,pop)
+ return commands
+end
+function helpers.appendcommands(commands,...)
+ insert(commands,1,push)
+ insert(commands,pop)
+ for i=1,select("#",...) do
+ local s=(select(i,...))
+ if s then
+ insert(commands,s)
+ end
+ end
+ return commands
+end
+function helpers.prependcommandtable(commands,t)
+ insert(commands,1,push)
+ for i=#t,1,-1 do
+ local s=t[i]
+ if s then
+ insert(commands,1,s)
+ end
+ end
+ insert(commands,pop)
+ return commands
+end
+function helpers.appendcommandtable(commands,t)
+ insert(commands,1,push)
+ insert(commands,pop)
+ for i=1,#t do
+ local s=t[i]
+ if s then
+ insert(commands,s)
+ end
+ end
+ return commands
+end
+local char=setmetatableindex(function(t,k)
+ local v={ "slot",0,k }
+ t[k]=v
+ return v
+end)
+local right=setmetatableindex(function(t,k)
+ local v={ "right",k }
+ t[k]=v
+ return v
+end)
+local left=setmetatableindex(function(t,k)
+ local v={ "right",-k }
+ t[k]=v
+ return v
+end)
+local down=setmetatableindex(function(t,k)
+ local v={ "down",k }
+ t[k]=v
+ return v
+end)
+local up=setmetatableindex(function(t,k)
+ local v={ "down",-k }
+ t[k]=v
+ return v
+end)
+helpers.commands=utilities.storage.allocate {
+ char=char,
+ right=right,
+ left=left,
+ down=down,
+ up=up,
+ push=push,
+ pop=pop,
+ dummy=dummy,
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-otr']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+local byte,lower,char,gsub=string.byte,string.lower,string.char,string.gsub
+local fullstrip=string.fullstrip
+local floor,round=math.floor,math.round
+local P,R,S,C,Cs,Cc,Ct,Carg,Cmt=lpeg.P,lpeg.R,lpeg.S,lpeg.C,lpeg.Cs,lpeg.Cc,lpeg.Ct,lpeg.Carg,lpeg.Cmt
+local lpegmatch=lpeg.match
+local rshift=bit32.rshift
+local setmetatableindex=table.setmetatableindex
+local sortedkeys=table.sortedkeys
+local sortedhash=table.sortedhash
+local stripstring=string.nospaces
+local utf16_to_utf8_be=utf.utf16_to_utf8_be
+local report=logs.reporter("otf reader")
+local report_cmap=logs.reporter("otf reader","cmap")
+local trace_cmap=false trackers.register("otf.cmap",function(v) trace_cmap=v end)
+local trace_cmap_details=false trackers.register("otf.cmap.details",function(v) trace_cmap_details=v end)
+fonts=fonts or {}
+local handlers=fonts.handlers or {}
+fonts.handlers=handlers
+local otf=handlers.otf or {}
+handlers.otf=otf
+local readers=otf.readers or {}
+otf.readers=readers
+local streamreader=utilities.files
+local streamwriter=utilities.files
+readers.streamreader=streamreader
+readers.streamwriter=streamwriter
+local openfile=streamreader.open
+local closefile=streamreader.close
+local setposition=streamreader.setposition
+local skipshort=streamreader.skipshort
+local readbytes=streamreader.readbytes
+local readstring=streamreader.readstring
+local readbyte=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readuint=streamreader.readcardinal3
+local readulong=streamreader.readcardinal4
+local readshort=streamreader.readinteger2
+local readlong=streamreader.readinteger4
+local readfixed=streamreader.readfixed4
+local read2dot14=streamreader.read2dot14
+local readfword=readshort
+local readufword=readushort
+local readoffset=readushort
+local readcardinaltable=streamreader.readcardinaltable
+local readintegertable=streamreader.readintegertable
+function streamreader.readtag(f)
+ return lower(stripstring(readstring(f,4)))
+end
+local short=2
+local ushort=2
+local ulong=4
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ openfile=streamreader.open
+ closefile=streamreader.close
+ setposition=streamreader.setposition
+ skipshort=streamreader.skipshort
+ readbytes=streamreader.readbytes
+ readstring=streamreader.readstring
+ readbyte=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readuint=streamreader.readcardinal3
+ readulong=streamreader.readcardinal4
+ readshort=streamreader.readinteger2
+ readlong=streamreader.readinteger4
+ readfixed=streamreader.readfixed4
+ read2dot14=streamreader.read2dot14
+ readfword=readshort
+ readufword=readushort
+ readoffset=readushort
+ readcardinaltable=streamreader.readcardinaltable
+ readintegertable=streamreader.readintegertable
+ function streamreader.readtag(f)
+ return lower(stripstring(readstring(f,4)))
+ end
+end)
+local function readlongdatetime(f)
+ local a,b,c,d,e,f,g,h=readbytes(f,8)
+ return 0x100000000*d+0x1000000*e+0x10000*f+0x100*g+h
+end
+local tableversion=0.004
+readers.tableversion=tableversion
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local reservednames={ [0]="copyright",
+ "family",
+ "subfamily",
+ "uniqueid",
+ "fullname",
+ "version",
+ "postscriptname",
+ "trademark",
+ "manufacturer",
+ "designer",
+ "description",
+ "vendorurl",
+ "designerurl",
+ "license",
+ "licenseurl",
+ "reserved",
+ "typographicfamily",
+ "typographicsubfamily",
+ "compatiblefullname",
+ "sampletext",
+ "cidfindfontname",
+ "wwsfamily",
+ "wwssubfamily",
+ "lightbackgroundpalette",
+ "darkbackgroundpalette",
+ "variationspostscriptnameprefix",
+}
+local platforms={ [0]="unicode",
+ "macintosh",
+ "iso",
+ "windows",
+ "custom",
+}
+local encodings={
+ unicode={ [0]="unicode 1.0 semantics",
+ "unicode 1.1 semantics",
+ "iso/iec 10646",
+ "unicode 2.0 bmp",
+ "unicode 2.0 full",
+ "unicode variation sequences",
+ "unicode full repertoire",
+ },
+ macintosh={ [0]="roman","japanese","chinese (traditional)","korean","arabic","hebrew","greek","russian",
+ "rsymbol","devanagari","gurmukhi","gujarati","oriya","bengali","tamil","telugu","kannada",
+ "malayalam","sinhalese","burmese","khmer","thai","laotian","georgian","armenian",
+ "chinese (simplified)","tibetan","mongolian","geez","slavic","vietnamese","sindhi",
+ "uninterpreted",
+ },
+ iso={ [0]="7-bit ascii",
+ "iso 10646",
+ "iso 8859-1",
+ },
+ windows={ [0]="symbol",
+ "unicode bmp",
+ "shiftjis",
+ "prc",
+ "big5",
+ "wansung",
+ "johab",
+ "reserved 7",
+ "reserved 8",
+ "reserved 9",
+ "unicode ucs-4",
+ },
+ custom={
+ }
+}
+local decoders={
+ unicode={},
+ macintosh={},
+ iso={},
+ windows={
+ ["unicode semantics"]=utf16_to_utf8_be,
+ ["unicode bmp"]=utf16_to_utf8_be,
+ ["unicode full"]=utf16_to_utf8_be,
+ ["unicode 1.0 semantics"]=utf16_to_utf8_be,
+ ["unicode 1.1 semantics"]=utf16_to_utf8_be,
+ ["unicode 2.0 bmp"]=utf16_to_utf8_be,
+ ["unicode 2.0 full"]=utf16_to_utf8_be,
+ ["unicode variation sequences"]=utf16_to_utf8_be,
+ ["unicode full repertoire"]=utf16_to_utf8_be,
+ },
+ custom={},
+}
+local languages={
+ unicode={
+ [ 0]="english",
+ },
+ macintosh={
+ [ 0]="english",
+ },
+ iso={},
+ windows={
+ [0x0409]="english - united states",
+ },
+ custom={},
+}
+local standardromanencoding={ [0]=
+ "notdef",".null","nonmarkingreturn","space","exclam","quotedbl",
+ "numbersign","dollar","percent","ampersand","quotesingle","parenleft",
+ "parenright","asterisk","plus","comma","hyphen","period","slash",
+ "zero","one","two","three","four","five","six","seven","eight",
+ "nine","colon","semicolon","less","equal","greater","question","at",
+ "A","B","C","D","E","F","G","H","I","J","K","L","M","N","O",
+ "P","Q","R","S","T","U","V","W","X","Y","Z","bracketleft",
+ "backslash","bracketright","asciicircum","underscore","grave","a","b",
+ "c","d","e","f","g","h","i","j","k","l","m","n","o","p","q",
+ "r","s","t","u","v","w","x","y","z","braceleft","bar",
+ "braceright","asciitilde","Adieresis","Aring","Ccedilla","Eacute",
+ "Ntilde","Odieresis","Udieresis","aacute","agrave","acircumflex",
+ "adieresis","atilde","aring","ccedilla","eacute","egrave",
+ "ecircumflex","edieresis","iacute","igrave","icircumflex","idieresis",
+ "ntilde","oacute","ograve","ocircumflex","odieresis","otilde","uacute",
+ "ugrave","ucircumflex","udieresis","dagger","degree","cent","sterling",
+ "section","bullet","paragraph","germandbls","registered","copyright",
+ "trademark","acute","dieresis","notequal","AE","Oslash","infinity",
+ "plusminus","lessequal","greaterequal","yen","mu","partialdiff",
+ "summation","product","pi","integral","ordfeminine","ordmasculine",
+ "Omega","ae","oslash","questiondown","exclamdown","logicalnot",
+ "radical","florin","approxequal","Delta","guillemotleft",
+ "guillemotright","ellipsis","nonbreakingspace","Agrave","Atilde",
+ "Otilde","OE","oe","endash","emdash","quotedblleft","quotedblright",
+ "quoteleft","quoteright","divide","lozenge","ydieresis","Ydieresis",
+ "fraction","currency","guilsinglleft","guilsinglright","fi","fl",
+ "daggerdbl","periodcentered","quotesinglbase","quotedblbase",
+ "perthousand","Acircumflex","Ecircumflex","Aacute","Edieresis","Egrave",
+ "Iacute","Icircumflex","Idieresis","Igrave","Oacute","Ocircumflex",
+ "apple","Ograve","Uacute","Ucircumflex","Ugrave","dotlessi",
+ "circumflex","tilde","macron","breve","dotaccent","ring","cedilla",
+ "hungarumlaut","ogonek","caron","Lslash","lslash","Scaron","scaron",
+ "Zcaron","zcaron","brokenbar","Eth","eth","Yacute","yacute","Thorn",
+ "thorn","minus","multiply","onesuperior","twosuperior","threesuperior",
+ "onehalf","onequarter","threequarters","franc","Gbreve","gbreve",
+ "Idotaccent","Scedilla","scedilla","Cacute","cacute","Ccaron","ccaron",
+ "dcroat",
+}
+local weights={
+ [100]="thin",
+ [200]="extralight",
+ [300]="light",
+ [400]="normal",
+ [500]="medium",
+ [600]="semibold",
+ [700]="bold",
+ [800]="extrabold",
+ [900]="black",
+}
+local widths={
+ [1]="ultracondensed",
+ [2]="extracondensed",
+ [3]="condensed",
+ [4]="semicondensed",
+ [5]="normal",
+ [6]="semiexpanded",
+ [7]="expanded",
+ [8]="extraexpanded",
+ [9]="ultraexpanded",
+}
+setmetatableindex(weights,function(t,k)
+ local r=floor((k+50)/100)*100
+ local v=(r>900 and "black") or rawget(t,r) or "normal"
+ return v
+end)
+setmetatableindex(widths,function(t,k)
+ return "normal"
+end)
+local panoseweights={
+ [ 0]="normal",
+ [ 1]="normal",
+ [ 2]="verylight",
+ [ 3]="light",
+ [ 4]="thin",
+ [ 5]="book",
+ [ 6]="medium",
+ [ 7]="demi",
+ [ 8]="bold",
+ [ 9]="heavy",
+ [10]="black",
+}
+local panosewidths={
+ [ 0]="normal",
+ [ 1]="normal",
+ [ 2]="normal",
+ [ 3]="normal",
+ [ 4]="normal",
+ [ 5]="expanded",
+ [ 6]="condensed",
+ [ 7]="veryexpanded",
+ [ 8]="verycondensed",
+ [ 9]="monospaced",
+}
+local helpers={}
+readers.helpers=helpers
+local function gotodatatable(f,fontdata,tag,criterium)
+ if criterium and f then
+ local tables=fontdata.tables
+ if tables then
+ local datatable=tables[tag]
+ if datatable then
+ local tableoffset=datatable.offset
+ setposition(f,tableoffset)
+ return tableoffset
+ end
+ else
+ report("no tables")
+ end
+ end
+end
+local function reportskippedtable(f,fontdata,tag,criterium)
+ if criterium and f then
+ local tables=fontdata.tables
+ if tables then
+ local datatable=tables[tag]
+ if datatable then
+ report("loading of table %a skipped",tag)
+ end
+ else
+ report("no tables")
+ end
+ end
+end
+local function setvariabledata(fontdata,tag,data)
+ local variabledata=fontdata.variabledata
+ if variabledata then
+ variabledata[tag]=data
+ else
+ fontdata.variabledata={ [tag]=data }
+ end
+end
+helpers.gotodatatable=gotodatatable
+helpers.setvariabledata=setvariabledata
+helpers.reportskippedtable=reportskippedtable
+local platformnames={
+ postscriptname=true,
+ fullname=true,
+ family=true,
+ subfamily=true,
+ typographicfamily=true,
+ typographicsubfamily=true,
+ compatiblefullname=true,
+}
+local platformextras={
+ uniqueid=true,
+ version=true,
+ copyright=true,
+ license=true,
+ licenseurl=true,
+ manufacturer=true,
+ vendorurl=true,
+}
+function readers.name(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"name",true)
+ if tableoffset then
+ local format=readushort(f)
+ local nofnames=readushort(f)
+ local offset=readushort(f)
+ local start=tableoffset+offset
+ local namelists={
+ unicode={},
+ windows={},
+ macintosh={},
+ }
+ for i=1,nofnames do
+ local platform=platforms[readushort(f)]
+ if platform then
+ local namelist=namelists[platform]
+ if namelist then
+ local encoding=readushort(f)
+ local language=readushort(f)
+ local encodings=encodings[platform]
+ local languages=languages[platform]
+ if encodings and languages then
+ local encoding=encodings[encoding]
+ local language=languages[language]
+ if encoding and language then
+ local index=readushort(f)
+ local name=reservednames[index]
+ namelist[#namelist+1]={
+ platform=platform,
+ encoding=encoding,
+ language=language,
+ name=name,
+ index=index,
+ length=readushort(f),
+ offset=start+readushort(f),
+ }
+ else
+ skipshort(f,3)
+ end
+ else
+ skipshort(f,3)
+ end
+ else
+ skipshort(f,5)
+ end
+ else
+ skipshort(f,5)
+ end
+ end
+ local names={}
+ local done={}
+ local extras={}
+ local function decoded(platform,encoding,content)
+ local decoder=decoders[platform]
+ if decoder then
+ decoder=decoder[encoding]
+ end
+ if decoder then
+ return decoder(content)
+ else
+ return content
+ end
+ end
+ local function filter(platform,e,l)
+ local namelist=namelists[platform]
+ for i=1,#namelist do
+ local name=namelist[i]
+ local nametag=name.name
+ local index=name.index
+ if not done[nametag or i] then
+ local encoding=name.encoding
+ local language=name.language
+ if (not e or encoding==e) and (not l or language==l) then
+ setposition(f,name.offset)
+ local content=decoded(platform,encoding,readstring(f,name.length))
+ if nametag then
+ names[nametag]={
+ content=content,
+ platform=platform,
+ encoding=encoding,
+ language=language,
+ }
+ end
+ extras[index]=content
+ done[nametag or i]=true
+ end
+ end
+ end
+ end
+ filter("windows","unicode bmp","english - united states")
+ filter("macintosh","roman","english")
+ filter("windows")
+ filter("macintosh")
+ filter("unicode")
+ fontdata.names=names
+ fontdata.extras=extras
+ if specification.platformnames then
+ local collected={}
+ local platformextras=specification.platformextras and platformextras
+ for platform,namelist in next,namelists do
+ local filtered=false
+ for i=1,#namelist do
+ local entry=namelist[i]
+ local name=entry.name
+ if platformnames[name] or (platformextras and platformextras[name]) then
+ setposition(f,entry.offset)
+ local content=decoded(platform,entry.encoding,readstring(f,entry.length))
+ if filtered then
+ filtered[name]=content
+ else
+ filtered={ [name]=content }
+ end
+ end
+ end
+ if filtered then
+ collected[platform]=filtered
+ end
+ end
+ fontdata.platformnames=collected
+ end
+ else
+ fontdata.names={}
+ end
+end
+local validutf=lpeg.patterns.validutf8
+local function getname(fontdata,key)
+ local names=fontdata.names
+ if names then
+ local value=names[key]
+ if value then
+ local content=value.content
+ return lpegmatch(validutf,content) and content or nil
+ end
+ end
+end
+readers["os/2"]=function(f,fontdata)
+ local tableoffset=gotodatatable(f,fontdata,"os/2",true)
+ if tableoffset then
+ local version=readushort(f)
+ local windowsmetrics={
+ version=version,
+ averagewidth=readshort(f),
+ weightclass=readushort(f),
+ widthclass=readushort(f),
+ fstype=readushort(f),
+ subscriptxsize=readshort(f),
+ subscriptysize=readshort(f),
+ subscriptxoffset=readshort(f),
+ subscriptyoffset=readshort(f),
+ superscriptxsize=readshort(f),
+ superscriptysize=readshort(f),
+ superscriptxoffset=readshort(f),
+ superscriptyoffset=readshort(f),
+ strikeoutsize=readshort(f),
+ strikeoutpos=readshort(f),
+ familyclass=readshort(f),
+ panose={ readbytes(f,10) },
+ unicoderanges={ readulong(f),readulong(f),readulong(f),readulong(f) },
+ vendor=readstring(f,4),
+ fsselection=readushort(f),
+ firstcharindex=readushort(f),
+ lastcharindex=readushort(f),
+ typoascender=readshort(f),
+ typodescender=readshort(f),
+ typolinegap=readshort(f),
+ winascent=readushort(f),
+ windescent=readushort(f),
+ }
+ if version>=1 then
+ windowsmetrics.codepageranges={ readulong(f),readulong(f) }
+ end
+ if version>=2 then
+ windowsmetrics.xheight=readshort(f)
+ windowsmetrics.capheight=readshort(f)
+ windowsmetrics.defaultchar=readushort(f)
+ windowsmetrics.breakchar=readushort(f)
+ end
+ windowsmetrics.weight=windowsmetrics.weightclass and weights[windowsmetrics.weightclass]
+ windowsmetrics.width=windowsmetrics.widthclass and widths [windowsmetrics.widthclass]
+ windowsmetrics.panoseweight=panoseweights[windowsmetrics.panose[3]]
+ windowsmetrics.panosewidth=panosewidths [windowsmetrics.panose[4]]
+ fontdata.windowsmetrics=windowsmetrics
+ else
+ fontdata.windowsmetrics={}
+ end
+end
+readers.head=function(f,fontdata)
+ local tableoffset=gotodatatable(f,fontdata,"head",true)
+ if tableoffset then
+ local version=readulong(f)
+ local fontversion=readulong(f)
+ local fontheader={
+ version=version,
+ fontversion=number.to16dot16(fontversion),
+ fontversionnumber=fontversion,
+ checksum=readushort(f)*0x10000+readushort(f),
+ magic=readulong(f),
+ flags=readushort(f),
+ units=readushort(f),
+ created=readlongdatetime(f),
+ modified=readlongdatetime(f),
+ xmin=readshort(f),
+ ymin=readshort(f),
+ xmax=readshort(f),
+ ymax=readshort(f),
+ macstyle=readushort(f),
+ smallpixels=readushort(f),
+ directionhint=readshort(f),
+ indextolocformat=readshort(f),
+ glyphformat=readshort(f),
+ }
+ fontdata.fontheader=fontheader
+ else
+ fontdata.fontheader={}
+ end
+ fontdata.nofglyphs=0
+end
+readers.hhea=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"hhea",specification.details)
+ if tableoffset then
+ fontdata.horizontalheader={
+ version=readulong(f),
+ ascender=readfword(f),
+ descender=readfword(f),
+ linegap=readfword(f),
+ maxadvancewidth=readufword(f),
+ minleftsidebearing=readfword(f),
+ minrightsidebearing=readfword(f),
+ maxextent=readfword(f),
+ caretsloperise=readshort(f),
+ caretsloperun=readshort(f),
+ caretoffset=readshort(f),
+ reserved_1=readshort(f),
+ reserved_2=readshort(f),
+ reserved_3=readshort(f),
+ reserved_4=readshort(f),
+ metricdataformat=readshort(f),
+ nofmetrics=readushort(f),
+ }
+ else
+ fontdata.horizontalheader={
+ nofmetrics=0,
+ }
+ end
+end
+readers.vhea=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"vhea",specification.details)
+ if tableoffset then
+ fontdata.verticalheader={
+ version=readulong(f),
+ ascender=readfword(f),
+ descender=readfword(f),
+ linegap=readfword(f),
+ maxadvanceheight=readufword(f),
+ mintopsidebearing=readfword(f),
+ minbottomsidebearing=readfword(f),
+ maxextent=readfword(f),
+ caretsloperise=readshort(f),
+ caretsloperun=readshort(f),
+ caretoffset=readshort(f),
+ reserved_1=readshort(f),
+ reserved_2=readshort(f),
+ reserved_3=readshort(f),
+ reserved_4=readshort(f),
+ metricdataformat=readshort(f),
+ nofmetrics=readushort(f),
+ }
+ else
+ fontdata.verticalheader={
+ nofmetrics=0,
+ }
+ end
+end
+readers.maxp=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"maxp",specification.details)
+ if tableoffset then
+ local version=readulong(f)
+ local nofglyphs=readushort(f)
+ fontdata.nofglyphs=nofglyphs
+ if version==0x00005000 then
+ fontdata.maximumprofile={
+ version=version,
+ nofglyphs=nofglyphs,
+ }
+ elseif version==0x00010000 then
+ fontdata.maximumprofile={
+ version=version,
+ nofglyphs=nofglyphs,
+ points=readushort(f),
+ contours=readushort(f),
+ compositepoints=readushort(f),
+ compositecontours=readushort(f),
+ zones=readushort(f),
+ twilightpoints=readushort(f),
+ storage=readushort(f),
+ functiondefs=readushort(f),
+ instructiondefs=readushort(f),
+ stackelements=readushort(f),
+ sizeofinstructions=readushort(f),
+ componentelements=readushort(f),
+ componentdepth=readushort(f),
+ }
+ else
+ fontdata.maximumprofile={
+ version=version,
+ nofglyphs=0,
+ }
+ end
+ end
+end
+readers.hmtx=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"hmtx",specification.glyphs)
+ if tableoffset then
+ local horizontalheader=fontdata.horizontalheader
+ local nofmetrics=horizontalheader.nofmetrics
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs
+ local width=0
+ local leftsidebearing=0
+ for i=0,nofmetrics-1 do
+ local glyph=glyphs[i]
+ width=readshort(f)
+ leftsidebearing=readshort(f)
+ if width~=0 then
+ glyph.width=width
+ end
+ end
+ for i=nofmetrics,nofglyphs-1 do
+ local glyph=glyphs[i]
+ if width~=0 then
+ glyph.width=width
+ end
+ end
+ end
+end
+readers.vmtx=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"vmtx",specification.glyphs)
+ if tableoffset then
+ local verticalheader=fontdata.verticalheader
+ local nofmetrics=verticalheader.nofmetrics
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs
+ local vheight=0
+ local vdefault=verticalheader.ascender-verticalheader.descender
+ local topsidebearing=0
+ for i=0,nofmetrics-1 do
+ local glyph=glyphs[i]
+ vheight=readushort(f)
+ topsidebearing=readshort(f)
+ if vheight~=0 and vheight~=vdefault then
+ glyph.vheight=vheight
+ end
+ if topsidebearing~=0 then
+ glyph.tsb=topsidebearing
+ end
+ end
+ for i=nofmetrics,nofglyphs-1 do
+ local glyph=glyphs[i]
+ if vheight~=0 and vheight~=vdefault then
+ glyph.vheight=vheight
+ end
+ end
+ end
+end
+readers.vorg=function(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"vorg",specification.glyphs)
+end
+readers.post=function(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"post",true)
+ if tableoffset then
+ local version=readulong(f)
+ fontdata.postscript={
+ version=version,
+ italicangle=round(1000*readfixed(f))/1000,
+ underlineposition=readfword(f),
+ underlinethickness=readfword(f),
+ monospaced=readulong(f),
+ minmemtype42=readulong(f),
+ maxmemtype42=readulong(f),
+ minmemtype1=readulong(f),
+ maxmemtype1=readulong(f),
+ }
+ if not specification.glyphs then
+ elseif version==0x00010000 then
+ for index=0,#standardromanencoding do
+ glyphs[index].name=standardromanencoding[index]
+ end
+ elseif version==0x00020000 then
+ local glyphs=fontdata.glyphs
+ local nofglyphs=readushort(f)
+ local indices={}
+ local names={}
+ local maxnames=0
+ for i=0,nofglyphs-1 do
+ local nameindex=readushort(f)
+ if nameindex>=258 then
+ maxnames=maxnames+1
+ nameindex=nameindex-257
+ indices[nameindex]=i
+ else
+ glyphs[i].name=standardromanencoding[nameindex]
+ end
+ end
+ for i=1,maxnames do
+ local mapping=indices[i]
+ if not mapping then
+ report("quit post name fetching at %a of %a: %s",i,maxnames,"no index")
+ break
+ else
+ local length=readbyte(f)
+ if length>0 then
+ glyphs[mapping].name=readstring(f,length)
+ else
+ report("quit post name fetching at %a of %a: %s",i,maxnames,"overflow")
+ break
+ end
+ end
+ end
+ end
+ else
+ fontdata.postscript={}
+ end
+end
+readers.cff=function(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cff",specification.glyphs)
+end
+local formatreaders={}
+local duplicatestoo=true
+local sequence={
+ { 3,1,4 },
+ { 3,10,12 },
+ { 0,3,4 },
+ { 0,3,12 },
+ { 0,1,4 },
+ { 0,1,12 },
+ { 0,0,6 },
+ { 3,0,6 },
+ { 3,0,4 },
+ { 0,5,14 },
+ { 0,4,12 },
+ { 3,10,13 },
+}
+local supported={}
+for i=1,#sequence do
+ local si=sequence[i]
+ local sp,se,sf=si[1],si[2],si[3]
+ local p=supported[sp]
+ if not p then
+ p={}
+ supported[sp]=p
+ end
+ local e=p[se]
+ if not e then
+ e={}
+ p[se]=e
+ end
+ e[sf]=true
+end
+formatreaders[4]=function(f,fontdata,offset)
+ setposition(f,offset+2)
+ local length=readushort(f)
+ local language=readushort(f)
+ local nofsegments=readushort(f)/2
+ skipshort(f,3)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local nofdone=0
+ local endchars=readcardinaltable(f,nofsegments,ushort)
+ local reserved=readushort(f)
+ local startchars=readcardinaltable(f,nofsegments,ushort)
+ local deltas=readcardinaltable(f,nofsegments,ushort)
+ local offsets=readcardinaltable(f,nofsegments,ushort)
+ local size=(length-2*2-5*2-4*2*nofsegments)/2
+ local indices=readcardinaltable(f,size-1,ushort)
+ for segment=1,nofsegments do
+ local startchar=startchars[segment]
+ local endchar=endchars[segment]
+ local offset=offsets[segment]
+ local delta=deltas[segment]
+ if startchar==0xFFFF and endchar==0xFFFF then
+ elseif startchar==0xFFFF and offset==0 then
+ elseif offset==0xFFFF then
+ elseif offset==0 then
+ if trace_cmap_details then
+ report("format 4.%i segment %2i from %C upto %C at index %H",1,segment,startchar,endchar,(startchar+delta)%65536)
+ end
+ for unicode=startchar,endchar do
+ local index=(unicode+delta)%65536
+ if index and index>0 then
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ if duplicatestoo then
+ local d=duplicates[gu]
+ if d then
+ d[unicode]=true
+ else
+ duplicates[gu]={ [unicode]=true }
+ end
+ else
+ report("duplicate case 1: %C %04i %s",unicode,index,glyphs[index].name)
+ end
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ end
+ end
+ else
+ local shift=(segment-nofsegments+offset/2)-startchar
+ if trace_cmap_details then
+ report_cmap("format 4.%i segment %2i from %C upto %C at index %H",0,segment,startchar,endchar,(startchar+delta)%65536)
+ end
+ for unicode=startchar,endchar do
+ local slot=shift+unicode
+ local index=indices[slot]
+ if index and index>0 then
+ index=(index+delta)%65536
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ if duplicatestoo then
+ local d=duplicates[gu]
+ if d then
+ d[unicode]=true
+ else
+ duplicates[gu]={ [unicode]=true }
+ end
+ else
+ report("duplicate case 2: %C %04i %s",unicode,index,glyphs[index].name)
+ end
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ end
+ end
+ end
+ end
+ return nofdone
+end
+formatreaders[6]=function(f,fontdata,offset)
+ setposition(f,offset)
+ local format=readushort(f)
+ local length=readushort(f)
+ local language=readushort(f)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local start=readushort(f)
+ local count=readushort(f)
+ local stop=start+count-1
+ local nofdone=0
+ if trace_cmap_details then
+ report_cmap("format 6 from %C to %C",2,start,stop)
+ end
+ for unicode=start,stop do
+ local index=readushort(f)
+ if index>0 then
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ end
+ end
+ return nofdone
+end
+formatreaders[12]=function(f,fontdata,offset)
+ setposition(f,offset+2+2+4+4)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local nofgroups=readulong(f)
+ local nofdone=0
+ for i=1,nofgroups do
+ local first=readulong(f)
+ local last=readulong(f)
+ local index=readulong(f)
+ if trace_cmap_details then
+ report_cmap("format 12 from %C to %C starts at index %i",first,last,index)
+ end
+ for unicode=first,last do
+ local glyph=glyphs[index]
+ if glyph then
+ local gu=glyph.unicode
+ if not gu then
+ glyph.unicode=unicode
+ nofdone=nofdone+1
+ elseif gu~=unicode then
+ local d=duplicates[gu]
+ if d then
+ d[unicode]=true
+ else
+ duplicates[gu]={ [unicode]=true }
+ end
+ end
+ if not mapping[index] then
+ mapping[index]=unicode
+ end
+ end
+ index=index+1
+ end
+ end
+ return nofdone
+end
+formatreaders[13]=function(f,fontdata,offset)
+ setposition(f,offset+2+2+4+4)
+ local mapping=fontdata.mapping
+ local glyphs=fontdata.glyphs
+ local duplicates=fontdata.duplicates
+ local nofgroups=readulong(f)
+ local nofdone=0
+ for i=1,nofgroups do
+ local first=readulong(f)
+ local last=readulong(f)
+ local index=readulong(f)
+ if first<privateoffset then
+ if trace_cmap_details then
+ report_cmap("format 13 from %C to %C get index %i",first,last,index)
+ end
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=first
+ glyph.unicode=unicode
+ first=first+1
+ end
+ local list=duplicates[unicode]
+ mapping[index]=unicode
+ if not list then
+ list={}
+ duplicates[unicode]=list
+ end
+ if last>=privateoffset then
+ local limit=privateoffset-1
+ report("format 13 from %C to %C pruned to %C",first,last,limit)
+ last=limit
+ end
+ for unicode=first,last do
+ list[unicode]=true
+ end
+ nofdone=nofdone+last-first+1
+ else
+ report("format 13 from %C to %C ignored",first,last)
+ end
+ end
+ return nofdone
+end
+formatreaders[14]=function(f,fontdata,offset)
+ if offset and offset~=0 then
+ setposition(f,offset)
+ local format=readushort(f)
+ local length=readulong(f)
+ local nofrecords=readulong(f)
+ local records={}
+ local variants={}
+ local nofdone=0
+ fontdata.variants=variants
+ for i=1,nofrecords do
+ records[i]={
+ selector=readuint(f),
+ default=readulong(f),
+ other=readulong(f),
+ }
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ local selector=record.selector
+ local default=record.default
+ local other=record.other
+ local other=record.other
+ if other~=0 then
+ setposition(f,offset+other)
+ local mapping={}
+ local count=readulong(f)
+ for i=1,count do
+ mapping[readuint(f)]=readushort(f)
+ end
+ nofdone=nofdone+count
+ variants[selector]=mapping
+ end
+ end
+ return nofdone
+ else
+ return 0
+ end
+end
+local function checkcmap(f,fontdata,records,platform,encoding,format)
+ local pdata=records[platform]
+ if not pdata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no platform",platform,encoding,format)
+ end
+ return 0
+ end
+ local edata=pdata[encoding]
+ if not edata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no encoding",platform,encoding,format)
+ end
+ return 0
+ end
+ local fdata=edata[format]
+ if not fdata then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","no format",platform,encoding,format)
+ end
+ return 0
+ elseif type(fdata)~="number" then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","already done",platform,encoding,format)
+ end
+ return 0
+ end
+ edata[format]=true
+ local reader=formatreaders[format]
+ if not reader then
+ if trace_cmap_details then
+ report_cmap("skipped, %s, p=%i e=%i f=%i","unsupported format",platform,encoding,format)
+ end
+ return 0
+ end
+ local n=reader(f,fontdata,fdata) or 0
+ if trace_cmap_details or trace_cmap then
+ local p=platforms[platform]
+ local e=encodings[p]
+ report_cmap("checked, platform %i (%s), encoding %i (%s), format %i, new unicodes %i",
+ platform,p,encoding,e and e[encoding] or "?",format,n)
+ end
+ return n
+end
+function readers.cmap(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cmap",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local noftables=readushort(f)
+ local records={}
+ local unicodecid=false
+ local variantcid=false
+ local variants={}
+ local duplicates=fontdata.duplicates or {}
+ fontdata.duplicates=duplicates
+ for i=1,noftables do
+ local platform=readushort(f)
+ local encoding=readushort(f)
+ local offset=readulong(f)
+ local record=records[platform]
+ if not record then
+ records[platform]={
+ [encoding]={
+ offsets={ offset },
+ formats={},
+ }
+ }
+ else
+ local subtables=record[encoding]
+ if not subtables then
+ record[encoding]={
+ offsets={ offset },
+ formats={},
+ }
+ else
+ local offsets=subtables.offsets
+ offsets[#offsets+1]=offset
+ end
+ end
+ end
+ if trace_cmap then
+ report("found cmaps:")
+ end
+ for platform,record in sortedhash(records) do
+ local p=platforms[platform]
+ local e=encodings[p]
+ local sp=supported[platform]
+ local ps=p or "?"
+ if trace_cmap then
+ if sp then
+ report(" platform %i: %s",platform,ps)
+ else
+ report(" platform %i: %s (unsupported)",platform,ps)
+ end
+ end
+ for encoding,subtables in sortedhash(record) do
+ local se=sp and sp[encoding]
+ local es=e and e[encoding] or "?"
+ if trace_cmap then
+ if se then
+ report(" encoding %i: %s",encoding,es)
+ else
+ report(" encoding %i: %s (unsupported)",encoding,es)
+ end
+ end
+ local offsets=subtables.offsets
+ local formats=subtables.formats
+ for i=1,#offsets do
+ local offset=tableoffset+offsets[i]
+ setposition(f,offset)
+ formats[readushort(f)]=offset
+ end
+ record[encoding]=formats
+ if trace_cmap then
+ local list=sortedkeys(formats)
+ for i=1,#list do
+ if not (se and se[list[i]]) then
+ list[i]=list[i].." (unsupported)"
+ end
+ end
+ report(" formats: % t",list)
+ end
+ end
+ end
+ local ok=false
+ for i=1,#sequence do
+ local si=sequence[i]
+ local sp,se,sf=si[1],si[2],si[3]
+ if checkcmap(f,fontdata,records,sp,se,sf)>0 then
+ ok=true
+ end
+ end
+ if not ok then
+ report("no useable unicode cmap found")
+ end
+ fontdata.cidmaps={
+ version=version,
+ noftables=noftables,
+ records=records,
+ }
+ else
+ fontdata.cidmaps={}
+ end
+end
+function readers.loca(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"loca",specification.glyphs)
+end
+function readers.glyf(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"glyf",specification.glyphs)
+end
+function readers.colr(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"colr",specification.glyphs)
+end
+function readers.cpal(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cpal",specification.glyphs)
+end
+function readers.svg(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"svg",specification.glyphs)
+end
+function readers.sbix(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"sbix",specification.glyphs)
+end
+function readers.cbdt(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cbdt",specification.glyphs)
+end
+function readers.cblc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"cblc",specification.glyphs)
+end
+function readers.ebdt(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"ebdt",specification.glyphs)
+end
+function readers.ebsc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"ebsc",specification.glyphs)
+end
+function readers.eblc(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"eblc",specification.glyphs)
+end
+function readers.kern(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"kern",specification.kerns)
+ if tableoffset then
+ local version=readushort(f)
+ local noftables=readushort(f)
+ for i=1,noftables do
+ local version=readushort(f)
+ local length=readushort(f)
+ local coverage=readushort(f)
+ local format=rshift(coverage,8)
+ if format==0 then
+ local nofpairs=readushort(f)
+ local searchrange=readushort(f)
+ local entryselector=readushort(f)
+ local rangeshift=readushort(f)
+ local kerns={}
+ local glyphs=fontdata.glyphs
+ for i=1,nofpairs do
+ local left=readushort(f)
+ local right=readushort(f)
+ local kern=readfword(f)
+ local glyph=glyphs[left]
+ local kerns=glyph.kerns
+ if kerns then
+ kerns[right]=kern
+ else
+ glyph.kerns={ [right]=kern }
+ end
+ end
+ elseif format==2 then
+ report("todo: kern classes")
+ else
+ report("todo: kerns")
+ end
+ end
+ end
+end
+function readers.gdef(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gdef",specification.details)
+end
+function readers.gsub(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gsub",specification.details)
+end
+function readers.gpos(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"gpos",specification.details)
+end
+function readers.math(f,fontdata,specification)
+ reportskippedtable(f,fontdata,"math",specification.details)
+end
+local function getinfo(maindata,sub,platformnames,rawfamilynames,metricstoo,instancenames)
+ local fontdata=sub and maindata.subfonts and maindata.subfonts[sub] or maindata
+ local names=fontdata.names
+ local info=nil
+ if names then
+ local metrics=fontdata.windowsmetrics or {}
+ local postscript=fontdata.postscript or {}
+ local fontheader=fontdata.fontheader or {}
+ local cffinfo=fontdata.cffinfo or {}
+ local verticalheader=fontdata.verticalheader or {}
+ local filename=fontdata.filename
+ local weight=getname(fontdata,"weight") or (cffinfo and cffinfo.weight) or (metrics and metrics.weight)
+ local width=getname(fontdata,"width") or (cffinfo and cffinfo.width ) or (metrics and metrics.width )
+ local fontname=getname(fontdata,"postscriptname")
+ local fullname=getname(fontdata,"fullname")
+ local family=getname(fontdata,"family")
+ local subfamily=getname(fontdata,"subfamily")
+ local familyname=getname(fontdata,"typographicfamily")
+ local subfamilyname=getname(fontdata,"typographicsubfamily")
+ local compatiblename=getname(fontdata,"compatiblefullname")
+ if rawfamilynames then
+ else
+ if not familyname then familyname=family end
+ if not subfamilyname then subfamilyname=subfamily end
+ end
+ if platformnames then
+ platformnames=fontdata.platformnames
+ end
+ if instancenames then
+ local variabledata=fontdata.variabledata
+ if variabledata then
+ local instances=variabledata and variabledata.instances
+ if instances then
+ instancenames={}
+ for i=1,#instances do
+ instancenames[i]=lower(stripstring(instances[i].subfamily))
+ end
+ else
+ instancenames=nil
+ end
+ else
+ instancenames=nil
+ end
+ end
+ info={
+ subfontindex=fontdata.subfontindex or sub or 0,
+ version=getname(fontdata,"version"),
+ fontname=fontname,
+ fullname=fullname,
+ family=family,
+ subfamily=subfamily,
+ familyname=familyname,
+ subfamilyname=subfamilyname,
+ compatiblename=compatiblename,
+ weight=weight and lower(weight),
+ width=width and lower(width),
+ pfmweight=metrics.weightclass or 400,
+ pfmwidth=metrics.widthclass or 5,
+ panosewidth=metrics.panosewidth,
+ panoseweight=metrics.panoseweight,
+ italicangle=postscript.italicangle or 0,
+ units=fontheader.units or 0,
+ designsize=fontdata.designsize,
+ minsize=fontdata.minsize,
+ maxsize=fontdata.maxsize,
+ boundingbox=fontheader and { fontheader.xmin or 0,fontheader.ymin or 0,fontheader.xmax or 0,fontheader.ymax or 0 } or nil,
+ monospaced=(tonumber(postscript.monospaced or 0)>0) or metrics.panosewidth=="monospaced",
+ averagewidth=metrics.averagewidth,
+ xheight=metrics.xheight,
+ capheight=metrics.capheight or fontdata.maxy,
+ ascender=metrics.typoascender,
+ descender=metrics.typodescender,
+ platformnames=platformnames or nil,
+ instancenames=instancenames or nil,
+ tableoffsets=fontdata.tableoffsets,
+ defaultvheight=(verticalheader.ascender or 0)-(verticalheader.descender or 0)
+ }
+ if metricstoo then
+ local keys={
+ "version",
+ "ascender","descender","linegap",
+ "maxadvancewidth","maxadvanceheight","maxextent",
+ "minbottomsidebearing","mintopsidebearing",
+ }
+ local h=fontdata.horizontalheader or {}
+ local v=fontdata.verticalheader or {}
+ if h then
+ local th={}
+ local tv={}
+ for i=1,#keys do
+ local key=keys[i]
+ th[key]=h[key] or 0
+ tv[key]=v[key] or 0
+ end
+ info.horizontalmetrics=th
+ info.verticalmetrics=tv
+ end
+ end
+ elseif n then
+ info={
+ filename=fontdata.filename,
+ comment="there is no info for subfont "..n,
+ }
+ else
+ info={
+ filename=fontdata.filename,
+ comment="there is no info",
+ }
+ end
+ return info
+end
+local function loadtables(f,specification,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ local tables={}
+ local basename=file.basename(specification.filename)
+ local filesize=specification.filesize
+ local filetime=specification.filetime
+ local fontdata={
+ filename=basename,
+ filesize=filesize,
+ filetime=filetime,
+ version=readstring(f,4),
+ noftables=readushort(f),
+ searchrange=readushort(f),
+ entryselector=readushort(f),
+ rangeshift=readushort(f),
+ tables=tables,
+ foundtables=false,
+ }
+ for i=1,fontdata.noftables do
+ local tag=lower(stripstring(readstring(f,4)))
+ local checksum=readushort(f)*0x10000+readushort(f)
+ local offset=readulong(f)
+ local length=readulong(f)
+ if offset+length>filesize then
+ report("bad %a table in file %a",tag,basename)
+ end
+ tables[tag]={
+ checksum=checksum,
+ offset=offset,
+ length=length,
+ }
+ end
+ fontdata.foundtables=sortedkeys(tables)
+ if tables.cff or tables.cff2 then
+ fontdata.format="opentype"
+ else
+ fontdata.format="truetype"
+ end
+ return fontdata,tables
+end
+local function prepareglyps(fontdata)
+ local glyphs=setmetatableindex(function(t,k)
+ local v={
+ index=k,
+ }
+ t[k]=v
+ return v
+ end)
+ fontdata.glyphs=glyphs
+ fontdata.mapping={}
+end
+local function readtable(tag,f,fontdata,specification,...)
+ local reader=readers[tag]
+ if reader then
+ reader(f,fontdata,specification,...)
+ end
+end
+local variablefonts_supported=(context and true) or (logs and logs.application and true) or false
+local function readdata(f,offset,specification)
+ local fontdata,tables=loadtables(f,specification,offset)
+ if specification.glyphs then
+ prepareglyps(fontdata)
+ end
+ if not variablefonts_supported then
+ specification.instance=nil
+ specification.variable=nil
+ specification.factors=nil
+ end
+ fontdata.temporary={}
+ readtable("name",f,fontdata,specification)
+ local askedname=specification.askedname
+ if askedname then
+ local fullname=getname(fontdata,"fullname") or ""
+ local cleanname=gsub(askedname,"[^a-zA-Z0-9]","")
+ local foundname=gsub(fullname,"[^a-zA-Z0-9]","")
+ if lower(cleanname)~=lower(foundname) then
+ return
+ end
+ end
+ readtable("stat",f,fontdata,specification)
+ readtable("avar",f,fontdata,specification)
+ readtable("fvar",f,fontdata,specification)
+ if variablefonts_supported then
+ local variabledata=fontdata.variabledata
+ if variabledata then
+ local instances=variabledata.instances
+ local axis=variabledata.axis
+ if axis and (not instances or #instances==0) then
+ instances={}
+ variabledata.instances=instances
+ local function add(n,subfamily,value)
+ local values={}
+ for i=1,#axis do
+ local a=axis[i]
+ values[i]={
+ axis=a.tag,
+ value=i==n and value or a.default,
+ }
+ end
+ instances[#instances+1]={
+ subfamily=subfamily,
+ values=values,
+ }
+ end
+ for i=1,#axis do
+ local a=axis[i]
+ local tag=a.tag
+ add(i,"default"..tag,a.default)
+ add(i,"minimum"..tag,a.minimum)
+ add(i,"maximum"..tag,a.maximum)
+ end
+ end
+ end
+ if not specification.factors then
+ local instance=specification.instance
+ if type(instance)=="string" then
+ local factors=helpers.getfactors(fontdata,instance)
+ if factors then
+ specification.factors=factors
+ fontdata.factors=factors
+ fontdata.instance=instance
+ report("user instance: %s, factors: % t",instance,factors)
+ else
+ report("user instance: %s, bad factors",instance)
+ end
+ end
+ end
+ if not fontdata.factors then
+ if fontdata.variabledata then
+ local factors=helpers.getfactors(fontdata,true)
+ if factors then
+ specification.factors=factors
+ fontdata.factors=factors
+ end
+ else
+ end
+ end
+ end
+ readtable("os/2",f,fontdata,specification)
+ readtable("head",f,fontdata,specification)
+ readtable("maxp",f,fontdata,specification)
+ readtable("hhea",f,fontdata,specification)
+ readtable("vhea",f,fontdata,specification)
+ readtable("hmtx",f,fontdata,specification)
+ readtable("vmtx",f,fontdata,specification)
+ readtable("vorg",f,fontdata,specification)
+ readtable("post",f,fontdata,specification)
+ readtable("mvar",f,fontdata,specification)
+ readtable("hvar",f,fontdata,specification)
+ readtable("vvar",f,fontdata,specification)
+ readtable("gdef",f,fontdata,specification)
+ readtable("cff",f,fontdata,specification)
+ readtable("cff2",f,fontdata,specification)
+ readtable("cmap",f,fontdata,specification)
+ readtable("loca",f,fontdata,specification)
+ readtable("glyf",f,fontdata,specification)
+ readtable("colr",f,fontdata,specification)
+ readtable("cpal",f,fontdata,specification)
+ readtable("svg",f,fontdata,specification)
+ readtable("sbix",f,fontdata,specification)
+ readtable("cbdt",f,fontdata,specification)
+ readtable("cblc",f,fontdata,specification)
+ readtable("ebdt",f,fontdata,specification)
+ readtable("eblc",f,fontdata,specification)
+ readtable("kern",f,fontdata,specification)
+ readtable("gsub",f,fontdata,specification)
+ readtable("gpos",f,fontdata,specification)
+ readtable("math",f,fontdata,specification)
+ fontdata.locations=nil
+ fontdata.cidmaps=nil
+ fontdata.dictionaries=nil
+ if specification.tableoffsets then
+ fontdata.tableoffsets=tables
+ setmetatableindex(tables,{
+ version=fontdata.version,
+ noftables=fontdata.noftables,
+ searchrange=fontdata.searchrange,
+ entryselector=fontdata.entryselector,
+ rangeshift=fontdata.rangeshift,
+ })
+ end
+ return fontdata
+end
+local function loadfontdata(specification)
+ local filename=specification.filename
+ local fileattr=lfs.attributes(filename)
+ local filesize=fileattr and fileattr.size or 0
+ local filetime=fileattr and fileattr.modification or 0
+ local f=openfile(filename,true)
+ if not f then
+ report("unable to open %a",filename)
+ elseif filesize==0 then
+ report("empty file %a",filename)
+ closefile(f)
+ else
+ specification.filesize=filesize
+ specification.filetime=filetime
+ local version=readstring(f,4)
+ local fontdata=nil
+ if version=="OTTO" or version=="true" or version=="\0\1\0\0" then
+ fontdata=readdata(f,0,specification)
+ elseif version=="ttcf" then
+ local subfont=tonumber(specification.subfont)
+ local ttcversion=readulong(f)
+ local nofsubfonts=readulong(f)
+ local offsets=readcardinaltable(f,nofsubfonts,ulong)
+ if subfont then
+ if subfont>=1 and subfont<=nofsubfonts then
+ fontdata=readdata(f,offsets[subfont],specification)
+ else
+ report("no subfont %a in file %a",subfont,filename)
+ end
+ else
+ subfont=specification.subfont
+ if type(subfont)=="string" and subfont~="" then
+ specification.askedname=subfont
+ for i=1,nofsubfonts do
+ fontdata=readdata(f,offsets[i],specification)
+ if fontdata then
+ fontdata.subfontindex=i
+ report("subfont named %a has index %a",subfont,i)
+ break
+ end
+ end
+ if not fontdata then
+ report("no subfont named %a",subfont)
+ end
+ else
+ local subfonts={}
+ fontdata={
+ filename=filename,
+ filesize=filesize,
+ filetime=filetime,
+ version=version,
+ subfonts=subfonts,
+ ttcversion=ttcversion,
+ nofsubfonts=nofsubfonts,
+ }
+ for i=1,nofsubfonts do
+ subfonts[i]=readdata(f,offsets[i],specification)
+ end
+ end
+ end
+ else
+ report("unknown version %a in file %a",version,filename)
+ end
+ closefile(f)
+ return fontdata or {}
+ end
+end
+local function loadfont(specification,n,instance)
+ if type(specification)=="string" then
+ specification={
+ filename=specification,
+ info=true,
+ details=true,
+ glyphs=true,
+ shapes=true,
+ kerns=true,
+ variable=true,
+ globalkerns=true,
+ lookups=true,
+ subfont=n or true,
+ tounicode=false,
+ instance=instance
+ }
+ end
+ if specification.shapes or specification.lookups or specification.kerns then
+ specification.glyphs=true
+ end
+ if specification.glyphs then
+ specification.details=true
+ end
+ if specification.details then
+ specification.info=true
+ end
+ if specification.platformnames then
+ specification.platformnames=true
+ end
+ if specification.instance or instance then
+ specification.variable=true
+ specification.instance=specification.instance or instance
+ end
+ local function message(str)
+ report("fatal error in file %a: %s\n%s",specification.filename,str,debug and debug.traceback())
+ end
+ local ok,result=xpcall(loadfontdata,message,specification)
+ if ok then
+ return result
+ end
+end
+function readers.loadshapes(filename,n,instance,streams)
+ local fontdata=loadfont {
+ filename=filename,
+ shapes=true,
+ streams=streams,
+ variable=true,
+ subfont=n,
+ instance=instance,
+ }
+ if fontdata then
+ for k,v in next,fontdata.glyphs do
+ v.class=nil
+ v.index=nil
+ v.math=nil
+ end
+ local names=fontdata.names
+ if names then
+ for k,v in next,names do
+ names[k]=fullstrip(v.content)
+ end
+ end
+ end
+ return fontdata and {
+ filename=filename,
+ format=fontdata.format,
+ glyphs=fontdata.glyphs,
+ units=fontdata.fontheader.units,
+ cffinfo=fontdata.cffinfo,
+ fontheader=fontdata.fontheader,
+ horizontalheader=fontdata.horizontalheader,
+ verticalheader=fontdata.verticalheader,
+ maximumprofile=fontdata.maximumprofile,
+ names=fontdata.names,
+ postscript=fontdata.postscript,
+ } or {
+ filename=filename,
+ format="unknown",
+ glyphs={},
+ units=0,
+ }
+end
+function readers.loadfont(filename,n,instance)
+ local fontdata=loadfont {
+ filename=filename,
+ glyphs=true,
+ shapes=false,
+ lookups=true,
+ variable=true,
+ subfont=n,
+ instance=instance,
+ }
+ if fontdata then
+ return {
+ tableversion=tableversion,
+ creator="context mkiv",
+ size=fontdata.filesize,
+ time=fontdata.filetime,
+ glyphs=fontdata.glyphs,
+ descriptions=fontdata.descriptions,
+ format=fontdata.format,
+ goodies={},
+ metadata=getinfo(fontdata,n,false,false,true,true),
+ properties={
+ hasitalics=fontdata.hasitalics or false,
+ maxcolorclass=fontdata.maxcolorclass,
+ hascolor=fontdata.hascolor or false,
+ instance=fontdata.instance,
+ factors=fontdata.factors,
+ },
+ resources={
+ filename=filename,
+ private=privateoffset,
+ duplicates=fontdata.duplicates or {},
+ features=fontdata.features or {},
+ sublookups=fontdata.sublookups or {},
+ marks=fontdata.marks or {},
+ markclasses=fontdata.markclasses or {},
+ marksets=fontdata.marksets or {},
+ sequences=fontdata.sequences or {},
+ variants=fontdata.variants,
+ version=getname(fontdata,"version"),
+ cidinfo=fontdata.cidinfo,
+ mathconstants=fontdata.mathconstants,
+ colorpalettes=fontdata.colorpalettes,
+ svgshapes=fontdata.svgshapes,
+ pngshapes=fontdata.pngshapes,
+ variabledata=fontdata.variabledata,
+ foundtables=fontdata.foundtables,
+ },
+ }
+ end
+end
+function readers.getinfo(filename,specification)
+ local subfont=nil
+ local platformnames=false
+ local rawfamilynames=false
+ local instancenames=true
+ local tableoffsets=false
+ if type(specification)=="table" then
+ subfont=tonumber(specification.subfont)
+ platformnames=specification.platformnames
+ rawfamilynames=specification.rawfamilynames
+ tableoffsets=specification.tableoffsets
+ else
+ subfont=tonumber(specification)
+ end
+ local fontdata=loadfont {
+ filename=filename,
+ details=true,
+ platformnames=platformnames,
+ instancenames=true,
+ tableoffsets=tableoffsets,
+ }
+ if fontdata then
+ local subfonts=fontdata.subfonts
+ if not subfonts then
+ return getinfo(fontdata,nil,platformnames,rawfamilynames,false,instancenames)
+ elseif not subfont then
+ local info={}
+ for i=1,#subfonts do
+ info[i]=getinfo(fontdata,i,platformnames,rawfamilynames,false,instancenames)
+ end
+ return info
+ elseif subfont>=1 and subfont<=#subfonts then
+ return getinfo(fontdata,subfont,platformnames,rawfamilynames,false,instancenames)
+ else
+ return {
+ filename=filename,
+ comment="there is no subfont "..subfont.." in this file"
+ }
+ end
+ else
+ return {
+ filename=filename,
+ comment="the file cannot be opened for reading",
+ }
+ end
+end
+function readers.rehash(fontdata,hashmethod)
+ report("the %a helper is not yet implemented","rehash")
+end
+function readers.checkhash(fontdata)
+ report("the %a helper is not yet implemented","checkhash")
+end
+function readers.pack(fontdata,hashmethod)
+ report("the %a helper is not yet implemented","pack")
+end
+function readers.unpack(fontdata)
+ report("the %a helper is not yet implemented","unpack")
+end
+function readers.expand(fontdata)
+ report("the %a helper is not yet implemented","unpack")
+end
+function readers.compact(fontdata)
+ report("the %a helper is not yet implemented","compact")
+end
+local extenders={}
+function readers.registerextender(extender)
+ extenders[#extenders+1]=extender
+end
+function readers.extend(fontdata)
+ for i=1,#extenders do
+ local extender=extenders[i]
+ local name=extender.name or "unknown"
+ local action=extender.action
+ if action then
+ action(fontdata)
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-oti']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local lower=string.lower
+local fonts=fonts
+local constructors=fonts.constructors
+local otf=constructors.handlers.otf
+local otffeatures=constructors.features.otf
+local registerotffeature=otffeatures.register
+local otftables=otf.tables or {}
+otf.tables=otftables
+local allocate=utilities.storage.allocate
+registerotffeature {
+ name="features",
+ description="initialization of feature handler",
+ default=true,
+}
+local function setmode(tfmdata,value)
+ if value then
+ tfmdata.properties.mode=lower(value)
+ end
+end
+otf.modeinitializer=setmode
+local function setlanguage(tfmdata,value)
+ if value then
+ local cleanvalue=lower(value)
+ local languages=otftables and otftables.languages
+ local properties=tfmdata.properties
+ if not languages then
+ properties.language=cleanvalue
+ elseif languages[value] then
+ properties.language=cleanvalue
+ else
+ properties.language="dflt"
+ end
+ end
+end
+local function setscript(tfmdata,value)
+ if value then
+ local cleanvalue=lower(value)
+ local scripts=otftables and otftables.scripts
+ local properties=tfmdata.properties
+ if not scripts then
+ properties.script=cleanvalue
+ elseif scripts[value] then
+ properties.script=cleanvalue
+ else
+ properties.script="dflt"
+ end
+ end
+end
+registerotffeature {
+ name="mode",
+ description="mode",
+ initializers={
+ base=setmode,
+ node=setmode,
+ plug=setmode,
+ }
+}
+registerotffeature {
+ name="language",
+ description="language",
+ initializers={
+ base=setlanguage,
+ node=setlanguage,
+ plug=setlanguage,
+ }
+}
+registerotffeature {
+ name="script",
+ description="script",
+ initializers={
+ base=setscript,
+ node=setscript,
+ plug=setscript,
+ }
+}
+otftables.featuretypes=allocate {
+ gpos_single="position",
+ gpos_pair="position",
+ gpos_cursive="position",
+ gpos_mark2base="position",
+ gpos_mark2ligature="position",
+ gpos_mark2mark="position",
+ gpos_context="position",
+ gpos_contextchain="position",
+ gsub_single="substitution",
+ gsub_multiple="substitution",
+ gsub_alternate="substitution",
+ gsub_ligature="substitution",
+ gsub_context="substitution",
+ gsub_contextchain="substitution",
+ gsub_reversecontextchain="substitution",
+ gsub_reversesub="substitution",
+}
+function otffeatures.checkeddefaultscript(featuretype,autoscript,scripts)
+ if featuretype=="position" then
+ local default=scripts.dflt
+ if default then
+ if autoscript=="position" or autoscript==true then
+ return default
+ else
+ report_otf("script feature %s not applied, enable default positioning")
+ end
+ else
+ end
+ elseif featuretype=="substitution" then
+ local default=scripts.dflt
+ if default then
+ if autoscript=="substitution" or autoscript==true then
+ return default
+ end
+ end
+ end
+end
+function otffeatures.checkeddefaultlanguage(featuretype,autolanguage,languages)
+ if featuretype=="position" then
+ local default=languages.dflt
+ if default then
+ if autolanguage=="position" or autolanguage==true then
+ return default
+ else
+ report_otf("language feature %s not applied, enable default positioning")
+ end
+ else
+ end
+ elseif featuretype=="substitution" then
+ local default=languages.dflt
+ if default then
+ if autolanguage=="substitution" or autolanguage==true then
+ return default
+ end
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ["font-ott"]={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+local type,next,tonumber,tostring,rawget,rawset=type,next,tonumber,tostring,rawget,rawset
+local gsub,lower,format,match,gmatch,find=string.gsub,string.lower,string.format,string.match,string.gmatch,string.find
+local sequenced=table.sequenced
+local is_boolean=string.is_boolean
+local setmetatableindex=table.setmetatableindex
+local setmetatablenewindex=table.setmetatablenewindex
+local allocate=utilities.storage.allocate
+local fonts=fonts
+local otf=fonts.handlers.otf
+local otffeatures=otf.features
+local tables=otf.tables or {}
+otf.tables=tables
+local statistics=otf.statistics or {}
+otf.statistics=statistics
+local scripts=allocate {
+ ["adlm"]="adlam",
+ ["aghb"]="caucasian albanian",
+ ["ahom"]="ahom",
+ ["arab"]="arabic",
+ ["armi"]="imperial aramaic",
+ ["armn"]="armenian",
+ ["avst"]="avestan",
+ ["bali"]="balinese",
+ ["bamu"]="bamum",
+ ["bass"]="bassa vah",
+ ["batk"]="batak",
+ ["beng"]="bengali",
+ ["bhks"]="bhaiksuki",
+ ["bng2"]="bengali variant 2",
+ ["bopo"]="bopomofo",
+ ["brah"]="brahmi",
+ ["brai"]="braille",
+ ["bugi"]="buginese",
+ ["buhd"]="buhid",
+ ["byzm"]="byzantine music",
+ ["cakm"]="chakma",
+ ["cans"]="canadian syllabics",
+ ["cari"]="carian",
+ ["cham"]="cham",
+ ["cher"]="cherokee",
+ ["copt"]="coptic",
+ ["cprt"]="cypriot syllabary",
+ ["cyrl"]="cyrillic",
+ ["dev2"]="devanagari variant 2",
+ ["deva"]="devanagari",
+ ["dogr"]="dogra",
+ ["dsrt"]="deseret",
+ ["dupl"]="duployan",
+ ["egyp"]="egyptian heiroglyphs",
+ ["elba"]="elbasan",
+ ["ethi"]="ethiopic",
+ ["geor"]="georgian",
+ ["gjr2"]="gujarati variant 2",
+ ["glag"]="glagolitic",
+ ["gong"]="gunjala gondi",
+ ["gonm"]="masaram gondi",
+ ["goth"]="gothic",
+ ["gran"]="grantha",
+ ["grek"]="greek",
+ ["gujr"]="gujarati",
+ ["gur2"]="gurmukhi variant 2",
+ ["guru"]="gurmukhi",
+ ["hang"]="hangul",
+ ["hani"]="cjk ideographic",
+ ["hano"]="hanunoo",
+ ["hatr"]="hatran",
+ ["hebr"]="hebrew",
+ ["hluw"]="anatolian hieroglyphs",
+ ["hmng"]="pahawh hmong",
+ ["hung"]="old hungarian",
+ ["ital"]="old italic",
+ ["jamo"]="hangul jamo",
+ ["java"]="javanese",
+ ["kali"]="kayah li",
+ ["kana"]="hiragana and katakana",
+ ["khar"]="kharosthi",
+ ["khmr"]="khmer",
+ ["khoj"]="khojki",
+ ["knd2"]="kannada variant 2",
+ ["knda"]="kannada",
+ ["kthi"]="kaithi",
+ ["lana"]="tai tham",
+ ["lao" ]="lao",
+ ["latn"]="latin",
+ ["lepc"]="lepcha",
+ ["limb"]="limbu",
+ ["lina"]="linear a",
+ ["linb"]="linear b",
+ ["lisu"]="lisu",
+ ["lyci"]="lycian",
+ ["lydi"]="lydian",
+ ["mahj"]="mahajani",
+ ["maka"]="makasar",
+ ["mand"]="mandaic and mandaean",
+ ["mani"]="manichaean",
+ ["marc"]="marchen",
+ ["math"]="mathematical alphanumeric symbols",
+ ["medf"]="medefaidrin",
+ ["mend"]="mende kikakui",
+ ["merc"]="meroitic cursive",
+ ["mero"]="meroitic hieroglyphs",
+ ["mlm2"]="malayalam variant 2",
+ ["mlym"]="malayalam",
+ ["modi"]="modi",
+ ["mong"]="mongolian",
+ ["mroo"]="mro",
+ ["mtei"]="meitei Mayek",
+ ["mult"]="multani",
+ ["musc"]="musical symbols",
+ ["mym2"]="myanmar variant 2",
+ ["mymr"]="myanmar",
+ ["narb"]="old north arabian",
+ ["nbat"]="nabataean",
+ ["newa"]="newa",
+ ["nko" ]='n"ko',
+ ["nshu"]="nüshu",
+ ["ogam"]="ogham",
+ ["olck"]="ol chiki",
+ ["orkh"]="old turkic and orkhon runic",
+ ["ory2"]="odia variant 2",
+ ["orya"]="oriya",
+ ["osge"]="osage",
+ ["osma"]="osmanya",
+ ["palm"]="palmyrene",
+ ["pauc"]="pau cin hau",
+ ["perm"]="old permic",
+ ["phag"]="phags-pa",
+ ["phli"]="inscriptional pahlavi",
+ ["phlp"]="psalter pahlavi",
+ ["phnx"]="phoenician",
+ ["plrd"]="miao",
+ ["prti"]="inscriptional parthian",
+ ["rjng"]="rejang",
+ ["rohg"]="hanifi rohingya",
+ ["runr"]="runic",
+ ["samr"]="samaritan",
+ ["sarb"]="old south arabian",
+ ["saur"]="saurashtra",
+ ["sgnw"]="sign writing",
+ ["shaw"]="shavian",
+ ["shrd"]="sharada",
+ ["sidd"]="siddham",
+ ["sind"]="khudawadi",
+ ["sinh"]="sinhala",
+ ["sogd"]="sogdian",
+ ["sogo"]="old sogdian",
+ ["sora"]="sora sompeng",
+ ["soyo"]="soyombo",
+ ["sund"]="sundanese",
+ ["sylo"]="syloti nagri",
+ ["syrc"]="syriac",
+ ["tagb"]="tagbanwa",
+ ["takr"]="takri",
+ ["tale"]="tai le",
+ ["talu"]="tai lu",
+ ["taml"]="tamil",
+ ["tang"]="tangut",
+ ["tavt"]="tai viet",
+ ["tel2"]="telugu variant 2",
+ ["telu"]="telugu",
+ ["tfng"]="tifinagh",
+ ["tglg"]="tagalog",
+ ["thaa"]="thaana",
+ ["thai"]="thai",
+ ["tibt"]="tibetan",
+ ["tirh"]="tirhuta",
+ ["tml2"]="tamil variant 2",
+ ["ugar"]="ugaritic cuneiform",
+ ["vai" ]="vai",
+ ["wara"]="warang citi",
+ ["xpeo"]="old persian cuneiform",
+ ["xsux"]="sumero-akkadian cuneiform",
+ ["yi" ]="yi",
+ ["zanb"]="zanabazar square",
+}
+local languages=allocate {
+ ["aba" ]="abaza",
+ ["abk" ]="abkhazian",
+ ["ach" ]="acholi",
+ ["acr" ]="achi",
+ ["ady" ]="adyghe",
+ ["afk" ]="afrikaans",
+ ["afr" ]="afar",
+ ["agw" ]="agaw",
+ ["aio" ]="aiton",
+ ["aka" ]="akan",
+ ["als" ]="alsatian",
+ ["alt" ]="altai",
+ ["amh" ]="amharic",
+ ["ang" ]="anglo-saxon",
+ ["apph"]="phonetic transcription—americanist conventions",
+ ["ara" ]="arabic",
+ ["arg" ]="aragonese",
+ ["ari" ]="aari",
+ ["ark" ]="rakhine",
+ ["asm" ]="assamese",
+ ["ast" ]="asturian",
+ ["ath" ]="athapaskan",
+ ["avr" ]="avar",
+ ["awa" ]="awadhi",
+ ["aym" ]="aymara",
+ ["azb" ]="torki",
+ ["aze" ]="azerbaijani",
+ ["bad" ]="badaga",
+ ["bad0"]="banda",
+ ["bag" ]="baghelkhandi",
+ ["bal" ]="balkar",
+ ["ban" ]="balinese",
+ ["bar" ]="bavarian",
+ ["bau" ]="baulé",
+ ["bbc" ]="batak toba",
+ ["bbr" ]="berber",
+ ["bch" ]="bench",
+ ["bcr" ]="bible cree",
+ ["bdy" ]="bandjalang",
+ ["bel" ]="belarussian",
+ ["bem" ]="bemba",
+ ["ben" ]="bengali",
+ ["bgc" ]="haryanvi",
+ ["bgq" ]="bagri",
+ ["bgr" ]="bulgarian",
+ ["bhi" ]="bhili",
+ ["bho" ]="bhojpuri",
+ ["bik" ]="bikol",
+ ["bil" ]="bilen",
+ ["bis" ]="bislama",
+ ["bjj" ]="kanauji",
+ ["bkf" ]="blackfoot",
+ ["bli" ]="baluchi",
+ ["blk" ]="pa'o karen",
+ ["bln" ]="balante",
+ ["blt" ]="balti",
+ ["bmb" ]="bambara (bamanankan)",
+ ["bml" ]="bamileke",
+ ["bos" ]="bosnian",
+ ["bpy" ]="bishnupriya manipuri",
+ ["bre" ]="breton",
+ ["brh" ]="brahui",
+ ["bri" ]="braj bhasha",
+ ["brm" ]="burmese",
+ ["brx" ]="bodo",
+ ["bsh" ]="bashkir",
+ ["bsk" ]="burushaski",
+ ["bti" ]="beti",
+ ["bts" ]="batak simalungun",
+ ["bug" ]="bugis",
+ ["byv" ]="medumba",
+ ["cak" ]="kaqchikel",
+ ["cat" ]="catalan",
+ ["cbk" ]="zamboanga chavacano",
+ ["cchn"]="chinantec",
+ ["ceb" ]="cebuano",
+ ["cgg" ]="chiga",
+ ["cha" ]="chamorro",
+ ["che" ]="chechen",
+ ["chg" ]="chaha gurage",
+ ["chh" ]="chattisgarhi",
+ ["chi" ]="chichewa (chewa, nyanja)",
+ ["chk" ]="chukchi",
+ ["chk0"]="chuukese",
+ ["cho" ]="choctaw",
+ ["chp" ]="chipewyan",
+ ["chr" ]="cherokee",
+ ["chu" ]="chuvash",
+ ["chy" ]="cheyenne",
+ ["cja" ]="western cham",
+ ["cjm" ]="eastern cham",
+ ["cmr" ]="comorian",
+ ["cop" ]="coptic",
+ ["cor" ]="cornish",
+ ["cos" ]="corsican",
+ ["cpp" ]="creoles",
+ ["cre" ]="cree",
+ ["crr" ]="carrier",
+ ["crt" ]="crimean tatar",
+ ["csb" ]="kashubian",
+ ["csl" ]="church slavonic",
+ ["csy" ]="czech",
+ ["ctg" ]="chittagonian",
+ ["cuk" ]="san blas kuna",
+ ["dan" ]="danish",
+ ["dar" ]="dargwa",
+ ["dax" ]="dayi",
+ ["dcr" ]="woods cree",
+ ["deu" ]="german",
+ ["dgo" ]="dogri",
+ ["dgr" ]="dogri",
+ ["dhg" ]="dhangu",
+ ["dhv" ]="divehi (dhivehi, maldivian)",
+ ["diq" ]="dimli",
+ ["div" ]="divehi (dhivehi, maldivian)",
+ ["djr" ]="zarma",
+ ["djr0"]="djambarrpuyngu",
+ ["dng" ]="dangme",
+ ["dnj" ]="dan",
+ ["dnk" ]="dinka",
+ ["dri" ]="dari",
+ ["duj" ]="dhuwal",
+ ["dun" ]="dungan",
+ ["dzn" ]="dzongkha",
+ ["ebi" ]="ebira",
+ ["ecr" ]="eastern cree",
+ ["edo" ]="edo",
+ ["efi" ]="efik",
+ ["ell" ]="greek",
+ ["emk" ]="eastern maninkakan",
+ ["eng" ]="english",
+ ["erz" ]="erzya",
+ ["esp" ]="spanish",
+ ["esu" ]="central yupik",
+ ["eti" ]="estonian",
+ ["euq" ]="basque",
+ ["evk" ]="evenki",
+ ["evn" ]="even",
+ ["ewe" ]="ewe",
+ ["fan" ]="french antillean",
+ ["fan0"]=" fang",
+ ["far" ]="persian",
+ ["fat" ]="fanti",
+ ["fin" ]="finnish",
+ ["fji" ]="fijian",
+ ["fle" ]="dutch (flemish)",
+ ["fmp" ]="fe’fe’",
+ ["fne" ]="forest nenets",
+ ["fon" ]="fon",
+ ["fos" ]="faroese",
+ ["fra" ]="french",
+ ["frc" ]="cajun french",
+ ["fri" ]="frisian",
+ ["frl" ]="friulian",
+ ["frp" ]="arpitan",
+ ["fta" ]="futa",
+ ["ful" ]="fulah",
+ ["fuv" ]="nigerian fulfulde",
+ ["gad" ]="ga",
+ ["gae" ]="scottish gaelic (gaelic)",
+ ["gag" ]="gagauz",
+ ["gal" ]="galician",
+ ["gar" ]="garshuni",
+ ["gaw" ]="garhwali",
+ ["gez" ]="ge'ez",
+ ["gih" ]="githabul",
+ ["gil" ]="gilyak",
+ ["gil0"]="kiribati (gilbertese)",
+ ["gkp" ]="kpelle (guinea)",
+ ["glk" ]="gilaki",
+ ["gmz" ]="gumuz",
+ ["gnn" ]="gumatj",
+ ["gog" ]="gogo",
+ ["gon" ]="gondi",
+ ["grn" ]="greenlandic",
+ ["gro" ]="garo",
+ ["gua" ]="guarani",
+ ["guc" ]="wayuu",
+ ["guf" ]="gupapuyngu",
+ ["guj" ]="gujarati",
+ ["guz" ]="gusii",
+ ["hai" ]="haitian (haitian creole)",
+ ["hal" ]="halam",
+ ["har" ]="harauti",
+ ["hau" ]="hausa",
+ ["haw" ]="hawaiian",
+ ["hay" ]="haya",
+ ["haz" ]="hazaragi",
+ ["hbn" ]="hammer-banna",
+ ["her" ]="herero",
+ ["hil" ]="hiligaynon",
+ ["hin" ]="hindi",
+ ["hma" ]="high mari",
+ ["hmn" ]="hmong",
+ ["hmo" ]="hiri motu",
+ ["hnd" ]="hindko",
+ ["ho" ]="ho",
+ ["hri" ]="harari",
+ ["hrv" ]="croatian",
+ ["hun" ]="hungarian",
+ ["hye" ]="armenian",
+ ["hye0"]="armenian east",
+ ["iba" ]="iban",
+ ["ibb" ]="ibibio",
+ ["ibo" ]="igbo",
+ ["ido" ]="ido",
+ ["ijo" ]="ijo languages",
+ ["ile" ]="interlingue",
+ ["ilo" ]="ilokano",
+ ["ina" ]="interlingua",
+ ["ind" ]="indonesian",
+ ["ing" ]="ingush",
+ ["inu" ]="inuktitut",
+ ["ipk" ]="inupiat",
+ ["ipph"]="phonetic transcription—ipa conventions",
+ ["iri" ]="irish",
+ ["irt" ]="irish traditional",
+ ["isl" ]="icelandic",
+ ["ism" ]="inari sami",
+ ["ita" ]="italian",
+ ["iwr" ]="hebrew",
+ ["jam" ]="jamaican creole",
+ ["jan" ]="japanese",
+ ["jav" ]="javanese",
+ ["jbo" ]="lojban",
+ ["jct" ]="krymchak",
+ ["jii" ]="yiddish",
+ ["jud" ]="ladino",
+ ["jul" ]="jula",
+ ["kab" ]="kabardian",
+ ["kab0"]="kabyle",
+ ["kac" ]="kachchi",
+ ["kal" ]="kalenjin",
+ ["kan" ]="kannada",
+ ["kar" ]="karachay",
+ ["kat" ]="georgian",
+ ["kaz" ]="kazakh",
+ ["kde" ]="makonde",
+ ["kea" ]="kabuverdianu (crioulo)",
+ ["keb" ]="kebena",
+ ["kek" ]="kekchi",
+ ["kge" ]="khutsuri georgian",
+ ["kha" ]="khakass",
+ ["khk" ]="khanty-kazim",
+ ["khm" ]="khmer",
+ ["khs" ]="khanty-shurishkar",
+ ["kht" ]="khamti shan",
+ ["khv" ]="khanty-vakhi",
+ ["khw" ]="khowar",
+ ["kik" ]="kikuyu (gikuyu)",
+ ["kir" ]="kirghiz (kyrgyz)",
+ ["kis" ]="kisii",
+ ["kiu" ]="kirmanjki",
+ ["kjd" ]="southern kiwai",
+ ["kjp" ]="eastern pwo karen",
+ ["kjz" ]="bumthangkha",
+ ["kkn" ]="kokni",
+ ["klm" ]="kalmyk",
+ ["kmb" ]="kamba",
+ ["kmn" ]="kumaoni",
+ ["kmo" ]="komo",
+ ["kms" ]="komso",
+ ["kmz" ]="khorasani turkic",
+ ["knr" ]="kanuri",
+ ["kod" ]="kodagu",
+ ["koh" ]="korean old hangul",
+ ["kok" ]="konkani",
+ ["kom" ]="komi",
+ ["kon" ]="kikongo",
+ ["kon0"]="kongo",
+ ["kop" ]="komi-permyak",
+ ["kor" ]="korean",
+ ["kos" ]="kosraean",
+ ["koz" ]="komi-zyrian",
+ ["kpl" ]="kpelle",
+ ["kri" ]="krio",
+ ["krk" ]="karakalpak",
+ ["krl" ]="karelian",
+ ["krm" ]="karaim",
+ ["krn" ]="karen",
+ ["krt" ]="koorete",
+ ["ksh" ]="kashmiri",
+ ["ksh0"]="ripuarian",
+ ["ksi" ]="khasi",
+ ["ksm" ]="kildin sami",
+ ["ksw" ]="s’gaw karen",
+ ["kua" ]="kuanyama",
+ ["kui" ]="kui",
+ ["kul" ]="kulvi",
+ ["kum" ]="kumyk",
+ ["kur" ]="kurdish",
+ ["kuu" ]="kurukh",
+ ["kuy" ]="kuy",
+ ["kyk" ]="koryak",
+ ["kyu" ]="western kayah",
+ ["lad" ]="ladin",
+ ["lah" ]="lahuli",
+ ["lak" ]="lak",
+ ["lam" ]="lambani",
+ ["lao" ]="lao",
+ ["lat" ]="latin",
+ ["laz" ]="laz",
+ ["lcr" ]="l-cree",
+ ["ldk" ]="ladakhi",
+ ["lez" ]="lezgi",
+ ["lij" ]="ligurian",
+ ["lim" ]="limburgish",
+ ["lin" ]="lingala",
+ ["lis" ]="lisu",
+ ["ljp" ]="lampung",
+ ["lki" ]="laki",
+ ["lma" ]="low mari",
+ ["lmb" ]="limbu",
+ ["lmo" ]="lombard",
+ ["lmw" ]="lomwe",
+ ["lom" ]="loma",
+ ["lrc" ]="luri",
+ ["lsb" ]="lower sorbian",
+ ["lsm" ]="lule sami",
+ ["lth" ]="lithuanian",
+ ["ltz" ]="luxembourgish",
+ ["lua" ]="luba-lulua",
+ ["lub" ]="luba-katanga",
+ ["lug" ]="ganda",
+ ["luh" ]="luyia",
+ ["luo" ]="luo",
+ ["lvi" ]="latvian",
+ ["mad" ]="madura",
+ ["mag" ]="magahi",
+ ["mah" ]="marshallese",
+ ["maj" ]="majang",
+ ["mak" ]="makhuwa",
+ ["mal" ]="malayalam reformed",
+ ["mam" ]="mam",
+ ["man" ]="mansi",
+ ["map" ]="mapudungun",
+ ["mar" ]="marathi",
+ ["maw" ]="marwari",
+ ["mbn" ]="mbundu",
+ ["mbo" ]="mbo",
+ ["mch" ]="manchu",
+ ["mcr" ]="moose cree",
+ ["mde" ]="mende",
+ ["mdr" ]="mandar",
+ ["men" ]="me'en",
+ ["mer" ]="meru",
+ ["mfa" ]="pattani malay",
+ ["mfe" ]="morisyen",
+ ["min" ]="minangkabau",
+ ["miz" ]="mizo",
+ ["mkd" ]="macedonian",
+ ["mkr" ]="makasar",
+ ["mkw" ]="kituba",
+ ["mle" ]="male",
+ ["mlg" ]="malagasy",
+ ["mln" ]="malinke",
+ ["mlr" ]="malayalam reformed",
+ ["mly" ]="malay",
+ ["mnd" ]="mandinka",
+ ["mng" ]="mongolian",
+ ["mni" ]="manipuri",
+ ["mnk" ]="maninka",
+ ["mnx" ]="manx",
+ ["moh" ]="mohawk",
+ ["mok" ]="moksha",
+ ["mol" ]="moldavian",
+ ["mon" ]="mon",
+ ["mor" ]="moroccan",
+ ["mos" ]="mossi",
+ ["mri" ]="maori",
+ ["mth" ]="maithili",
+ ["mts" ]="maltese",
+ ["mun" ]="mundari",
+ ["mus" ]="muscogee",
+ ["mwl" ]="mirandese",
+ ["mww" ]="hmong daw",
+ ["myn" ]="mayan",
+ ["mzn" ]="mazanderani",
+ ["nag" ]="naga-assamese",
+ ["nah" ]="nahuatl",
+ ["nan" ]="nanai",
+ ["nap" ]="neapolitan",
+ ["nas" ]="naskapi",
+ ["nau" ]="nauruan",
+ ["nav" ]="navajo",
+ ["ncr" ]="n-cree",
+ ["ndb" ]="ndebele",
+ ["ndc" ]="ndau",
+ ["ndg" ]="ndonga",
+ ["nds" ]="low saxon",
+ ["nep" ]="nepali",
+ ["new" ]="newari",
+ ["nga" ]="ngbaka",
+ ["ngr" ]="nagari",
+ ["nhc" ]="norway house cree",
+ ["nis" ]="nisi",
+ ["niu" ]="niuean",
+ ["nkl" ]="nyankole",
+ ["nko" ]="n'ko",
+ ["nld" ]="dutch",
+ ["noe" ]="nimadi",
+ ["nog" ]="nogai",
+ ["nor" ]="norwegian",
+ ["nov" ]="novial",
+ ["nsm" ]="northern sami",
+ ["nso" ]="sotho, northern",
+ ["nta" ]="northern tai",
+ ["nto" ]="esperanto",
+ ["nym" ]="nyamwezi",
+ ["nyn" ]="norwegian nynorsk",
+ ["nza" ]="mbembe tigon",
+ ["oci" ]="occitan",
+ ["ocr" ]="oji-cree",
+ ["ojb" ]="ojibway",
+ ["ori" ]="odia",
+ ["oro" ]="oromo",
+ ["oss" ]="ossetian",
+ ["paa" ]="palestinian aramaic",
+ ["pag" ]="pangasinan",
+ ["pal" ]="pali",
+ ["pam" ]="pampangan",
+ ["pan" ]="punjabi",
+ ["pap" ]="palpa",
+ ["pap0"]="papiamentu",
+ ["pas" ]="pashto",
+ ["pau" ]="palauan",
+ ["pcc" ]="bouyei",
+ ["pcd" ]="picard",
+ ["pdc" ]="pennsylvania german",
+ ["pgr" ]="polytonic greek",
+ ["phk" ]="phake",
+ ["pih" ]="norfolk",
+ ["pil" ]="filipino",
+ ["plg" ]="palaung",
+ ["plk" ]="polish",
+ ["pms" ]="piemontese",
+ ["pnb" ]="western panjabi",
+ ["poh" ]="pocomchi",
+ ["pon" ]="pohnpeian",
+ ["pro" ]="provencal",
+ ["ptg" ]="portuguese",
+ ["pwo" ]="western pwo karen",
+ ["qin" ]="chin",
+ ["quc" ]="k’iche’",
+ ["quh" ]="quechua (bolivia)",
+ ["quz" ]="quechua",
+ ["qvi" ]="quechua (ecuador)",
+ ["qwh" ]="quechua (peru)",
+ ["raj" ]="rajasthani",
+ ["rar" ]="rarotongan",
+ ["rbu" ]="russian buriat",
+ ["rcr" ]="r-cree",
+ ["rej" ]="rejang",
+ ["ria" ]="riang",
+ ["rif" ]="tarifit",
+ ["rit" ]="ritarungo",
+ ["rkw" ]="arakwal",
+ ["rms" ]="romansh",
+ ["rmy" ]="vlax romani",
+ ["rom" ]="romanian",
+ ["roy" ]="romany",
+ ["rsy" ]="rusyn",
+ ["rtm" ]="rotuman",
+ ["rua" ]="kinyarwanda",
+ ["run" ]="rundi",
+ ["rup" ]="aromanian",
+ ["rus" ]="russian",
+ ["sad" ]="sadri",
+ ["san" ]="sanskrit",
+ ["sas" ]="sasak",
+ ["sat" ]="santali",
+ ["say" ]="sayisi",
+ ["scn" ]="sicilian",
+ ["sco" ]="scots",
+ ["scs" ]="north slavey",
+ ["sek" ]="sekota",
+ ["sel" ]="selkup",
+ ["sga" ]="old irish",
+ ["sgo" ]="sango",
+ ["sgs" ]="samogitian",
+ ["shi" ]="tachelhit",
+ ["shn" ]="shan",
+ ["sib" ]="sibe",
+ ["sid" ]="sidamo",
+ ["sig" ]="silte gurage",
+ ["sks" ]="skolt sami",
+ ["sky" ]="slovak",
+ ["sla" ]="slavey",
+ ["slv" ]="slovenian",
+ ["sml" ]="somali",
+ ["smo" ]="samoan",
+ ["sna" ]="sena",
+ ["sna0"]="shona",
+ ["snd" ]="sindhi",
+ ["snh" ]="sinhala (sinhalese)",
+ ["snk" ]="soninke",
+ ["sog" ]="sodo gurage",
+ ["sop" ]="songe",
+ ["sot" ]="sotho, southern",
+ ["sqi" ]="albanian",
+ ["srb" ]="serbian",
+ ["srd" ]="sardinian",
+ ["srk" ]="saraiki",
+ ["srr" ]="serer",
+ ["ssl" ]="south slavey",
+ ["ssm" ]="southern sami",
+ ["stq" ]="saterland frisian",
+ ["suk" ]="sukuma",
+ ["sun" ]="sundanese",
+ ["sur" ]="suri",
+ ["sva" ]="svan",
+ ["sve" ]="swedish",
+ ["swa" ]="swadaya aramaic",
+ ["swk" ]="swahili",
+ ["swz" ]="swati",
+ ["sxt" ]="sutu",
+ ["sxu" ]="upper saxon",
+ ["syl" ]="sylheti",
+ ["syr" ]="syriac",
+ ["syre"]="estrangela syriac",
+ ["syrj"]="western syriac",
+ ["syrn"]="eastern syriac",
+ ["szl" ]="silesian",
+ ["tab" ]="tabasaran",
+ ["taj" ]="tajiki",
+ ["tam" ]="tamil",
+ ["tat" ]="tatar",
+ ["tcr" ]="th-cree",
+ ["tdd" ]="dehong dai",
+ ["tel" ]="telugu",
+ ["tet" ]="tetum",
+ ["tgl" ]="tagalog",
+ ["tgn" ]="tongan",
+ ["tgr" ]="tigre",
+ ["tgy" ]="tigrinya",
+ ["tha" ]="thai",
+ ["tht" ]="tahitian",
+ ["tib" ]="tibetan",
+ ["tiv" ]="tiv",
+ ["tkm" ]="turkmen",
+ ["tmh" ]="tamashek",
+ ["tmn" ]="temne",
+ ["tna" ]="tswana",
+ ["tne" ]="tundra nenets",
+ ["tng" ]="tonga",
+ ["tod" ]="todo",
+ ["tod0"]="toma",
+ ["tpi" ]="tok pisin",
+ ["trk" ]="turkish",
+ ["tsg" ]="tsonga",
+ ["tsj" ]="tshangla",
+ ["tua" ]="turoyo aramaic",
+ ["tul" ]="tulu",
+ ["tum" ]="tulu",
+ ["tuv" ]="tuvin",
+ ["tvl" ]="tuvalu",
+ ["twi" ]="twi",
+ ["tyz" ]="tày",
+ ["tzm" ]="tamazight",
+ ["tzo" ]="tzotzil",
+ ["udm" ]="udmurt",
+ ["ukr" ]="ukrainian",
+ ["umb" ]="umbundu",
+ ["urd" ]="urdu",
+ ["usb" ]="upper sorbian",
+ ["uyg" ]="uyghur",
+ ["uzb" ]="uzbek",
+ ["vec" ]="venetian",
+ ["ven" ]="venda",
+ ["vit" ]="vietnamese",
+ ["vol" ]="volapük",
+ ["vro" ]="võro",
+ ["wa" ]="wa",
+ ["wag" ]="wagdi",
+ ["war" ]="waray-waray",
+ ["wcr" ]="west-cree",
+ ["wel" ]="welsh",
+ ["wlf" ]="wolof",
+ ["wln" ]="walloon",
+ ["wtm" ]="mewati",
+ ["xbd" ]="lü",
+ ["xhs" ]="xhosa",
+ ["xjb" ]="minjangbal",
+ ["xkf" ]="khengkha",
+ ["xog" ]="soga",
+ ["xpe" ]="kpelle (liberia)",
+ ["yak" ]="sakha",
+ ["yao" ]="yao",
+ ["yap" ]="yapese",
+ ["yba" ]="yoruba",
+ ["ycr" ]="y-cree",
+ ["yic" ]="yi classic",
+ ["yim" ]="yi modern",
+ ["zea" ]="zealandic",
+ ["zgh" ]="standard morrocan tamazigh",
+ ["zha" ]="zhuang",
+ ["zhh" ]="chinese, hong kong sar",
+ ["zhp" ]="chinese phonetic",
+ ["zhs" ]="chinese simplified",
+ ["zht" ]="chinese traditional",
+ ["znd" ]="zande",
+ ["zul" ]="zulu",
+ ["zza" ]="zazaki",
+}
+local features=allocate {
+ ["aalt"]="access all alternates",
+ ["abvf"]="above-base forms",
+ ["abvm"]="above-base mark positioning",
+ ["abvs"]="above-base substitutions",
+ ["afrc"]="alternative fractions",
+ ["akhn"]="akhands",
+ ["blwf"]="below-base forms",
+ ["blwm"]="below-base mark positioning",
+ ["blws"]="below-base substitutions",
+ ["c2pc"]="petite capitals from capitals",
+ ["c2sc"]="small capitals from capitals",
+ ["calt"]="contextual alternates",
+ ["case"]="case-sensitive forms",
+ ["ccmp"]="glyph composition/decomposition",
+ ["cfar"]="conjunct form after ro",
+ ["cjct"]="conjunct forms",
+ ["clig"]="contextual ligatures",
+ ["cpct"]="centered cjk punctuation",
+ ["cpsp"]="capital spacing",
+ ["cswh"]="contextual swash",
+ ["curs"]="cursive positioning",
+ ["dflt"]="default processing",
+ ["dist"]="distances",
+ ["dlig"]="discretionary ligatures",
+ ["dnom"]="denominators",
+ ["dtls"]="dotless forms",
+ ["expt"]="expert forms",
+ ["falt"]="final glyph alternates",
+ ["fin2"]="terminal forms #2",
+ ["fin3"]="terminal forms #3",
+ ["fina"]="terminal forms",
+ ["flac"]="flattened accents over capitals",
+ ["frac"]="fractions",
+ ["fwid"]="full width",
+ ["half"]="half forms",
+ ["haln"]="halant forms",
+ ["halt"]="alternate half width",
+ ["hist"]="historical forms",
+ ["hkna"]="horizontal kana alternates",
+ ["hlig"]="historical ligatures",
+ ["hngl"]="hangul",
+ ["hojo"]="hojo kanji forms",
+ ["hwid"]="half width",
+ ["init"]="initial forms",
+ ["isol"]="isolated forms",
+ ["ital"]="italics",
+ ["jalt"]="justification alternatives",
+ ["jp04"]="jis2004 forms",
+ ["jp78"]="jis78 forms",
+ ["jp83"]="jis83 forms",
+ ["jp90"]="jis90 forms",
+ ["kern"]="kerning",
+ ["lfbd"]="left bounds",
+ ["liga"]="standard ligatures",
+ ["ljmo"]="leading jamo forms",
+ ["lnum"]="lining figures",
+ ["locl"]="localized forms",
+ ["ltra"]="left-to-right alternates",
+ ["ltrm"]="left-to-right mirrored forms",
+ ["mark"]="mark positioning",
+ ["med2"]="medial forms #2",
+ ["medi"]="medial forms",
+ ["mgrk"]="mathematical greek",
+ ["mkmk"]="mark to mark positioning",
+ ["mset"]="mark positioning via substitution",
+ ["nalt"]="alternate annotation forms",
+ ["nlck"]="nlc kanji forms",
+ ["nukt"]="nukta forms",
+ ["numr"]="numerators",
+ ["onum"]="old style figures",
+ ["opbd"]="optical bounds",
+ ["ordn"]="ordinals",
+ ["ornm"]="ornaments",
+ ["palt"]="proportional alternate width",
+ ["pcap"]="petite capitals",
+ ["pkna"]="proportional kana",
+ ["pnum"]="proportional figures",
+ ["pref"]="pre-base forms",
+ ["pres"]="pre-base substitutions",
+ ["pstf"]="post-base forms",
+ ["psts"]="post-base substitutions",
+ ["pwid"]="proportional widths",
+ ["qwid"]="quarter widths",
+ ["rand"]="randomize",
+ ["rclt"]="required contextual alternates",
+ ["rkrf"]="rakar forms",
+ ["rlig"]="required ligatures",
+ ["rphf"]="reph form",
+ ["rtbd"]="right bounds",
+ ["rtla"]="right-to-left alternates",
+ ["rtlm"]="right to left mirrored forms",
+ ["rvrn"]="required variation alternates",
+ ["ruby"]="ruby notation forms",
+ ["salt"]="stylistic alternates",
+ ["sinf"]="scientific inferiors",
+ ["size"]="optical size",
+ ["smcp"]="small capitals",
+ ["smpl"]="simplified forms",
+ ["ssty"]="script style",
+ ["stch"]="stretching glyph decomposition",
+ ["subs"]="subscript",
+ ["sups"]="superscript",
+ ["swsh"]="swash",
+ ["titl"]="titling",
+ ["tjmo"]="trailing jamo forms",
+ ["tnam"]="traditional name forms",
+ ["tnum"]="tabular figures",
+ ["trad"]="traditional forms",
+ ["twid"]="third widths",
+ ["unic"]="unicase",
+ ["valt"]="alternate vertical metrics",
+ ["vatu"]="vattu variants",
+ ["vert"]="vertical writing",
+ ["vhal"]="alternate vertical half metrics",
+ ["vjmo"]="vowel jamo forms",
+ ["vkna"]="vertical kana alternates",
+ ["vkrn"]="vertical kerning",
+ ["vpal"]="proportional alternate vertical metrics",
+ ["vrtr"]="vertical alternates for rotation",
+ ["vrt2"]="vertical rotation",
+ ["zero"]="slashed zero",
+ ["trep"]="traditional tex replacements",
+ ["tlig"]="traditional tex ligatures",
+ ["ss.."]="stylistic set ..",
+ ["cv.."]="character variant ..",
+ ["js.."]="justification ..",
+ ["dv.."]="devanagari ..",
+ ["ml.."]="malayalam ..",
+}
+local baselines=allocate {
+ ["hang"]="hanging baseline",
+ ["icfb"]="ideographic character face bottom edge baseline",
+ ["icft"]="ideographic character face tope edige baseline",
+ ["ideo"]="ideographic em-box bottom edge baseline",
+ ["idtp"]="ideographic em-box top edge baseline",
+ ["math"]="mathematical centered baseline",
+ ["romn"]="roman baseline"
+}
+tables.scripts=scripts
+tables.languages=languages
+tables.features=features
+tables.baselines=baselines
+local acceptscripts=true directives.register("otf.acceptscripts",function(v) acceptscripts=v end)
+local acceptlanguages=true directives.register("otf.acceptlanguages",function(v) acceptlanguages=v end)
+local report_checks=logs.reporter("fonts","checks")
+if otffeatures.features then
+ for k,v in next,otffeatures.features do
+ features[k]=v
+ end
+ otffeatures.features=features
+end
+local function swapped(h)
+ local r={}
+ for k,v in next,h do
+ r[gsub(v,"[^a-z0-9]","")]=k
+ end
+ return r
+end
+local verbosescripts=allocate(swapped(scripts ))
+local verboselanguages=allocate(swapped(languages))
+local verbosefeatures=allocate(swapped(features ))
+local verbosebaselines=allocate(swapped(baselines))
+local function resolve(t,k)
+ if k then
+ k=gsub(lower(k),"[^a-z0-9]","")
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ end
+end
+setmetatableindex(verbosescripts,resolve)
+setmetatableindex(verboselanguages,resolve)
+setmetatableindex(verbosefeatures,resolve)
+setmetatableindex(verbosebaselines,resolve)
+setmetatableindex(scripts,function(t,k)
+ if k then
+ k=lower(k)
+ if k=="dflt" then
+ return k
+ end
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ k=gsub(k," ","")
+ v=rawget(t,v)
+ if v then
+ return v
+ elseif acceptscripts then
+ report_checks("registering extra script %a",k)
+ rawset(t,k,k)
+ return k
+ end
+ end
+ return "dflt"
+end)
+setmetatableindex(languages,function(t,k)
+ if k then
+ k=lower(k)
+ if k=="dflt" then
+ return k
+ end
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ k=gsub(k," ","")
+ v=rawget(t,v)
+ if v then
+ return v
+ elseif acceptlanguages then
+ report_checks("registering extra language %a",k)
+ rawset(t,k,k)
+ return k
+ end
+ end
+ return "dflt"
+end)
+if setmetatablenewindex then
+ setmetatablenewindex(languages,"ignore")
+ setmetatablenewindex(scripts,"ignore")
+ setmetatablenewindex(baselines,"ignore")
+end
+local function resolve(t,k)
+ if k then
+ k=lower(k)
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ k=gsub(k," ","")
+ local v=rawget(t,k)
+ if v then
+ return v
+ end
+ local tag,dd=match(k,"(..)(%d+)")
+ if tag and dd then
+ local v=rawget(t,tag)
+ if v then
+ return v
+ else
+ local v=rawget(t,tag.."..")
+ if v then
+ return (gsub(v,"%.%.",tonumber(dd)))
+ end
+ end
+ end
+ end
+ return k
+end
+setmetatableindex(features,resolve)
+local function assign(t,k,v)
+ if k and v then
+ v=lower(v)
+ rawset(t,k,v)
+ end
+end
+if setmetatablenewindex then
+ setmetatablenewindex(features,assign)
+end
+local checkers={
+ rand=function(v)
+ return v==true and "random" or v
+ end
+}
+if not storage then
+ return
+end
+local usedfeatures=statistics.usedfeatures or {}
+statistics.usedfeatures=usedfeatures
+table.setmetatableindex(usedfeatures,function(t,k) if k then local v={} t[k]=v return v end end)
+storage.register("fonts/otf/usedfeatures",usedfeatures,"fonts.handlers.otf.statistics.usedfeatures" )
+local normalizedaxis=otf.readers.helpers.normalizedaxis or function(s) return s end
+function otffeatures.normalize(features,wrap)
+ if features then
+ local h={}
+ for key,value in next,features do
+ local k=lower(key)
+ if k=="language" then
+ local v=gsub(lower(value),"[^a-z0-9]","")
+ h.language=rawget(verboselanguages,v) or (languages[v] and v) or "dflt"
+ elseif k=="script" then
+ local v=gsub(lower(value),"[^a-z0-9]","")
+ h.script=rawget(verbosescripts,v) or (scripts[v] and v) or "dflt"
+ elseif k=="axis" then
+ h[k]=normalizedaxis(value)
+ if not callbacks.supported.glyph_stream_provider then
+ h.variableshapes=true
+ end
+ else
+ local uk=usedfeatures[key]
+ local uv=uk[value]
+ if uv then
+ else
+ uv=tonumber(value)
+ if uv then
+ elseif type(value)=="string" then
+ local b=is_boolean(value)
+ if type(b)=="nil" then
+ if wrap and find(value,",") then
+ uv="{"..lower(value).."}"
+ else
+ uv=lower(value)
+ end
+ else
+ uv=b
+ end
+ elseif type(value)=="table" then
+ uv=sequenced(t,",")
+ else
+ uv=value
+ end
+ if not rawget(features,k) then
+ k=rawget(verbosefeatures,k) or k
+ end
+ local c=checkers[k]
+ if c then
+ uv=c(uv) or vc
+ end
+ uk[value]=uv
+ end
+ h[k]=uv
+ end
+ end
+ return h
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-cff']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber,rawget=next,type,tonumber,rawget
+local byte,char,gmatch=string.byte,string.char,string.gmatch
+local concat,remove,unpack=table.concat,table.remove,table.unpack
+local floor,abs,round,ceil,min,max=math.floor,math.abs,math.round,math.ceil,math.min,math.max
+local P,C,R,S,C,Cs,Ct=lpeg.P,lpeg.C,lpeg.R,lpeg.S,lpeg.C,lpeg.Cs,lpeg.Ct
+local lpegmatch=lpeg.match
+local formatters=string.formatters
+local bytetable=string.bytetable
+local idiv=number.idiv
+local rshift,band,extract=bit32.rshift,bit32.band,bit32.extract
+local readers=fonts.handlers.otf.readers
+local streamreader=readers.streamreader
+local readstring=streamreader.readstring
+local readbyte=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readuint=streamreader.readcardinal3
+local readulong=streamreader.readcardinal4
+local setposition=streamreader.setposition
+local getposition=streamreader.getposition
+local readbytetable=streamreader.readbytetable
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ readstring=streamreader.readstring
+ readbyte=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readuint=streamreader.readcardinal3
+ readulong=streamreader.readcardinal4
+ setposition=streamreader.setposition
+ getposition=streamreader.getposition
+ readbytetable=streamreader.readbytetable
+end)
+local setmetatableindex=table.setmetatableindex
+local trace_charstrings=false trackers.register("fonts.cff.charstrings",function(v) trace_charstrings=v end)
+local report=logs.reporter("otf reader","cff")
+local parsedictionaries
+local parsecharstring
+local parsecharstrings
+local resetcharstrings
+local parseprivates
+local startparsing
+local stopparsing
+local defaultstrings={ [0]=
+ ".notdef","space","exclam","quotedbl","numbersign","dollar","percent",
+ "ampersand","quoteright","parenleft","parenright","asterisk","plus",
+ "comma","hyphen","period","slash","zero","one","two","three","four",
+ "five","six","seven","eight","nine","colon","semicolon","less",
+ "equal","greater","question","at","A","B","C","D","E","F","G","H",
+ "I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W",
+ "X","Y","Z","bracketleft","backslash","bracketright","asciicircum",
+ "underscore","quoteleft","a","b","c","d","e","f","g","h","i","j",
+ "k","l","m","n","o","p","q","r","s","t","u","v","w","x","y",
+ "z","braceleft","bar","braceright","asciitilde","exclamdown","cent",
+ "sterling","fraction","yen","florin","section","currency",
+ "quotesingle","quotedblleft","guillemotleft","guilsinglleft",
+ "guilsinglright","fi","fl","endash","dagger","daggerdbl",
+ "periodcentered","paragraph","bullet","quotesinglbase","quotedblbase",
+ "quotedblright","guillemotright","ellipsis","perthousand","questiondown",
+ "grave","acute","circumflex","tilde","macron","breve","dotaccent",
+ "dieresis","ring","cedilla","hungarumlaut","ogonek","caron","emdash",
+ "AE","ordfeminine","Lslash","Oslash","OE","ordmasculine","ae",
+ "dotlessi","lslash","oslash","oe","germandbls","onesuperior",
+ "logicalnot","mu","trademark","Eth","onehalf","plusminus","Thorn",
+ "onequarter","divide","brokenbar","degree","thorn","threequarters",
+ "twosuperior","registered","minus","eth","multiply","threesuperior",
+ "copyright","Aacute","Acircumflex","Adieresis","Agrave","Aring",
+ "Atilde","Ccedilla","Eacute","Ecircumflex","Edieresis","Egrave",
+ "Iacute","Icircumflex","Idieresis","Igrave","Ntilde","Oacute",
+ "Ocircumflex","Odieresis","Ograve","Otilde","Scaron","Uacute",
+ "Ucircumflex","Udieresis","Ugrave","Yacute","Ydieresis","Zcaron",
+ "aacute","acircumflex","adieresis","agrave","aring","atilde",
+ "ccedilla","eacute","ecircumflex","edieresis","egrave","iacute",
+ "icircumflex","idieresis","igrave","ntilde","oacute","ocircumflex",
+ "odieresis","ograve","otilde","scaron","uacute","ucircumflex",
+ "udieresis","ugrave","yacute","ydieresis","zcaron","exclamsmall",
+ "Hungarumlautsmall","dollaroldstyle","dollarsuperior","ampersandsmall",
+ "Acutesmall","parenleftsuperior","parenrightsuperior","twodotenleader",
+ "onedotenleader","zerooldstyle","oneoldstyle","twooldstyle",
+ "threeoldstyle","fouroldstyle","fiveoldstyle","sixoldstyle",
+ "sevenoldstyle","eightoldstyle","nineoldstyle","commasuperior",
+ "threequartersemdash","periodsuperior","questionsmall","asuperior",
+ "bsuperior","centsuperior","dsuperior","esuperior","isuperior",
+ "lsuperior","msuperior","nsuperior","osuperior","rsuperior","ssuperior",
+ "tsuperior","ff","ffi","ffl","parenleftinferior","parenrightinferior",
+ "Circumflexsmall","hyphensuperior","Gravesmall","Asmall","Bsmall",
+ "Csmall","Dsmall","Esmall","Fsmall","Gsmall","Hsmall","Ismall",
+ "Jsmall","Ksmall","Lsmall","Msmall","Nsmall","Osmall","Psmall",
+ "Qsmall","Rsmall","Ssmall","Tsmall","Usmall","Vsmall","Wsmall",
+ "Xsmall","Ysmall","Zsmall","colonmonetary","onefitted","rupiah",
+ "Tildesmall","exclamdownsmall","centoldstyle","Lslashsmall",
+ "Scaronsmall","Zcaronsmall","Dieresissmall","Brevesmall","Caronsmall",
+ "Dotaccentsmall","Macronsmall","figuredash","hypheninferior",
+ "Ogoneksmall","Ringsmall","Cedillasmall","questiondownsmall","oneeighth",
+ "threeeighths","fiveeighths","seveneighths","onethird","twothirds",
+ "zerosuperior","foursuperior","fivesuperior","sixsuperior",
+ "sevensuperior","eightsuperior","ninesuperior","zeroinferior",
+ "oneinferior","twoinferior","threeinferior","fourinferior",
+ "fiveinferior","sixinferior","seveninferior","eightinferior",
+ "nineinferior","centinferior","dollarinferior","periodinferior",
+ "commainferior","Agravesmall","Aacutesmall","Acircumflexsmall",
+ "Atildesmall","Adieresissmall","Aringsmall","AEsmall","Ccedillasmall",
+ "Egravesmall","Eacutesmall","Ecircumflexsmall","Edieresissmall",
+ "Igravesmall","Iacutesmall","Icircumflexsmall","Idieresissmall",
+ "Ethsmall","Ntildesmall","Ogravesmall","Oacutesmall","Ocircumflexsmall",
+ "Otildesmall","Odieresissmall","OEsmall","Oslashsmall","Ugravesmall",
+ "Uacutesmall","Ucircumflexsmall","Udieresissmall","Yacutesmall",
+ "Thornsmall","Ydieresissmall","001.000","001.001","001.002","001.003",
+ "Black","Bold","Book","Light","Medium","Regular","Roman","Semibold",
+}
+local cffreaders={
+ readbyte,
+ readushort,
+ readuint,
+ readulong,
+}
+local function readheader(f)
+ local offset=getposition(f)
+ local major=readbyte(f)
+ local header={
+ offset=offset,
+ major=major,
+ minor=readbyte(f),
+ size=readbyte(f),
+ }
+ if major==1 then
+ header.dsize=readbyte(f)
+ elseif major==2 then
+ header.dsize=readushort(f)
+ else
+ end
+ setposition(f,offset+header.size)
+ return header
+end
+local function readlengths(f,longcount)
+ local count=longcount and readulong(f) or readushort(f)
+ if count==0 then
+ return {}
+ end
+ local osize=readbyte(f)
+ local read=cffreaders[osize]
+ if not read then
+ report("bad offset size: %i",osize)
+ return {}
+ end
+ local lengths={}
+ local previous=read(f)
+ for i=1,count do
+ local offset=read(f)
+ local length=offset-previous
+ if length<0 then
+ report("bad offset: %i",length)
+ length=0
+ end
+ lengths[i]=length
+ previous=offset
+ end
+ return lengths
+end
+local function readfontnames(f)
+ local names=readlengths(f)
+ for i=1,#names do
+ names[i]=readstring(f,names[i])
+ end
+ return names
+end
+local function readtopdictionaries(f)
+ local dictionaries=readlengths(f)
+ for i=1,#dictionaries do
+ dictionaries[i]=readstring(f,dictionaries[i])
+ end
+ return dictionaries
+end
+local function readstrings(f)
+ local lengths=readlengths(f)
+ local strings=setmetatableindex({},defaultstrings)
+ local index=#defaultstrings
+ for i=1,#lengths do
+ index=index+1
+ strings[index]=readstring(f,lengths[i])
+ end
+ return strings
+end
+do
+ local stack={}
+ local top=0
+ local result={}
+ local strings={}
+ local p_single=P("\00")/function()
+ result.version=strings[stack[top]] or "unset"
+ top=0
+ end+P("\01")/function()
+ result.notice=strings[stack[top]] or "unset"
+ top=0
+ end+P("\02")/function()
+ result.fullname=strings[stack[top]] or "unset"
+ top=0
+ end+P("\03")/function()
+ result.familyname=strings[stack[top]] or "unset"
+ top=0
+ end+P("\04")/function()
+ result.weight=strings[stack[top]] or "unset"
+ top=0
+ end+P("\05")/function()
+ result.fontbbox={ unpack(stack,1,4) }
+ top=0
+ end+P("\06")/function()
+ result.bluevalues={ unpack(stack,1,top) }
+ top=0
+ end+P("\07")/function()
+ result.otherblues={ unpack(stack,1,top) }
+ top=0
+ end+P("\08")/function()
+ result.familyblues={ unpack(stack,1,top) }
+ top=0
+ end+P("\09")/function()
+ result.familyotherblues={ unpack(stack,1,top) }
+ top=0
+ end+P("\10")/function()
+ result.strhw=stack[top]
+ top=0
+ end+P("\11")/function()
+ result.strvw=stack[top]
+ top=0
+ end+P("\13")/function()
+ result.uniqueid=stack[top]
+ top=0
+ end+P("\14")/function()
+ result.xuid=concat(stack,"",1,top)
+ top=0
+ end+P("\15")/function()
+ result.charset=stack[top]
+ top=0
+ end+P("\16")/function()
+ result.encoding=stack[top]
+ top=0
+ end+P("\17")/function()
+ result.charstrings=stack[top]
+ top=0
+ end+P("\18")/function()
+ result.private={
+ size=stack[top-1],
+ offset=stack[top],
+ }
+ top=0
+ end+P("\19")/function()
+ result.subroutines=stack[top]
+ top=0
+ end+P("\20")/function()
+ result.defaultwidthx=stack[top]
+ top=0
+ end+P("\21")/function()
+ result.nominalwidthx=stack[top]
+ top=0
+ end
++P("\24")/function()
+ result.vstore=stack[top]
+ top=0
+ end+P("\25")/function()
+ result.maxstack=stack[top]
+ top=0
+ end
+ local p_double=P("\12")*(
+ P("\00")/function()
+ result.copyright=stack[top]
+ top=0
+ end+P("\01")/function()
+ result.monospaced=stack[top]==1 and true or false
+ top=0
+ end+P("\02")/function()
+ result.italicangle=stack[top]
+ top=0
+ end+P("\03")/function()
+ result.underlineposition=stack[top]
+ top=0
+ end+P("\04")/function()
+ result.underlinethickness=stack[top]
+ top=0
+ end+P("\05")/function()
+ result.painttype=stack[top]
+ top=0
+ end+P("\06")/function()
+ result.charstringtype=stack[top]
+ top=0
+ end+P("\07")/function()
+ result.fontmatrix={ unpack(stack,1,6) }
+ top=0
+ end+P("\08")/function()
+ result.strokewidth=stack[top]
+ top=0
+ end+P("\09")/function()
+ result.bluescale=stack[top]
+ top=0
+ end+P("\10")/function()
+ result.bluesnap=stack[top]
+ top=0
+ end+P("\11")/function()
+ result.bluefuzz=stack[top]
+ top=0
+ end+P("\12")/function()
+ result.stemsnaph={ unpack(stack,1,top) }
+ top=0
+ end+P("\13")/function()
+ result.stemsnapv={ unpack(stack,1,top) }
+ top=0
+ end+P("\20")/function()
+ result.syntheticbase=stack[top]
+ top=0
+ end+P("\21")/function()
+ result.postscript=strings[stack[top]] or "unset"
+ top=0
+ end+P("\22")/function()
+ result.basefontname=strings[stack[top]] or "unset"
+ top=0
+ end+P("\21")/function()
+ result.basefontblend=stack[top]
+ top=0
+ end+P("\30")/function()
+ result.cid.registry=strings[stack[top-2]] or "unset"
+ result.cid.ordering=strings[stack[top-1]] or "unset"
+ result.cid.supplement=stack[top]
+ top=0
+ end+P("\31")/function()
+ result.cid.fontversion=stack[top]
+ top=0
+ end+P("\32")/function()
+ result.cid.fontrevision=stack[top]
+ top=0
+ end+P("\33")/function()
+ result.cid.fonttype=stack[top]
+ top=0
+ end+P("\34")/function()
+ result.cid.count=stack[top]
+ top=0
+ end+P("\35")/function()
+ result.cid.uidbase=stack[top]
+ top=0
+ end+P("\36")/function()
+ result.cid.fdarray=stack[top]
+ top=0
+ end+P("\37")/function()
+ result.cid.fdselect=stack[top]
+ top=0
+ end+P("\38")/function()
+ result.cid.fontname=strings[stack[top]] or "unset"
+ top=0
+ end
+ )
+ local remap={
+ ["\x00"]="00",["\x01"]="01",["\x02"]="02",["\x03"]="03",["\x04"]="04",["\x05"]="05",["\x06"]="06",["\x07"]="07",["\x08"]="08",["\x09"]="09",["\x0A"]="0.",["\x0B"]="0E",["\x0C"]="0E-",["\x0D"]="0",["\x0E"]="0-",["\x0F"]="0",
+ ["\x10"]="10",["\x11"]="11",["\x12"]="12",["\x13"]="13",["\x14"]="14",["\x15"]="15",["\x16"]="16",["\x17"]="17",["\x18"]="18",["\x19"]="19",["\x1A"]="1.",["\x1B"]="1E",["\x1C"]="1E-",["\x1D"]="1",["\x1E"]="1-",["\x1F"]="1",
+ ["\x20"]="20",["\x21"]="21",["\x22"]="22",["\x23"]="23",["\x24"]="24",["\x25"]="25",["\x26"]="26",["\x27"]="27",["\x28"]="28",["\x29"]="29",["\x2A"]="2.",["\x2B"]="2E",["\x2C"]="2E-",["\x2D"]="2",["\x2E"]="2-",["\x2F"]="2",
+ ["\x30"]="30",["\x31"]="31",["\x32"]="32",["\x33"]="33",["\x34"]="34",["\x35"]="35",["\x36"]="36",["\x37"]="37",["\x38"]="38",["\x39"]="39",["\x3A"]="3.",["\x3B"]="3E",["\x3C"]="3E-",["\x3D"]="3",["\x3E"]="3-",["\x3F"]="3",
+ ["\x40"]="40",["\x41"]="41",["\x42"]="42",["\x43"]="43",["\x44"]="44",["\x45"]="45",["\x46"]="46",["\x47"]="47",["\x48"]="48",["\x49"]="49",["\x4A"]="4.",["\x4B"]="4E",["\x4C"]="4E-",["\x4D"]="4",["\x4E"]="4-",["\x4F"]="4",
+ ["\x50"]="50",["\x51"]="51",["\x52"]="52",["\x53"]="53",["\x54"]="54",["\x55"]="55",["\x56"]="56",["\x57"]="57",["\x58"]="58",["\x59"]="59",["\x5A"]="5.",["\x5B"]="5E",["\x5C"]="5E-",["\x5D"]="5",["\x5E"]="5-",["\x5F"]="5",
+ ["\x60"]="60",["\x61"]="61",["\x62"]="62",["\x63"]="63",["\x64"]="64",["\x65"]="65",["\x66"]="66",["\x67"]="67",["\x68"]="68",["\x69"]="69",["\x6A"]="6.",["\x6B"]="6E",["\x6C"]="6E-",["\x6D"]="6",["\x6E"]="6-",["\x6F"]="6",
+ ["\x70"]="70",["\x71"]="71",["\x72"]="72",["\x73"]="73",["\x74"]="74",["\x75"]="75",["\x76"]="76",["\x77"]="77",["\x78"]="78",["\x79"]="79",["\x7A"]="7.",["\x7B"]="7E",["\x7C"]="7E-",["\x7D"]="7",["\x7E"]="7-",["\x7F"]="7",
+ ["\x80"]="80",["\x81"]="81",["\x82"]="82",["\x83"]="83",["\x84"]="84",["\x85"]="85",["\x86"]="86",["\x87"]="87",["\x88"]="88",["\x89"]="89",["\x8A"]="8.",["\x8B"]="8E",["\x8C"]="8E-",["\x8D"]="8",["\x8E"]="8-",["\x8F"]="8",
+ ["\x90"]="90",["\x91"]="91",["\x92"]="92",["\x93"]="93",["\x94"]="94",["\x95"]="95",["\x96"]="96",["\x97"]="97",["\x98"]="98",["\x99"]="99",["\x9A"]="9.",["\x9B"]="9E",["\x9C"]="9E-",["\x9D"]="9",["\x9E"]="9-",["\x9F"]="9",
+ ["\xA0"]=".0",["\xA1"]=".1",["\xA2"]=".2",["\xA3"]=".3",["\xA4"]=".4",["\xA5"]=".5",["\xA6"]=".6",["\xA7"]=".7",["\xA8"]=".8",["\xA9"]=".9",["\xAA"]="..",["\xAB"]=".E",["\xAC"]=".E-",["\xAD"]=".",["\xAE"]=".-",["\xAF"]=".",
+ ["\xB0"]="E0",["\xB1"]="E1",["\xB2"]="E2",["\xB3"]="E3",["\xB4"]="E4",["\xB5"]="E5",["\xB6"]="E6",["\xB7"]="E7",["\xB8"]="E8",["\xB9"]="E9",["\xBA"]="E.",["\xBB"]="EE",["\xBC"]="EE-",["\xBD"]="E",["\xBE"]="E-",["\xBF"]="E",
+ ["\xC0"]="E-0",["\xC1"]="E-1",["\xC2"]="E-2",["\xC3"]="E-3",["\xC4"]="E-4",["\xC5"]="E-5",["\xC6"]="E-6",["\xC7"]="E-7",["\xC8"]="E-8",["\xC9"]="E-9",["\xCA"]="E-.",["\xCB"]="E-E",["\xCC"]="E-E-",["\xCD"]="E-",["\xCE"]="E--",["\xCF"]="E-",
+ ["\xD0"]="-0",["\xD1"]="-1",["\xD2"]="-2",["\xD3"]="-3",["\xD4"]="-4",["\xD5"]="-5",["\xD6"]="-6",["\xD7"]="-7",["\xD8"]="-8",["\xD9"]="-9",["\xDA"]="-.",["\xDB"]="-E",["\xDC"]="-E-",["\xDD"]="-",["\xDE"]="--",["\xDF"]="-",
+ }
+ local p_last=S("\x0F\x1F\x2F\x3F\x4F\x5F\x6F\x7F\x8F\x9F\xAF\xBF")+R("\xF0\xFF")
+ local p_nibbles=P("\30")*Cs(((1-p_last)/remap)^0*(P(1)/remap))/function(n)
+ top=top+1
+ stack[top]=tonumber(n) or 0
+ end
+ local p_byte=C(R("\32\246"))/function(b0)
+ top=top+1
+ stack[top]=byte(b0)-139
+ end
+ local p_positive=C(R("\247\250"))*C(1)/function(b0,b1)
+ top=top+1
+ stack[top]=(byte(b0)-247)*256+byte(b1)+108
+ end
+ local p_negative=C(R("\251\254"))*C(1)/function(b0,b1)
+ top=top+1
+ stack[top]=-(byte(b0)-251)*256-byte(b1)-108
+ end
+ local p_short=P("\28")*C(1)*C(1)/function(b1,b2)
+ top=top+1
+ local n=0x100*byte(b1)+byte(b2)
+ if n>=0x8000 then
+ stack[top]=n-0xFFFF-1
+ else
+ stack[top]=n
+ end
+ end
+ local p_long=P("\29")*C(1)*C(1)*C(1)*C(1)/function(b1,b2,b3,b4)
+ top=top+1
+ local n=0x1000000*byte(b1)+0x10000*byte(b2)+0x100*byte(b3)+byte(b4)
+ if n>=0x8000000 then
+ stack[top]=n-0xFFFFFFFF-1
+ else
+ stack[top]=n
+ end
+ end
+ local p_unsupported=P(1)/function(detail)
+ top=0
+ end
+ local p_dictionary=(
+ p_byte+p_positive+p_negative+p_short+p_long+p_nibbles+p_single+p_double+p_unsupported
+ )^1
+ parsedictionaries=function(data,dictionaries,what)
+ stack={}
+ strings=data.strings
+ for i=1,#dictionaries do
+ top=0
+ result=what=="cff" and {
+ monospaced=false,
+ italicangle=0,
+ underlineposition=-100,
+ underlinethickness=50,
+ painttype=0,
+ charstringtype=2,
+ fontmatrix={ 0.001,0,0,0.001,0,0 },
+ fontbbox={ 0,0,0,0 },
+ strokewidth=0,
+ charset=0,
+ encoding=0,
+ cid={
+ fontversion=0,
+ fontrevision=0,
+ fonttype=0,
+ count=8720,
+ }
+ } or {
+ charstringtype=2,
+ charset=0,
+ vstore=0,
+ cid={
+ },
+ }
+ lpegmatch(p_dictionary,dictionaries[i])
+ dictionaries[i]=result
+ end
+ result={}
+ top=0
+ stack={}
+ end
+ parseprivates=function(data,dictionaries)
+ stack={}
+ strings=data.strings
+ for i=1,#dictionaries do
+ local private=dictionaries[i].private
+ if private and private.data then
+ top=0
+ result={
+ forcebold=false,
+ languagegroup=0,
+ expansionfactor=0.06,
+ initialrandomseed=0,
+ subroutines=0,
+ defaultwidthx=0,
+ nominalwidthx=0,
+ cid={
+ },
+ }
+ lpegmatch(p_dictionary,private.data)
+ private.data=result
+ end
+ end
+ result={}
+ top=0
+ stack={}
+ end
+ local x=0
+ local y=0
+ local width=false
+ local r=0
+ local stems=0
+ local globalbias=0
+ local localbias=0
+ local nominalwidth=0
+ local defaultwidth=0
+ local charset=false
+ local globals=false
+ local locals=false
+ local depth=1
+ local xmin=0
+ local xmax=0
+ local ymin=0
+ local ymax=0
+ local checked=false
+ local keepcurve=false
+ local version=2
+ local regions=false
+ local nofregions=0
+ local region=false
+ local factors=false
+ local axis=false
+ local vsindex=0
+ local function showstate(where)
+ report("%w%-10s : [%s] n=%i",depth*2,where,concat(stack," ",1,top),top)
+ end
+ local function showvalue(where,value,showstack)
+ if showstack then
+ report("%w%-10s : %s : [%s] n=%i",depth*2,where,tostring(value),concat(stack," ",1,top),top)
+ else
+ report("%w%-10s : %s",depth*2,where,tostring(value))
+ end
+ end
+ local function xymoveto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"m" }
+ end
+ if checked then
+ if x>xmax then xmax=x elseif x<xmin then xmin=x end
+ if y>ymax then ymax=y elseif y<ymin then ymin=y end
+ else
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ end
+ end
+ local function xmoveto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"m" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif x>xmax then
+ xmax=x
+ elseif x<xmin then
+ xmin=x
+ end
+ end
+ local function ymoveto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"m" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif y>ymax then
+ ymax=y
+ elseif y<ymin then
+ ymin=y
+ end
+ end
+ local function moveto()
+ if trace_charstrings then
+ showstate("moveto")
+ end
+ top=0
+ xymoveto()
+ end
+ local function xylineto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"l" }
+ end
+ if checked then
+ if x>xmax then xmax=x elseif x<xmin then xmin=x end
+ if y>ymax then ymax=y elseif y<ymin then ymin=y end
+ else
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ end
+ end
+ local function xlineto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"l" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif x>xmax then
+ xmax=x
+ elseif x<xmin then
+ xmin=x
+ end
+ end
+ local function ylineto()
+ if keepcurve then
+ r=r+1
+ result[r]={ x,y,"l" }
+ end
+ if not checked then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ checked=true
+ elseif y>ymax then
+ ymax=y
+ elseif y<ymin then
+ ymin=y
+ end
+ end
+ local function xycurveto(x1,y1,x2,y2,x3,y3)
+ if trace_charstrings then
+ showstate("curveto")
+ end
+ if keepcurve then
+ r=r+1
+ result[r]={ x1,y1,x2,y2,x3,y3,"c" }
+ end
+ if checked then
+ if x1>xmax then xmax=x1 elseif x1<xmin then xmin=x1 end
+ if y1>ymax then ymax=y1 elseif y1<ymin then ymin=y1 end
+ else
+ xmin=x1
+ ymin=y1
+ xmax=x1
+ ymax=y1
+ checked=true
+ end
+ if x2>xmax then xmax=x2 elseif x2<xmin then xmin=x2 end
+ if y2>ymax then ymax=y2 elseif y2<ymin then ymin=y2 end
+ if x3>xmax then xmax=x3 elseif x3<xmin then xmin=x3 end
+ if y3>ymax then ymax=y3 elseif y3<ymin then ymin=y3 end
+ end
+ local function rmoveto()
+ if not width then
+ if top>2 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width=true
+ end
+ end
+ if trace_charstrings then
+ showstate("rmoveto")
+ end
+ x=x+stack[top-1]
+ y=y+stack[top]
+ top=0
+ xymoveto()
+ end
+ local function hmoveto()
+ if not width then
+ if top>1 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width=true
+ end
+ end
+ if trace_charstrings then
+ showstate("hmoveto")
+ end
+ x=x+stack[top]
+ top=0
+ xmoveto()
+ end
+ local function vmoveto()
+ if not width then
+ if top>1 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("backtrack width",width)
+ end
+ else
+ width=true
+ end
+ end
+ if trace_charstrings then
+ showstate("vmoveto")
+ end
+ y=y+stack[top]
+ top=0
+ ymoveto()
+ end
+ local function rlineto()
+ if trace_charstrings then
+ showstate("rlineto")
+ end
+ for i=1,top,2 do
+ x=x+stack[i]
+ y=y+stack[i+1]
+ xylineto()
+ end
+ top=0
+ end
+ local function hlineto()
+ if trace_charstrings then
+ showstate("hlineto")
+ end
+ if top==1 then
+ x=x+stack[1]
+ xlineto()
+ else
+ local swap=true
+ for i=1,top do
+ if swap then
+ x=x+stack[i]
+ xlineto()
+ swap=false
+ else
+ y=y+stack[i]
+ ylineto()
+ swap=true
+ end
+ end
+ end
+ top=0
+ end
+ local function vlineto()
+ if trace_charstrings then
+ showstate("vlineto")
+ end
+ if top==1 then
+ y=y+stack[1]
+ ylineto()
+ else
+ local swap=false
+ for i=1,top do
+ if swap then
+ x=x+stack[i]
+ xlineto()
+ swap=false
+ else
+ y=y+stack[i]
+ ylineto()
+ swap=true
+ end
+ end
+ end
+ top=0
+ end
+ local function rrcurveto()
+ if trace_charstrings then
+ showstate("rrcurveto")
+ end
+ for i=1,top,6 do
+ local ax=x+stack[i]
+ local ay=y+stack[i+1]
+ local bx=ax+stack[i+2]
+ local by=ay+stack[i+3]
+ x=bx+stack[i+4]
+ y=by+stack[i+5]
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top=0
+ end
+ local function hhcurveto()
+ if trace_charstrings then
+ showstate("hhcurveto")
+ end
+ local s=1
+ if top%2~=0 then
+ y=y+stack[1]
+ s=2
+ end
+ for i=s,top,4 do
+ local ax=x+stack[i]
+ local ay=y
+ local bx=ax+stack[i+1]
+ local by=ay+stack[i+2]
+ x=bx+stack[i+3]
+ y=by
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top=0
+ end
+ local function vvcurveto()
+ if trace_charstrings then
+ showstate("vvcurveto")
+ end
+ local s=1
+ local d=0
+ if top%2~=0 then
+ d=stack[1]
+ s=2
+ end
+ for i=s,top,4 do
+ local ax=x+d
+ local ay=y+stack[i]
+ local bx=ax+stack[i+1]
+ local by=ay+stack[i+2]
+ x=bx
+ y=by+stack[i+3]
+ xycurveto(ax,ay,bx,by,x,y)
+ d=0
+ end
+ top=0
+ end
+ local function xxcurveto(swap)
+ local last=top%4~=0 and stack[top]
+ if last then
+ top=top-1
+ end
+ for i=1,top,4 do
+ local ax,ay,bx,by
+ if swap then
+ ax=x+stack[i]
+ ay=y
+ bx=ax+stack[i+1]
+ by=ay+stack[i+2]
+ y=by+stack[i+3]
+ if last and i+3==top then
+ x=bx+last
+ else
+ x=bx
+ end
+ swap=false
+ else
+ ax=x
+ ay=y+stack[i]
+ bx=ax+stack[i+1]
+ by=ay+stack[i+2]
+ x=bx+stack[i+3]
+ if last and i+3==top then
+ y=by+last
+ else
+ y=by
+ end
+ swap=true
+ end
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ top=0
+ end
+ local function hvcurveto()
+ if trace_charstrings then
+ showstate("hvcurveto")
+ end
+ xxcurveto(true)
+ end
+ local function vhcurveto()
+ if trace_charstrings then
+ showstate("vhcurveto")
+ end
+ xxcurveto(false)
+ end
+ local function rcurveline()
+ if trace_charstrings then
+ showstate("rcurveline")
+ end
+ for i=1,top-2,6 do
+ local ax=x+stack[i]
+ local ay=y+stack[i+1]
+ local bx=ax+stack[i+2]
+ local by=ay+stack[i+3]
+ x=bx+stack[i+4]
+ y=by+stack[i+5]
+ xycurveto(ax,ay,bx,by,x,y)
+ end
+ x=x+stack[top-1]
+ y=y+stack[top]
+ xylineto()
+ top=0
+ end
+ local function rlinecurve()
+ if trace_charstrings then
+ showstate("rlinecurve")
+ end
+ if top>6 then
+ for i=1,top-6,2 do
+ x=x+stack[i]
+ y=y+stack[i+1]
+ xylineto()
+ end
+ end
+ local ax=x+stack[top-5]
+ local ay=y+stack[top-4]
+ local bx=ax+stack[top-3]
+ local by=ay+stack[top-2]
+ x=bx+stack[top-1]
+ y=by+stack[top]
+ xycurveto(ax,ay,bx,by,x,y)
+ top=0
+ end
+ local function flex()
+ if trace_charstrings then
+ showstate("flex")
+ end
+ local ax=x+stack[1]
+ local ay=y+stack[2]
+ local bx=ax+stack[3]
+ local by=ay+stack[4]
+ local cx=bx+stack[5]
+ local cy=by+stack[6]
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[7]
+ local dy=cy+stack[8]
+ local ex=dx+stack[9]
+ local ey=dy+stack[10]
+ x=ex+stack[11]
+ y=ey+stack[12]
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function hflex()
+ if trace_charstrings then
+ showstate("hflex")
+ end
+ local ax=x+stack[1]
+ local ay=y
+ local bx=ax+stack[2]
+ local by=ay+stack[3]
+ local cx=bx+stack[4]
+ local cy=by
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[5]
+ local dy=by
+ local ex=dx+stack[6]
+ local ey=y
+ x=ex+stack[7]
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function hflex1()
+ if trace_charstrings then
+ showstate("hflex1")
+ end
+ local ax=x+stack[1]
+ local ay=y+stack[2]
+ local bx=ax+stack[3]
+ local by=ay+stack[4]
+ local cx=bx+stack[5]
+ local cy=by
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[6]
+ local dy=by
+ local ex=dx+stack[7]
+ local ey=dy+stack[8]
+ x=ex+stack[9]
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function flex1()
+ if trace_charstrings then
+ showstate("flex1")
+ end
+ local ax=x+stack[1]
+ local ay=y+stack[2]
+ local bx=ax+stack[3]
+ local by=ay+stack[4]
+ local cx=bx+stack[5]
+ local cy=by+stack[6]
+ xycurveto(ax,ay,bx,by,cx,cy)
+ local dx=cx+stack[7]
+ local dy=cy+stack[8]
+ local ex=dx+stack[9]
+ local ey=dy+stack[10]
+ if abs(ex-x)>abs(ey-y) then
+ x=ex+stack[11]
+ else
+ y=ey+stack[11]
+ end
+ xycurveto(dx,dy,ex,ey,x,y)
+ top=0
+ end
+ local function getstem()
+ if top==0 then
+ elseif top%2~=0 then
+ if width then
+ remove(stack,1)
+ else
+ width=remove(stack,1)
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ end
+ top=top-1
+ end
+ if trace_charstrings then
+ showstate("stem")
+ end
+ stems=stems+idiv(top,2)
+ top=0
+ end
+ local function getmask()
+ if top==0 then
+ elseif top%2~=0 then
+ if width then
+ remove(stack,1)
+ else
+ width=remove(stack,1)
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ end
+ top=top-1
+ end
+ if trace_charstrings then
+ showstate(operator==19 and "hintmark" or "cntrmask")
+ end
+ stems=stems+idiv(top,2)
+ top=0
+ if stems==0 then
+ elseif stems<=8 then
+ return 1
+ else
+ return idiv(stems+7,8)
+ end
+ end
+ local function unsupported(t)
+ if trace_charstrings then
+ showstate("unsupported "..t)
+ end
+ top=0
+ end
+ local function unsupportedsub(t)
+ if trace_charstrings then
+ showstate("unsupported sub "..t)
+ end
+ top=0
+ end
+ local function getstem3()
+ if trace_charstrings then
+ showstate("stem3")
+ end
+ top=0
+ end
+ local function divide()
+ if version==1 then
+ local d=stack[top]
+ top=top-1
+ stack[top]=stack[top]/d
+ end
+ end
+ local function closepath()
+ if version==1 then
+ if trace_charstrings then
+ showstate("closepath")
+ end
+ end
+ top=0
+ end
+ local function hsbw()
+ if version==1 then
+ if trace_charstrings then
+ showstate("hsbw")
+ end
+ width=stack[top]
+ end
+ top=0
+ end
+ local function seac()
+ if version==1 then
+ if trace_charstrings then
+ showstate("seac")
+ end
+ end
+ top=0
+ end
+ local function sbw()
+ if version==1 then
+ if trace_charstrings then
+ showstate("sbw")
+ end
+ width=stack[top-1]
+ end
+ top=0
+ end
+ local function callothersubr()
+ if version==1 then
+ if trace_charstrings then
+ showstate("callothersubr (unsupported)")
+ end
+ end
+ top=0
+ end
+ local function pop()
+ if version==1 then
+ if trace_charstrings then
+ showstate("pop (unsupported)")
+ end
+ top=top+1
+ stack[top]=0
+ else
+ top=0
+ end
+ end
+ local function setcurrentpoint()
+ if version==1 then
+ if trace_charstrings then
+ showstate("pop (unsupported)")
+ end
+ x=x+stack[top-1]
+ y=y+stack[top]
+ end
+ top=0
+ end
+ local reginit=false
+ local function updateregions(n)
+ if regions then
+ local current=regions[n] or regions[1]
+ nofregions=#current
+ if axis and n~=reginit then
+ factors={}
+ for i=1,nofregions do
+ local region=current[i]
+ local s=1
+ for j=1,#axis do
+ local f=axis[j]
+ local r=region[j]
+ local start=r.start
+ local peak=r.peak
+ local stop=r.stop
+ if start>peak or peak>stop then
+ elseif start<0 and stop>0 and peak~=0 then
+ elseif peak==0 then
+ elseif f<start or f>stop then
+ s=0
+ break
+ elseif f<peak then
+ s=s*(f-start)/(peak-start)
+ elseif f>peak then
+ s=s*(stop-f)/(stop-peak)
+ else
+ end
+ end
+ factors[i]=s
+ end
+ end
+ end
+ reginit=n
+ end
+ local function setvsindex()
+ local vsindex=stack[top]
+ if trace_charstrings then
+ showstate(formatters["vsindex %i"](vsindex))
+ end
+ updateregions(vsindex)
+ top=top-1
+ end
+ local function blend()
+ local n=stack[top]
+ top=top-1
+ if axis then
+ if trace_charstrings then
+ local t=top-nofregions*n
+ local m=t-n
+ for i=1,n do
+ local k=m+i
+ local d=m+n+(i-1)*nofregions
+ local old=stack[k]
+ local new=old
+ for r=1,nofregions do
+ new=new+stack[d+r]*factors[r]
+ end
+ stack[k]=new
+ showstate(formatters["blend %i of %i: %s -> %s"](i,n,old,new))
+ end
+ top=t
+ elseif n==1 then
+ top=top-nofregions
+ local v=stack[top]
+ for r=1,nofregions do
+ v=v+stack[top+r]*factors[r]
+ end
+ stack[top]=v
+ else
+ top=top-nofregions*n
+ local d=top
+ local k=top-n
+ for i=1,n do
+ k=k+1
+ local v=stack[k]
+ for r=1,nofregions do
+ v=v+stack[d+r]*factors[r]
+ end
+ stack[k]=v
+ d=d+nofregions
+ end
+ end
+ else
+ end
+ end
+ local actions={ [0]=unsupported,
+ getstem,
+ unsupported,
+ getstem,
+ vmoveto,
+ rlineto,
+ hlineto,
+ vlineto,
+ rrcurveto,
+ unsupported,
+ unsupported,
+ unsupported,
+ unsupported,
+ hsbw,
+ unsupported,
+ setvsindex,
+ blend,
+ unsupported,
+ getstem,
+ getmask,
+ getmask,
+ rmoveto,
+ hmoveto,
+ getstem,
+ rcurveline,
+ rlinecurve,
+ vvcurveto,
+ hhcurveto,
+ unsupported,
+ unsupported,
+ vhcurveto,
+ hvcurveto,
+ }
+ local subactions={
+ [000]=dotsection,
+ [001]=getstem3,
+ [002]=getstem3,
+ [006]=seac,
+ [007]=sbw,
+ [012]=divide,
+ [016]=callothersubr,
+ [017]=pop,
+ [033]=setcurrentpoint,
+ [034]=hflex,
+ [035]=flex,
+ [036]=hflex1,
+ [037]=flex1,
+ }
+ local chars=setmetatableindex(function (t,k)
+ local v=char(k)
+ t[k]=v
+ return v
+ end)
+ local c_endchar=chars[14]
+ local encode={}
+ setmetatableindex(encode,function(t,i)
+ for i=-2048,-1130 do
+ t[i]=char(28,band(rshift(i,8),0xFF),band(i,0xFF))
+ end
+ for i=-1131,-108 do
+ local v=0xFB00-i-108
+ t[i]=char(band(rshift(v,8),0xFF),band(v,0xFF))
+ end
+ for i=-107,107 do
+ t[i]=chars[i+139]
+ end
+ for i=108,1131 do
+ local v=0xF700+i-108
+ t[i]=char(extract(v,8,8),extract(v,0,8))
+ end
+ for i=1132,2048 do
+ t[i]=char(28,band(rshift(i,8),0xFF),band(i,0xFF))
+ end
+ setmetatableindex(encode,function(t,k)
+ local r=round(k)
+ local v=rawget(t,r)
+ if v then
+ return v
+ end
+ local v1=floor(k)
+ local v2=floor((k-v1)*0x10000)
+ return char(255,extract(v1,8,8),extract(v1,0,8),extract(v2,8,8),extract(v2,0,8))
+ end)
+ return t[i]
+ end)
+ readers.cffencoder=encode
+ local function p_setvsindex()
+ local vsindex=stack[top]
+ updateregions(vsindex)
+ top=top-1
+ end
+ local function p_blend()
+ local n=stack[top]
+ top=top-1
+ if not axis then
+ elseif n==1 then
+ top=top-nofregions
+ local v=stack[top]
+ for r=1,nofregions do
+ v=v+stack[top+r]*factors[r]
+ end
+ stack[top]=round(v)
+ else
+ top=top-nofregions*n
+ local d=top
+ local k=top-n
+ for i=1,n do
+ k=k+1
+ local v=stack[k]
+ for r=1,nofregions do
+ v=v+stack[d+r]*factors[r]
+ end
+ stack[k]=round(v)
+ d=d+nofregions
+ end
+ end
+ end
+ local function p_getstem()
+ local n=0
+ if top%2~=0 then
+ n=1
+ end
+ if top>n then
+ stems=stems+idiv(top-n,2)
+ end
+ end
+ local function p_getmask()
+ local n=0
+ if top%2~=0 then
+ n=1
+ end
+ if top>n then
+ stems=stems+idiv(top-n,2)
+ end
+ if stems==0 then
+ return 0
+ elseif stems<=8 then
+ return 1
+ else
+ return idiv(stems+7,8)
+ end
+ end
+ local process
+ local function call(scope,list,bias)
+ depth=depth+1
+ if top==0 then
+ showstate(formatters["unknown %s call %s"](scope,"?"))
+ top=0
+ else
+ local index=stack[top]+bias
+ top=top-1
+ if trace_charstrings then
+ showvalue(scope,index,true)
+ end
+ local tab=list[index]
+ if tab then
+ process(tab)
+ else
+ showstate(formatters["unknown %s call %s"](scope,index))
+ top=0
+ end
+ end
+ depth=depth-1
+ end
+ local justpass=false
+ process=function(tab)
+ local i=1
+ local n=#tab
+ while i<=n do
+ local t=tab[i]
+ if t>=32 then
+ top=top+1
+ if t<=246 then
+ stack[top]=t-139
+ i=i+1
+ elseif t<=250 then
+ stack[top]=t*256-63124+tab[i+1]
+ i=i+2
+ elseif t<=254 then
+ stack[top]=-t*256+64148-tab[i+1]
+ i=i+2
+ else
+ local n=0x100*tab[i+1]+tab[i+2]
+ if n>=0x8000 then
+ stack[top]=n-0x10000+(0x100*tab[i+3]+tab[i+4])/0xFFFF
+ else
+ stack[top]=n+(0x100*tab[i+3]+tab[i+4])/0xFFFF
+ end
+ i=i+5
+ end
+ elseif t==28 then
+ top=top+1
+ local n=0x100*tab[i+1]+tab[i+2]
+ if n>=0x8000 then
+ stack[top]=n-0x10000
+ else
+ stack[top]=n
+ end
+ i=i+3
+ elseif t==11 then
+ if trace_charstrings then
+ showstate("return")
+ end
+ return
+ elseif t==10 then
+ call("local",locals,localbias)
+ i=i+1
+ elseif t==14 then
+ if width then
+ elseif top>0 then
+ width=stack[1]
+ if trace_charstrings then
+ showvalue("width",width)
+ end
+ else
+ width=true
+ end
+ if trace_charstrings then
+ showstate("endchar")
+ end
+ return
+ elseif t==29 then
+ call("global",globals,globalbias)
+ i=i+1
+ elseif t==12 then
+ i=i+1
+ local t=tab[i]
+ if justpass then
+ if t>=34 and t<=37 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ r=r+1;result[r]=chars[12]
+ r=r+1;result[r]=chars[t]
+ top=0
+ else
+ local a=subactions[t]
+ if a then
+ a(t)
+ else
+ top=0
+ end
+ end
+ else
+ local a=subactions[t]
+ if a then
+ a(t)
+ else
+ if trace_charstrings then
+ showvalue("<subaction>",t)
+ end
+ top=0
+ end
+ end
+ i=i+1
+ elseif justpass then
+ if t==15 then
+ p_setvsindex()
+ i=i+1
+ elseif t==16 then
+ local s=p_blend() or 0
+ i=i+s+1
+ elseif t==1 or t==3 or t==18 or operation==23 then
+ p_getstem()
+if true then
+ if top>0 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ top=0
+ end
+ r=r+1;result[r]=chars[t]
+else
+ top=0
+end
+ i=i+1
+ elseif t==19 or t==20 then
+ local s=p_getmask() or 0
+if true then
+ if top>0 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ top=0
+ end
+ r=r+1;result[r]=chars[t]
+ for j=1,s do
+ i=i+1
+ r=r+1;result[r]=chars[tab[i]]
+ end
+else
+ i=i+s
+ top=0
+end
+ i=i+1
+ elseif t==9 then
+ top=0
+ i=i+1
+ elseif t==13 then
+ local s=hsbw() or 0
+ i=i+s+1
+ else
+ if top>0 then
+ for i=1,top do
+ r=r+1;result[r]=encode[stack[i]]
+ end
+ top=0
+ end
+ r=r+1;result[r]=chars[t]
+ i=i+1
+ end
+ else
+ local a=actions[t]
+ if a then
+ local s=a(t)
+ if s then
+ i=i+s+1
+ else
+ i=i+1
+ end
+ else
+ if trace_charstrings then
+ showvalue("<action>",t)
+ end
+ top=0
+ i=i+1
+ end
+ end
+ end
+ end
+ local function setbias(globals,locals,nobias)
+ if nobias then
+ return 0,0
+ else
+ local g=#globals
+ local l=#locals
+ return
+ ((g<1240 and 107) or (g<33900 and 1131) or 32768)+1,
+ ((l<1240 and 107) or (l<33900 and 1131) or 32768)+1
+ end
+ end
+ local function processshape(tab,index)
+ if not tab then
+ glyphs[index]={
+ boundingbox={ 0,0,0,0 },
+ width=0,
+ name=charset and charset[index] or nil,
+ }
+ return
+ end
+ tab=bytetable(tab)
+ x=0
+ y=0
+ width=false
+ r=0
+ top=0
+ stems=0
+ result={}
+ xmin=0
+ xmax=0
+ ymin=0
+ ymax=0
+ checked=false
+ if trace_charstrings then
+ report("glyph: %i",index)
+ report("data : % t",tab)
+ end
+ if regions then
+ updateregions(vsindex)
+ end
+ process(tab)
+ local boundingbox={
+ round(xmin),
+ round(ymin),
+ round(xmax),
+ round(ymax),
+ }
+ if width==true or width==false then
+ width=defaultwidth
+ else
+ width=nominalwidth+width
+ end
+ local glyph=glyphs[index]
+ if justpass then
+ r=r+1
+ result[r]=c_endchar
+ local stream=concat(result)
+ if glyph then
+ glyph.stream=stream
+ else
+ glyphs[index]={ stream=stream }
+ end
+ elseif glyph then
+ glyph.segments=keepcurve~=false and result or nil
+ glyph.boundingbox=boundingbox
+ if not glyph.width then
+ glyph.width=width
+ end
+ if charset and not glyph.name then
+ glyph.name=charset[index]
+ end
+ elseif keepcurve then
+ glyphs[index]={
+ segments=result,
+ boundingbox=boundingbox,
+ width=width,
+ name=charset and charset[index] or nil,
+ }
+ else
+ glyphs[index]={
+ boundingbox=boundingbox,
+ width=width,
+ name=charset and charset[index] or nil,
+ }
+ end
+ if trace_charstrings then
+ report("width : %s",tostring(width))
+ report("boundingbox: % t",boundingbox)
+ end
+ end
+ startparsing=function(fontdata,data,streams)
+ reginit=false
+ axis=false
+ regions=data.regions
+ justpass=streams==true
+ if regions then
+ regions={ regions }
+ axis=data.factors or false
+ end
+ end
+ stopparsing=function(fontdata,data)
+ stack={}
+ glyphs=false
+ result={}
+ top=0
+ locals=false
+ globals=false
+ strings=false
+ end
+ local function setwidths(private)
+ if not private then
+ return 0,0
+ end
+ local privatedata=private.data
+ if not privatedata then
+ return 0,0
+ end
+ return privatedata.nominalwidthx or 0,privatedata.defaultwidthx or 0
+ end
+ parsecharstrings=function(fontdata,data,glphs,doshapes,tversion,streams,nobias)
+ local dictionary=data.dictionaries[1]
+ local charstrings=dictionary.charstrings
+ keepcurve=doshapes
+ version=tversion
+ strings=data.strings
+ globals=data.routines or {}
+ locals=dictionary.subroutines or {}
+ charset=dictionary.charset
+ vsindex=dictionary.vsindex or 0
+ glyphs=glphs or {}
+ globalbias,localbias=setbias(globals,locals,nobias)
+ nominalwidth,defaultwidth=setwidths(dictionary.private)
+ if charstrings then
+ startparsing(fontdata,data,streams)
+ for index=1,#charstrings do
+ processshape(charstrings[index],index-1)
+ end
+ stopparsing(fontdata,data)
+ else
+ report("no charstrings")
+ end
+ return glyphs
+ end
+ parsecharstring=function(fontdata,data,dictionary,tab,glphs,index,doshapes,tversion,streams)
+ keepcurve=doshapes
+ version=tversion
+ strings=data.strings
+ globals=data.routines or {}
+ locals=dictionary.subroutines or {}
+ charset=false
+ vsindex=dictionary.vsindex or 0
+ glyphs=glphs or {}
+ justpass=streams==true
+ globalbias,localbias=setbias(globals,locals,nobias)
+ nominalwidth,defaultwidth=setwidths(dictionary.private)
+ processshape(tab,index-1)
+ end
+end
+local function readglobals(f,data)
+ local routines=readlengths(f)
+ for i=1,#routines do
+ routines[i]=readbytetable(f,routines[i])
+ end
+ data.routines=routines
+end
+local function readencodings(f,data)
+ data.encodings={}
+end
+local function readcharsets(f,data,dictionary)
+ local header=data.header
+ local strings=data.strings
+ local nofglyphs=data.nofglyphs
+ local charsetoffset=dictionary.charset
+ if charsetoffset and charsetoffset~=0 then
+ setposition(f,header.offset+charsetoffset)
+ local format=readbyte(f)
+ local charset={ [0]=".notdef" }
+ dictionary.charset=charset
+ if format==0 then
+ for i=1,nofglyphs do
+ charset[i]=strings[readushort(f)]
+ end
+ elseif format==1 or format==2 then
+ local readcount=format==1 and readbyte or readushort
+ local i=1
+ while i<=nofglyphs do
+ local sid=readushort(f)
+ local n=readcount(f)
+ for s=sid,sid+n do
+ charset[i]=strings[s]
+ i=i+1
+ if i>nofglyphs then
+ break
+ end
+ end
+ end
+ else
+ report("cff parser: unsupported charset format %a",format)
+ end
+ else
+ dictionary.nocharset=true
+ dictionary.charset=nil
+ end
+end
+local function readprivates(f,data)
+ local header=data.header
+ local dictionaries=data.dictionaries
+ local private=dictionaries[1].private
+ if private then
+ setposition(f,header.offset+private.offset)
+ private.data=readstring(f,private.size)
+ end
+end
+local function readlocals(f,data,dictionary)
+ local header=data.header
+ local private=dictionary.private
+ if private then
+ local subroutineoffset=private.data.subroutines
+ if subroutineoffset~=0 then
+ setposition(f,header.offset+private.offset+subroutineoffset)
+ local subroutines=readlengths(f)
+ for i=1,#subroutines do
+ subroutines[i]=readbytetable(f,subroutines[i])
+ end
+ dictionary.subroutines=subroutines
+ private.data.subroutines=nil
+ else
+ dictionary.subroutines={}
+ end
+ else
+ dictionary.subroutines={}
+ end
+end
+local function readcharstrings(f,data,what)
+ local header=data.header
+ local dictionaries=data.dictionaries
+ local dictionary=dictionaries[1]
+ local stringtype=dictionary.charstringtype
+ local offset=dictionary.charstrings
+ if type(offset)~="number" then
+ elseif stringtype==2 then
+ setposition(f,header.offset+offset)
+ local charstrings=readlengths(f,what=="cff2")
+ local nofglyphs=#charstrings
+ for i=1,nofglyphs do
+ charstrings[i]=readstring(f,charstrings[i])
+ end
+ data.nofglyphs=nofglyphs
+ dictionary.charstrings=charstrings
+ else
+ report("unsupported charstr type %i",stringtype)
+ data.nofglyphs=0
+ dictionary.charstrings={}
+ end
+end
+local function readcidprivates(f,data)
+ local header=data.header
+ local dictionaries=data.dictionaries[1].cid.dictionaries
+ for i=1,#dictionaries do
+ local dictionary=dictionaries[i]
+ local private=dictionary.private
+ if private then
+ setposition(f,header.offset+private.offset)
+ private.data=readstring(f,private.size)
+ end
+ end
+ parseprivates(data,dictionaries)
+end
+readers.parsecharstrings=parsecharstrings
+local function readnoselect(f,fontdata,data,glyphs,doshapes,version,streams)
+ local dictionaries=data.dictionaries
+ local dictionary=dictionaries[1]
+ readglobals(f,data)
+ readcharstrings(f,data,version)
+ if version=="cff2" then
+ dictionary.charset=nil
+ else
+ readencodings(f,data)
+ readcharsets(f,data,dictionary)
+ end
+ readprivates(f,data)
+ parseprivates(data,data.dictionaries)
+ readlocals(f,data,dictionary)
+ startparsing(fontdata,data,streams)
+ parsecharstrings(fontdata,data,glyphs,doshapes,version,streams)
+ stopparsing(fontdata,data)
+end
+local function readfdselect(f,fontdata,data,glyphs,doshapes,version,streams)
+ local header=data.header
+ local dictionaries=data.dictionaries
+ local dictionary=dictionaries[1]
+ local cid=dictionary.cid
+ local cidselect=cid and cid.fdselect
+ readglobals(f,data)
+ readcharstrings(f,data,version)
+ if version~="cff2" then
+ readencodings(f,data)
+ end
+ local charstrings=dictionary.charstrings
+ local fdindex={}
+ local nofglyphs=data.nofglyphs
+ local maxindex=-1
+ setposition(f,header.offset+cidselect)
+ local format=readbyte(f)
+ if format==1 then
+ for i=0,nofglyphs do
+ local index=readbyte(f)
+ fdindex[i]=index
+ if index>maxindex then
+ maxindex=index
+ end
+ end
+ elseif format==3 then
+ local nofranges=readushort(f)
+ local first=readushort(f)
+ local index=readbyte(f)
+ while true do
+ local last=readushort(f)
+ if index>maxindex then
+ maxindex=index
+ end
+ for i=first,last do
+ fdindex[i]=index
+ end
+ if last>=nofglyphs then
+ break
+ else
+ first=last+1
+ index=readbyte(f)
+ end
+ end
+ else
+ end
+ if maxindex>=0 then
+ local cidarray=cid.fdarray
+ if cidarray then
+ setposition(f,header.offset+cidarray)
+ local dictionaries=readlengths(f)
+ for i=1,#dictionaries do
+ dictionaries[i]=readstring(f,dictionaries[i])
+ end
+ parsedictionaries(data,dictionaries)
+ cid.dictionaries=dictionaries
+ readcidprivates(f,data)
+ for i=1,#dictionaries do
+ readlocals(f,data,dictionaries[i])
+ end
+ startparsing(fontdata,data,streams)
+ for i=1,#charstrings do
+ parsecharstring(fontdata,data,dictionaries[fdindex[i]+1],charstrings[i],glyphs,i,doshapes,version,streams)
+ end
+ stopparsing(fontdata,data)
+ else
+ report("no cid array")
+ end
+ end
+end
+local gotodatatable=readers.helpers.gotodatatable
+local function cleanup(data,dictionaries)
+end
+function readers.cff(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cff",specification.details or specification.glyphs)
+ if tableoffset then
+ local header=readheader(f)
+ if header.major~=1 then
+ report("only version %s is supported for table %a",1,"cff")
+ return
+ end
+ local glyphs=fontdata.glyphs
+ local names=readfontnames(f)
+ local dictionaries=readtopdictionaries(f)
+ local strings=readstrings(f)
+ local data={
+ header=header,
+ names=names,
+ dictionaries=dictionaries,
+ strings=strings,
+ nofglyphs=fontdata.nofglyphs,
+ }
+ parsedictionaries(data,dictionaries,"cff")
+ local dic=dictionaries[1]
+ local cid=dic.cid
+ local cffinfo={
+ familyname=dic.familyname,
+ fullname=dic.fullname,
+ boundingbox=dic.boundingbox,
+ weight=dic.weight,
+ italicangle=dic.italicangle,
+ underlineposition=dic.underlineposition,
+ underlinethickness=dic.underlinethickness,
+ defaultwidth=dic.defaultwidthx,
+ nominalwidth=dic.nominalwidthx,
+ monospaced=dic.monospaced,
+ }
+ fontdata.cidinfo=cid and {
+ registry=cid.registry,
+ ordering=cid.ordering,
+ supplement=cid.supplement,
+ }
+ fontdata.cffinfo=cffinfo
+ local all=specification.shapes or specification.streams or false
+ if specification.glyphs or all then
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,all,"cff",specification.streams)
+ else
+ readnoselect(f,fontdata,data,glyphs,all,"cff",specification.streams)
+ end
+ end
+ local private=dic.private
+ if private then
+ local data=private.data
+ if type(data)=="table" then
+ cffinfo.defaultwidth=data.defaultwidthx or cffinfo.defaultwidth
+ cffinfo.nominalwidth=data.nominalwidthx or cffinfo.nominalwidth
+ cffinfo.bluevalues=data.bluevalues
+ cffinfo.otherblues=data.otherblues
+ cffinfo.familyblues=data.familyblues
+ cffinfo.familyotherblues=data.familyotherblues
+ cffinfo.bluescale=data.bluescale
+ cffinfo.blueshift=data.blueshift
+ cffinfo.bluefuzz=data.bluefuzz
+ cffinfo.stdhw=data.stdhw
+ cffinfo.stdvw=data.stdvw
+ end
+ end
+ cleanup(data,dictionaries)
+ end
+end
+function readers.cff2(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cff2",specification.glyphs)
+ if tableoffset then
+ local header=readheader(f)
+ if header.major~=2 then
+ report("only version %s is supported for table %a",2,"cff2")
+ return
+ end
+ local glyphs=fontdata.glyphs
+ local dictionaries={ readstring(f,header.dsize) }
+ local data={
+ header=header,
+ dictionaries=dictionaries,
+ nofglyphs=fontdata.nofglyphs,
+ }
+ parsedictionaries(data,dictionaries,"cff2")
+ local offset=dictionaries[1].vstore
+ if offset>0 then
+ local storeoffset=dictionaries[1].vstore+data.header.offset+2
+ local regions,deltas=readers.helpers.readvariationdata(f,storeoffset,factors)
+ data.regions=regions
+ data.deltas=deltas
+ else
+ data.regions={}
+ data.deltas={}
+ end
+ data.factors=specification.factors
+ local cid=data.dictionaries[1].cid
+ local all=specification.shapes or specification.streams or false
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,all,"cff2",specification.streams)
+ else
+ readnoselect(f,fontdata,data,glyphs,all,"cff2",specification.streams)
+ end
+ cleanup(data,dictionaries)
+ end
+end
+function readers.cffcheck(filename)
+ local f=io.open(filename,"rb")
+ if f then
+ local fontdata={
+ glyphs={},
+ }
+ local header=readheader(f)
+ if header.major~=1 then
+ report("only version %s is supported for table %a",1,"cff")
+ return
+ end
+ local names=readfontnames(f)
+ local dictionaries=readtopdictionaries(f)
+ local strings=readstrings(f)
+ local glyphs={}
+ local data={
+ header=header,
+ names=names,
+ dictionaries=dictionaries,
+ strings=strings,
+ glyphs=glyphs,
+ nofglyphs=0,
+ }
+ parsedictionaries(data,dictionaries,"cff")
+ local cid=data.dictionaries[1].cid
+ if cid and cid.fdselect then
+ readfdselect(f,fontdata,data,glyphs,false)
+ else
+ readnoselect(f,fontdata,data,glyphs,false)
+ end
+ return data
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-ttf']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,unpack=next,type,unpack
+local band,rshift=bit32.band,bit32.rshift
+local sqrt,round=math.sqrt,math.round
+local char,rep=string.char,string.rep
+local concat=table.concat
+local idiv=number.idiv
+local setmetatableindex=table.setmetatableindex
+local report=logs.reporter("otf reader","ttf")
+local trace_deltas=false
+local readers=fonts.handlers.otf.readers
+local streamreader=readers.streamreader
+local setposition=streamreader.setposition
+local getposition=streamreader.getposition
+local skipbytes=streamreader.skip
+local readbyte=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readulong=streamreader.readcardinal4
+local readchar=streamreader.readinteger1
+local readshort=streamreader.readinteger2
+local read2dot14=streamreader.read2dot14
+local readinteger=streamreader.readinteger1
+local readcardinaltable=streamreader.readcardinaltable
+local readintegertable=streamreader.readintegertable
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ setposition=streamreader.setposition
+ getposition=streamreader.getposition
+ skipbytes=streamreader.skip
+ readbyte=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readulong=streamreader.readcardinal4
+ readchar=streamreader.readinteger1
+ readshort=streamreader.readinteger2
+ read2dot14=streamreader.read2dot14
+ readinteger=streamreader.readinteger1
+ readcardinaltable=streamreader.readcardinaltable
+ readintegertable=streamreader.readintegertable
+end)
+local short=2
+local ushort=2
+local ulong=4
+local helpers=readers.helpers
+local gotodatatable=helpers.gotodatatable
+local function mergecomposites(glyphs,shapes)
+ local function merge(index,shape,components)
+ local contours={}
+ local points={}
+ local nofcontours=0
+ local nofpoints=0
+ local offset=0
+ local deltas=shape.deltas
+ for i=1,#components do
+ local component=components[i]
+ local subindex=component.index
+ local subshape=shapes[subindex]
+ local subcontours=subshape.contours
+ local subpoints=subshape.points
+ if not subcontours then
+ local subcomponents=subshape.components
+ if subcomponents then
+ subcontours,subpoints=merge(subindex,subshape,subcomponents)
+ end
+ end
+ if subpoints then
+ local matrix=component.matrix
+ local xscale=matrix[1]
+ local xrotate=matrix[2]
+ local yrotate=matrix[3]
+ local yscale=matrix[4]
+ local xoffset=matrix[5]
+ local yoffset=matrix[6]
+ local count=#subpoints
+ if xscale==1 and yscale==1 and xrotate==0 and yrotate==0 then
+ for i=1,count do
+ local p=subpoints[i]
+ nofpoints=nofpoints+1
+ points[nofpoints]={
+ p[1]+xoffset,
+ p[2]+yoffset,
+ p[3]
+ }
+ end
+ else
+ for i=1,count do
+ local p=subpoints[i]
+ local x=p[1]
+ local y=p[2]
+ nofpoints=nofpoints+1
+ points[nofpoints]={
+ xscale*x+xrotate*y+xoffset,
+ yscale*y+yrotate*x+yoffset,
+ p[3]
+ }
+ end
+ end
+ local subcount=#subcontours
+ if subcount==1 then
+ nofcontours=nofcontours+1
+ contours[nofcontours]=offset+subcontours[1]
+ else
+ for i=1,#subcontours do
+ nofcontours=nofcontours+1
+ contours[nofcontours]=offset+subcontours[i]
+ end
+ end
+ offset=offset+count
+ else
+ report("missing contours composite %s, component %s of %s, glyph %s",index,i,#components,subindex)
+ end
+ end
+ shape.points=points
+ shape.contours=contours
+ shape.components=nil
+ return contours,points
+ end
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local components=shape.components
+ if components then
+ merge(index,shape,components)
+ end
+ end
+ end
+end
+local function readnothing(f)
+ return {
+ type="nothing",
+ }
+end
+local function curveto(m_x,m_y,l_x,l_y,r_x,r_y)
+ return
+ l_x+2/3*(m_x-l_x),l_y+2/3*(m_y-l_y),
+ r_x+2/3*(m_x-r_x),r_y+2/3*(m_y-r_y),
+ r_x,r_y,"c"
+end
+local function applyaxis(glyph,shape,deltas,dowidth)
+ local points=shape.points
+ if points then
+ local nofpoints=#points
+ local h=nofpoints+2
+ local l=nofpoints+1
+ local dw=0
+ local dl=0
+ for i=1,#deltas do
+ local deltaset=deltas[i]
+ local xvalues=deltaset.xvalues
+ local yvalues=deltaset.yvalues
+ local dpoints=deltaset.points
+ local factor=deltaset.factor
+ if dpoints then
+ local nofdpoints=#dpoints
+ for i=1,nofdpoints do
+ local d=dpoints[i]
+ local p=points[d]
+ if p then
+ if xvalues then
+ local x=xvalues[i]
+ if x and x~=0 then
+ p[1]=p[1]+factor*x
+ end
+ end
+ if yvalues then
+ local y=yvalues[i]
+ if y and y~=0 then
+ p[2]=p[2]+factor*y
+ end
+ end
+ elseif dowidth then
+ if d==h then
+ local x=xvalues[i]
+ if x then
+ dw=dw+factor*x
+ end
+ elseif d==l then
+ local x=xvalues[i]
+ if x then
+ dl=dl+factor*x
+ end
+ end
+ end
+ end
+ else
+ for i=1,nofpoints do
+ local p=points[i]
+ if xvalues then
+ local x=xvalues[i]
+ if x and x~=0 then
+ p[1]=p[1]+factor*x
+ end
+ end
+ if yvalues then
+ local y=yvalues[i]
+ if y and y~=0 then
+ p[2]=p[2]+factor*y
+ end
+ end
+ end
+ if dowidth then
+ local x=xvalues[h]
+ if x then
+ dw=dw+factor*x
+ end
+ local x=xvalues[l]
+ if x then
+ dl=dl+factor*x
+ end
+ end
+ end
+ end
+ if dowidth then
+ local width=glyph.width or 0
+ glyph.width=width+dw-dl
+ end
+ else
+ report("no points for glyph %a",glyph.name)
+ end
+end
+local quadratic=false
+local function contours2outlines_normal(glyphs,shapes)
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local glyph=glyphs[index]
+ local contours=shape.contours
+ local points=shape.points
+ if contours then
+ local nofcontours=#contours
+ local segments={}
+ local nofsegments=0
+ glyph.segments=segments
+ if nofcontours>0 then
+ local px=0
+ local py=0
+ local first=1
+ for i=1,nofcontours do
+ local last=contours[i]
+ if last>=first then
+ local first_pt=points[first]
+ local first_on=first_pt[3]
+ if first==last then
+ first_pt[3]="m"
+ nofsegments=nofsegments+1
+ segments[nofsegments]=first_pt
+ else
+ local first_on=first_pt[3]
+ local last_pt=points[last]
+ local last_on=last_pt[3]
+ local start=1
+ local control_pt=false
+ if first_on then
+ start=2
+ else
+ if last_on then
+ first_pt=last_pt
+ else
+ first_pt={ (first_pt[1]+last_pt[1])/2,(first_pt[2]+last_pt[2])/2,false }
+ end
+ control_pt=first_pt
+ end
+ local x=first_pt[1]
+ local y=first_pt[2]
+ if not done then
+ xmin=x
+ ymin=y
+ xmax=x
+ ymax=y
+ done=true
+ end
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"m" }
+ if not quadratic then
+ px=x
+ py=y
+ end
+ local previous_pt=first_pt
+ for i=first,last do
+ local current_pt=points[i]
+ local current_on=current_pt[3]
+ local previous_on=previous_pt[3]
+ if previous_on then
+ if current_on then
+ local x,y=current_pt[1],current_pt[2]
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"l" }
+ if not quadratic then
+ px,py=x,y
+ end
+ else
+ control_pt=current_pt
+ end
+ elseif current_on then
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ local x2=current_pt[1]
+ local y2=current_pt[2]
+ nofsegments=nofsegments+1
+ if quadratic then
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ control_pt=false
+ else
+ local x2=(previous_pt[1]+current_pt[1])/2
+ local y2=(previous_pt[2]+current_pt[2])/2
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ nofsegments=nofsegments+1
+ if quadratic then
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ control_pt=current_pt
+ end
+ previous_pt=current_pt
+ end
+ if first_pt==last_pt then
+ else
+ nofsegments=nofsegments+1
+ local x2=first_pt[1]
+ local y2=first_pt[2]
+ if not control_pt then
+ segments[nofsegments]={ x2,y2,"l" }
+ elseif quadratic then
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ else
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ end
+ end
+ first=last+1
+ end
+ end
+ end
+ end
+ end
+end
+local function contours2outlines_shaped(glyphs,shapes,keepcurve)
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local glyph=glyphs[index]
+ local contours=shape.contours
+ local points=shape.points
+ if contours then
+ local nofcontours=#contours
+ local segments=keepcurve and {} or nil
+ local nofsegments=0
+ if keepcurve then
+ glyph.segments=segments
+ end
+ if nofcontours>0 then
+ local xmin,ymin,xmax,ymax,done=0,0,0,0,false
+ local px,py=0,0
+ local first=1
+ for i=1,nofcontours do
+ local last=contours[i]
+ if last>=first then
+ local first_pt=points[first]
+ local first_on=first_pt[3]
+ if first==last then
+ if keepcurve then
+ first_pt[3]="m"
+ nofsegments=nofsegments+1
+ segments[nofsegments]=first_pt
+ end
+ else
+ local first_on=first_pt[3]
+ local last_pt=points[last]
+ local last_on=last_pt[3]
+ local start=1
+ local control_pt=false
+ if first_on then
+ start=2
+ else
+ if last_on then
+ first_pt=last_pt
+ else
+ first_pt={ (first_pt[1]+last_pt[1])/2,(first_pt[2]+last_pt[2])/2,false }
+ end
+ control_pt=first_pt
+ end
+ local x=first_pt[1]
+ local y=first_pt[2]
+ if not done then
+ xmin,ymin,xmax,ymax=x,y,x,y
+ done=true
+ else
+ if x<xmin then xmin=x elseif x>xmax then xmax=x end
+ if y<ymin then ymin=y elseif y>ymax then ymax=y end
+ end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"m" }
+ end
+ if not quadratic then
+ px=x
+ py=y
+ end
+ local previous_pt=first_pt
+ for i=first,last do
+ local current_pt=points[i]
+ local current_on=current_pt[3]
+ local previous_on=previous_pt[3]
+ if previous_on then
+ if current_on then
+ local x=current_pt[1]
+ local y=current_pt[2]
+ if x<xmin then xmin=x elseif x>xmax then xmax=x end
+ if y<ymin then ymin=y elseif y>ymax then ymax=y end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x,y,"l" }
+ end
+ if not quadratic then
+ px=x
+ py=y
+ end
+ else
+ control_pt=current_pt
+ end
+ elseif current_on then
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ local x2=current_pt[1]
+ local y2=current_pt[2]
+ if quadratic then
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ end
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if x2<xmin then xmin=x2 elseif x2>xmax then xmax=x2 end
+ if y2<ymin then ymin=y2 elseif y2>ymax then ymax=y2 end
+ if px<xmin then xmin=px elseif px>xmax then xmax=px end
+ if py<ymin then ymin=py elseif py>ymax then ymax=py end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ control_pt=false
+ else
+ local x2=(previous_pt[1]+current_pt[1])/2
+ local y2=(previous_pt[2]+current_pt[2])/2
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ if quadratic then
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ end
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if x2<xmin then xmin=x2 elseif x2>xmax then xmax=x2 end
+ if y2<ymin then ymin=y2 elseif y2>ymax then ymax=y2 end
+ if px<xmin then xmin=px elseif px>xmax then xmax=px end
+ if py<ymin then ymin=py elseif py>ymax then ymax=py end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ control_pt=current_pt
+ end
+ previous_pt=current_pt
+ end
+ if first_pt==last_pt then
+ elseif not control_pt then
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ first_pt[1],first_pt[2],"l" }
+ end
+ else
+ local x1=control_pt[1]
+ local y1=control_pt[2]
+ local x2=first_pt[1]
+ local y2=first_pt[2]
+ if x1<xmin then xmin=x1 elseif x1>xmax then xmax=x1 end
+ if y1<ymin then ymin=y1 elseif y1>ymax then ymax=y1 end
+ if quadratic then
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,"q" }
+ end
+ else
+ x1,y1,x2,y2,px,py=curveto(x1,y1,px,py,x2,y2)
+ if x2<xmin then xmin=x2 elseif x2>xmax then xmax=x2 end
+ if y2<ymin then ymin=y2 elseif y2>ymax then ymax=y2 end
+ if px<xmin then xmin=px elseif px>xmax then xmax=px end
+ if py<ymin then ymin=py elseif py>ymax then ymax=py end
+ if keepcurve then
+ nofsegments=nofsegments+1
+ segments[nofsegments]={ x1,y1,x2,y2,px,py,"c" }
+ end
+ end
+ end
+ end
+ end
+ first=last+1
+ end
+ glyph.boundingbox={ round(xmin),round(ymin),round(xmax),round(ymax) }
+ end
+ end
+ end
+ end
+end
+local c_zero=char(0)
+local s_zero=char(0,0)
+local function toushort(n)
+ return char(band(rshift(n,8),0xFF),band(n,0xFF))
+end
+local function toshort(n)
+ if n<0 then
+ n=n+0x10000
+ end
+ return char(band(rshift(n,8),0xFF),band(n,0xFF))
+end
+local chars=setmetatableindex(function(t,k)
+ for i=0,255 do local v=char(i) t[i]=v end return t[k]
+end)
+local function repackpoints(glyphs,shapes)
+ local noboundingbox={ 0,0,0,0 }
+ local result={}
+ local xpoints={}
+ local ypoints={}
+ for index=0,#glyphs-1 do
+ local shape=shapes[index]
+ if shape then
+ local r=0
+ local glyph=glyphs[index]
+ local contours=shape.contours
+ local nofcontours=contours and #contours or 0
+ local boundingbox=glyph.boundingbox or noboundingbox
+ r=r+1 result[r]=toshort(nofcontours)
+ r=r+1 result[r]=toshort(boundingbox[1])
+ r=r+1 result[r]=toshort(boundingbox[2])
+ r=r+1 result[r]=toshort(boundingbox[3])
+ r=r+1 result[r]=toshort(boundingbox[4])
+ if nofcontours>0 then
+ for i=1,nofcontours do
+ r=r+1 result[r]=toshort(contours[i]-1)
+ end
+ r=r+1 result[r]=s_zero
+ local points=shape.points
+ local currentx=0
+ local currenty=0
+ local x=0
+ local y=0
+ local lastflag=nil
+ local nofflags=0
+ for i=1,#points do
+ local pt=points[i]
+ local px=pt[1]
+ local py=pt[2]
+ local fl=pt[3] and 0x01 or 0x00
+ if px==currentx then
+ fl=fl+0x10
+ else
+ local dx=round(px-currentx)
+ x=x+1
+ if dx<-255 or dx>255 then
+ xpoints[x]=toshort(dx)
+ elseif dx<0 then
+ fl=fl+0x02
+ xpoints[x]=chars[-dx]
+ elseif dx>0 then
+ fl=fl+0x12
+ xpoints[x]=chars[dx]
+ else
+ fl=fl+0x02
+ xpoints[x]=c_zero
+ end
+ end
+ if py==currenty then
+ fl=fl+0x20
+ else
+ local dy=round(py-currenty)
+ y=y+1
+ if dy<-255 or dy>255 then
+ ypoints[y]=toshort(dy)
+ elseif dy<0 then
+ fl=fl+0x04
+ ypoints[y]=chars[-dy]
+ elseif dy>0 then
+ fl=fl+0x24
+ ypoints[y]=chars[dy]
+ else
+ fl=fl+0x04
+ ypoints[y]=c_zero
+ end
+ end
+ currentx=px
+ currenty=py
+ if lastflag==fl then
+ if nofflags==255 then
+ lastflag=lastflag+0x08
+ r=r+1 result[r]=char(lastflag,nofflags-1)
+ nofflags=1
+ lastflag=fl
+ else
+ nofflags=nofflags+1
+ end
+ else
+ if nofflags==1 then
+ r=r+1 result[r]=chars[lastflag]
+ elseif nofflags==2 then
+ r=r+1 result[r]=char(lastflag,lastflag)
+ elseif nofflags>2 then
+ lastflag=lastflag+0x08
+ r=r+1 result[r]=char(lastflag,nofflags-1)
+ end
+ nofflags=1
+ lastflag=fl
+ end
+ end
+ if nofflags==1 then
+ r=r+1 result[r]=chars[lastflag]
+ elseif nofflags==2 then
+ r=r+1 result[r]=char(lastflag,lastflag)
+ elseif nofflags>2 then
+ lastflag=lastflag+0x08
+ r=r+1 result[r]=char(lastflag,nofflags-1)
+ end
+ r=r+1 result[r]=concat(xpoints,"",1,x)
+ r=r+1 result[r]=concat(ypoints,"",1,y)
+ end
+ local stream=concat(result,"",1,r)
+ local length=#stream
+ local padding=idiv(length+3,4)*4-length
+ if padding>0 then
+ if padding==1 then
+ padding="\0"
+ elseif padding==2 then
+ padding="\0\0"
+ else
+ padding="\0\0\0"
+ end
+ padding=stream..padding
+ end
+ glyph.stream=stream
+ end
+ end
+end
+local flags={}
+local function readglyph(f,nofcontours)
+ local points={}
+ local contours={}
+ for i=1,nofcontours do
+ contours[i]=readshort(f)+1
+ end
+ local nofpoints=contours[nofcontours]
+ local nofinstructions=readushort(f)
+ skipbytes(f,nofinstructions)
+ local i=1
+ while i<=nofpoints do
+ local flag=readbyte(f)
+ flags[i]=flag
+ if band(flag,0x08)~=0 then
+ local n=readbyte(f)
+ if n==1 then
+ i=i+1
+ flags[i]=flag
+ else
+ for j=1,n do
+ i=i+1
+ flags[i]=flag
+ end
+ end
+ end
+ i=i+1
+ end
+ local x=0
+ for i=1,nofpoints do
+ local flag=flags[i]
+ if band(flag,0x02)~=0 then
+ if band(flag,0x10)~=0 then
+ x=x+readbyte(f)
+ else
+ x=x-readbyte(f)
+ end
+ elseif band(flag,0x10)~=0 then
+ else
+ x=x+readshort(f)
+ end
+ points[i]={ x,0,band(flag,0x01)~=0 }
+ end
+ local y=0
+ for i=1,nofpoints do
+ local flag=flags[i]
+ if band(flag,0x04)~=0 then
+ if band(flag,0x20)~=0 then
+ y=y+readbyte(f)
+ else
+ y=y-readbyte(f)
+ end
+ elseif band(flag,0x20)~=0 then
+ else
+ y=y+readshort(f)
+ end
+ points[i][2]=y
+ end
+ return {
+ type="glyph",
+ points=points,
+ contours=contours,
+ nofpoints=nofpoints,
+ }
+end
+local function readcomposite(f)
+ local components={}
+ local nofcomponents=0
+ local instructions=false
+ while true do
+ local flags=readushort(f)
+ local index=readushort(f)
+ local f_xyarg=band(flags,0x0002)~=0
+ local f_offset=band(flags,0x0800)~=0
+ local xscale=1
+ local xrotate=0
+ local yrotate=0
+ local yscale=1
+ local xoffset=0
+ local yoffset=0
+ local base=false
+ local reference=false
+ if f_xyarg then
+ if band(flags,0x0001)~=0 then
+ xoffset=readshort(f)
+ yoffset=readshort(f)
+ else
+ xoffset=readchar(f)
+ yoffset=readchar(f)
+ end
+ else
+ if band(flags,0x0001)~=0 then
+ base=readshort(f)
+ reference=readshort(f)
+ else
+ base=readchar(f)
+ reference=readchar(f)
+ end
+ end
+ if band(flags,0x0008)~=0 then
+ xscale=read2dot14(f)
+ yscale=xscale
+ if f_xyarg and f_offset then
+ xoffset=xoffset*xscale
+ yoffset=yoffset*yscale
+ end
+ elseif band(flags,0x0040)~=0 then
+ xscale=read2dot14(f)
+ yscale=read2dot14(f)
+ if f_xyarg and f_offset then
+ xoffset=xoffset*xscale
+ yoffset=yoffset*yscale
+ end
+ elseif band(flags,0x0080)~=0 then
+ xscale=read2dot14(f)
+ xrotate=read2dot14(f)
+ yrotate=read2dot14(f)
+ yscale=read2dot14(f)
+ if f_xyarg and f_offset then
+ xoffset=xoffset*sqrt(xscale^2+xrotate^2)
+ yoffset=yoffset*sqrt(yrotate^2+yscale^2)
+ end
+ end
+ nofcomponents=nofcomponents+1
+ components[nofcomponents]={
+ index=index,
+ usemine=band(flags,0x0200)~=0,
+ round=band(flags,0x0006)~=0,
+ base=base,
+ reference=reference,
+ matrix={ xscale,xrotate,yrotate,yscale,xoffset,yoffset },
+ }
+ if band(flags,0x0100)~=0 then
+ instructions=true
+ end
+ if band(flags,0x0020)==0 then
+ break
+ end
+ end
+ return {
+ type="composite",
+ components=components,
+ }
+end
+function readers.loca(f,fontdata,specification)
+ if specification.glyphs then
+ local datatable=fontdata.tables.loca
+ if datatable then
+ local offset=fontdata.tables.glyf.offset
+ local format=fontdata.fontheader.indextolocformat
+ local profile=fontdata.maximumprofile
+ local nofglyphs=profile and profile.nofglyphs
+ local locations={}
+ setposition(f,datatable.offset)
+ if format==1 then
+ if not nofglyphs then
+ nofglyphs=idiv(datatable.length,4)-1
+ end
+ for i=0,nofglyphs do
+ locations[i]=offset+readulong(f)
+ end
+ fontdata.nofglyphs=nofglyphs
+ else
+ if not nofglyphs then
+ nofglyphs=idiv(datatable.length,2)-1
+ end
+ for i=0,nofglyphs do
+ locations[i]=offset+readushort(f)*2
+ end
+ end
+ fontdata.nofglyphs=nofglyphs
+ fontdata.locations=locations
+ end
+ end
+end
+function readers.glyf(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"glyf",specification.glyphs)
+ if tableoffset then
+ local locations=fontdata.locations
+ if locations then
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs
+ local filesize=fontdata.filesize
+ local nothing={ 0,0,0,0 }
+ local shapes={}
+ local loadshapes=specification.shapes or specification.instance or specification.streams
+ for index=0,nofglyphs-1 do
+ local location=locations[index]
+ local length=locations[index+1]-location
+ if location>=filesize then
+ report("discarding %s glyphs due to glyph location bug",nofglyphs-index+1)
+ fontdata.nofglyphs=index-1
+ fontdata.badfont=true
+ break
+ elseif length>0 then
+ setposition(f,location)
+ local nofcontours=readshort(f)
+ glyphs[index].boundingbox={
+ readshort(f),
+ readshort(f),
+ readshort(f),
+ readshort(f),
+ }
+ if not loadshapes then
+ elseif nofcontours==0 then
+ shapes[index]=readnothing(f)
+ elseif nofcontours>0 then
+ shapes[index]=readglyph(f,nofcontours)
+ else
+ shapes[index]=readcomposite(f,nofcontours)
+ end
+ else
+ if loadshapes then
+ shapes[index]=readnothing(f)
+ end
+ glyphs[index].boundingbox=nothing
+ end
+ end
+ if loadshapes then
+ if readers.gvar then
+ readers.gvar(f,fontdata,specification,glyphs,shapes)
+ end
+ mergecomposites(glyphs,shapes)
+ if specification.instance then
+ if specification.streams then
+ repackpoints(glyphs,shapes)
+ else
+ contours2outlines_shaped(glyphs,shapes,specification.shapes)
+ end
+ elseif specification.shapes then
+ if specification.streams then
+ repackpoints(glyphs,shapes)
+ else
+ contours2outlines_normal(glyphs,shapes)
+ end
+ elseif specification.streams then
+ repackpoints(glyphs,shapes)
+ end
+ end
+ end
+ end
+end
+local function readtuplerecord(f,nofaxis)
+ local record={}
+ for i=1,nofaxis do
+ record[i]=read2dot14(f)
+ end
+ return record
+end
+local function readpoints(f)
+ local count=readbyte(f)
+ if count==0 then
+ return nil,0
+ else
+ if count<128 then
+ elseif band(count,0x80)~=0 then
+ count=band(count,0x7F)*256+readbyte(f)
+ else
+ end
+ local points={}
+ local p=0
+ local n=1
+ while p<count do
+ local control=readbyte(f)
+ local runreader=band(control,0x80)~=0 and readushort or readbyte
+ local runlength=band(control,0x7F)
+ for i=1,runlength+1 do
+ n=n+runreader(f)
+ p=p+1
+ points[p]=n
+ end
+ end
+ return points,p
+ end
+end
+local function readdeltas(f,nofpoints)
+ local deltas={}
+ local p=0
+ local z=0
+ while nofpoints>0 do
+ local control=readbyte(f)
+if not control then
+ break
+end
+ local allzero=band(control,0x80)~=0
+ local runlength=band(control,0x3F)+1
+ if allzero then
+ z=z+runlength
+ else
+ local runreader=band(control,0x40)~=0 and readshort or readinteger
+ if z>0 then
+ for i=1,z do
+ p=p+1
+ deltas[p]=0
+ end
+ z=0
+ end
+ for i=1,runlength do
+ p=p+1
+ deltas[p]=runreader(f)
+ end
+ end
+ nofpoints=nofpoints-runlength
+ end
+ if p>0 then
+ return deltas
+ else
+ end
+end
+local function readdeltas(f,nofpoints)
+ local deltas={}
+ local p=0
+ while nofpoints>0 do
+ local control=readbyte(f)
+ if control then
+ local allzero=band(control,0x80)~=0
+ local runlength=band(control,0x3F)+1
+ if allzero then
+ for i=1,runlength do
+ p=p+1
+ deltas[p]=0
+ end
+ else
+ local runreader=band(control,0x40)~=0 and readshort or readinteger
+ for i=1,runlength do
+ p=p+1
+ deltas[p]=runreader(f)
+ end
+ end
+ nofpoints=nofpoints-runlength
+ else
+ break
+ end
+ end
+ if p>0 then
+ return deltas
+ else
+ end
+end
+function readers.gvar(f,fontdata,specification,glyphdata,shapedata)
+ local instance=specification.instance
+ if not instance then
+ return
+ end
+ local factors=specification.factors
+ if not factors then
+ return
+ end
+ local tableoffset=gotodatatable(f,fontdata,"gvar",specification.variable or specification.shapes)
+ if tableoffset then
+ local version=readulong(f)
+ local nofaxis=readushort(f)
+ local noftuples=readushort(f)
+ local tupleoffset=tableoffset+readulong(f)
+ local nofglyphs=readushort(f)
+ local flags=readushort(f)
+ local dataoffset=tableoffset+readulong(f)
+ local data={}
+ local tuples={}
+ local glyphdata=fontdata.glyphs
+ local dowidth=not fontdata.variabledata.hvarwidths
+ if band(flags,0x0001)~=0 then
+ for i=1,nofglyphs+1 do
+ data[i]=dataoffset+readulong(f)
+ end
+ else
+ for i=1,nofglyphs+1 do
+ data[i]=dataoffset+2*readushort(f)
+ end
+ end
+ if noftuples>0 then
+ setposition(f,tupleoffset)
+ for i=1,noftuples do
+ tuples[i]=readtuplerecord(f,nofaxis)
+ end
+ end
+ local nextoffset=false
+ local startoffset=data[1]
+ for i=1,nofglyphs do
+ nextoffset=data[i+1]
+ local glyph=glyphdata[i-1]
+ local name=trace_deltas and glyph.name
+ if startoffset==nextoffset then
+ if name then
+ report("no deltas for glyph %a",name)
+ end
+ else
+ local shape=shapedata[i-1]
+ if not shape then
+ if name then
+ report("no shape for glyph %a",name)
+ end
+ else
+ lastoffset=startoffset
+ setposition(f,startoffset)
+ local flags=readushort(f)
+ local count=band(flags,0x0FFF)
+ local offset=startoffset+readushort(f)
+ local deltas={}
+ local allpoints=(shape.nofpoints or 0)
+ local shared=false
+ local nofshared=0
+ if band(flags,0x8000)~=0 then
+ local current=getposition(f)
+ setposition(f,offset)
+ shared,nofshared=readpoints(f)
+ offset=getposition(f)
+ setposition(f,current)
+ end
+ for j=1,count do
+ local size=readushort(f)
+ local flags=readushort(f)
+ local index=band(flags,0x0FFF)
+ local haspeak=band(flags,0x8000)~=0
+ local intermediate=band(flags,0x4000)~=0
+ local private=band(flags,0x2000)~=0
+ local peak=nil
+ local start=nil
+ local stop=nil
+ local xvalues=nil
+ local yvalues=nil
+ local points=shared
+ local nofpoints=nofshared
+ if haspeak then
+ peak=readtuplerecord(f,nofaxis)
+ else
+ if index+1>#tuples then
+ report("error, bad tuple index",index)
+ end
+ peak=tuples[index+1]
+ end
+ if intermediate then
+ start=readtuplerecord(f,nofaxis)
+ stop=readtuplerecord(f,nofaxis)
+ end
+ if size>0 then
+ local current=getposition(f)
+ setposition(f,offset)
+ if private then
+ points,nofpoints=readpoints(f)
+ end
+ if nofpoints==0 then
+ nofpoints=allpoints+4
+ end
+ if nofpoints>0 then
+ xvalues=readdeltas(f,nofpoints)
+ yvalues=readdeltas(f,nofpoints)
+ end
+ offset=offset+size
+ setposition(f,current)
+ end
+ if not xvalues and not yvalues then
+ points=nil
+ end
+ local s=1
+ for i=1,nofaxis do
+ local f=factors[i]
+ local peak=peak and peak [i] or 0
+ local start=start and start[i] or (peak<0 and peak or 0)
+ local stop=stop and stop [i] or (peak>0 and peak or 0)
+ if start>peak or peak>stop then
+ elseif start<0 and stop>0 and peak~=0 then
+ elseif peak==0 then
+ elseif f<start or f>stop then
+ s=0
+ break
+ elseif f<peak then
+ s=s*(f-start)/(peak-start)
+ elseif f>peak then
+ s=s*(stop-f)/(stop-peak)
+ else
+ end
+ end
+ if s==0 then
+ if name then
+ report("no deltas applied for glyph %a",name)
+ end
+ else
+ deltas[#deltas+1]={
+ factor=s,
+ points=points,
+ xvalues=xvalues,
+ yvalues=yvalues,
+ }
+ end
+ end
+ if shape.type=="glyph" then
+ applyaxis(glyph,shape,deltas,dowidth)
+ else
+ shape.deltas=deltas
+ end
+ end
+ end
+ startoffset=nextoffset
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-dsp']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+local band=bit32.band
+local extract=bit32.extract
+local bor=bit32.bor
+local lshift=bit32.lshift
+local rshift=bit32.rshift
+local gsub=string.gsub
+local lower=string.lower
+local sub=string.sub
+local strip=string.strip
+local tohash=table.tohash
+local concat=table.concat
+local copy=table.copy
+local reversed=table.reversed
+local sort=table.sort
+local insert=table.insert
+local round=math.round
+local settings_to_hash=utilities.parsers.settings_to_hash_colon_too
+local setmetatableindex=table.setmetatableindex
+local formatters=string.formatters
+local sortedkeys=table.sortedkeys
+local sortedhash=table.sortedhash
+local sequenced=table.sequenced
+local report=logs.reporter("otf reader")
+local readers=fonts.handlers.otf.readers
+local streamreader=readers.streamreader
+local setposition=streamreader.setposition
+local getposition=streamreader.getposition
+local readuinteger=streamreader.readcardinal1
+local readushort=streamreader.readcardinal2
+local readulong=streamreader.readcardinal4
+local readinteger=streamreader.readinteger1
+local readshort=streamreader.readinteger2
+local readstring=streamreader.readstring
+local readtag=streamreader.readtag
+local readbytes=streamreader.readbytes
+local readfixed=streamreader.readfixed4
+local read2dot14=streamreader.read2dot14
+local skipshort=streamreader.skipshort
+local skipbytes=streamreader.skip
+local readbytetable=streamreader.readbytetable
+local readbyte=streamreader.readbyte
+local readcardinaltable=streamreader.readcardinaltable
+local readintegertable=streamreader.readintegertable
+local readfword=readshort
+local short=2
+local ushort=2
+local ulong=4
+directives.register("fonts.streamreader",function()
+ streamreader=utilities.streams
+ setposition=streamreader.setposition
+ getposition=streamreader.getposition
+ readuinteger=streamreader.readcardinal1
+ readushort=streamreader.readcardinal2
+ readulong=streamreader.readcardinal4
+ readinteger=streamreader.readinteger1
+ readshort=streamreader.readinteger2
+ readstring=streamreader.readstring
+ readtag=streamreader.readtag
+ readbytes=streamreader.readbytes
+ readfixed=streamreader.readfixed4
+ read2dot14=streamreader.read2dot14
+ skipshort=streamreader.skipshort
+ skipbytes=streamreader.skip
+ readbytetable=streamreader.readbytetable
+ readbyte=streamreader.readbyte
+ readcardinaltable=streamreader.readcardinaltable
+ readintegertable=streamreader.readintegertable
+ readfword=readshort
+end)
+local gsubhandlers={}
+local gposhandlers={}
+readers.gsubhandlers=gsubhandlers
+readers.gposhandlers=gposhandlers
+local helpers=readers.helpers
+local gotodatatable=helpers.gotodatatable
+local setvariabledata=helpers.setvariabledata
+local lookupidoffset=-1
+local classes={
+ "base",
+ "ligature",
+ "mark",
+ "component",
+}
+local gsubtypes={
+ "single",
+ "multiple",
+ "alternate",
+ "ligature",
+ "context",
+ "chainedcontext",
+ "extension",
+ "reversechainedcontextsingle",
+}
+local gpostypes={
+ "single",
+ "pair",
+ "cursive",
+ "marktobase",
+ "marktoligature",
+ "marktomark",
+ "context",
+ "chainedcontext",
+ "extension",
+}
+local chaindirections={
+ context=0,
+ chainedcontext=1,
+ reversechainedcontextsingle=-1,
+}
+local function setmetrics(data,where,tag,d)
+ local w=data[where]
+ if w then
+ local v=w[tag]
+ if v then
+ w[tag]=v+d
+ end
+ end
+end
+local variabletags={
+ hasc=function(data,d) setmetrics(data,"windowsmetrics","typoascender",d) end,
+ hdsc=function(data,d) setmetrics(data,"windowsmetrics","typodescender",d) end,
+ hlgp=function(data,d) setmetrics(data,"windowsmetrics","typolinegap",d) end,
+ hcla=function(data,d) setmetrics(data,"windowsmetrics","winascent",d) end,
+ hcld=function(data,d) setmetrics(data,"windowsmetrics","windescent",d) end,
+ vasc=function(data,d) setmetrics(data,"vhea not done","ascent",d) end,
+ vdsc=function(data,d) setmetrics(data,"vhea not done","descent",d) end,
+ vlgp=function(data,d) setmetrics(data,"vhea not done","linegap",d) end,
+ xhgt=function(data,d) setmetrics(data,"windowsmetrics","xheight",d) end,
+ cpht=function(data,d) setmetrics(data,"windowsmetrics","capheight",d) end,
+ sbxs=function(data,d) setmetrics(data,"windowsmetrics","subscriptxsize",d) end,
+ sbys=function(data,d) setmetrics(data,"windowsmetrics","subscriptysize",d) end,
+ sbxo=function(data,d) setmetrics(data,"windowsmetrics","subscriptxoffset",d) end,
+ sbyo=function(data,d) setmetrics(data,"windowsmetrics","subscriptyoffset",d) end,
+ spxs=function(data,d) setmetrics(data,"windowsmetrics","superscriptxsize",d) end,
+ spys=function(data,d) setmetrics(data,"windowsmetrics","superscriptysize",d) end,
+ spxo=function(data,d) setmetrics(data,"windowsmetrics","superscriptxoffset",d) end,
+ spyo=function(data,d) setmetrics(data,"windowsmetrics","superscriptyoffset",d) end,
+ strs=function(data,d) setmetrics(data,"windowsmetrics","strikeoutsize",d) end,
+ stro=function(data,d) setmetrics(data,"windowsmetrics","strikeoutpos",d) end,
+ unds=function(data,d) setmetrics(data,"postscript","underlineposition",d) end,
+ undo=function(data,d) setmetrics(data,"postscript","underlinethickness",d) end,
+}
+local read_cardinal={
+ streamreader.readcardinal1,
+ streamreader.readcardinal2,
+ streamreader.readcardinal3,
+ streamreader.readcardinal4,
+}
+local read_integer={
+ streamreader.readinteger1,
+ streamreader.readinteger2,
+ streamreader.readinteger3,
+ streamreader.readinteger4,
+}
+local lookupnames={
+ gsub={
+ single="gsub_single",
+ multiple="gsub_multiple",
+ alternate="gsub_alternate",
+ ligature="gsub_ligature",
+ context="gsub_context",
+ chainedcontext="gsub_contextchain",
+ reversechainedcontextsingle="gsub_reversecontextchain",
+ },
+ gpos={
+ single="gpos_single",
+ pair="gpos_pair",
+ cursive="gpos_cursive",
+ marktobase="gpos_mark2base",
+ marktoligature="gpos_mark2ligature",
+ marktomark="gpos_mark2mark",
+ context="gpos_context",
+ chainedcontext="gpos_contextchain",
+ }
+}
+local lookupflags=setmetatableindex(function(t,k)
+ local v={
+ band(k,0x0008)~=0 and true or false,
+ band(k,0x0004)~=0 and true or false,
+ band(k,0x0002)~=0 and true or false,
+ band(k,0x0001)~=0 and true or false,
+ }
+ t[k]=v
+ return v
+end)
+local function axistofactors(str)
+ local t=settings_to_hash(str)
+ for k,v in next,t do
+ t[k]=tonumber(v) or v
+ end
+ return t
+end
+local hash=table.setmetatableindex(function(t,k)
+ local v=sequenced(axistofactors(k),",")
+ t[k]=v
+ return v
+end)
+helpers.normalizedaxishash=hash
+local cleanname=fonts.names and fonts.names.cleanname or function(name)
+ return name and (gsub(lower(name),"[^%a%d]","")) or nil
+end
+helpers.cleanname=cleanname
+function helpers.normalizedaxis(str)
+ return hash[str] or str
+end
+local function getaxisscale(segments,minimum,default,maximum,user)
+ if not minimum or not default or not maximum then
+ return false
+ end
+ if user<minimum then
+ user=minimum
+ elseif user>maximum then
+ user=maximum
+ end
+ if user<default then
+ default=- (default-user)/(default-minimum)
+ elseif user>default then
+ default=(user-default)/(maximum-default)
+ else
+ default=0
+ end
+ if not segments then
+ return default
+ end
+ local e
+ for i=1,#segments do
+ local s=segments[i]
+ if type(s)~="number" then
+ report("using default axis scale")
+ return default
+ elseif s[1]>=default then
+ if s[2]==default then
+ return default
+ else
+ e=i
+ break
+ end
+ end
+ end
+ if e then
+ local b=segments[e-1]
+ local e=segments[e]
+ return b[2]+(e[2]-b[2])*(default-b[1])/(e[1]-b[1])
+ else
+ return false
+ end
+end
+local function getfactors(data,instancespec)
+ if instancespec==true then
+ elseif type(instancespec)~="string" or instancespec=="" then
+ return
+ end
+ local variabledata=data.variabledata
+ if not variabledata then
+ return
+ end
+ local instances=variabledata.instances
+ local axis=variabledata.axis
+ local segments=variabledata.segments
+ if instances and axis then
+ local values
+ if instancespec==true then
+ values={}
+ for i=1,#axis do
+ values[i]={
+ value=axis[i].default,
+ }
+ end
+ else
+ for i=1,#instances do
+ local instance=instances[i]
+ if cleanname(instance.subfamily)==instancespec then
+ values=instance.values
+ break
+ end
+ end
+ end
+ if values then
+ local factors={}
+ for i=1,#axis do
+ local a=axis[i]
+ factors[i]=getaxisscale(segments,a.minimum,a.default,a.maximum,values[i].value)
+ end
+ return factors
+ end
+ local values=axistofactors(hash[instancespec] or instancespec)
+ if values then
+ local factors={}
+ for i=1,#axis do
+ local a=axis[i]
+ local d=a.default
+ factors[i]=getaxisscale(segments,a.minimum,d,a.maximum,values[a.name or a.tag] or d)
+ end
+ return factors
+ end
+ end
+end
+local function getscales(regions,factors)
+ local scales={}
+ for i=1,#regions do
+ local region=regions[i]
+ local s=1
+ for j=1,#region do
+ local axis=region[j]
+ local f=factors[j]
+ local start=axis.start
+ local peak=axis.peak
+ local stop=axis.stop
+ if start>peak or peak>stop then
+ elseif start<0 and stop>0 and peak~=0 then
+ elseif peak==0 then
+ elseif f<start or f>stop then
+ s=0
+ break
+ elseif f<peak then
+ s=s*(f-start)/(peak-start)
+ elseif f>peak then
+ s=s*(stop-f)/(stop-peak)
+ else
+ end
+ end
+ scales[i]=s
+ end
+ return scales
+end
+helpers.getaxisscale=getaxisscale
+helpers.getfactors=getfactors
+helpers.getscales=getscales
+helpers.axistofactors=axistofactors
+local function readvariationdata(f,storeoffset,factors)
+ local position=getposition(f)
+ setposition(f,storeoffset)
+ local format=readushort(f)
+ local regionoffset=storeoffset+readulong(f)
+ local nofdeltadata=readushort(f)
+ local deltadata=readcardinaltable(f,nofdeltadata,ulong)
+ setposition(f,regionoffset)
+ local nofaxis=readushort(f)
+ local nofregions=readushort(f)
+ local regions={}
+ for i=1,nofregions do
+ local t={}
+ for i=1,nofaxis do
+ t[i]={
+ start=read2dot14(f),
+ peak=read2dot14(f),
+ stop=read2dot14(f),
+ }
+ end
+ regions[i]=t
+ end
+ if factors then
+ for i=1,nofdeltadata do
+ setposition(f,storeoffset+deltadata[i])
+ local nofdeltasets=readushort(f)
+ local nofshorts=readushort(f)
+ local nofregions=readushort(f)
+ local usedregions={}
+ local deltas={}
+ for i=1,nofregions do
+ usedregions[i]=regions[readushort(f)+1]
+ end
+ for i=1,nofdeltasets do
+ local t=readintegertable(f,nofshorts,short)
+ for i=nofshorts+1,nofregions do
+ t[i]=readinteger(f)
+ end
+ deltas[i]=t
+ end
+ deltadata[i]={
+ regions=usedregions,
+ deltas=deltas,
+ scales=factors and getscales(usedregions,factors) or nil,
+ }
+ end
+ end
+ setposition(f,position)
+ return regions,deltadata
+end
+helpers.readvariationdata=readvariationdata
+local function readcoverage(f,offset,simple)
+ setposition(f,offset)
+ local coverageformat=readushort(f)
+ if coverageformat==1 then
+ local nofcoverage=readushort(f)
+ if simple then
+ if nofcoverage==1 then
+ return { readushort(f) }
+ elseif nofcoverage==2 then
+ return { readushort(f),readushort(f) }
+ else
+ return readcardinaltable(f,nofcoverage,ushort)
+ end
+ elseif nofcoverage==1 then
+ return { [readushort(f)]=0 }
+ elseif nofcoverage==2 then
+ return { [readushort(f)]=0,[readushort(f)]=1 }
+ else
+ local coverage={}
+ for i=0,nofcoverage-1 do
+ coverage[readushort(f)]=i
+ end
+ return coverage
+ end
+ elseif coverageformat==2 then
+ local nofranges=readushort(f)
+ local coverage={}
+ local n=simple and 1 or 0
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local coverindex=readushort(f)
+ if simple then
+ for i=firstindex,lastindex do
+ coverage[n]=i
+ n=n+1
+ end
+ else
+ for i=firstindex,lastindex do
+ coverage[i]=n
+ n=n+1
+ end
+ end
+ end
+ return coverage
+ else
+ report("unknown coverage format %a ",coverageformat)
+ return {}
+ end
+end
+local function readclassdef(f,offset,preset)
+ setposition(f,offset)
+ local classdefformat=readushort(f)
+ local classdef={}
+ if type(preset)=="number" then
+ for k=0,preset-1 do
+ classdef[k]=1
+ end
+ end
+ if classdefformat==1 then
+ local index=readushort(f)
+ local nofclassdef=readushort(f)
+ for i=1,nofclassdef do
+ classdef[index]=readushort(f)+1
+ index=index+1
+ end
+ elseif classdefformat==2 then
+ local nofranges=readushort(f)
+ local n=0
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local class=readushort(f)+1
+ for i=firstindex,lastindex do
+ classdef[i]=class
+ end
+ end
+ else
+ report("unknown classdef format %a ",classdefformat)
+ end
+ if type(preset)=="table" then
+ for k in next,preset do
+ if not classdef[k] then
+ classdef[k]=1
+ end
+ end
+ end
+ return classdef
+end
+local function classtocoverage(defs)
+ if defs then
+ local list={}
+ for index,class in next,defs do
+ local c=list[class]
+ if c then
+ c[#c+1]=index
+ else
+ list[class]={ index }
+ end
+ end
+ return list
+ end
+end
+local skips={ [0]=0,
+ 1,
+ 1,
+ 2,
+ 1,
+ 2,
+ 2,
+ 3,
+ 2,
+ 2,
+ 3,
+ 2,
+ 3,
+ 3,
+ 4,
+}
+local function readvariation(f,offset)
+ local p=getposition(f)
+ setposition(f,offset)
+ local outer=readushort(f)
+ local inner=readushort(f)
+ local format=readushort(f)
+ setposition(f,p)
+ if format==0x8000 then
+ return outer,inner
+ end
+end
+local function readposition(f,format,mainoffset,getdelta)
+ if format==0 then
+ return false
+ end
+ if format==0x04 then
+ local h=readshort(f)
+ if h==0 then
+ return true
+ else
+ return { 0,0,h,0 }
+ end
+ end
+ if format==0x05 then
+ local x=readshort(f)
+ local h=readshort(f)
+ if x==0 and h==0 then
+ return true
+ else
+ return { x,0,h,0 }
+ end
+ end
+ if format==0x44 then
+ local h=readshort(f)
+ if getdelta then
+ local d=readshort(f)
+ if d>0 then
+ local outer,inner=readvariation(f,mainoffset+d)
+ if outer then
+ h=h+getdelta(outer,inner)
+ end
+ end
+ else
+ skipshort(f,1)
+ end
+ if h==0 then
+ return true
+ else
+ return { 0,0,h,0 }
+ end
+ end
+ local x=band(format,0x1)~=0 and readshort(f) or 0
+ local y=band(format,0x2)~=0 and readshort(f) or 0
+ local h=band(format,0x4)~=0 and readshort(f) or 0
+ local v=band(format,0x8)~=0 and readshort(f) or 0
+ if format>=0x10 then
+ local X=band(format,0x10)~=0 and skipshort(f) or 0
+ local Y=band(format,0x20)~=0 and skipshort(f) or 0
+ local H=band(format,0x40)~=0 and skipshort(f) or 0
+ local V=band(format,0x80)~=0 and skipshort(f) or 0
+ local s=skips[extract(format,4,4)]
+ if s>0 then
+ skipshort(f,s)
+ end
+ if getdelta then
+ if X>0 then
+ local outer,inner=readvariation(f,mainoffset+X)
+ if outer then
+ x=x+getdelta(outer,inner)
+ end
+ end
+ if Y>0 then
+ local outer,inner=readvariation(f,mainoffset+Y)
+ if outer then
+ y=y+getdelta(outer,inner)
+ end
+ end
+ if H>0 then
+ local outer,inner=readvariation(f,mainoffset+H)
+ if outer then
+ h=h+getdelta(outer,inner)
+ end
+ end
+ if V>0 then
+ local outer,inner=readvariation(f,mainoffset+V)
+ if outer then
+ v=v+getdelta(outer,inner)
+ end
+ end
+ end
+ return { x,y,h,v }
+ elseif x==0 and y==0 and h==0 and v==0 then
+ return true
+ else
+ return { x,y,h,v }
+ end
+end
+local function readanchor(f,offset,getdelta)
+ if not offset or offset==0 then
+ return nil
+ end
+ setposition(f,offset)
+ local format=readshort(f)
+ local x=readshort(f)
+ local y=readshort(f)
+ if format==3 then
+ if getdelta then
+ local X=readshort(f)
+ local Y=readshort(f)
+ if X>0 then
+ local outer,inner=readvariation(f,offset+X)
+ if outer then
+ x=x+getdelta(outer,inner)
+ end
+ end
+ if Y>0 then
+ local outer,inner=readvariation(f,offset+Y)
+ if outer then
+ y=y+getdelta(outer,inner)
+ end
+ end
+ else
+ skipshort(f,2)
+ end
+ return { x,y }
+ else
+ return { x,y }
+ end
+end
+local function readfirst(f,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ return { readushort(f) }
+end
+function readarray(f,offset)
+ if offset then
+ setposition(f,offset)
+ end
+ local n=readushort(f)
+ if n==1 then
+ return { readushort(f) },1
+ elseif n>0 then
+ return readcardinaltable(f,n,ushort),n
+ end
+end
+local function readcoveragearray(f,offset,t,simple)
+ if not t then
+ return nil
+ end
+ local n=#t
+ if n==0 then
+ return nil
+ end
+ for i=1,n do
+ t[i]=readcoverage(f,offset+t[i],simple)
+ end
+ return t
+end
+local function covered(subset,all)
+ local used,u
+ for i=1,#subset do
+ local s=subset[i]
+ if all[s] then
+ if used then
+ u=u+1
+ used[u]=s
+ else
+ u=1
+ used={ s }
+ end
+ end
+ end
+ return used
+end
+local function readlookuparray(f,noflookups,nofcurrent)
+ local lookups={}
+ if noflookups>0 then
+ local length=0
+ for i=1,noflookups do
+ local index=readushort(f)+1
+ if index>length then
+ length=index
+ end
+ local lookup=readushort(f)+1
+ local list=lookups[index]
+ if list then
+ list[#list+1]=lookup
+ else
+ lookups[index]={ lookup }
+ end
+ end
+ for index=1,length do
+ if not lookups[index] then
+ lookups[index]=false
+ end
+ end
+ end
+ return lookups
+end
+local function unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ coverage=readcoverage(f,tableoffset+coverage,true)
+ for i=1,#subclasssets do
+ local offset=subclasssets[i]
+ if offset>0 then
+ local firstcoverage=coverage[i]
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofcurrent=readushort(f)
+ local noflookups=readushort(f)
+ local current={ { firstcoverage } }
+ for i=2,nofcurrent do
+ current[i]={ readushort(f) }
+ end
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ current=current,
+ lookups=lookups
+ }
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","unchainedcontext",subtype)
+ end
+ return {
+ format="glyphs",
+ rules=rules,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local currentclassdef=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ coverage=readcoverage(f,tableoffset+coverage)
+ currentclassdef=readclassdef(f,tableoffset+currentclassdef,coverage)
+ local currentclasses=classtocoverage(currentclassdef,fontdata.glyphs)
+ for class=1,#subclasssets do
+ local offset=subclasssets[class]
+ if offset>0 then
+ local firstcoverage=currentclasses[class]
+ if firstcoverage then
+ firstcoverage=covered(firstcoverage,coverage)
+ if firstcoverage then
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofcurrent=readushort(f)
+ local noflookups=readushort(f)
+ local current={ firstcoverage }
+ for i=2,nofcurrent do
+ current[i]=currentclasses[readushort(f)+1]
+ end
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ current=current,
+ lookups=lookups
+ }
+ end
+ else
+ report("no coverage")
+ end
+ else
+ report("no coverage class")
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","unchainedcontext",subtype)
+ end
+ return {
+ format="class",
+ rules=rules,
+ }
+ elseif subtype==3 then
+ local nofglyphs=readushort(f)
+ local noflookups=readushort(f)
+ local current=readcardinaltable(f,nofglyphs,ushort)
+ local lookups=readlookuparray(f,noflookups,#current)
+ current=readcoveragearray(f,tableoffset,current,true)
+ return {
+ format="coverage",
+ rules={
+ {
+ current=current,
+ lookups=lookups,
+ }
+ }
+ }
+ else
+ report("unsupported subtype %a in %a %s",subtype,"unchainedcontext",what)
+ end
+end
+local function chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ coverage=readcoverage(f,tableoffset+coverage,true)
+ for i=1,#subclasssets do
+ local offset=subclasssets[i]
+ if offset>0 then
+ local firstcoverage=coverage[i]
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofbefore=readushort(f)
+ local before
+ if nofbefore>0 then
+ before={}
+ for i=1,nofbefore do
+ before[i]={ readushort(f) }
+ end
+ end
+ local nofcurrent=readushort(f)
+ local current={ { firstcoverage } }
+ for i=2,nofcurrent do
+ current[i]={ readushort(f) }
+ end
+ local nofafter=readushort(f)
+ local after
+ if nofafter>0 then
+ after={}
+ for i=1,nofafter do
+ after[i]={ readushort(f) }
+ end
+ end
+ local noflookups=readushort(f)
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ before=before,
+ current=current,
+ after=after,
+ lookups=lookups,
+ }
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","chainedcontext",subtype)
+ end
+ return {
+ format="glyphs",
+ rules=rules,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local beforeclassdef=readushort(f)
+ local currentclassdef=readushort(f)
+ local afterclassdef=readushort(f)
+ local subclasssets=readarray(f)
+ local rules={}
+ if subclasssets then
+ local coverage=readcoverage(f,tableoffset+coverage)
+ local beforeclassdef=readclassdef(f,tableoffset+beforeclassdef,nofglyphs)
+ local currentclassdef=readclassdef(f,tableoffset+currentclassdef,coverage)
+ local afterclassdef=readclassdef(f,tableoffset+afterclassdef,nofglyphs)
+ local beforeclasses=classtocoverage(beforeclassdef,fontdata.glyphs)
+ local currentclasses=classtocoverage(currentclassdef,fontdata.glyphs)
+ local afterclasses=classtocoverage(afterclassdef,fontdata.glyphs)
+ for class=1,#subclasssets do
+ local offset=subclasssets[class]
+ if offset>0 then
+ local firstcoverage=currentclasses[class]
+ if firstcoverage then
+ firstcoverage=covered(firstcoverage,coverage)
+ if firstcoverage then
+ local rulesoffset=tableoffset+offset
+ local subclassrules=readarray(f,rulesoffset)
+ for rule=1,#subclassrules do
+ setposition(f,rulesoffset+subclassrules[rule])
+ local nofbefore=readushort(f)
+ local before
+ if nofbefore>0 then
+ before={}
+ for i=1,nofbefore do
+ before[i]=beforeclasses[readushort(f)+1]
+ end
+ end
+ local nofcurrent=readushort(f)
+ local current={ firstcoverage }
+ for i=2,nofcurrent do
+ current[i]=currentclasses[readushort(f)+1]
+ end
+ local nofafter=readushort(f)
+ local after
+ if nofafter>0 then
+ after={}
+ for i=1,nofafter do
+ after[i]=afterclasses[readushort(f)+1]
+ end
+ end
+ local noflookups=readushort(f)
+ local lookups=readlookuparray(f,noflookups,nofcurrent)
+ rules[#rules+1]={
+ before=before,
+ current=current,
+ after=after,
+ lookups=lookups,
+ }
+ end
+ else
+ report("no coverage")
+ end
+ else
+ report("class is not covered")
+ end
+ end
+ end
+ else
+ report("empty subclassset in %a subtype %i","chainedcontext",subtype)
+ end
+ return {
+ format="class",
+ rules=rules,
+ }
+ elseif subtype==3 then
+ local before=readarray(f)
+ local current=readarray(f)
+ local after=readarray(f)
+ local noflookups=readushort(f)
+ local lookups=readlookuparray(f,noflookups,#current)
+ before=readcoveragearray(f,tableoffset,before,true)
+ current=readcoveragearray(f,tableoffset,current,true)
+ after=readcoveragearray(f,tableoffset,after,true)
+ return {
+ format="coverage",
+ rules={
+ {
+ before=before,
+ current=current,
+ after=after,
+ lookups=lookups,
+ }
+ }
+ }
+ else
+ report("unsupported subtype %a in %a %s",subtype,"chainedcontext",what)
+ end
+end
+local function extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,types,handlers,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local lookuptype=types[readushort(f)]
+ local faroffset=readulong(f)
+ local handler=handlers[lookuptype]
+ if handler then
+ return handler(f,fontdata,lookupid,tableoffset+faroffset,0,glyphs,nofglyphs),lookuptype
+ else
+ report("no handler for lookuptype %a subtype %a in %s %s",lookuptype,subtype,what,"extension")
+ end
+ else
+ report("unsupported subtype %a in %s %s",subtype,what,"extension")
+ end
+end
+function gsubhandlers.single(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local delta=readshort(f)
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index in next,coverage do
+ local newindex=(index+delta)%65536
+ if index>nofglyphs or newindex>nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)","single",subtype,index,newindex,nofglyphs)
+ coverage[index]=nil
+ else
+ coverage[index]=newindex
+ end
+ end
+ return {
+ coverage=coverage
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local nofreplacements=readushort(f)
+ local replacements=readcardinaltable(f,nofreplacements,ushort)
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ newindex=newindex+1
+ if index>nofglyphs or newindex>nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)","single",subtype,index,newindex,nofglyphs)
+ coverage[index]=nil
+ else
+ coverage[index]=replacements[newindex]
+ end
+ end
+ return {
+ coverage=coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"single")
+ end
+end
+local function sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,what)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local nofsequence=readushort(f)
+ local sequences=readcardinaltable(f,nofsequence,ushort)
+ for i=1,nofsequence do
+ setposition(f,tableoffset+sequences[i])
+ sequences[i]=readcardinaltable(f,readushort(f),ushort)
+ end
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ newindex=newindex+1
+ if index>nofglyphs or newindex>nofglyphs then
+ report("invalid index in %s format %i: %i -> %i (max %i)",what,subtype,index,newindex,nofglyphs)
+ coverage[index]=nil
+ else
+ coverage[index]=sequences[newindex]
+ end
+ end
+ return {
+ coverage=coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,what)
+ end
+end
+function gsubhandlers.multiple(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"multiple")
+end
+function gsubhandlers.alternate(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return sethandler(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"alternate")
+end
+function gsubhandlers.ligature(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local coverage=readushort(f)
+ local nofsets=readushort(f)
+ local ligatures=readcardinaltable(f,nofsets,ushort)
+ for i=1,nofsets do
+ local offset=lookupoffset+offset+ligatures[i]
+ setposition(f,offset)
+ local n=readushort(f)
+ if n==1 then
+ ligatures[i]={ offset+readushort(f) }
+ else
+ local l={}
+ for i=1,n do
+ l[i]=offset+readushort(f)
+ end
+ ligatures[i]=l
+ end
+ end
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ local hash={}
+ local ligatures=ligatures[newindex+1]
+ for i=1,#ligatures do
+ local offset=ligatures[i]
+ setposition(f,offset)
+ local lig=readushort(f)
+ local cnt=readushort(f)
+ local hsh=hash
+ for i=2,cnt do
+ local c=readushort(f)
+ local h=hsh[c]
+ if not h then
+ h={}
+ hsh[c]=h
+ end
+ hsh=h
+ end
+ hsh.ligature=lig
+ end
+ coverage[index]=hash
+ end
+ return {
+ coverage=coverage
+ }
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"ligature")
+ end
+end
+function gsubhandlers.context(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"substitution"),"context"
+end
+function gsubhandlers.chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"substitution"),"chainedcontext"
+end
+function gsubhandlers.extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,gsubtypes,gsubhandlers,"substitution")
+end
+function gsubhandlers.reversechainedcontextsingle(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ if subtype==1 then
+ local current=readfirst(f)
+ local before=readarray(f)
+ local after=readarray(f)
+ local replacements=readarray(f)
+ current=readcoveragearray(f,tableoffset,current,true)
+ before=readcoveragearray(f,tableoffset,before,true)
+ after=readcoveragearray(f,tableoffset,after,true)
+ return {
+ format="reversecoverage",
+ rules={
+ {
+ before=before,
+ current=current,
+ after=after,
+ replacements=replacements,
+ }
+ }
+ },"reversechainedcontextsingle"
+ else
+ report("unsupported subtype %a in %a substitution",subtype,"reversechainedcontextsingle")
+ end
+end
+local function readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+ local done={}
+ for i=1,#sets do
+ local offset=sets[i]
+ local reused=done[offset]
+ if not reused then
+ offset=tableoffset+offset
+ setposition(f,offset)
+ local n=readushort(f)
+ reused={}
+ for i=1,n do
+ reused[i]={
+ readushort(f),
+ readposition(f,format1,offset,getdelta),
+ readposition(f,format2,offset,getdelta),
+ }
+ end
+ done[offset]=reused
+ end
+ sets[i]=reused
+ end
+ return sets
+end
+local function readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,mainoffset,getdelta)
+ local classlist1={}
+ for i=1,nofclasses1 do
+ local classlist2={}
+ classlist1[i]=classlist2
+ for j=1,nofclasses2 do
+ local one=readposition(f,format1,mainoffset,getdelta)
+ local two=readposition(f,format2,mainoffset,getdelta)
+ if one or two then
+ classlist2[j]={ one,two }
+ else
+ classlist2[j]=false
+ end
+ end
+ end
+ return classlist1
+end
+function gposhandlers.single(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local coverage=readushort(f)
+ local format=readushort(f)
+ local value=readposition(f,format,tableoffset,getdelta)
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ coverage[index]=value
+ end
+ return {
+ format="single",
+ coverage=coverage,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local format=readushort(f)
+ local nofvalues=readushort(f)
+ local values={}
+ for i=1,nofvalues do
+ values[i]=readposition(f,format,tableoffset,getdelta)
+ end
+ local coverage=readcoverage(f,tableoffset+coverage)
+ for index,newindex in next,coverage do
+ coverage[index]=values[newindex+1]
+ end
+ return {
+ format="single",
+ coverage=coverage,
+ }
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"single")
+ end
+end
+function gposhandlers.pair(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local coverage=readushort(f)
+ local format1=readushort(f)
+ local format2=readushort(f)
+ local sets=readarray(f)
+ sets=readpairsets(f,tableoffset,sets,format1,format2,mainoffset,getdelta)
+ coverage=readcoverage(f,tableoffset+coverage)
+ local shared={}
+ for index,newindex in next,coverage do
+ local set=sets[newindex+1]
+ local hash={}
+ for i=1,#set do
+ local value=set[i]
+ if value then
+ local other=value[1]
+ local share=shared[value]
+ if share==nil then
+ local first=value[2]
+ local second=value[3]
+ if first or second then
+ share={ first,second or nil }
+ else
+ share=false
+ end
+ shared[value]=share
+ end
+ hash[other]=share or nil
+ end
+ end
+ coverage[index]=hash
+ end
+ return {
+ shared=shared and true or nil,
+ format="pair",
+ coverage=coverage,
+ }
+ elseif subtype==2 then
+ local coverage=readushort(f)
+ local format1=readushort(f)
+ local format2=readushort(f)
+ local classdef1=readushort(f)
+ local classdef2=readushort(f)
+ local nofclasses1=readushort(f)
+ local nofclasses2=readushort(f)
+ local classlist=readpairclasssets(f,nofclasses1,nofclasses2,format1,format2,tableoffset,getdelta)
+ coverage=readcoverage(f,tableoffset+coverage)
+ classdef1=readclassdef(f,tableoffset+classdef1,coverage)
+ classdef2=readclassdef(f,tableoffset+classdef2,nofglyphs)
+ local usedcoverage={}
+ local shared={}
+ for g1,c1 in next,classdef1 do
+ if coverage[g1] then
+ local l1=classlist[c1]
+ if l1 then
+ local hash={}
+ for paired,class in next,classdef2 do
+ local offsets=l1[class]
+ if offsets then
+ local first=offsets[1]
+ local second=offsets[2]
+ if first or second then
+ local s1=shared[first]
+ if s1==nil then
+ s1={}
+ shared[first]=s1
+ end
+ local s2=s1[second]
+ if s2==nil then
+ s2={ first,second or nil }
+ s1[second]=s2
+ end
+ hash[paired]=s2
+ end
+ end
+ end
+ usedcoverage[g1]=hash
+ end
+ end
+ end
+ return {
+ shared=shared and true or nil,
+ format="pair",
+ coverage=usedcoverage,
+ }
+ elseif subtype==3 then
+ report("yet unsupported subtype %a in %a positioning",subtype,"pair")
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"pair")
+ end
+end
+function gposhandlers.cursive(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local coverage=tableoffset+readushort(f)
+ local nofrecords=readushort(f)
+ local records={}
+ for i=1,nofrecords do
+ local entry=readushort(f)
+ local exit=readushort(f)
+ records[i]={
+ entry~=0 and (tableoffset+entry) or false,
+ exit~=0 and (tableoffset+exit ) or nil,
+ }
+ end
+ local cc=(fontdata.temporary.cursivecount or 0)+1
+ fontdata.temporary.cursivecount=cc
+ cc="cc-"..cc
+ coverage=readcoverage(f,coverage)
+ for i=1,nofrecords do
+ local r=records[i]
+ records[i]={
+ cc,
+ readanchor(f,r[1],getdelta) or false,
+ readanchor(f,r[2],getdelta) or nil,
+ }
+ end
+ for index,newindex in next,coverage do
+ coverage[index]=records[newindex+1]
+ end
+ return {
+ coverage=coverage,
+ }
+ else
+ report("unsupported subtype %a in %a positioning",subtype,"cursive")
+ end
+end
+local function handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,ligature)
+ local tableoffset=lookupoffset+offset
+ setposition(f,tableoffset)
+ local subtype=readushort(f)
+ local getdelta=fontdata.temporary.getdelta
+ if subtype==1 then
+ local markcoverage=tableoffset+readushort(f)
+ local basecoverage=tableoffset+readushort(f)
+ local nofclasses=readushort(f)
+ local markoffset=tableoffset+readushort(f)
+ local baseoffset=tableoffset+readushort(f)
+ local markcoverage=readcoverage(f,markcoverage)
+ local basecoverage=readcoverage(f,basecoverage,true)
+ setposition(f,markoffset)
+ local markclasses={}
+ local nofmarkclasses=readushort(f)
+ local lastanchor=fontdata.lastanchor or 0
+ local usedanchors={}
+ for i=1,nofmarkclasses do
+ local class=readushort(f)+1
+ local offset=readushort(f)
+ if offset==0 then
+ markclasses[i]=false
+ else
+ markclasses[i]={ class,markoffset+offset }
+ end
+ usedanchors[class]=true
+ end
+ for i=1,nofmarkclasses do
+ local mc=markclasses[i]
+ if mc then
+ mc[2]=readanchor(f,mc[2],getdelta)
+ end
+ end
+ setposition(f,baseoffset)
+ local nofbaserecords=readushort(f)
+ local baserecords={}
+ if ligature then
+ for i=1,nofbaserecords do
+ local offset=readushort(f)
+ if offset==0 then
+ baserecords[i]=false
+ else
+ baserecords[i]=baseoffset+offset
+ end
+ end
+ for i=1,nofbaserecords do
+ local recordoffset=baserecords[i]
+ if recordoffset then
+ setposition(f,recordoffset)
+ local nofcomponents=readushort(f)
+ local components={}
+ for i=1,nofcomponents do
+ local classes={}
+ for i=1,nofclasses do
+ local offset=readushort(f)
+ if offset~=0 then
+ classes[i]=recordoffset+offset
+ else
+ classes[i]=false
+ end
+ end
+ components[i]=classes
+ end
+ baserecords[i]=components
+ end
+ end
+ local baseclasses={}
+ for i=1,nofclasses do
+ baseclasses[i]={}
+ end
+ for i=1,nofbaserecords do
+ local components=baserecords[i]
+ if components then
+ local b=basecoverage[i]
+ for c=1,#components do
+ local classes=components[c]
+ if classes then
+ for i=1,nofclasses do
+ local anchor=readanchor(f,classes[i],getdelta)
+ local bclass=baseclasses[i]
+ local bentry=bclass[b]
+ if bentry then
+ bentry[c]=anchor
+ else
+ bclass[b]={ [c]=anchor }
+ end
+ end
+ end
+ end
+ end
+ end
+ for index,newindex in next,markcoverage do
+ markcoverage[index]=markclasses[newindex+1] or nil
+ end
+ return {
+ format="ligature",
+ baseclasses=baseclasses,
+ coverage=markcoverage,
+ }
+ else
+ for i=1,nofbaserecords do
+ local r={}
+ for j=1,nofclasses do
+ local offset=readushort(f)
+ if offset==0 then
+ r[j]=false
+ else
+ r[j]=baseoffset+offset
+ end
+ end
+ baserecords[i]=r
+ end
+ local baseclasses={}
+ for i=1,nofclasses do
+ baseclasses[i]={}
+ end
+ for i=1,nofbaserecords do
+ local r=baserecords[i]
+ local b=basecoverage[i]
+ for j=1,nofclasses do
+ baseclasses[j][b]=readanchor(f,r[j],getdelta)
+ end
+ end
+ for index,newindex in next,markcoverage do
+ markcoverage[index]=markclasses[newindex+1] or nil
+ end
+ return {
+ format="base",
+ baseclasses=baseclasses,
+ coverage=markcoverage,
+ }
+ end
+ else
+ report("unsupported subtype %a in",subtype)
+ end
+end
+function gposhandlers.marktobase(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+end
+function gposhandlers.marktoligature(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,true)
+end
+function gposhandlers.marktomark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return handlemark(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+end
+function gposhandlers.context(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return unchainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"positioning"),"context"
+end
+function gposhandlers.chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return chainedcontext(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,"positioning"),"chainedcontext"
+end
+function gposhandlers.extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs)
+ return extension(f,fontdata,lookupid,lookupoffset,offset,glyphs,nofglyphs,gpostypes,gposhandlers,"positioning")
+end
+do
+ local plugins={}
+ function plugins.size(f,fontdata,tableoffset,feature)
+ if fontdata.designsize then
+ else
+ local function check(offset)
+ setposition(f,offset)
+ local designsize=readushort(f)
+ if designsize>0 then
+ local fontstyleid=readushort(f)
+ local guimenuid=readushort(f)
+ local minsize=readushort(f)
+ local maxsize=readushort(f)
+ if minsize==0 and maxsize==0 and fontstyleid==0 and guimenuid==0 then
+ minsize=designsize
+ maxsize=designsize
+ end
+ if designsize>=minsize and designsize<=maxsize then
+ return minsize,maxsize,designsize
+ end
+ end
+ end
+ local minsize,maxsize,designsize=check(tableoffset+feature.offset+feature.parameters)
+ if not designsize then
+ minsize,maxsize,designsize=check(tableoffset+feature.parameters)
+ if designsize then
+ report("bad size feature in %a, falling back to wrong offset",fontdata.filename or "?")
+ else
+ report("bad size feature in %a,",fontdata.filename or "?")
+ end
+ end
+ if designsize then
+ fontdata.minsize=minsize
+ fontdata.maxsize=maxsize
+ fontdata.designsize=designsize
+ end
+ end
+ end
+ local function reorderfeatures(fontdata,scripts,features)
+ local scriptlangs={}
+ local featurehash={}
+ local featureorder={}
+ for script,languages in next,scripts do
+ for language,record in next,languages do
+ local hash={}
+ local list=record.featureindices
+ for k=1,#list do
+ local index=list[k]
+ local feature=features[index]
+ local lookups=feature.lookups
+ local tag=feature.tag
+ if tag then
+ hash[tag]=true
+ end
+ if lookups then
+ for i=1,#lookups do
+ local lookup=lookups[i]
+ local o=featureorder[lookup]
+ if o then
+ local okay=true
+ for i=1,#o do
+ if o[i]==tag then
+ okay=false
+ break
+ end
+ end
+ if okay then
+ o[#o+1]=tag
+ end
+ else
+ featureorder[lookup]={ tag }
+ end
+ local f=featurehash[lookup]
+ if f then
+ local h=f[tag]
+ if h then
+ local s=h[script]
+ if s then
+ s[language]=true
+ else
+ h[script]={ [language]=true }
+ end
+ else
+ f[tag]={ [script]={ [language]=true } }
+ end
+ else
+ featurehash[lookup]={ [tag]={ [script]={ [language]=true } } }
+ end
+ local h=scriptlangs[tag]
+ if h then
+ local s=h[script]
+ if s then
+ s[language]=true
+ else
+ h[script]={ [language]=true }
+ end
+ else
+ scriptlangs[tag]={ [script]={ [language]=true } }
+ end
+ end
+ end
+ end
+ end
+ end
+ return scriptlangs,featurehash,featureorder
+ end
+ local function readscriplan(f,fontdata,scriptoffset)
+ setposition(f,scriptoffset)
+ local nofscripts=readushort(f)
+ local scripts={}
+ for i=1,nofscripts do
+ scripts[readtag(f)]=scriptoffset+readushort(f)
+ end
+ local languagesystems=setmetatableindex("table")
+ for script,offset in next,scripts do
+ setposition(f,offset)
+ local defaultoffset=readushort(f)
+ local noflanguages=readushort(f)
+ local languages={}
+ if defaultoffset>0 then
+ languages.dflt=languagesystems[offset+defaultoffset]
+ end
+ for i=1,noflanguages do
+ local language=readtag(f)
+ local offset=offset+readushort(f)
+ languages[language]=languagesystems[offset]
+ end
+ scripts[script]=languages
+ end
+ for offset,usedfeatures in next,languagesystems do
+ if offset>0 then
+ setposition(f,offset)
+ local featureindices={}
+ usedfeatures.featureindices=featureindices
+ usedfeatures.lookuporder=readushort(f)
+ usedfeatures.requiredindex=readushort(f)
+ local noffeatures=readushort(f)
+ for i=1,noffeatures do
+ featureindices[i]=readushort(f)+1
+ end
+ end
+ end
+ return scripts
+ end
+ local function readfeatures(f,fontdata,featureoffset)
+ setposition(f,featureoffset)
+ local features={}
+ local noffeatures=readushort(f)
+ for i=1,noffeatures do
+ features[i]={
+ tag=readtag(f),
+ offset=readushort(f)
+ }
+ end
+ for i=1,noffeatures do
+ local feature=features[i]
+ local offset=featureoffset+feature.offset
+ setposition(f,offset)
+ local parameters=readushort(f)
+ local noflookups=readushort(f)
+ if noflookups>0 then
+ local lookups=readcardinaltable(f,noflookups,ushort)
+ feature.lookups=lookups
+ for j=1,noflookups do
+ lookups[j]=lookups[j]+1
+ end
+ end
+ if parameters>0 then
+ feature.parameters=parameters
+ local plugin=plugins[feature.tag]
+ if plugin then
+ plugin(f,fontdata,featureoffset,feature)
+ end
+ end
+ end
+ return features
+ end
+ local function readlookups(f,lookupoffset,lookuptypes,featurehash,featureorder)
+ setposition(f,lookupoffset)
+ local noflookups=readushort(f)
+ local lookups=readcardinaltable(f,noflookups,ushort)
+ for lookupid=1,noflookups do
+ local offset=lookups[lookupid]
+ setposition(f,lookupoffset+offset)
+ local subtables={}
+ local typebits=readushort(f)
+ local flagbits=readushort(f)
+ local lookuptype=lookuptypes[typebits]
+ local lookupflags=lookupflags[flagbits]
+ local nofsubtables=readushort(f)
+ for j=1,nofsubtables do
+ subtables[j]=offset+readushort(f)
+ end
+ local markclass=band(flagbits,0x0010)~=0
+ if markclass then
+ markclass=readushort(f)
+ end
+ local markset=rshift(flagbits,8)
+ if markset>0 then
+ markclass=markset
+ end
+ lookups[lookupid]={
+ type=lookuptype,
+ flags=lookupflags,
+ name=lookupid,
+ subtables=subtables,
+ markclass=markclass,
+ features=featurehash[lookupid],
+ order=featureorder[lookupid],
+ }
+ end
+ return lookups
+ end
+ local f_lookupname=formatters["%s_%s_%s"]
+ local function resolvelookups(f,lookupoffset,fontdata,lookups,lookuptypes,lookuphandlers,what,tableoffset)
+ local sequences=fontdata.sequences or {}
+ local sublookuplist=fontdata.sublookups or {}
+ fontdata.sequences=sequences
+ fontdata.sublookups=sublookuplist
+ local nofsublookups=#sublookuplist
+ local nofsequences=#sequences
+ local lastsublookup=nofsublookups
+ local lastsequence=nofsequences
+ local lookupnames=lookupnames[what]
+ local sublookuphash={}
+ local sublookupcheck={}
+ local glyphs=fontdata.glyphs
+ local nofglyphs=fontdata.nofglyphs or #glyphs
+ local noflookups=#lookups
+ local lookupprefix=sub(what,2,2)
+ local usedlookups=false
+ for lookupid=1,noflookups do
+ local lookup=lookups[lookupid]
+ local lookuptype=lookup.type
+ local subtables=lookup.subtables
+ local features=lookup.features
+ local handler=lookuphandlers[lookuptype]
+ if handler then
+ local nofsubtables=#subtables
+ local order=lookup.order
+ local flags=lookup.flags
+ if flags[1] then flags[1]="mark" end
+ if flags[2] then flags[2]="ligature" end
+ if flags[3] then flags[3]="base" end
+ local markclass=lookup.markclass
+ if nofsubtables>0 then
+ local steps={}
+ local nofsteps=0
+ local oldtype=nil
+ for s=1,nofsubtables do
+ local step,lt=handler(f,fontdata,lookupid,lookupoffset,subtables[s],glyphs,nofglyphs)
+ if lt then
+ lookuptype=lt
+ if oldtype and lt~=oldtype then
+ report("messy %s lookup type %a and %a",what,lookuptype,oldtype)
+ end
+ oldtype=lookuptype
+ end
+ if not step then
+ report("unsupported %s lookup type %a",what,lookuptype)
+ else
+ nofsteps=nofsteps+1
+ steps[nofsteps]=step
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local before=rule.before
+ local current=rule.current
+ local after=rule.after
+ local replacements=rule.replacements
+ if before then
+ for i=1,#before do
+ before[i]=tohash(before[i])
+ end
+ rule.before=reversed(before)
+ end
+ if current then
+ if replacements then
+ local first=current[1]
+ local hash={}
+ local repl={}
+ for i=1,#first do
+ local c=first[i]
+ hash[c]=true
+ repl[c]=replacements[i]
+ end
+ rule.current={ hash }
+ rule.replacements=repl
+ else
+ for i=1,#current do
+ current[i]=tohash(current[i])
+ end
+ end
+ else
+ end
+ if after then
+ for i=1,#after do
+ after[i]=tohash(after[i])
+ end
+ end
+ if usedlookups then
+ local lookups=rule.lookups
+ if lookups then
+ for k,v in next,lookups do
+ if v then
+ for k,v in next,v do
+ usedlookups[v]=usedlookups[v]+1
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if nofsteps~=nofsubtables then
+ report("bogus subtables removed in %s lookup type %a",what,lookuptype)
+ end
+ lookuptype=lookupnames[lookuptype] or lookuptype
+ if features then
+ nofsequences=nofsequences+1
+ local l={
+ index=nofsequences,
+ name=f_lookupname(lookupprefix,"s",lookupid+lookupidoffset),
+ steps=steps,
+ nofsteps=nofsteps,
+ type=lookuptype,
+ markclass=markclass or nil,
+ flags=flags,
+ order=order,
+ features=features,
+ }
+ sequences[nofsequences]=l
+ lookup.done=l
+ else
+ nofsublookups=nofsublookups+1
+ local l={
+ index=nofsublookups,
+ name=f_lookupname(lookupprefix,"l",lookupid+lookupidoffset),
+ steps=steps,
+ nofsteps=nofsteps,
+ type=lookuptype,
+ markclass=markclass or nil,
+ flags=flags,
+ }
+ sublookuplist[nofsublookups]=l
+ sublookuphash[lookupid]=nofsublookups
+ sublookupcheck[lookupid]=0
+ lookup.done=l
+ end
+ else
+ report("no subtables for lookup %a",lookupid)
+ end
+ else
+ report("no handler for lookup %a with type %a",lookupid,lookuptype)
+ end
+ end
+ if usedlookups then
+ report("used %s lookups: % t",what,sortedkeys(usedlookups))
+ end
+ local reported={}
+ local function report_issue(i,what,sequence,kind)
+ local name=sequence.name
+ if not reported[name] then
+ report("rule %i in %s lookup %a has %s lookups",i,what,name,kind)
+ reported[name]=true
+ end
+ end
+ for i=lastsequence+1,nofsequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ for i=1,#steps do
+ local step=steps[i]
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local rlookups=rule.lookups
+ if not rlookups then
+ report_issue(i,what,sequence,"no")
+ elseif not next(rlookups) then
+ rule.lookups=nil
+ else
+ local length=#rlookups
+ for index=1,length do
+ local lookuplist=rlookups[index]
+ if lookuplist then
+ local length=#lookuplist
+ local found={}
+ local noffound=0
+ for index=1,length do
+ local lookupid=lookuplist[index]
+ if lookupid then
+ local h=sublookuphash[lookupid]
+ if not h then
+ local lookup=lookups[lookupid]
+ if lookup then
+ local d=lookup.done
+ if d then
+ nofsublookups=nofsublookups+1
+ local l={
+ index=nofsublookups,
+ name=f_lookupname(lookupprefix,"d",lookupid+lookupidoffset),
+ derived=true,
+ steps=d.steps,
+ nofsteps=d.nofsteps,
+ type=d.lookuptype or "gsub_single",
+ markclass=d.markclass or nil,
+ flags=d.flags,
+ }
+ sublookuplist[nofsublookups]=copy(l)
+ sublookuphash[lookupid]=nofsublookups
+ sublookupcheck[lookupid]=1
+ h=nofsublookups
+ else
+ report_issue(i,what,sequence,"missing")
+ rule.lookups=nil
+ break
+ end
+ else
+ report_issue(i,what,sequence,"bad")
+ rule.lookups=nil
+ break
+ end
+ else
+ sublookupcheck[lookupid]=sublookupcheck[lookupid]+1
+ end
+ if h then
+ noffound=noffound+1
+ found[noffound]=h
+ end
+ end
+ end
+ rlookups[index]=noffound>0 and found or false
+ else
+ rlookups[index]=false
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ for i,n in sortedhash(sublookupcheck) do
+ local l=lookups[i]
+ local t=l.type
+ if n==0 and t~="extension" then
+ local d=l.done
+ report("%s lookup %s of type %a is not used",what,d and d.name or l.name,t)
+ end
+ end
+ end
+ local function loadvariations(f,fontdata,variationsoffset,lookuptypes,featurehash,featureorder)
+ setposition(f,variationsoffset)
+ local version=readulong(f)
+ local nofrecords=readulong(f)
+ local records={}
+ for i=1,nofrecords do
+ records[i]={
+ conditions=readulong(f),
+ substitutions=readulong(f),
+ }
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ local offset=record.conditions
+ if offset==0 then
+ record.condition=nil
+ record.matchtype="always"
+ else
+ local offset=variationsoffset+offset
+ setposition(f,offset)
+ local nofconditions=readushort(f)
+ local conditions={}
+ for i=1,nofconditions do
+ conditions[i]=offset+readulong(f)
+ end
+ record.conditions=conditions
+ record.matchtype="condition"
+ end
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ if record.matchtype=="condition" then
+ local conditions=record.conditions
+ for i=1,#conditions do
+ setposition(f,conditions[i])
+ conditions[i]={
+ format=readushort(f),
+ axis=readushort(f),
+ minvalue=read2dot14(f),
+ maxvalue=read2dot14(f),
+ }
+ end
+ end
+ end
+ for i=1,nofrecords do
+ local record=records[i]
+ local offset=record.substitutions
+ if offset==0 then
+ record.substitutions={}
+ else
+ setposition(f,variationsoffset+offset)
+ local version=readulong(f)
+ local nofsubstitutions=readushort(f)
+ local substitutions={}
+ for i=1,nofsubstitutions do
+ substitutions[readushort(f)]=readulong(f)
+ end
+ for index,alternates in sortedhash(substitutions) do
+ if index==0 then
+ record.substitutions=false
+ else
+ local tableoffset=variationsoffset+offset+alternates
+ setposition(f,tableoffset)
+ local parameters=readulong(f)
+ local noflookups=readushort(f)
+ local lookups=readcardinaltable(f,noflookups,ushort)
+ record.substitutions=lookups
+ end
+ end
+ end
+ end
+ setvariabledata(fontdata,"features",records)
+ end
+ local function readscripts(f,fontdata,what,lookuptypes,lookuphandlers,lookupstoo)
+ local tableoffset=gotodatatable(f,fontdata,what,true)
+ if tableoffset then
+ local version=readulong(f)
+ local scriptoffset=tableoffset+readushort(f)
+ local featureoffset=tableoffset+readushort(f)
+ local lookupoffset=tableoffset+readushort(f)
+ local variationsoffset=version>0x00010000 and (tableoffset+readulong(f)) or 0
+ if not scriptoffset then
+ return
+ end
+ local scripts=readscriplan(f,fontdata,scriptoffset)
+ local features=readfeatures(f,fontdata,featureoffset)
+ local scriptlangs,featurehash,featureorder=reorderfeatures(fontdata,scripts,features)
+ if fontdata.features then
+ fontdata.features[what]=scriptlangs
+ else
+ fontdata.features={ [what]=scriptlangs }
+ end
+ if not lookupstoo then
+ return
+ end
+ local lookups=readlookups(f,lookupoffset,lookuptypes,featurehash,featureorder)
+ if lookups then
+ resolvelookups(f,lookupoffset,fontdata,lookups,lookuptypes,lookuphandlers,what,tableoffset)
+ end
+ if variationsoffset>0 then
+ loadvariations(f,fontdata,variationsoffset,lookuptypes,featurehash,featureorder)
+ end
+ end
+ end
+ local function checkkerns(f,fontdata,specification)
+ local datatable=fontdata.tables.kern
+ if not datatable then
+ return
+ end
+ local features=fontdata.features
+ local gposfeatures=features and features.gpos
+ local name
+ if not gposfeatures or not gposfeatures.kern then
+ name="kern"
+ elseif specification.globalkerns then
+ name="globalkern"
+ else
+ report("ignoring global kern table, using gpos kern feature")
+ return
+ end
+ setposition(f,datatable.offset)
+ local version=readushort(f)
+ local noftables=readushort(f)
+ if noftables>1 then
+ report("adding global kern table as gpos feature %a",name)
+ local kerns=setmetatableindex("table")
+ for i=1,noftables do
+ local version=readushort(f)
+ local length=readushort(f)
+ local coverage=readushort(f)
+ local format=rshift(coverage,8)
+ if format==0 then
+ local nofpairs=readushort(f)
+ local searchrange=readushort(f)
+ local entryselector=readushort(f)
+ local rangeshift=readushort(f)
+ for i=1,nofpairs do
+ kerns[readushort(f)][readushort(f)]=readfword(f)
+ end
+ elseif format==2 then
+ else
+ end
+ end
+ local feature={ dflt={ dflt=true } }
+ if not features then
+ fontdata.features={ gpos={ [name]=feature } }
+ elseif not gposfeatures then
+ fontdata.features.gpos={ [name]=feature }
+ else
+ gposfeatures[name]=feature
+ end
+ local sequences=fontdata.sequences
+ if not sequences then
+ sequences={}
+ fontdata.sequences=sequences
+ end
+ local nofsequences=#sequences+1
+ sequences[nofsequences]={
+ index=nofsequences,
+ name=name,
+ steps={
+ {
+ coverage=kerns,
+ format="kern",
+ },
+ },
+ nofsteps=1,
+ type="gpos_pair",
+ flags={ false,false,false,false },
+ order={ name },
+ features={ [name]=feature },
+ }
+ else
+ report("ignoring empty kern table of feature %a",name)
+ end
+ end
+ function readers.gsub(f,fontdata,specification)
+ if specification.details then
+ readscripts(f,fontdata,"gsub",gsubtypes,gsubhandlers,specification.lookups)
+ end
+ end
+ function readers.gpos(f,fontdata,specification)
+ if specification.details then
+ readscripts(f,fontdata,"gpos",gpostypes,gposhandlers,specification.lookups)
+ if specification.lookups then
+ checkkerns(f,fontdata,specification)
+ end
+ end
+ end
+end
+function readers.gdef(f,fontdata,specification)
+ if not specification.glyphs then
+ return
+ end
+ local datatable=fontdata.tables.gdef
+ if datatable then
+ local tableoffset=datatable.offset
+ setposition(f,tableoffset)
+ local version=readulong(f)
+ local classoffset=readushort(f)
+ local attachmentoffset=readushort(f)
+ local ligaturecarets=readushort(f)
+ local markclassoffset=readushort(f)
+ local marksetsoffset=version>=0x00010002 and readushort(f) or 0
+ local varsetsoffset=version>=0x00010003 and readulong(f) or 0
+ local glyphs=fontdata.glyphs
+ local marks={}
+ local markclasses=setmetatableindex("table")
+ local marksets=setmetatableindex("table")
+ fontdata.marks=marks
+ fontdata.markclasses=markclasses
+ fontdata.marksets=marksets
+ if classoffset~=0 then
+ setposition(f,tableoffset+classoffset)
+ local classformat=readushort(f)
+ if classformat==1 then
+ local firstindex=readushort(f)
+ local lastindex=firstindex+readushort(f)-1
+ for index=firstindex,lastindex do
+ local class=classes[readushort(f)]
+ if class=="mark" then
+ marks[index]=true
+ end
+ glyphs[index].class=class
+ end
+ elseif classformat==2 then
+ local nofranges=readushort(f)
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local class=classes[readushort(f)]
+ if class then
+ for index=firstindex,lastindex do
+ glyphs[index].class=class
+ if class=="mark" then
+ marks[index]=true
+ end
+ end
+ end
+ end
+ end
+ end
+ if markclassoffset~=0 then
+ setposition(f,tableoffset+markclassoffset)
+ local classformat=readushort(f)
+ if classformat==1 then
+ local firstindex=readushort(f)
+ local lastindex=firstindex+readushort(f)-1
+ for index=firstindex,lastindex do
+ markclasses[readushort(f)][index]=true
+ end
+ elseif classformat==2 then
+ local nofranges=readushort(f)
+ for i=1,nofranges do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local class=markclasses[readushort(f)]
+ for index=firstindex,lastindex do
+ class[index]=true
+ end
+ end
+ end
+ end
+ if marksetsoffset~=0 then
+ marksetsoffset=tableoffset+marksetsoffset
+ setposition(f,marksetsoffset)
+ local format=readushort(f)
+ if format==1 then
+ local nofsets=readushort(f)
+ local sets=readcardinaltable(f,nofsets,ulong)
+ for i=1,nofsets do
+ local offset=sets[i]
+ if offset~=0 then
+ marksets[i]=readcoverage(f,marksetsoffset+offset)
+ end
+ end
+ end
+ end
+ local factors=specification.factors
+ if (specification.variable or factors) and varsetsoffset~=0 then
+ local regions,deltas=readvariationdata(f,tableoffset+varsetsoffset,factors)
+ if factors then
+ fontdata.temporary.getdelta=function(outer,inner)
+ local delta=deltas[outer+1]
+ if delta then
+ local d=delta.deltas[inner+1]
+ if d then
+ local scales=delta.scales
+ local dd=0
+ for i=1,#scales do
+ local di=d[i]
+ if di then
+ dd=dd+scales[i]*di
+ else
+ break
+ end
+ end
+ return round(dd)
+ end
+ end
+ return 0
+ end
+ end
+ end
+ end
+end
+local function readmathvalue(f)
+ local v=readshort(f)
+ skipshort(f,1)
+ return v
+end
+local function readmathconstants(f,fontdata,offset)
+ setposition(f,offset)
+ fontdata.mathconstants={
+ ScriptPercentScaleDown=readshort(f),
+ ScriptScriptPercentScaleDown=readshort(f),
+ DelimitedSubFormulaMinHeight=readushort(f),
+ DisplayOperatorMinHeight=readushort(f),
+ MathLeading=readmathvalue(f),
+ AxisHeight=readmathvalue(f),
+ AccentBaseHeight=readmathvalue(f),
+ FlattenedAccentBaseHeight=readmathvalue(f),
+ SubscriptShiftDown=readmathvalue(f),
+ SubscriptTopMax=readmathvalue(f),
+ SubscriptBaselineDropMin=readmathvalue(f),
+ SuperscriptShiftUp=readmathvalue(f),
+ SuperscriptShiftUpCramped=readmathvalue(f),
+ SuperscriptBottomMin=readmathvalue(f),
+ SuperscriptBaselineDropMax=readmathvalue(f),
+ SubSuperscriptGapMin=readmathvalue(f),
+ SuperscriptBottomMaxWithSubscript=readmathvalue(f),
+ SpaceAfterScript=readmathvalue(f),
+ UpperLimitGapMin=readmathvalue(f),
+ UpperLimitBaselineRiseMin=readmathvalue(f),
+ LowerLimitGapMin=readmathvalue(f),
+ LowerLimitBaselineDropMin=readmathvalue(f),
+ StackTopShiftUp=readmathvalue(f),
+ StackTopDisplayStyleShiftUp=readmathvalue(f),
+ StackBottomShiftDown=readmathvalue(f),
+ StackBottomDisplayStyleShiftDown=readmathvalue(f),
+ StackGapMin=readmathvalue(f),
+ StackDisplayStyleGapMin=readmathvalue(f),
+ StretchStackTopShiftUp=readmathvalue(f),
+ StretchStackBottomShiftDown=readmathvalue(f),
+ StretchStackGapAboveMin=readmathvalue(f),
+ StretchStackGapBelowMin=readmathvalue(f),
+ FractionNumeratorShiftUp=readmathvalue(f),
+ FractionNumeratorDisplayStyleShiftUp=readmathvalue(f),
+ FractionDenominatorShiftDown=readmathvalue(f),
+ FractionDenominatorDisplayStyleShiftDown=readmathvalue(f),
+ FractionNumeratorGapMin=readmathvalue(f),
+ FractionNumeratorDisplayStyleGapMin=readmathvalue(f),
+ FractionRuleThickness=readmathvalue(f),
+ FractionDenominatorGapMin=readmathvalue(f),
+ FractionDenominatorDisplayStyleGapMin=readmathvalue(f),
+ SkewedFractionHorizontalGap=readmathvalue(f),
+ SkewedFractionVerticalGap=readmathvalue(f),
+ OverbarVerticalGap=readmathvalue(f),
+ OverbarRuleThickness=readmathvalue(f),
+ OverbarExtraAscender=readmathvalue(f),
+ UnderbarVerticalGap=readmathvalue(f),
+ UnderbarRuleThickness=readmathvalue(f),
+ UnderbarExtraDescender=readmathvalue(f),
+ RadicalVerticalGap=readmathvalue(f),
+ RadicalDisplayStyleVerticalGap=readmathvalue(f),
+ RadicalRuleThickness=readmathvalue(f),
+ RadicalExtraAscender=readmathvalue(f),
+ RadicalKernBeforeDegree=readmathvalue(f),
+ RadicalKernAfterDegree=readmathvalue(f),
+ RadicalDegreeBottomRaisePercent=readshort(f),
+ }
+end
+local function readmathglyphinfo(f,fontdata,offset)
+ setposition(f,offset)
+ local italics=readushort(f)
+ local accents=readushort(f)
+ local extensions=readushort(f)
+ local kerns=readushort(f)
+ local glyphs=fontdata.glyphs
+ if italics~=0 then
+ setposition(f,offset+italics)
+ local coverage=readushort(f)
+ local nofglyphs=readushort(f)
+ coverage=readcoverage(f,offset+italics+coverage,true)
+ setposition(f,offset+italics+4)
+ for i=1,nofglyphs do
+ local italic=readmathvalue(f)
+ if italic~=0 then
+ local glyph=glyphs[coverage[i]]
+ local math=glyph.math
+ if not math then
+ glyph.math={ italic=italic }
+ else
+ math.italic=italic
+ end
+ end
+ end
+ fontdata.hasitalics=true
+ end
+ if accents~=0 then
+ setposition(f,offset+accents)
+ local coverage=readushort(f)
+ local nofglyphs=readushort(f)
+ coverage=readcoverage(f,offset+accents+coverage,true)
+ setposition(f,offset+accents+4)
+ for i=1,nofglyphs do
+ local accent=readmathvalue(f)
+ if accent~=0 then
+ local glyph=glyphs[coverage[i]]
+ local math=glyph.math
+ if not math then
+ glyph.math={ accent=accent }
+ else
+ math.accent=accent
+ end
+ end
+ end
+ end
+ if extensions~=0 then
+ setposition(f,offset+extensions)
+ end
+ if kerns~=0 then
+ local kernoffset=offset+kerns
+ setposition(f,kernoffset)
+ local coverage=readushort(f)
+ local nofglyphs=readushort(f)
+ if nofglyphs>0 then
+ local function get(offset)
+ setposition(f,kernoffset+offset)
+ local n=readushort(f)
+ if n==0 then
+ local k=readmathvalue(f)
+ if k==0 then
+ else
+ return { { kern=k } }
+ end
+ else
+ local l={}
+ for i=1,n do
+ l[i]={ height=readmathvalue(f) }
+ end
+ for i=1,n do
+ l[i].kern=readmathvalue(f)
+ end
+ l[n+1]={ kern=readmathvalue(f) }
+ return l
+ end
+ end
+ local kernsets={}
+ for i=1,nofglyphs do
+ local topright=readushort(f)
+ local topleft=readushort(f)
+ local bottomright=readushort(f)
+ local bottomleft=readushort(f)
+ kernsets[i]={
+ topright=topright~=0 and topright or nil,
+ topleft=topleft~=0 and topleft or nil,
+ bottomright=bottomright~=0 and bottomright or nil,
+ bottomleft=bottomleft~=0 and bottomleft or nil,
+ }
+ end
+ coverage=readcoverage(f,kernoffset+coverage,true)
+ for i=1,nofglyphs do
+ local kernset=kernsets[i]
+ if next(kernset) then
+ local k=kernset.topright if k then kernset.topright=get(k) end
+ local k=kernset.topleft if k then kernset.topleft=get(k) end
+ local k=kernset.bottomright if k then kernset.bottomright=get(k) end
+ local k=kernset.bottomleft if k then kernset.bottomleft=get(k) end
+ if next(kernset) then
+ local glyph=glyphs[coverage[i]]
+ local math=glyph.math
+ if math then
+ math.kerns=kernset
+ else
+ glyph.math={ kerns=kernset }
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local function readmathvariants(f,fontdata,offset)
+ setposition(f,offset)
+ local glyphs=fontdata.glyphs
+ local minoverlap=readushort(f)
+ local vcoverage=readushort(f)
+ local hcoverage=readushort(f)
+ local vnofglyphs=readushort(f)
+ local hnofglyphs=readushort(f)
+ local vconstruction=readcardinaltable(f,vnofglyphs,ushort)
+ local hconstruction=readcardinaltable(f,hnofglyphs,ushort)
+ fontdata.mathconstants.MinConnectorOverlap=minoverlap
+ local function get(offset,coverage,nofglyphs,construction,kvariants,kparts,kitalic)
+ if coverage~=0 and nofglyphs>0 then
+ local coverage=readcoverage(f,offset+coverage,true)
+ for i=1,nofglyphs do
+ local c=construction[i]
+ if c~=0 then
+ local index=coverage[i]
+ local glyph=glyphs[index]
+ local math=glyph.math
+ setposition(f,offset+c)
+ local assembly=readushort(f)
+ local nofvariants=readushort(f)
+ if nofvariants>0 then
+ local variants,v=nil,0
+ for i=1,nofvariants do
+ local variant=readushort(f)
+ if variant==index then
+ elseif variants then
+ v=v+1
+ variants[v]=variant
+ else
+ v=1
+ variants={ variant }
+ end
+ skipshort(f)
+ end
+ if not variants then
+ elseif not math then
+ math={ [kvariants]=variants }
+ glyph.math=math
+ else
+ math[kvariants]=variants
+ end
+ end
+ if assembly~=0 then
+ setposition(f,offset+c+assembly)
+ local italic=readmathvalue(f)
+ local nofparts=readushort(f)
+ local parts={}
+ for i=1,nofparts do
+ local p={
+ glyph=readushort(f),
+ start=readushort(f),
+ ["end"]=readushort(f),
+ advance=readushort(f),
+ }
+ local flags=readushort(f)
+ if band(flags,0x0001)~=0 then
+ p.extender=1
+ end
+ parts[i]=p
+ end
+ if not math then
+ math={
+ [kparts]=parts
+ }
+ glyph.math=math
+ else
+ math[kparts]=parts
+ end
+ if italic and italic~=0 then
+ math[kitalic]=italic
+ end
+ end
+ end
+ end
+ end
+ end
+ get(offset,vcoverage,vnofglyphs,vconstruction,"vvariants","vparts","vitalic")
+ get(offset,hcoverage,hnofglyphs,hconstruction,"hvariants","hparts","hitalic")
+end
+function readers.math(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"math",specification.glyphs)
+ if tableoffset then
+ local version=readulong(f)
+ local constants=readushort(f)
+ local glyphinfo=readushort(f)
+ local variants=readushort(f)
+ if constants==0 then
+ report("the math table of %a has no constants",fontdata.filename)
+ else
+ readmathconstants(f,fontdata,tableoffset+constants)
+ end
+ if glyphinfo~=0 then
+ readmathglyphinfo(f,fontdata,tableoffset+glyphinfo)
+ end
+ if variants~=0 then
+ readmathvariants(f,fontdata,tableoffset+variants)
+ end
+ end
+end
+function readers.colr(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"colr",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ if version~=0 then
+ report("table version %a of %a is not supported (yet), maybe font %s is bad",version,"colr",fontdata.filename)
+ return
+ end
+ if not fontdata.tables.cpal then
+ report("color table %a in font %a has no mandate %a table","colr",fontdata.filename,"cpal")
+ fontdata.colorpalettes={}
+ end
+ local glyphs=fontdata.glyphs
+ local nofglyphs=readushort(f)
+ local baseoffset=readulong(f)
+ local layeroffset=readulong(f)
+ local noflayers=readushort(f)
+ local layerrecords={}
+ local maxclass=0
+ setposition(f,tableoffset+layeroffset)
+ for i=1,noflayers do
+ local slot=readushort(f)
+ local class=readushort(f)
+ if class<0xFFFF then
+ class=class+1
+ if class>maxclass then
+ maxclass=class
+ end
+ end
+ layerrecords[i]={
+ slot=slot,
+ class=class,
+ }
+ end
+ fontdata.maxcolorclass=maxclass
+ setposition(f,tableoffset+baseoffset)
+ for i=0,nofglyphs-1 do
+ local glyphindex=readushort(f)
+ local firstlayer=readushort(f)
+ local noflayers=readushort(f)
+ local t={}
+ for i=1,noflayers do
+ t[i]=layerrecords[firstlayer+i]
+ end
+ glyphs[glyphindex].colors=t
+ end
+ end
+ fontdata.hascolor=true
+end
+function readers.cpal(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"cpal",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local nofpaletteentries=readushort(f)
+ local nofpalettes=readushort(f)
+ local nofcolorrecords=readushort(f)
+ local firstcoloroffset=readulong(f)
+ local colorrecords={}
+ local palettes=readcardinaltable(f,nofpalettes,ushort)
+ if version==1 then
+ local palettettypesoffset=readulong(f)
+ local palettelabelsoffset=readulong(f)
+ local paletteentryoffset=readulong(f)
+ end
+ setposition(f,tableoffset+firstcoloroffset)
+ for i=1,nofcolorrecords do
+ local b,g,r,a=readbytes(f,4)
+ colorrecords[i]={
+ r,g,b,a~=255 and a or nil,
+ }
+ end
+ for i=1,nofpalettes do
+ local p={}
+ local o=palettes[i]
+ for j=1,nofpaletteentries do
+ p[j]=colorrecords[o+j]
+ end
+ palettes[i]=p
+ end
+ fontdata.colorpalettes=palettes
+ end
+end
+function readers.svg(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"svg",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local glyphs=fontdata.glyphs
+ local indexoffset=tableoffset+readulong(f)
+ local reserved=readulong(f)
+ setposition(f,indexoffset)
+ local nofentries=readushort(f)
+ local entries={}
+ for i=1,nofentries do
+ entries[i]={
+ first=readushort(f),
+ last=readushort(f),
+ offset=indexoffset+readulong(f),
+ length=readulong(f),
+ }
+ end
+ for i=1,nofentries do
+ local entry=entries[i]
+ setposition(f,entry.offset)
+ entries[i]={
+ first=entry.first,
+ last=entry.last,
+ data=readstring(f,entry.length)
+ }
+ end
+ fontdata.svgshapes=entries
+ end
+ fontdata.hascolor=true
+end
+function readers.sbix(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"sbix",specification.glyphs)
+ if tableoffset then
+ local version=readushort(f)
+ local flags=readushort(f)
+ local nofstrikes=readulong(f)
+ local strikes={}
+ local nofglyphs=fontdata.nofglyphs
+ for i=1,nofstrikes do
+ strikes[i]=readulong(f)
+ end
+ local shapes={}
+ local done=0
+ for i=1,nofstrikes do
+ local strikeoffset=strikes[i]+tableoffset
+ setposition(f,strikeoffset)
+ strikes[i]={
+ ppem=readushort(f),
+ ppi=readushort(f),
+ offset=strikeoffset
+ }
+ end
+ sort(strikes,function(a,b)
+ if b.ppem==a.ppem then
+ return b.ppi<a.ppi
+ else
+ return b.ppem<a.ppem
+ end
+ end)
+ local glyphs={}
+ for i=1,nofstrikes do
+ local strike=strikes[i]
+ local strikeppem=strike.ppem
+ local strikeppi=strike.ppi
+ local strikeoffset=strike.offset
+ setposition(f,strikeoffset)
+ for i=0,nofglyphs do
+ glyphs[i]=readulong(f)
+ end
+ local glyphoffset=glyphs[0]
+ for i=0,nofglyphs-1 do
+ local nextoffset=glyphs[i+1]
+ if not shapes[i] then
+ local datasize=nextoffset-glyphoffset
+ if datasize>0 then
+ setposition(f,strikeoffset+glyphoffset)
+ shapes[i]={
+ x=readshort(f),
+ y=readshort(f),
+ tag=readtag(f),
+ data=readstring(f,datasize-8),
+ ppem=strikeppem,
+ ppi=strikeppi,
+ }
+ done=done+1
+ if done==nofglyphs then
+ break
+ end
+ end
+ end
+ glyphoffset=nextoffset
+ end
+ end
+ fontdata.pngshapes=shapes
+ end
+end
+do
+ local function getmetrics(f)
+ return {
+ ascender=readinteger(f),
+ descender=readinteger(f),
+ widthmax=readuinteger(f),
+ caretslopedumerator=readinteger(f),
+ caretslopedenominator=readinteger(f),
+ caretoffset=readinteger(f),
+ minorigin=readinteger(f),
+ minadvance=readinteger(f),
+ maxbefore=readinteger(f),
+ minafter=readinteger(f),
+ pad1=readinteger(f),
+ pad2=readinteger(f),
+ }
+ end
+ local function getbigmetrics(f)
+ return {
+ height=readuinteger(f),
+ width=readuinteger(f),
+ horiBearingX=readinteger(f),
+ horiBearingY=readinteger(f),
+ horiAdvance=readuinteger(f),
+ vertBearingX=readinteger(f),
+ vertBearingY=readinteger(f),
+ vertAdvance=readuinteger(f),
+ }
+ end
+ local function getsmallmetrics(f)
+ return {
+ height=readuinteger(f),
+ width=readuinteger(f),
+ bearingX=readinteger(f),
+ bearingY=readinteger(f),
+ advance=readuinteger(f),
+ }
+ end
+ function readers.cblc(f,fontdata,specification)
+ local ctdttableoffset=gotodatatable(f,fontdata,"cbdt",specification.glyphs)
+ if not ctdttableoffset then
+ return
+ end
+ local cblctableoffset=gotodatatable(f,fontdata,"cblc",specification.glyphs)
+ if cblctableoffset then
+ local majorversion=readushort(f)
+ local minorversion=readushort(f)
+ local nofsizetables=readulong(f)
+ local sizetables={}
+ local shapes={}
+ local subtables={}
+ for i=1,nofsizetables do
+ sizetables[i]={
+ subtables=readulong(f),
+ indexsize=readulong(f),
+ nofsubtables=readulong(f),
+ colorref=readulong(f),
+ hormetrics=getmetrics(f),
+ vermetrics=getmetrics(f),
+ firstindex=readushort(f),
+ lastindex=readushort(f),
+ ppemx=readbyte(f),
+ ppemy=readbyte(f),
+ bitdepth=readbyte(f),
+ flags=readbyte(f),
+ }
+ end
+ sort(sizetables,function(a,b)
+ if b.ppemx==a.ppemx then
+ return b.bitdepth<a.bitdepth
+ else
+ return b.ppemx<a.ppemx
+ end
+ end)
+ for i=1,nofsizetables do
+ local s=sizetables[i]
+ local d=false
+ for j=s.firstindex,s.lastindex do
+ if not shapes[j] then
+ shapes[j]=i
+ d=true
+ end
+ end
+ if d then
+ s.used=true
+ end
+ end
+ for i=1,nofsizetables do
+ local s=sizetables[i]
+ if s.used then
+ local offset=s.subtables
+ setposition(f,cblctableoffset+offset)
+ for j=1,s.nofsubtables do
+ local firstindex=readushort(f)
+ local lastindex=readushort(f)
+ local tableoffset=readulong(f)+offset
+ for k=firstindex,lastindex do
+ if shapes[k]==i then
+ local s=subtables[tableoffset]
+ if not s then
+ s={
+ firstindex=firstindex,
+ lastindex=lastindex,
+ }
+ subtables[tableoffset]=s
+ end
+ shapes[k]=s
+ end
+ end
+ end
+ end
+ end
+ for offset,subtable in sortedhash(subtables) do
+ local tabletype=readushort(f)
+ subtable.format=readushort(f)
+ local baseoffset=readulong(f)+ctdttableoffset
+ local offsets={}
+ local metrics=nil
+ if tabletype==1 then
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i]=readulong(f)+baseoffset
+ end
+ skipbytes(f,4)
+ elseif tabletype==2 then
+ local size=readulong(f)
+ local done=baseoffset
+ metrics=getbigmetrics(f)
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i]=done
+ done=done+size
+ end
+ elseif tabletype==3 then
+ local n=subtable.lastindex-subtable.firstindex+2
+ for i=subtable.firstindex,subtable.lastindex do
+ offsets[i]=readushort(f)+baseoffset
+ end
+ if math.odd(n) then
+ skipbytes(f,4)
+ else
+ skipbytes(f,2)
+ end
+ elseif tabletype==4 then
+ for i=1,readulong(f) do
+ offsets[readushort(f)]=readushort(f)+baseoffset
+ end
+ elseif tabletype==5 then
+ local size=readulong(f)
+ local done=baseoffset
+ metrics=getbigmetrics(f)
+ local n=readulong(f)
+ for i=1,n do
+ offsets[readushort(f)]=done
+ done=done+size
+ end
+ if math.odd(n) then
+ skipbytes(f,2)
+ end
+ else
+ return
+ end
+ subtable.offsets=offsets
+ subtable.metrics=metrics
+ end
+ local default={ width=0,height=0 }
+ local glyphs=fontdata.glyphs
+ for index,subtable in sortedhash(shapes) do
+ if type(subtable)=="table" then
+ local data=nil
+ local metrics=default
+ local format=subtable.format
+ local offset=subtable.offsets[index]
+ setposition(f,offset)
+ if format==17 then
+ metrics=getsmallmetrics(f)
+ data=readstring(f,readulong(f))
+ elseif format==18 then
+ metrics=getbigmetrics(f)
+ data=readstring(f,readulong(f))
+ elseif format==19 then
+ metrics=subtable.metrics
+ data=readstring(f,readulong(f))
+ else
+ end
+ local x=metrics.width
+ local y=metrics.height
+ shapes[index]={
+ x=x,
+ y=y,
+ data=data,
+ }
+ local glyph=glyphs[index]
+ if not glyph.boundingbox then
+ local width=glyph.width
+ local height=width*y/x
+ glyph.boundingbox={ 0,0,width,height }
+ end
+ else
+ shapes[index]={
+ x=0,
+ y=0,
+ data="",
+ }
+ end
+ end
+ fontdata.pngshapes=shapes
+ end
+ end
+ function readers.cbdt(f,fontdata,specification)
+ end
+end
+function readers.stat(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"stat",true)
+ if tableoffset then
+ local extras=fontdata.extras
+ local version=readulong(f)
+ local axissize=readushort(f)
+ local nofaxis=readushort(f)
+ local axisoffset=readulong(f)
+ local nofvalues=readushort(f)
+ local valuesoffset=readulong(f)
+ local fallbackname=extras[readushort(f)]
+ local axis={}
+ local values={}
+ setposition(f,tableoffset+axisoffset)
+ for i=1,nofaxis do
+ local tag=readtag(f)
+ axis[i]={
+ tag=tag,
+ name=lower(extras[readushort(f)] or tag),
+ ordering=readushort(f),
+ variants={}
+ }
+ end
+ setposition(f,tableoffset+valuesoffset)
+ for i=1,nofvalues do
+ values[i]=readushort(f)
+ end
+ for i=1,nofvalues do
+ setposition(f,tableoffset+valuesoffset+values[i])
+ local format=readushort(f)
+ local index=readushort(f)+1
+ local flags=readushort(f)
+ local name=lower(extras[readushort(f)] or "no name")
+ local value=readfixed(f)
+ local variant
+ if format==1 then
+ variant={
+ flags=flags,
+ name=name,
+ value=value,
+ }
+ elseif format==2 then
+ variant={
+ flags=flags,
+ name=name,
+ value=value,
+ minimum=readfixed(f),
+ maximum=readfixed(f),
+ }
+ elseif format==3 then
+ variant={
+ flags=flags,
+ name=name,
+ value=value,
+ link=readfixed(f),
+ }
+ end
+ insert(axis[index].variants,variant)
+ end
+ sort(axis,function(a,b)
+ return a.ordering<b.ordering
+ end)
+ for i=1,#axis do
+ local a=axis[i]
+ sort(a.variants,function(a,b)
+ return a.name<b.name
+ end)
+ a.ordering=nil
+ end
+ setvariabledata(fontdata,"designaxis",axis)
+ setvariabledata(fontdata,"fallbackname",fallbackname)
+ end
+end
+function readers.avar(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"avar",true)
+ if tableoffset then
+ local function collect()
+ local nofvalues=readushort(f)
+ local values={}
+ local lastfrom=false
+ local lastto=false
+ for i=1,nofvalues do
+ local from=read2dot14(f)
+ local to=read2dot14(f)
+ if lastfrom and from<=lastfrom then
+ elseif lastto and to>=lastto then
+ else
+ values[#values+1]={ from,to }
+ lastfrom,lastto=from,to
+ end
+ end
+ nofvalues=#values
+ if nofvalues>2 then
+ local some=values[1]
+ if some[1]==-1 and some[2]==-1 then
+ some=values[nofvalues]
+ if some[1]==1 and some[2]==1 then
+ for i=2,nofvalues-1 do
+ some=values[i]
+ if some[1]==0 and some[2]==0 then
+ return values
+ end
+ end
+ end
+ end
+ end
+ return false
+ end
+ local version=readulong(f)
+ local reserved=readushort(f)
+ local nofaxis=readushort(f)
+ local segments={}
+ for i=1,nofaxis do
+ segments[i]=collect()
+ end
+ setvariabledata(fontdata,"segments",segments)
+ end
+end
+function readers.fvar(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"fvar",true)
+ if tableoffset then
+ local version=readulong(f)
+ local offsettoaxis=tableoffset+readushort(f)
+ local reserved=skipshort(f)
+ local nofaxis=readushort(f)
+ local sizeofaxis=readushort(f)
+ local nofinstances=readushort(f)
+ local sizeofinstances=readushort(f)
+ local extras=fontdata.extras
+ local axis={}
+ local instances={}
+ setposition(f,offsettoaxis)
+ for i=1,nofaxis do
+ axis[i]={
+ tag=readtag(f),
+ minimum=readfixed(f),
+ default=readfixed(f),
+ maximum=readfixed(f),
+ flags=readushort(f),
+ name=lower(extras[readushort(f)] or "bad name"),
+ }
+ local n=sizeofaxis-20
+ if n>0 then
+ skipbytes(f,n)
+ elseif n<0 then
+ end
+ end
+ local nofbytes=2+2+2+nofaxis*4
+ local readpsname=nofbytes<=sizeofinstances
+ local skippable=sizeofinstances-nofbytes
+ for i=1,nofinstances do
+ local subfamid=readushort(f)
+ local flags=readushort(f)
+ local values={}
+ for i=1,nofaxis do
+ values[i]={
+ axis=axis[i].tag,
+ value=readfixed(f),
+ }
+ end
+ local psnameid=readpsname and readushort(f) or 0xFFFF
+ if subfamid==2 or subfamid==17 then
+ elseif subfamid==0xFFFF then
+ subfamid=nil
+ elseif subfamid<=256 or subfamid>=32768 then
+ subfamid=nil
+ end
+ if psnameid==6 then
+ elseif psnameid==0xFFFF then
+ psnameid=nil
+ elseif psnameid<=256 or psnameid>=32768 then
+ psnameid=nil
+ end
+ instances[i]={
+ subfamily=extras[subfamid],
+ psname=psnameid and extras[psnameid] or nil,
+ values=values,
+ }
+ if skippable>0 then
+ skipbytes(f,skippable)
+ end
+ end
+ setvariabledata(fontdata,"axis",axis)
+ setvariabledata(fontdata,"instances",instances)
+ end
+end
+function readers.hvar(f,fontdata,specification)
+ local factors=specification.factors
+ if not factors then
+ return
+ end
+ local tableoffset=gotodatatable(f,fontdata,"hvar",specification.variable)
+ if not tableoffset then
+ return
+ end
+ local version=readulong(f)
+ local variationoffset=tableoffset+readulong(f)
+ local advanceoffset=tableoffset+readulong(f)
+ local lsboffset=tableoffset+readulong(f)
+ local rsboffset=tableoffset+readulong(f)
+ local regions={}
+ local variations={}
+ local innerindex={}
+ local outerindex={}
+ if variationoffset>0 then
+ regions,deltas=readvariationdata(f,variationoffset,factors)
+ end
+ if not regions then
+ return
+ end
+ if advanceoffset>0 then
+ setposition(f,advanceoffset)
+ local format=readushort(f)
+ local mapcount=readushort(f)
+ local entrysize=rshift(band(format,0x0030),4)+1
+ local nofinnerbits=band(format,0x000F)+1
+ local innermask=lshift(1,nofinnerbits)-1
+ local readcardinal=read_cardinal[entrysize]
+ for i=0,mapcount-1 do
+ local mapdata=readcardinal(f)
+ outerindex[i]=rshift(mapdata,nofinnerbits)
+ innerindex[i]=band(mapdata,innermask)
+ end
+ setvariabledata(fontdata,"hvarwidths",true)
+ local glyphs=fontdata.glyphs
+ for i=0,fontdata.nofglyphs-1 do
+ local glyph=glyphs[i]
+ local width=glyph.width
+ if width then
+ local outer=outerindex[i] or 0
+ local inner=innerindex[i] or i
+ if outer and inner then
+ local delta=deltas[outer+1]
+ if delta then
+ local d=delta.deltas[inner+1]
+ if d then
+ local scales=delta.scales
+ local deltaw=0
+ for i=1,#scales do
+ local di=d[i]
+ if di then
+ deltaw=deltaw+scales[i]*di
+ else
+ break
+ end
+ end
+ glyph.width=width+round(deltaw)
+ end
+ end
+ end
+ end
+ end
+ end
+end
+function readers.vvar(f,fontdata,specification)
+ if not specification.variable then
+ return
+ end
+end
+function readers.mvar(f,fontdata,specification)
+ local tableoffset=gotodatatable(f,fontdata,"mvar",specification.variable)
+ if tableoffset then
+ local version=readulong(f)
+ local reserved=skipshort(f,1)
+ local recordsize=readushort(f)
+ local nofrecords=readushort(f)
+ local offsettostore=tableoffset+readushort(f)
+ local dimensions={}
+ local factors=specification.factors
+ if factors then
+ local regions,deltas=readvariationdata(f,offsettostore,factors)
+ for i=1,nofrecords do
+ local tag=readtag(f)
+ local var=variabletags[tag]
+ if var then
+ local outer=readushort(f)
+ local inner=readushort(f)
+ local delta=deltas[outer+1]
+ if delta then
+ local d=delta.deltas[inner+1]
+ if d then
+ local scales=delta.scales
+ local dd=0
+ for i=1,#scales do
+ dd=dd+scales[i]*d[i]
+ end
+ var(fontdata,round(dd))
+ end
+ end
+ else
+ skipshort(f,2)
+ end
+ if recordsize>8 then
+ skipbytes(recordsize-8)
+ end
+ end
+ end
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-oup']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type=next,type
+local P,R,S=lpeg.P,lpeg.R,lpeg.S
+local lpegmatch=lpeg.match
+local insert,remove,copy,unpack=table.insert,table.remove,table.copy,table.unpack
+local formatters=string.formatters
+local sortedkeys=table.sortedkeys
+local sortedhash=table.sortedhash
+local tohash=table.tohash
+local setmetatableindex=table.setmetatableindex
+local report_error=logs.reporter("otf reader","error")
+local report_markwidth=logs.reporter("otf reader","markwidth")
+local report_cleanup=logs.reporter("otf reader","cleanup")
+local report_optimizations=logs.reporter("otf reader","merges")
+local report_unicodes=logs.reporter("otf reader","unicodes")
+local trace_markwidth=false trackers.register("otf.markwidth",function(v) trace_markwidth=v end)
+local trace_cleanup=false trackers.register("otf.cleanups",function(v) trace_cleanups=v end)
+local trace_optimizations=false trackers.register("otf.optimizations",function(v) trace_optimizations=v end)
+local trace_unicodes=false trackers.register("otf.unicodes",function(v) trace_unicodes=v end)
+local readers=fonts.handlers.otf.readers
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local f_private=formatters["P%05X"]
+local f_unicode=formatters["U%05X"]
+local f_index=formatters["I%05X"]
+local f_character_y=formatters["%C"]
+local f_character_n=formatters["[ %C ]"]
+local check_duplicates=true
+local check_soft_hyphen=true
+directives.register("otf.checksofthyphen",function(v)
+ check_soft_hyphen=v
+end)
+local function replaced(list,index,replacement)
+ if type(list)=="number" then
+ return replacement
+ elseif type(replacement)=="table" then
+ local t={}
+ local n=index-1
+ for i=1,n do
+ t[i]=list[i]
+ end
+ for i=1,#replacement do
+ n=n+1
+ t[n]=replacement[i]
+ end
+ for i=index+1,#list do
+ n=n+1
+ t[n]=list[i]
+ end
+ else
+ list[index]=replacement
+ return list
+ end
+end
+local function unifyresources(fontdata,indices)
+ local descriptions=fontdata.descriptions
+ local resources=fontdata.resources
+ if not descriptions or not resources then
+ return
+ end
+ local nofindices=#indices
+ local variants=fontdata.resources.variants
+ if variants then
+ for selector,unicodes in next,variants do
+ for unicode,index in next,unicodes do
+ unicodes[unicode]=indices[index]
+ end
+ end
+ end
+ local function remark(marks)
+ if marks then
+ local newmarks={}
+ for k,v in next,marks do
+ local u=indices[k]
+ if u then
+ newmarks[u]=v
+ elseif trace_optimizations then
+ report_optimizations("discarding mark %i",k)
+ end
+ end
+ return newmarks
+ end
+ end
+ local marks=resources.marks
+ if marks then
+ resources.marks=remark(marks)
+ end
+ local markclasses=resources.markclasses
+ if markclasses then
+ for class,marks in next,markclasses do
+ markclasses[class]=remark(marks)
+ end
+ end
+ local marksets=resources.marksets
+ if marksets then
+ for class,marks in next,marksets do
+ marksets[class]=remark(marks)
+ end
+ end
+ local done={}
+ local duplicates=check_duplicates and resources.duplicates
+ if duplicates and not next(duplicates) then
+ duplicates=false
+ end
+ local function recover(cover)
+ for i=1,#cover do
+ local c=cover[i]
+ if not done[c] then
+ local t={}
+ for k,v in next,c do
+ local ug=indices[k]
+ if ug then
+ t[ug]=v
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,"coverage",k,nofindices)
+ end
+ end
+ cover[i]=t
+ done[c]=d
+ end
+ end
+ end
+ local function recursed(c,kind)
+ local t={}
+ for g,d in next,c do
+ if type(d)=="table" then
+ local ug=indices[g]
+ if ug then
+ t[ug]=recursed(d,kind)
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g,nofindices)
+ end
+ else
+ t[g]=indices[d]
+ end
+ end
+ return t
+ end
+ local function unifythem(sequences)
+ if not sequences then
+ return
+ end
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local features=sequence.features
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gsub_single" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ local ud1=indices[d1]
+ if ud1 then
+ t1[ug1]=ud1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=ud1
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",3,kind,d1,nofindices)
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=indices[d1]
+ else
+ report_error("fuzzy case %i in unifying %s: %i",2,kind,g1)
+ end
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ local t2=done[d1]
+ if not t2 then
+ t2={}
+ for g2,d2 in next,d1 do
+ local ug2=indices[g2]
+ if ug2 then
+ t2[ug2]=d2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g2,nofindices,nofindices)
+ end
+ end
+ done[d1]=t2
+ end
+ t1[ug1]=t2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gsub_ligature" then
+ local c=step.coverage
+ if c then
+ step.coverage=recursed(c,kind)
+ end
+ elseif kind=="gsub_alternate" or kind=="gsub_multiple" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ for i=1,#d1 do
+ local d1i=d1[i]
+ local d1u=indices[d1i]
+ if d1u then
+ d1[i]=d1u
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,i,d1i,nofindices)
+ end
+ end
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=copy(d1)
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ for i=1,#d1 do
+ local d1i=d1[i]
+ local d1u=indices[d1i]
+ if d1u then
+ d1[i]=d1u
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,d1i,nofindices)
+ end
+ end
+ t1[indices[g1]]=d1
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gpos_single" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=d1
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ elseif kind=="gpos_mark2base" or kind=="gpos_mark2mark" or kind=="gpos_mark2ligature" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ local c=step.baseclasses
+ if c then
+ local t1=done[c]
+ if not t1 then
+ for g1,d1 in next,c do
+ local t2=done[d1]
+ if not t2 then
+ t2={}
+ for g2,d2 in next,d1 do
+ local ug2=indices[g2]
+ if ug2 then
+ t2[ug2]=d2
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g2,nofindices)
+ end
+ end
+ done[d1]=t2
+ end
+ c[g1]=t2
+ end
+ done[c]=c
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ local t1=done[c]
+ if not t1 then
+ t1={}
+ if duplicates then
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ local dg1=duplicates[ug1]
+ if dg1 then
+ for u in next,dg1 do
+ t1[u]=copy(d1)
+ end
+ end
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",1,kind,g1,nofindices)
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local ug1=indices[g1]
+ if ug1 then
+ t1[ug1]=d1
+ else
+ report_error("case %i, bad index in unifying %s: %s of %s",2,kind,g1,nofindices)
+ end
+ end
+ end
+ done[c]=t1
+ end
+ step.coverage=t1
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local before=rule.before if before then recover(before) end
+ local after=rule.after if after then recover(after) end
+ local current=rule.current if current then recover(current) end
+ local replacements=rule.replacements
+ if replacements then
+ if not done[replacements] then
+ local r={}
+ for k,v in next,replacements do
+ r[indices[k]]=indices[v]
+ end
+ rule.replacements=r
+ done[replacements]=r
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ unifythem(resources.sequences)
+ unifythem(resources.sublookups)
+end
+local function copyduplicates(fontdata)
+ if check_duplicates then
+ local descriptions=fontdata.descriptions
+ local resources=fontdata.resources
+ local duplicates=resources.duplicates
+ if check_soft_hyphen then
+ local ds=descriptions[0xAD]
+ if not ds or ds.width==0 then
+ if ds then
+ descriptions[0xAD]=nil
+ if trace_unicodes then
+ report_unicodes("patching soft hyphen")
+ end
+ else
+ if trace_unicodes then
+ report_unicodes("adding soft hyphen")
+ end
+ end
+ if not duplicates then
+ duplicates={}
+ resources.duplicates=duplicates
+ end
+ local dh=duplicates[0x2D]
+ if dh then
+ dh[#dh+1]={ [0xAD]=true }
+ else
+ duplicates[0x2D]={ [0xAD]=true }
+ end
+ end
+ end
+ if duplicates then
+ for u,d in next,duplicates do
+ local du=descriptions[u]
+ if du then
+ local t={ f_character_y(u),"@",f_index(du.index),"->" }
+ local n=0
+ local m=25
+ for u in next,d do
+ if descriptions[u] then
+ if n<m then
+ t[n+4]=f_character_n(u)
+ end
+ else
+ local c=copy(du)
+ c.unicode=u
+ descriptions[u]=c
+ if n<m then
+ t[n+4]=f_character_y(u)
+ end
+ end
+ n=n+1
+ end
+ if trace_unicodes then
+ if n<=m then
+ report_unicodes("%i : % t",n,t)
+ else
+ report_unicodes("%i : % t ...",n,t)
+ end
+ end
+ else
+ end
+ end
+ end
+ end
+end
+local ignore={
+ ["notdef"]=true,
+ [".notdef"]=true,
+ ["null"]=true,
+ [".null"]=true,
+ ["nonmarkingreturn"]=true,
+}
+local function checklookups(fontdata,missing,nofmissing)
+ local descriptions=fontdata.descriptions
+ local resources=fontdata.resources
+ if missing and nofmissing and nofmissing<=0 then
+ return
+ end
+ local singles={}
+ local alternates={}
+ local ligatures={}
+ if not missing then
+ missing={}
+ nofmissing=0
+ for u,d in next,descriptions do
+ if not d.unicode then
+ nofmissing=nofmissing+1
+ missing[u]=true
+ end
+ end
+ end
+ local function collectthem(sequences)
+ if not sequences then
+ return
+ end
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gsub_single" then
+ local c=step.coverage
+ if c then
+ singles[#singles+1]=c
+ end
+ elseif kind=="gsub_alternate" then
+ local c=step.coverage
+ if c then
+ alternates[#alternates+1]=c
+ end
+ elseif kind=="gsub_ligature" then
+ local c=step.coverage
+ if c then
+ ligatures[#ligatures+1]=c
+ end
+ end
+ end
+ end
+ end
+ end
+ collectthem(resources.sequences)
+ collectthem(resources.sublookups)
+ local loops=0
+ while true do
+ loops=loops+1
+ local old=nofmissing
+ for i=1,#singles do
+ local c=singles[i]
+ for g1,g2 in next,c do
+ if missing[g1] then
+ local u2=descriptions[g2].unicode
+ if u2 then
+ missing[g1]=false
+ descriptions[g1].unicode=u2
+ nofmissing=nofmissing-1
+ end
+ end
+ if missing[g2] then
+ local u1=descriptions[g1].unicode
+ if u1 then
+ missing[g2]=false
+ descriptions[g2].unicode=u1
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ end
+ for i=1,#alternates do
+ local c=alternates[i]
+ for g1,d1 in next,c do
+ if missing[g1] then
+ for i=1,#d1 do
+ local g2=d1[i]
+ local u2=descriptions[g2].unicode
+ if u2 then
+ missing[g1]=false
+ descriptions[g1].unicode=u2
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ if not missing[g1] then
+ for i=1,#d1 do
+ local g2=d1[i]
+ if missing[g2] then
+ local u1=descriptions[g1].unicode
+ if u1 then
+ missing[g2]=false
+ descriptions[g2].unicode=u1
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ end
+ end
+ end
+ if nofmissing<=0 then
+ if trace_unicodes then
+ report_unicodes("all missings done in %s loops",loops)
+ end
+ return
+ elseif old==nofmissing then
+ break
+ end
+ end
+ local t,n
+ local function recursed(c)
+ for g,d in next,c do
+ if g~="ligature" then
+ local u=descriptions[g].unicode
+ if u then
+ n=n+1
+ t[n]=u
+ recursed(d)
+ n=n-1
+ end
+ elseif missing[d] then
+ local l={}
+ local m=0
+ for i=1,n do
+ local u=t[i]
+ if type(u)=="table" then
+ for i=1,#u do
+ m=m+1
+ l[m]=u[i]
+ end
+ else
+ m=m+1
+ l[m]=u
+ end
+ end
+ missing[d]=false
+ descriptions[d].unicode=l
+ nofmissing=nofmissing-1
+ end
+ end
+ end
+ if nofmissing>0 then
+ t={}
+ n=0
+ local loops=0
+ while true do
+ loops=loops+1
+ local old=nofmissing
+ for i=1,#ligatures do
+ recursed(ligatures[i])
+ end
+ if nofmissing<=0 then
+ if trace_unicodes then
+ report_unicodes("all missings done in %s loops",loops)
+ end
+ return
+ elseif old==nofmissing then
+ break
+ end
+ end
+ t=nil
+ n=0
+ end
+ if trace_unicodes and nofmissing>0 then
+ local done={}
+ for i,r in next,missing do
+ if r then
+ local data=descriptions[i]
+ local name=data and data.name or f_index(i)
+ if not ignore[name] then
+ done[name]=true
+ end
+ end
+ end
+ if next(done) then
+ report_unicodes("not unicoded: % t",sortedkeys(done))
+ end
+ end
+end
+local function unifymissing(fontdata)
+ if not fonts.mappings then
+ require("font-map")
+ require("font-agl")
+ end
+ local unicodes={}
+ local resources=fontdata.resources
+ resources.unicodes=unicodes
+ for unicode,d in next,fontdata.descriptions do
+ if unicode<privateoffset then
+ local name=d.name
+ if name then
+ unicodes[name]=unicode
+ end
+ end
+ end
+ fonts.mappings.addtounicode(fontdata,fontdata.filename,checklookups)
+ resources.unicodes=nil
+end
+local firstprivate=fonts.privateoffsets and fonts.privateoffsets.textbase or 0xF0000
+local puafirst=0xE000
+local pualast=0xF8FF
+local function unifyglyphs(fontdata,usenames)
+ local private=fontdata.private or privateoffset
+ local glyphs=fontdata.glyphs
+ local indices={}
+ local descriptions={}
+ local names=usenames and {}
+ local resources=fontdata.resources
+ local zero=glyphs[0]
+ local zerocode=zero.unicode
+ if not zerocode then
+ zerocode=private
+ zero.unicode=zerocode
+ private=private+1
+ end
+ descriptions[zerocode]=zero
+ if names then
+ local name=glyphs[0].name or f_private(zerocode)
+ indices[0]=name
+ names[name]=zerocode
+ else
+ indices[0]=zerocode
+ end
+ if names then
+ for index=1,#glyphs do
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=private
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ private=private+1
+ elseif unicode>=firstprivate then
+ unicode=private
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ private=private+1
+ elseif unicode>=puafirst and unicode<=pualast then
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ elseif descriptions[unicode] then
+ unicode=private
+ local name=glyph.name or f_private(unicode)
+ indices[index]=name
+ names[name]=unicode
+ private=private+1
+ else
+ local name=glyph.name or f_unicode(unicode)
+ indices[index]=name
+ names[name]=unicode
+ end
+ descriptions[unicode]=glyph
+ end
+ elseif trace_unicodes then
+ for index=1,#glyphs do
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=firstprivate then
+ local name=glyph.name
+ if name then
+ report_unicodes("moving glyph %a indexed %05X from private %U to %U ",name,index,unicode,private)
+ else
+ report_unicodes("moving glyph indexed %05X from private %U to %U ",index,unicode,private)
+ end
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=puafirst and unicode<=pualast then
+ local name=glyph.name
+ if name then
+ report_unicodes("keeping private unicode %U for glyph %a indexed %05X",unicode,name,index)
+ else
+ report_unicodes("keeping private unicode %U for glyph indexed %05X",unicode,index)
+ end
+ indices[index]=unicode
+ elseif descriptions[unicode] then
+ local name=glyph.name
+ if name then
+ report_unicodes("assigning duplicate unicode %U to %U for glyph %a indexed %05X ",unicode,private,name,index)
+ else
+ report_unicodes("assigning duplicate unicode %U to %U for glyph indexed %05X ",unicode,private,index)
+ end
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ else
+ indices[index]=unicode
+ end
+ descriptions[unicode]=glyph
+ end
+ else
+ for index=1,#glyphs do
+ local glyph=glyphs[index]
+ local unicode=glyph.unicode
+ if not unicode then
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=firstprivate then
+ local name=glyph.name
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ elseif unicode>=puafirst and unicode<=pualast then
+ local name=glyph.name
+ indices[index]=unicode
+ elseif descriptions[unicode] then
+ local name=glyph.name
+ unicode=private
+ indices[index]=unicode
+ private=private+1
+ else
+ indices[index]=unicode
+ end
+ descriptions[unicode]=glyph
+ end
+ end
+ for index=1,#glyphs do
+ local math=glyphs[index].math
+ if math then
+ local list=math.vparts
+ if list then
+ for i=1,#list do local l=list[i] l.glyph=indices[l.glyph] end
+ end
+ local list=math.hparts
+ if list then
+ for i=1,#list do local l=list[i] l.glyph=indices[l.glyph] end
+ end
+ local list=math.vvariants
+ if list then
+ for i=1,#list do list[i]=indices[list[i]] end
+ end
+ local list=math.hvariants
+ if list then
+ for i=1,#list do list[i]=indices[list[i]] end
+ end
+ end
+ end
+ local colorpalettes=resources.colorpalettes
+ if colorpalettes then
+ for index=1,#glyphs do
+ local colors=glyphs[index].colors
+ if colors then
+ for i=1,#colors do
+ local c=colors[i]
+ c.slot=indices[c.slot]
+ end
+ end
+ end
+ end
+ fontdata.private=private
+ fontdata.glyphs=nil
+ fontdata.names=names
+ fontdata.descriptions=descriptions
+ fontdata.hashmethod=hashmethod
+ return indices,names
+end
+local p_crappyname do
+ local p_hex=R("af","AF","09")
+ local p_digit=R("09")
+ local p_done=S("._-")^0+P(-1)
+ local p_alpha=R("az","AZ")
+ local p_ALPHA=R("AZ")
+ p_crappyname=(
+ lpeg.utfchartabletopattern({ "uni","u" },true)*S("Xx_")^0*p_hex^1
++lpeg.utfchartabletopattern({ "identity","glyph","jamo" },true)*p_hex^1
++lpeg.utfchartabletopattern({ "index","afii" },true)*p_digit^1
++p_digit*p_hex^3+p_alpha*p_digit^1
++P("aj")*p_digit^1+P("eh_")*(p_digit^1+p_ALPHA*p_digit^1)+(1-P("_"))^1*P("_uni")*p_hex^1+P("_")*P(1)^1
+ )*p_done
+end
+local forcekeep=false
+directives.register("otf.keepnames",function(v)
+ report_cleanup("keeping weird glyph names, expect larger files and more memory usage")
+ forcekeep=v
+end)
+local function stripredundant(fontdata)
+ local descriptions=fontdata.descriptions
+ if descriptions then
+ local n=0
+ local c=0
+ if (not context and fonts.privateoffsets.keepnames) or forcekeep then
+ for unicode,d in next,descriptions do
+ if d.class=="base" then
+ d.class=nil
+ c=c+1
+ end
+ end
+ else
+ for unicode,d in next,descriptions do
+ local name=d.name
+ if name and lpegmatch(p_crappyname,name) then
+ d.name=nil
+ n=n+1
+ end
+ if d.class=="base" then
+ d.class=nil
+ c=c+1
+ end
+ end
+ end
+ if trace_cleanup then
+ if n>0 then
+ report_cleanup("%s bogus names removed (verbose unicode)",n)
+ end
+ if c>0 then
+ report_cleanup("%s base class tags removed (default is base)",c)
+ end
+ end
+ end
+end
+readers.stripredundant=stripredundant
+function readers.getcomponents(fontdata)
+ local resources=fontdata.resources
+ if resources then
+ local sequences=resources.sequences
+ if sequences then
+ local collected={}
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ if sequence.type=="gsub_ligature" then
+ local steps=sequence.steps
+ if steps then
+ local l={}
+ local function traverse(p,k,v)
+ if k=="ligature" then
+ collected[v]={ unpack(l) }
+ else
+ insert(l,k)
+ for k,vv in next,v do
+ traverse(p,k,vv)
+ end
+ remove(l)
+ end
+ end
+ for i=1,#steps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ traverse(k,k,v)
+ end
+ end
+ end
+ end
+ end
+ end
+ if next(collected) then
+ while true do
+ local done=false
+ for k,v in next,collected do
+ for i=1,#v do
+ local vi=v[i]
+ if vi==k then
+ collected[k]=nil
+ break
+ else
+ local c=collected[vi]
+ if c then
+ done=true
+ local t={}
+ local n=i-1
+ for j=1,n do
+ t[j]=v[j]
+ end
+ for j=1,#c do
+ n=n+1
+ t[n]=c[j]
+ end
+ for j=i+1,#v do
+ n=n+1
+ t[n]=v[j]
+ end
+ collected[k]=t
+ break
+ end
+ end
+ end
+ end
+ if not done then
+ break
+ end
+ end
+ return collected
+ end
+ end
+ end
+end
+readers.unifymissing=unifymissing
+function readers.rehash(fontdata,hashmethod)
+ if not (fontdata and fontdata.glyphs) then
+ return
+ end
+ if hashmethod=="indices" then
+ fontdata.hashmethod="indices"
+ elseif hashmethod=="names" then
+ fontdata.hashmethod="names"
+ local indices=unifyglyphs(fontdata,true)
+ unifyresources(fontdata,indices)
+ copyduplicates(fontdata)
+ unifymissing(fontdata)
+ else
+ fontdata.hashmethod="unicodes"
+ local indices=unifyglyphs(fontdata)
+ unifyresources(fontdata,indices)
+ copyduplicates(fontdata)
+ unifymissing(fontdata)
+ stripredundant(fontdata)
+ end
+end
+function readers.checkhash(fontdata)
+ local hashmethod=fontdata.hashmethod
+ if hashmethod=="unicodes" then
+ fontdata.names=nil
+ elseif hashmethod=="names" and fontdata.names then
+ unifyresources(fontdata,fontdata.names)
+ copyduplicates(fontdata)
+ fontdata.hashmethod="unicodes"
+ fontdata.names=nil
+ else
+ readers.rehash(fontdata,"unicodes")
+ end
+end
+function readers.addunicodetable(fontdata)
+ local resources=fontdata.resources
+ local unicodes=resources.unicodes
+ if not unicodes then
+ local descriptions=fontdata.descriptions
+ if descriptions then
+ unicodes={}
+ resources.unicodes=unicodes
+ for u,d in next,descriptions do
+ local n=d.name
+ if n then
+ unicodes[n]=u
+ end
+ end
+ end
+ end
+end
+local concat,sort=table.concat,table.sort
+local next,type,tostring=next,type,tostring
+local criterium=1
+local threshold=0
+local trace_packing=false trackers.register("otf.packing",function(v) trace_packing=v end)
+local trace_loading=false trackers.register("otf.loading",function(v) trace_loading=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local function tabstr_normal(t)
+ local s={}
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ if type(v)=="table" then
+ s[n]=k..">"..tabstr_normal(v)
+ elseif v==true then
+ s[n]=k.."+"
+ elseif v then
+ s[n]=k.."="..v
+ else
+ s[n]=k.."-"
+ end
+ end
+ if n==0 then
+ return ""
+ elseif n==1 then
+ return s[1]
+ else
+ sort(s)
+ return concat(s,",")
+ end
+end
+local function tabstr_flat(t)
+ local s={}
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ s[n]=k.."="..v
+ end
+ if n==0 then
+ return ""
+ elseif n==1 then
+ return s[1]
+ else
+ sort(s)
+ return concat(s,",")
+ end
+end
+local function tabstr_mixed(t)
+ local s={}
+ local n=#t
+ if n==0 then
+ return ""
+ elseif n==1 then
+ local k=t[1]
+ if k==true then
+ return "++"
+ elseif k==false then
+ return "--"
+ else
+ return tostring(k)
+ end
+ else
+ for i=1,n do
+ local k=t[i]
+ if k==true then
+ s[i]="++"
+ elseif k==false then
+ s[i]="--"
+ else
+ s[i]=k
+ end
+ end
+ return concat(s,",")
+ end
+end
+local function tabstr_boolean(t)
+ local s={}
+ local n=0
+ for k,v in next,t do
+ n=n+1
+ if v then
+ s[n]=k.."+"
+ else
+ s[n]=k.."-"
+ end
+ end
+ if n==0 then
+ return ""
+ elseif n==1 then
+ return s[1]
+ else
+ sort(s)
+ return concat(s,",")
+ end
+end
+function readers.pack(data)
+ if data then
+ local h,t,c={},{},{}
+ local hh,tt,cc={},{},{}
+ local nt,ntt=0,0
+ local function pack_normal(v)
+ local tag=tabstr_normal(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_normal_cc(v)
+ local tag=tabstr_normal(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ v[1]=0
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_flat(v)
+ local tag=tabstr_flat(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_indexed(v)
+ local tag=concat(v," ")
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_mixed(v)
+ local tag=tabstr_mixed(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_boolean(v)
+ local tag=tabstr_boolean(v)
+ local ht=h[tag]
+ if ht then
+ c[ht]=c[ht]+1
+ return ht
+ else
+ nt=nt+1
+ t[nt]=v
+ h[tag]=nt
+ c[nt]=1
+ return nt
+ end
+ end
+ local function pack_final(v)
+ if c[v]<=criterium then
+ return t[v]
+ else
+ local hv=hh[v]
+ if hv then
+ return hv
+ else
+ ntt=ntt+1
+ tt[ntt]=t[v]
+ hh[v]=ntt
+ cc[ntt]=c[v]
+ return ntt
+ end
+ end
+ end
+ local function pack_final_cc(v)
+ if c[v]<=criterium then
+ return t[v]
+ else
+ local hv=hh[v]
+ if hv then
+ return hv
+ else
+ ntt=ntt+1
+ tt[ntt]=t[v]
+ hh[v]=ntt
+ cc[ntt]=c[v]
+ return ntt
+ end
+ end
+ end
+ local function success(stage,pass)
+ if nt==0 then
+ if trace_loading or trace_packing then
+ report_otf("pack quality: nothing to pack")
+ end
+ return false
+ elseif nt>=threshold then
+ local one=0
+ local two=0
+ local rest=0
+ if pass==1 then
+ for k,v in next,c do
+ if v==1 then
+ one=one+1
+ elseif v==2 then
+ two=two+1
+ else
+ rest=rest+1
+ end
+ end
+ else
+ for k,v in next,cc do
+ if v>20 then
+ rest=rest+1
+ elseif v>10 then
+ two=two+1
+ else
+ one=one+1
+ end
+ end
+ data.tables=tt
+ end
+ if trace_loading or trace_packing then
+ report_otf("pack quality: stage %s, pass %s, %s packed, 1-10:%s, 11-20:%s, rest:%s (criterium: %s)",
+ stage,pass,one+two+rest,one,two,rest,criterium)
+ end
+ return true
+ else
+ if trace_loading or trace_packing then
+ report_otf("pack quality: stage %s, pass %s, %s packed, aborting pack (threshold: %s)",
+ stage,pass,nt,threshold)
+ end
+ return false
+ end
+ end
+ local function packers(pass)
+ if pass==1 then
+ return pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc
+ else
+ return pack_final,pack_final,pack_final,pack_final,pack_final,pack_final_cc
+ end
+ end
+ local resources=data.resources
+ local sequences=resources.sequences
+ local sublookups=resources.sublookups
+ local features=resources.features
+ local palettes=resources.colorpalettes
+ local variable=resources.variabledata
+ local chardata=characters and characters.data
+ local descriptions=data.descriptions or data.glyphs
+ if not descriptions then
+ return
+ end
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 1, pass %s",pass)
+ end
+ local pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc=packers(pass)
+ for unicode,description in next,descriptions do
+ local boundingbox=description.boundingbox
+ if boundingbox then
+ description.boundingbox=pack_indexed(boundingbox)
+ end
+ local math=description.math
+ if math then
+ local kerns=math.kerns
+ if kerns then
+ for tag,kern in next,kerns do
+ kerns[tag]=pack_normal(kern)
+ end
+ end
+ end
+ end
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local order=sequence.order
+ local features=sequence.features
+ local flags=sequence.flags
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format~="pair" then
+ for g1,d1 in next,c do
+ c[g1]=pack_normal(d1)
+ end
+ elseif step.shared then
+ local shared={}
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ if not shared[d2] then
+ local f=d2[1] if f and f~=true then d2[1]=pack_indexed(f) end
+ local s=d2[2] if s and s~=true then d2[2]=pack_indexed(s) end
+ shared[d2]=true
+ end
+ end
+ end
+ if pass==2 then
+ step.shared=nil
+ end
+ else
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ local f=d2[1] if f and f~=true then d2[1]=pack_indexed(f) end
+ local s=d2[2] if s and s~=true then d2[2]=pack_indexed(s) end
+ end
+ end
+ end
+ end
+ elseif kind=="gpos_single" then
+ local c=step.coverage
+ if c then
+ if step.format=="single" then
+ for g1,d1 in next,c do
+ if d1 and d1~=true then
+ c[g1]=pack_indexed(d1)
+ end
+ end
+ else
+ step.coverage=pack_normal(c)
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local f=d1[2] if f then d1[2]=pack_indexed(f) end
+ local s=d1[3] if s then d1[3]=pack_indexed(s) end
+ end
+ end
+ elseif kind=="gpos_mark2base" or kind=="gpos_mark2mark" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ d1[g2]=pack_indexed(d2)
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ d1[2]=pack_indexed(d1[2])
+ end
+ end
+ elseif kind=="gpos_mark2ligature" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ for g3,d3 in next,d2 do
+ d2[g3]=pack_indexed(d3)
+ end
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ d1[2]=pack_indexed(d1[2])
+ end
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local r=rule.before if r then for i=1,#r do r[i]=pack_boolean(r[i]) end end
+ local r=rule.after if r then for i=1,#r do r[i]=pack_boolean(r[i]) end end
+ local r=rule.current if r then for i=1,#r do r[i]=pack_boolean(r[i]) end end
+ local r=rule.replacements if r then rule.replacements=pack_flat (r) end
+ end
+ end
+ end
+ end
+ if order then
+ sequence.order=pack_indexed(order)
+ end
+ if features then
+ for script,feature in next,features do
+ features[script]=pack_normal(feature)
+ end
+ end
+ if flags then
+ sequence.flags=pack_normal(flags)
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ if features then
+ for k,list in next,features do
+ for feature,spec in next,list do
+ list[feature]=pack_normal(spec)
+ end
+ end
+ end
+ if palettes then
+ for i=1,#palettes do
+ local p=palettes[i]
+ for j=1,#p do
+ p[j]=pack_indexed(p[j])
+ end
+ end
+ end
+ if variable then
+ local instances=variable.instances
+ if instances then
+ for i=1,#instances do
+ local v=instances[i].values
+ for j=1,#v do
+ v[j]=pack_normal(v[j])
+ end
+ end
+ end
+ local function packdeltas(main)
+ if main then
+ local deltas=main.deltas
+ if deltas then
+ for i=1,#deltas do
+ local di=deltas[i]
+ local d=di.deltas
+ for j=1,#d do
+ d[j]=pack_indexed(d[j])
+ end
+ di.regions=pack_indexed(di.regions)
+ end
+ end
+ local regions=main.regions
+ if regions then
+ for i=1,#regions do
+ local r=regions[i]
+ for j=1,#r do
+ r[j]=pack_normal(r[j])
+ end
+ end
+ end
+ end
+ end
+ packdeltas(variable.global)
+ packdeltas(variable.horizontal)
+ packdeltas(variable.vertical)
+ packdeltas(variable.metrics)
+ end
+ if not success(1,pass) then
+ return
+ end
+ end
+ if nt>0 then
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 2, pass %s",pass)
+ end
+ local pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc=packers(pass)
+ for unicode,description in next,descriptions do
+ local math=description.math
+ if math then
+ local kerns=math.kerns
+ if kerns then
+ math.kerns=pack_normal(kerns)
+ end
+ end
+ end
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local features=sequence.features
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format=="pair" then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ d1[g2]=pack_normal(d2)
+ end
+ end
+ end
+ end
+ elseif kind=="gpos_mark2ligature" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ d1[g2]=pack_normal(d2)
+ end
+ end
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local r=rule.before if r then rule.before=pack_normal(r) end
+ local r=rule.after if r then rule.after=pack_normal(r) end
+ local r=rule.current if r then rule.current=pack_normal(r) end
+ end
+ end
+ end
+ end
+ if features then
+ sequence.features=pack_normal(features)
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ if variable then
+ local function unpackdeltas(main)
+ if main then
+ local regions=main.regions
+ if regions then
+ main.regions=pack_normal(regions)
+ end
+ end
+ end
+ unpackdeltas(variable.global)
+ unpackdeltas(variable.horizontal)
+ unpackdeltas(variable.vertical)
+ unpackdeltas(variable.metrics)
+ end
+ end
+ for pass=1,2 do
+ if trace_packing then
+ report_otf("start packing: stage 3, pass %s",pass)
+ end
+ local pack_normal,pack_indexed,pack_flat,pack_boolean,pack_mixed,pack_normal_cc=packers(pass)
+ local function packthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local features=sequence.features
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format=="pair" then
+ for g1,d1 in next,c do
+ c[g1]=pack_normal(d1)
+ end
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ c[g1]=pack_normal_cc(d1)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if sequences then
+ packthem(sequences)
+ end
+ if sublookups then
+ packthem(sublookups)
+ end
+ end
+ end
+ end
+end
+local unpacked_mt={
+ __index=function(t,k)
+ t[k]=false
+ return k
+ end
+}
+function readers.unpack(data)
+ if data then
+ local tables=data.tables
+ if tables then
+ local resources=data.resources
+ local descriptions=data.descriptions or data.glyphs
+ local sequences=resources.sequences
+ local sublookups=resources.sublookups
+ local features=resources.features
+ local palettes=resources.colorpalettes
+ local variable=resources.variabledata
+ local unpacked={}
+ setmetatable(unpacked,unpacked_mt)
+ for unicode,description in next,descriptions do
+ local tv=tables[description.boundingbox]
+ if tv then
+ description.boundingbox=tv
+ end
+ local math=description.math
+ if math then
+ local kerns=math.kerns
+ if kerns then
+ local tm=tables[kerns]
+ if tm then
+ math.kerns=tm
+ kerns=unpacked[tm]
+ end
+ if kerns then
+ for k,kern in next,kerns do
+ local tv=tables[kern]
+ if tv then
+ kerns[k]=tv
+ end
+ end
+ end
+ end
+ end
+ end
+ local function unpackthem(sequences)
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local kind=sequence.type
+ local steps=sequence.steps
+ local order=sequence.order
+ local features=sequence.features
+ local flags=sequence.flags
+ local markclass=sequence.markclass
+ if features then
+ local tv=tables[features]
+ if tv then
+ sequence.features=tv
+ features=tv
+ end
+ for script,feature in next,features do
+ local tv=tables[feature]
+ if tv then
+ features[script]=tv
+ end
+ end
+ end
+ if steps then
+ for i=1,#steps do
+ local step=steps[i]
+ if kind=="gpos_pair" then
+ local c=step.coverage
+ if c then
+ if step.format=="pair" then
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ c[g1]=tv
+ d1=tv
+ end
+ for g2,d2 in next,d1 do
+ local tv=tables[d2]
+ if tv then
+ d1[g2]=tv
+ d2=tv
+ end
+ local f=tables[d2[1]] if f then d2[1]=f end
+ local s=tables[d2[2]] if s then d2[2]=s end
+ end
+ end
+ else
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ c[g1]=tv
+ end
+ end
+ end
+ end
+ elseif kind=="gpos_single" then
+ local c=step.coverage
+ if c then
+ if step.format=="single" then
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ c[g1]=tv
+ end
+ end
+ else
+ local tv=tables[c]
+ if tv then
+ step.coverage=tv
+ end
+ end
+ end
+ elseif kind=="gpos_cursive" then
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local tv=tables[d1]
+ if tv then
+ d1=tv
+ c[g1]=d1
+ end
+ local f=tables[d1[2]] if f then d1[2]=f end
+ local s=tables[d1[3]] if s then d1[3]=s end
+ end
+ end
+ elseif kind=="gpos_mark2base" or kind=="gpos_mark2mark" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ local tv=tables[d2]
+ if tv then
+ d1[g2]=tv
+ end
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local tv=tables[d1[2]]
+ if tv then
+ d1[2]=tv
+ end
+ end
+ end
+ elseif kind=="gpos_mark2ligature" then
+ local c=step.baseclasses
+ if c then
+ for g1,d1 in next,c do
+ for g2,d2 in next,d1 do
+ local tv=tables[d2]
+ if tv then
+ d2=tv
+ d1[g2]=d2
+ end
+ for g3,d3 in next,d2 do
+ local tv=tables[d2[g3]]
+ if tv then
+ d2[g3]=tv
+ end
+ end
+ end
+ end
+ end
+ local c=step.coverage
+ if c then
+ for g1,d1 in next,c do
+ local tv=tables[d1[2]]
+ if tv then
+ d1[2]=tv
+ end
+ end
+ end
+ end
+ local rules=step.rules
+ if rules then
+ for i=1,#rules do
+ local rule=rules[i]
+ local before=rule.before
+ if before then
+ local tv=tables[before]
+ if tv then
+ rule.before=tv
+ before=tv
+ end
+ for i=1,#before do
+ local tv=tables[before[i]]
+ if tv then
+ before[i]=tv
+ end
+ end
+ end
+ local after=rule.after
+ if after then
+ local tv=tables[after]
+ if tv then
+ rule.after=tv
+ after=tv
+ end
+ for i=1,#after do
+ local tv=tables[after[i]]
+ if tv then
+ after[i]=tv
+ end
+ end
+ end
+ local current=rule.current
+ if current then
+ local tv=tables[current]
+ if tv then
+ rule.current=tv
+ current=tv
+ end
+ for i=1,#current do
+ local tv=tables[current[i]]
+ if tv then
+ current[i]=tv
+ end
+ end
+ end
+ local replacements=rule.replacements
+ if replacements then
+ local tv=tables[replacements]
+ if tv then
+ rule.replacements=tv
+ end
+ end
+ end
+ end
+ end
+ end
+ if order then
+ local tv=tables[order]
+ if tv then
+ sequence.order=tv
+ end
+ end
+ if flags then
+ local tv=tables[flags]
+ if tv then
+ sequence.flags=tv
+ end
+ end
+ end
+ end
+ if sequences then
+ unpackthem(sequences)
+ end
+ if sublookups then
+ unpackthem(sublookups)
+ end
+ if features then
+ for k,list in next,features do
+ for feature,spec in next,list do
+ local tv=tables[spec]
+ if tv then
+ list[feature]=tv
+ end
+ end
+ end
+ end
+ if palettes then
+ for i=1,#palettes do
+ local p=palettes[i]
+ for j=1,#p do
+ local tv=tables[p[j]]
+ if tv then
+ p[j]=tv
+ end
+ end
+ end
+ end
+ if variable then
+ local instances=variable.instances
+ if instances then
+ for i=1,#instances do
+ local v=instances[i].values
+ for j=1,#v do
+ local tv=tables[v[j]]
+ if tv then
+ v[j]=tv
+ end
+ end
+ end
+ end
+ local function unpackdeltas(main)
+ if main then
+ local deltas=main.deltas
+ if deltas then
+ for i=1,#deltas do
+ local di=deltas[i]
+ local d=di.deltas
+ local r=di.regions
+ for j=1,#d do
+ local tv=tables[d[j]]
+ if tv then
+ d[j]=tv
+ end
+ end
+ local tv=di.regions
+ if tv then
+ di.regions=tv
+ end
+ end
+ end
+ local regions=main.regions
+ if regions then
+ local tv=tables[regions]
+ if tv then
+ main.regions=tv
+ regions=tv
+ end
+ for i=1,#regions do
+ local r=regions[i]
+ for j=1,#r do
+ local tv=tables[r[j]]
+ if tv then
+ r[j]=tv
+ end
+ end
+ end
+ end
+ end
+ end
+ unpackdeltas(variable.global)
+ unpackdeltas(variable.horizontal)
+ unpackdeltas(variable.vertical)
+ unpackdeltas(variable.metrics)
+ end
+ data.tables=nil
+ end
+ end
+end
+local mt={
+ __index=function(t,k)
+ if k=="height" then
+ local ht=t.boundingbox[4]
+ return ht<0 and 0 or ht
+ elseif k=="depth" then
+ local dp=-t.boundingbox[2]
+ return dp<0 and 0 or dp
+ elseif k=="width" then
+ return 0
+ elseif k=="name" then
+ return forcenotdef and ".notdef"
+ end
+ end
+}
+local function sameformat(sequence,steps,first,nofsteps,kind)
+ return true
+end
+local function mergesteps_1(lookup,strict)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if strict then
+ local f=first.format
+ for i=2,nofsteps do
+ if steps[i].format~=f then
+ if trace_optimizations then
+ report_optimizations("not merging %a steps of %a lookup %a, different formats",nofsteps,lookup.type,lookup.name)
+ end
+ return 0
+ end
+ end
+ end
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ if not target[k] then
+ target[k]=v
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function mergesteps_2(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if strict then
+ local f=first.format
+ for i=2,nofsteps do
+ if steps[i].format~=f then
+ if trace_optimizations then
+ report_optimizations("not merging %a steps of %a lookup %a, different formats",nofsteps,lookup.type,lookup.name)
+ end
+ return 0
+ end
+ end
+ end
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=target[k]
+ if tk then
+ for kk,vv in next,v do
+ if tk[kk]==nil then
+ tk[kk]=vv
+ end
+ end
+ else
+ target[k]=v
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function mergesteps_3(lookup,strict)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local coverage={}
+ for i=1,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=coverage[k]
+ if tk then
+ if trace_optimizations then
+ report_optimizations("quitting merge due to multiple checks")
+ end
+ return nofsteps
+ else
+ coverage[k]=v
+ end
+ end
+ end
+ end
+ local first=steps[1]
+ local baseclasses={}
+ for i=1,nofsteps do
+ local offset=i*10
+ local step=steps[i]
+ for k,v in sortedhash(step.baseclasses) do
+ baseclasses[offset+k]=v
+ end
+ for k,v in next,step.coverage do
+ v[1]=offset+v[1]
+ end
+ end
+ first.baseclasses=baseclasses
+ first.coverage=coverage
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function nested(old,new)
+ for k,v in next,old do
+ if k=="ligature" then
+ if not new.ligature then
+ new.ligature=v
+ end
+ else
+ local n=new[k]
+ if n then
+ nested(v,n)
+ else
+ new[k]=v
+ end
+ end
+ end
+end
+local function mergesteps_4(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=target[k]
+ if tk then
+ nested(v,tk)
+ else
+ target[k]=v
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function mergesteps_5(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local first=steps[1]
+ if trace_optimizations then
+ report_optimizations("merging %a steps of %a lookup %a",nofsteps,lookup.type,lookup.name)
+ end
+ local target=first.coverage
+ local hash=nil
+ for k,v in next,target do
+ hash=v[1]
+ break
+ end
+ for i=2,nofsteps do
+ local c=steps[i].coverage
+ if c then
+ for k,v in next,c do
+ local tk=target[k]
+ if tk then
+ if not tk[2] then
+ tk[2]=v[2]
+ end
+ if not tk[3] then
+ tk[3]=v[3]
+ end
+ else
+ target[k]=v
+ v[1]=hash
+ end
+ end
+ end
+ end
+ lookup.nofsteps=1
+ lookup.merged=true
+ lookup.steps={ first }
+ return nofsteps-1
+end
+local function checkkerns(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local kerned=0
+ for i=1,nofsteps do
+ local step=steps[i]
+ if step.format=="pair" then
+ local coverage=step.coverage
+ local kerns=true
+ for g1,d1 in next,coverage do
+ if d1==true then
+ elseif not d1 then
+ elseif d1[1]~=0 or d1[2]~=0 or d1[4]~=0 then
+ kerns=false
+ break
+ end
+ end
+ if kerns then
+ if trace_optimizations then
+ report_optimizations("turning pairs of step %a of %a lookup %a into kerns",i,lookup.type,lookup.name)
+ end
+ local c={}
+ for g1,d1 in next,coverage do
+ if d1 and d1~=true then
+ c[g1]=d1[3]
+ end
+ end
+ step.coverage=c
+ step.format="move"
+ kerned=kerned+1
+ end
+ end
+ end
+ return kerned
+end
+local function checkpairs(lookup)
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ local kerned=0
+ local function onlykerns(step)
+ local coverage=step.coverage
+ for g1,d1 in next,coverage do
+ for g2,d2 in next,d1 do
+ if d2[2] then
+ return false
+ else
+ local v=d2[1]
+ if v==true then
+ elseif v and (v[1]~=0 or v[2]~=0 or v[4]~=0) then
+ return false
+ end
+ end
+ end
+ end
+ return coverage
+ end
+ for i=1,nofsteps do
+ local step=steps[i]
+ if step.format=="pair" then
+ local coverage=onlykerns(step)
+ if coverage then
+ if trace_optimizations then
+ report_optimizations("turning pairs of step %a of %a lookup %a into kerns",i,lookup.type,lookup.name)
+ end
+ for g1,d1 in next,coverage do
+ local d={}
+ for g2,d2 in next,d1 do
+ local v=d2[1]
+ if v==true then
+ elseif v then
+ d[g2]=v[3]
+ end
+ end
+ coverage[g1]=d
+ end
+ step.format="move"
+ kerned=kerned+1
+ end
+ end
+ end
+ return kerned
+end
+local compact_pairs=true
+local compact_singles=true
+local merge_pairs=true
+local merge_singles=true
+local merge_substitutions=true
+local merge_alternates=true
+local merge_multiples=true
+local merge_ligatures=true
+local merge_cursives=true
+local merge_marks=true
+directives.register("otf.compact.pairs",function(v) compact_pairs=v end)
+directives.register("otf.compact.singles",function(v) compact_singles=v end)
+directives.register("otf.merge.pairs",function(v) merge_pairs=v end)
+directives.register("otf.merge.singles",function(v) merge_singles=v end)
+directives.register("otf.merge.substitutions",function(v) merge_substitutions=v end)
+directives.register("otf.merge.alternates",function(v) merge_alternates=v end)
+directives.register("otf.merge.multiples",function(v) merge_multiples=v end)
+directives.register("otf.merge.ligatures",function(v) merge_ligatures=v end)
+directives.register("otf.merge.cursives",function(v) merge_cursives=v end)
+directives.register("otf.merge.marks",function(v) merge_marks=v end)
+function readers.compact(data)
+ if not data or data.compacted then
+ return
+ else
+ data.compacted=true
+ end
+ local resources=data.resources
+ local merged=0
+ local kerned=0
+ local allsteps=0
+ local function compact(what)
+ local lookups=resources[what]
+ if lookups then
+ for i=1,#lookups do
+ local lookup=lookups[i]
+ local nofsteps=lookup.nofsteps
+ local kind=lookup.type
+ allsteps=allsteps+nofsteps
+ if nofsteps>1 then
+ local merg=merged
+ if kind=="gsub_single" then
+ if merge_substitutions then
+ merged=merged+mergesteps_1(lookup)
+ end
+ elseif kind=="gsub_alternate" then
+ if merge_alternates then
+ merged=merged+mergesteps_1(lookup)
+ end
+ elseif kind=="gsub_multiple" then
+ if merge_multiples then
+ merged=merged+mergesteps_1(lookup)
+ end
+ elseif kind=="gsub_ligature" then
+ if merge_ligatures then
+ merged=merged+mergesteps_4(lookup)
+ end
+ elseif kind=="gpos_single" then
+ if merge_singles then
+ merged=merged+mergesteps_1(lookup,true)
+ end
+ if compact_singles then
+ kerned=kerned+checkkerns(lookup)
+ end
+ elseif kind=="gpos_pair" then
+ if merge_pairs then
+ merged=merged+mergesteps_2(lookup)
+ end
+ if compact_pairs then
+ kerned=kerned+checkpairs(lookup)
+ end
+ elseif kind=="gpos_cursive" then
+ if merge_cursives then
+ merged=merged+mergesteps_5(lookup)
+ end
+ elseif kind=="gpos_mark2mark" or kind=="gpos_mark2base" or kind=="gpos_mark2ligature" then
+ if merge_marks then
+ merged=merged+mergesteps_3(lookup)
+ end
+ end
+ if merg~=merged then
+ lookup.merged=true
+ end
+ elseif nofsteps==1 then
+ local kern=kerned
+ if kind=="gpos_single" then
+ if compact_singles then
+ kerned=kerned+checkkerns(lookup)
+ end
+ elseif kind=="gpos_pair" then
+ if compact_pairs then
+ kerned=kerned+checkpairs(lookup)
+ end
+ end
+ if kern~=kerned then
+ end
+ end
+ end
+ elseif trace_optimizations then
+ report_optimizations("no lookups in %a",what)
+ end
+ end
+ compact("sequences")
+ compact("sublookups")
+ if trace_optimizations then
+ if merged>0 then
+ report_optimizations("%i steps of %i removed due to merging",merged,allsteps)
+ end
+ if kerned>0 then
+ report_optimizations("%i steps of %i steps turned from pairs into kerns",kerned,allsteps)
+ end
+ end
+end
+local function mergesteps(t,k)
+ if k=="merged" then
+ local merged={}
+ for i=1,#t do
+ local step=t[i]
+ local coverage=step.coverage
+ for k in next,coverage do
+ local m=merged[k]
+ if m then
+ m[2]=i
+ else
+ merged[k]={ i,i }
+ end
+ end
+ end
+ t.merged=merged
+ return merged
+ end
+end
+local function checkmerge(sequence)
+ local steps=sequence.steps
+ if steps then
+ setmetatableindex(steps,mergesteps)
+ end
+end
+local function checkflags(sequence,resources)
+ if not sequence.skiphash then
+ local flags=sequence.flags
+ if flags then
+ local skipmark=flags[1]
+ local skipligature=flags[2]
+ local skipbase=flags[3]
+ local markclass=sequence.markclass
+ local skipsome=skipmark or skipligature or skipbase or markclass or false
+ if skipsome then
+ sequence.skiphash=setmetatableindex(function(t,k)
+ local c=resources.classes[k]
+ local v=c==skipmark
+ or (markclass and c=="mark" and not markclass[k])
+ or c==skipligature
+ or c==skipbase
+ or false
+ t[k]=v
+ return v
+ end)
+ else
+ sequence.skiphash=false
+ end
+ else
+ sequence.skiphash=false
+ end
+ end
+end
+local function checksteps(sequence)
+ local steps=sequence.steps
+ if steps then
+ for i=1,#steps do
+ steps[i].index=i
+ end
+ end
+end
+if fonts.helpers then
+ fonts.helpers.checkmerge=checkmerge
+ fonts.helpers.checkflags=checkflags
+ fonts.helpers.checksteps=checksteps
+end
+function readers.expand(data)
+ if not data or data.expanded then
+ return
+ else
+ data.expanded=true
+ end
+ local resources=data.resources
+ local sublookups=resources.sublookups
+ local sequences=resources.sequences
+ local markclasses=resources.markclasses
+ local descriptions=data.descriptions
+ if descriptions then
+ local defaultwidth=resources.defaultwidth or 0
+ local defaultheight=resources.defaultheight or 0
+ local defaultdepth=resources.defaultdepth or 0
+ local basename=trace_markwidth and file.basename(resources.filename)
+ for u,d in next,descriptions do
+ local bb=d.boundingbox
+ local wd=d.width
+ if not wd then
+ d.width=defaultwidth
+ elseif trace_markwidth and wd~=0 and d.class=="mark" then
+ report_markwidth("mark %a with width %b found in %a",d.name or "<noname>",wd,basename)
+ end
+ if bb then
+ local ht=bb[4]
+ local dp=-bb[2]
+ if ht==0 or ht<0 then
+ else
+ d.height=ht
+ end
+ if dp==0 or dp<0 then
+ else
+ d.depth=dp
+ end
+ end
+ end
+ end
+ local function expandlookups(sequences)
+ if sequences then
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ if steps then
+ local nofsteps=sequence.nofsteps
+ local kind=sequence.type
+ local markclass=sequence.markclass
+ if markclass then
+ if not markclasses then
+ report_warning("missing markclasses")
+ sequence.markclass=false
+ else
+ sequence.markclass=markclasses[markclass]
+ end
+ end
+ for i=1,nofsteps do
+ local step=steps[i]
+ local baseclasses=step.baseclasses
+ if baseclasses then
+ local coverage=step.coverage
+ for k,v in next,coverage do
+ v[1]=baseclasses[v[1]]
+ end
+ elseif kind=="gpos_cursive" then
+ local coverage=step.coverage
+ for k,v in next,coverage do
+ v[1]=coverage
+ end
+ end
+ local rules=step.rules
+ if rules then
+ local rulehash={ n=0 }
+ local rulesize=0
+ local coverage={}
+ local lookuptype=sequence.type
+ local nofrules=#rules
+ step.coverage=coverage
+ for currentrule=1,nofrules do
+ local rule=rules[currentrule]
+ local current=rule.current
+ local before=rule.before
+ local after=rule.after
+ local replacements=rule.replacements or false
+ local sequence={}
+ local nofsequences=0
+ if before then
+ for n=1,#before do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=before[n]
+ end
+ end
+ local start=nofsequences+1
+ for n=1,#current do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=current[n]
+ end
+ local stop=nofsequences
+ if after then
+ for n=1,#after do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=after[n]
+ end
+ end
+ local lookups=rule.lookups or false
+ local subtype=nil
+ if lookups then
+ for i=1,#lookups do
+ local lookups=lookups[i]
+ if lookups then
+ for k,v in next,lookups do
+ local lookup=sublookups[v]
+ if lookup then
+ lookups[k]=lookup
+ if not subtype then
+ subtype=lookup.type
+ end
+ else
+ end
+ end
+ end
+ end
+ end
+ if sequence[1] then
+ sequence.n=#sequence
+ local ruledata={
+ currentrule,
+ lookuptype,
+ sequence,
+ start,
+ stop,
+ lookups,
+ replacements,
+ subtype,
+ }
+ rulesize=rulesize+1
+ rulehash[rulesize]=ruledata
+ rulehash.n=rulesize
+ if true then
+ for unic in next,sequence[start] do
+ local cu=coverage[unic]
+ if cu then
+ local n=#cu+1
+ cu[n]=ruledata
+ cu.n=n
+ else
+ coverage[unic]={ ruledata,n=1 }
+ end
+ end
+ else
+ for unic in next,sequence[start] do
+ local cu=coverage[unic]
+ if cu then
+ else
+ coverage[unic]=rulehash
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ checkmerge(sequence)
+ checkflags(sequence,resources)
+ checksteps(sequence)
+ end
+ end
+ end
+ end
+ expandlookups(sequences)
+ expandlookups(sublookups)
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-otl']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+local lower=string.lower
+local type,next,tonumber,tostring,unpack=type,next,tonumber,tostring,unpack
+local abs=math.abs
+local derivetable=table.derive
+local formatters=string.formatters
+local setmetatableindex=table.setmetatableindex
+local allocate=utilities.storage.allocate
+local registertracker=trackers.register
+local registerdirective=directives.register
+local starttiming=statistics.starttiming
+local stoptiming=statistics.stoptiming
+local elapsedtime=statistics.elapsedtime
+local findbinfile=resolvers.findbinfile
+local trace_loading=false registertracker("otf.loading",function(v) trace_loading=v end)
+local trace_features=false registertracker("otf.features",function(v) trace_features=v end)
+local trace_defining=false registertracker("fonts.defining",function(v) trace_defining=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local fonts=fonts
+local otf=fonts.handlers.otf
+otf.version=3.109
+otf.cache=containers.define("fonts","otl",otf.version,true)
+otf.svgcache=containers.define("fonts","svg",otf.version,true)
+otf.pngcache=containers.define("fonts","png",otf.version,true)
+otf.pdfcache=containers.define("fonts","pdf",otf.version,true)
+otf.svgenabled=false
+otf.pngenabled=false
+local otfreaders=otf.readers
+local hashes=fonts.hashes
+local definers=fonts.definers
+local readers=fonts.readers
+local constructors=fonts.constructors
+local otffeatures=constructors.features.otf
+local registerotffeature=otffeatures.register
+local otfenhancers=constructors.enhancers.otf
+local registerotfenhancer=otfenhancers.register
+local forceload=false
+local cleanup=0
+local syncspace=true
+local forcenotdef=false
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local applyruntimefixes=fonts.treatments and fonts.treatments.applyfixes
+local wildcard="*"
+local default="dflt"
+local formats=fonts.formats
+formats.otf="opentype"
+formats.ttf="truetype"
+formats.ttc="truetype"
+registerdirective("fonts.otf.loader.cleanup",function(v) cleanup=tonumber(v) or (v and 1) or 0 end)
+registerdirective("fonts.otf.loader.force",function(v) forceload=v end)
+registerdirective("fonts.otf.loader.syncspace",function(v) syncspace=v end)
+registerdirective("fonts.otf.loader.forcenotdef",function(v) forcenotdef=v end)
+registerotfenhancer("check extra features",function() end)
+local checkmemory=utilities.lua and utilities.lua.checkmemory
+local threshold=100
+local tracememory=false
+registertracker("fonts.otf.loader.memory",function(v) tracememory=v end)
+if not checkmemory then
+ local collectgarbage=collectgarbage
+ checkmemory=function(previous,threshold)
+ local current=collectgarbage("count")
+ if previous then
+ local checked=(threshold or 64)*1024
+ if current-previous>checked then
+ collectgarbage("collect")
+ current=collectgarbage("count")
+ end
+ end
+ return current
+ end
+end
+function otf.load(filename,sub,instance)
+ local base=file.basename(file.removesuffix(filename))
+ local name=file.removesuffix(base)
+ local attr=lfs.attributes(filename)
+ local size=attr and attr.size or 0
+ local time=attr and attr.modification or 0
+ if sub=="" then
+ sub=false
+ end
+ local hash=name
+ if sub then
+ hash=hash.."-"..sub
+ end
+ if instance then
+ hash=hash.."-"..instance
+ end
+ hash=containers.cleanname(hash)
+ local data=containers.read(otf.cache,hash)
+ local reload=not data or data.size~=size or data.time~=time or data.tableversion~=otfreaders.tableversion
+ if forceload then
+ report_otf("forced reload of %a due to hard coded flag",filename)
+ reload=true
+ end
+ if reload then
+ report_otf("loading %a, hash %a",filename,hash)
+ starttiming(otfreaders,true)
+ data=otfreaders.loadfont(filename,sub or 1,instance)
+ if data then
+ local used=checkmemory()
+ local resources=data.resources
+ local svgshapes=resources.svgshapes
+ local pngshapes=resources.pngshapes
+ if cleanup==0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ if svgshapes then
+ resources.svgshapes=nil
+ if otf.svgenabled then
+ local timestamp=os.date()
+ containers.write(otf.svgcache,hash,{
+ svgshapes=svgshapes,
+ timestamp=timestamp,
+ })
+ data.properties.svg={
+ hash=hash,
+ timestamp=timestamp,
+ }
+ end
+ if cleanup>1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ end
+ if pngshapes then
+ resources.pngshapes=nil
+ if otf.pngenabled then
+ local timestamp=os.date()
+ containers.write(otf.pngcache,hash,{
+ pngshapes=pngshapes,
+ timestamp=timestamp,
+ })
+ data.properties.png={
+ hash=hash,
+ timestamp=timestamp,
+ }
+ end
+ if cleanup>1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ end
+ otfreaders.compact(data)
+ if cleanup==0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ otfreaders.rehash(data,"unicodes")
+ otfreaders.addunicodetable(data)
+ otfreaders.extend(data)
+ if cleanup==0 then
+ checkmemory(used,threshold,tracememory)
+ end
+ otfreaders.pack(data)
+ report_otf("loading done")
+ report_otf("saving %a in cache",filename)
+ data=containers.write(otf.cache,hash,data)
+ if cleanup>1 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ stoptiming(otfreaders)
+ if elapsedtime then
+ report_otf("loading, optimizing, packing and caching time %s",elapsedtime(otfreaders))
+ end
+ if cleanup>3 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ data=containers.read(otf.cache,hash)
+ if cleanup>2 then
+ collectgarbage("collect")
+ else
+ checkmemory(used,threshold,tracememory)
+ end
+ else
+ stoptiming(otfreaders)
+ data=nil
+ report_otf("loading failed due to read error")
+ end
+ end
+ if data then
+ if trace_defining then
+ report_otf("loading from cache using hash %a",hash)
+ end
+ otfreaders.unpack(data)
+ otfreaders.expand(data)
+ otfreaders.addunicodetable(data)
+ otfenhancers.apply(data,filename,data)
+ if applyruntimefixes then
+ applyruntimefixes(filename,data)
+ end
+ data.metadata.math=data.resources.mathconstants
+ local classes=data.resources.classes
+ if not classes then
+ local descriptions=data.descriptions
+ classes=setmetatableindex(function(t,k)
+ local d=descriptions[k]
+ local v=(d and d.class or "base") or false
+ t[k]=v
+ return v
+ end)
+ data.resources.classes=classes
+ end
+ end
+ return data
+end
+function otf.setfeatures(tfmdata,features)
+ local okay=constructors.initializefeatures("otf",tfmdata,features,trace_features,report_otf)
+ if okay then
+ return constructors.collectprocessors("otf",tfmdata,features,trace_features,report_otf)
+ else
+ return {}
+ end
+end
+local function copytotfm(data,cache_id)
+ if data then
+ local metadata=data.metadata
+ local properties=derivetable(data.properties)
+ local descriptions=derivetable(data.descriptions)
+ local goodies=derivetable(data.goodies)
+ local characters={}
+ local parameters={}
+ local mathparameters={}
+ local resources=data.resources
+ local unicodes=resources.unicodes
+ local spaceunits=500
+ local spacer="space"
+ local designsize=metadata.designsize or 100
+ local minsize=metadata.minsize or designsize
+ local maxsize=metadata.maxsize or designsize
+ local mathspecs=metadata.math
+ if designsize==0 then
+ designsize=100
+ minsize=100
+ maxsize=100
+ end
+ if mathspecs then
+ for name,value in next,mathspecs do
+ mathparameters[name]=value
+ end
+ end
+ for unicode in next,data.descriptions do
+ characters[unicode]={}
+ end
+ if mathspecs then
+ for unicode,character in next,characters do
+ local d=descriptions[unicode]
+ local m=d.math
+ if m then
+ local italic=m.italic
+ local vitalic=m.vitalic
+ local variants=m.hvariants
+ local parts=m.hparts
+ if variants then
+ local c=character
+ for i=1,#variants do
+ local un=variants[i]
+ c.next=un
+ c=characters[un]
+ end
+ c.horiz_variants=parts
+ elseif parts then
+ character.horiz_variants=parts
+ italic=m.hitalic
+ end
+ local variants=m.vvariants
+ local parts=m.vparts
+ if variants then
+ local c=character
+ for i=1,#variants do
+ local un=variants[i]
+ c.next=un
+ c=characters[un]
+ end
+ c.vert_variants=parts
+ elseif parts then
+ character.vert_variants=parts
+ end
+ if italic and italic~=0 then
+ character.italic=italic
+ end
+ if vitalic and vitalic~=0 then
+ character.vert_italic=vitalic
+ end
+ local accent=m.accent
+ if accent then
+ character.accent=accent
+ end
+ local kerns=m.kerns
+ if kerns then
+ character.mathkerns=kerns
+ end
+ end
+ end
+ end
+ local filename=constructors.checkedfilename(resources)
+ local fontname=metadata.fontname
+ local fullname=metadata.fullname or fontname
+ local psname=fontname or fullname
+ local subfont=metadata.subfontindex
+ local units=metadata.units or 1000
+ if units==0 then
+ units=1000
+ metadata.units=1000
+ report_otf("changing %a units to %a",0,units)
+ end
+ local monospaced=metadata.monospaced
+ local charwidth=metadata.averagewidth
+ local charxheight=metadata.xheight
+ local italicangle=metadata.italicangle
+ local hasitalics=metadata.hasitalics
+ properties.monospaced=monospaced
+ properties.hasitalics=hasitalics
+ parameters.italicangle=italicangle
+ parameters.charwidth=charwidth
+ parameters.charxheight=charxheight
+ local space=0x0020
+ local emdash=0x2014
+ if monospaced then
+ if descriptions[space] then
+ spaceunits,spacer=descriptions[space].width,"space"
+ end
+ if not spaceunits and descriptions[emdash] then
+ spaceunits,spacer=descriptions[emdash].width,"emdash"
+ end
+ if not spaceunits and charwidth then
+ spaceunits,spacer=charwidth,"charwidth"
+ end
+ else
+ if descriptions[space] then
+ spaceunits,spacer=descriptions[space].width,"space"
+ end
+ if not spaceunits and descriptions[emdash] then
+ spaceunits,spacer=descriptions[emdash].width/2,"emdash/2"
+ end
+ if not spaceunits and charwidth then
+ spaceunits,spacer=charwidth,"charwidth"
+ end
+ end
+ spaceunits=tonumber(spaceunits) or units/2
+ parameters.slant=0
+ parameters.space=spaceunits
+ parameters.space_stretch=1*units/2
+ parameters.space_shrink=1*units/3
+ parameters.x_height=2*units/5
+ parameters.quad=units
+ if spaceunits<2*units/5 then
+ end
+ if italicangle and italicangle~=0 then
+ parameters.italicangle=italicangle
+ parameters.italicfactor=math.cos(math.rad(90+italicangle))
+ parameters.slant=- math.tan(italicangle*math.pi/180)
+ end
+ if monospaced then
+ parameters.space_stretch=0
+ parameters.space_shrink=0
+ elseif syncspace then
+ parameters.space_stretch=spaceunits/2
+ parameters.space_shrink=spaceunits/3
+ end
+ parameters.extra_space=parameters.space_shrink
+ if charxheight then
+ parameters.x_height=charxheight
+ else
+ local x=0x0078
+ if x then
+ local x=descriptions[x]
+ if x then
+ parameters.x_height=x.height
+ end
+ end
+ end
+ parameters.designsize=(designsize/10)*65536
+ parameters.minsize=(minsize/10)*65536
+ parameters.maxsize=(maxsize/10)*65536
+ parameters.ascender=abs(metadata.ascender or 0)
+ parameters.descender=abs(metadata.descender or 0)
+ parameters.units=units
+ parameters.vheight=metadata.defaultvheight
+ properties.space=spacer
+ properties.encodingbytes=2
+ properties.format=data.format or formats.otf
+ properties.filename=filename
+ properties.fontname=fontname
+ properties.fullname=fullname
+ properties.psname=psname
+ properties.name=filename or fullname
+ properties.subfont=subfont
+ properties.private=properties.private or data.private or privateoffset
+ return {
+ characters=characters,
+ descriptions=descriptions,
+ parameters=parameters,
+ mathparameters=mathparameters,
+ resources=resources,
+ properties=properties,
+ goodies=goodies,
+ }
+ end
+end
+local converters={
+ woff={
+ cachename="webfonts",
+ action=otf.readers.woff2otf,
+ }
+}
+local function checkconversion(specification)
+ local filename=specification.filename
+ local converter=converters[lower(file.suffix(filename))]
+ if converter then
+ local base=file.basename(filename)
+ local name=file.removesuffix(base)
+ local attr=lfs.attributes(filename)
+ local size=attr and attr.size or 0
+ local time=attr and attr.modification or 0
+ if size>0 then
+ local cleanname=containers.cleanname(name)
+ local cachename=caches.setfirstwritablefile(cleanname,converter.cachename)
+ if not io.exists(cachename) or (time~=lfs.attributes(cachename).modification) then
+ report_otf("caching font %a in %a",filename,cachename)
+ converter.action(filename,cachename)
+ lfs.touch(cachename,time,time)
+ end
+ specification.filename=cachename
+ end
+ end
+end
+local function otftotfm(specification)
+ local cache_id=specification.hash
+ local tfmdata=containers.read(constructors.cache,cache_id)
+ if not tfmdata then
+ checkconversion(specification)
+ local name=specification.name
+ local sub=specification.sub
+ local subindex=specification.subindex
+ local filename=specification.filename
+ local features=specification.features.normal
+ local instance=specification.instance or (features and features.axis)
+ local rawdata=otf.load(filename,sub,instance)
+ if rawdata and next(rawdata) then
+ local descriptions=rawdata.descriptions
+ rawdata.lookuphash={}
+ tfmdata=copytotfm(rawdata,cache_id)
+ if tfmdata and next(tfmdata) then
+ local features=constructors.checkedfeatures("otf",features)
+ local shared=tfmdata.shared
+ if not shared then
+ shared={}
+ tfmdata.shared=shared
+ end
+ shared.rawdata=rawdata
+ shared.dynamics={}
+ tfmdata.changed={}
+ shared.features=features
+ shared.processes=otf.setfeatures(tfmdata,features)
+ end
+ end
+ containers.write(constructors.cache,cache_id,tfmdata)
+ end
+ return tfmdata
+end
+local function read_from_otf(specification)
+ local tfmdata=otftotfm(specification)
+ if tfmdata then
+ tfmdata.properties.name=specification.name
+ tfmdata.properties.sub=specification.sub
+ tfmdata=constructors.scale(tfmdata,specification)
+ local allfeatures=tfmdata.shared.features or specification.features.normal
+ constructors.applymanipulators("otf",tfmdata,allfeatures,trace_features,report_otf)
+ constructors.setname(tfmdata,specification)
+ fonts.loggers.register(tfmdata,file.suffix(specification.filename),specification)
+ end
+ return tfmdata
+end
+local function checkmathsize(tfmdata,mathsize)
+ local mathdata=tfmdata.shared.rawdata.metadata.math
+ local mathsize=tonumber(mathsize)
+ if mathdata then
+ local parameters=tfmdata.parameters
+ parameters.scriptpercentage=mathdata.ScriptPercentScaleDown
+ parameters.scriptscriptpercentage=mathdata.ScriptScriptPercentScaleDown
+ parameters.mathsize=mathsize
+ end
+end
+registerotffeature {
+ name="mathsize",
+ description="apply mathsize specified in the font",
+ initializers={
+ base=checkmathsize,
+ node=checkmathsize,
+ }
+}
+function otf.collectlookups(rawdata,kind,script,language)
+ if not kind then
+ return
+ end
+ if not script then
+ script=default
+ end
+ if not language then
+ language=default
+ end
+ local lookupcache=rawdata.lookupcache
+ if not lookupcache then
+ lookupcache={}
+ rawdata.lookupcache=lookupcache
+ end
+ local kindlookup=lookupcache[kind]
+ if not kindlookup then
+ kindlookup={}
+ lookupcache[kind]=kindlookup
+ end
+ local scriptlookup=kindlookup[script]
+ if not scriptlookup then
+ scriptlookup={}
+ kindlookup[script]=scriptlookup
+ end
+ local languagelookup=scriptlookup[language]
+ if not languagelookup then
+ local sequences=rawdata.resources.sequences
+ local featuremap={}
+ local featurelist={}
+ if sequences then
+ for s=1,#sequences do
+ local sequence=sequences[s]
+ local features=sequence.features
+ if features then
+ features=features[kind]
+ if features then
+ features=features[script] or features[wildcard]
+ if features then
+ features=features[language] or features[wildcard]
+ if features then
+ if not featuremap[sequence] then
+ featuremap[sequence]=true
+ featurelist[#featurelist+1]=sequence
+ end
+ end
+ end
+ end
+ end
+ end
+ if #featurelist==0 then
+ featuremap,featurelist=false,false
+ end
+ else
+ featuremap,featurelist=false,false
+ end
+ languagelookup={ featuremap,featurelist }
+ scriptlookup[language]=languagelookup
+ end
+ return unpack(languagelookup)
+end
+local function getgsub(tfmdata,k,kind,value)
+ local shared=tfmdata.shared
+ local rawdata=shared and shared.rawdata
+ if rawdata then
+ local sequences=rawdata.resources.sequences
+ if sequences then
+ local properties=tfmdata.properties
+ local validlookups,lookuplist=otf.collectlookups(rawdata,kind,properties.script,properties.language)
+ if validlookups then
+ for i=1,#lookuplist do
+ local lookup=lookuplist[i]
+ local steps=lookup.steps
+ local nofsteps=lookup.nofsteps
+ for i=1,nofsteps do
+ local coverage=steps[i].coverage
+ if coverage then
+ local found=coverage[k]
+ if found then
+ return found,lookup.type
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+end
+otf.getgsub=getgsub
+function otf.getsubstitution(tfmdata,k,kind,value)
+ local found,kind=getgsub(tfmdata,k,kind,value)
+ if not found then
+ elseif kind=="gsub_single" then
+ return found
+ elseif kind=="gsub_alternate" then
+ local choice=tonumber(value) or 1
+ return found[choice] or found[1] or k
+ end
+ return k
+end
+otf.getalternate=otf.getsubstitution
+function otf.getmultiple(tfmdata,k,kind)
+ local found,kind=getgsub(tfmdata,k,kind)
+ if found and kind=="gsub_multiple" then
+ return found
+ end
+ return { k }
+end
+function otf.getkern(tfmdata,left,right,kind)
+ local kerns=getgsub(tfmdata,left,kind or "kern",true)
+ if kerns then
+ local found=kerns[right]
+ local kind=type(found)
+ if kind=="table" then
+ found=found[1][3]
+ elseif kind~="number" then
+ found=false
+ end
+ if found then
+ return found*tfmdata.parameters.factor
+ end
+ end
+ return 0
+end
+local function check_otf(forced,specification,suffix)
+ local name=specification.name
+ if forced then
+ name=specification.forcedname
+ end
+ local fullname=findbinfile(name,suffix) or ""
+ if fullname=="" then
+ fullname=fonts.names.getfilename(name,suffix) or ""
+ end
+ if fullname~="" and not fonts.names.ignoredfile(fullname) then
+ specification.filename=fullname
+ return read_from_otf(specification)
+ end
+end
+local function opentypereader(specification,suffix)
+ local forced=specification.forced or ""
+ if formats[forced] then
+ return check_otf(true,specification,forced)
+ else
+ return check_otf(false,specification,suffix)
+ end
+end
+readers.opentype=opentypereader
+function readers.otf(specification) return opentypereader(specification,"otf") end
+function readers.ttf(specification) return opentypereader(specification,"ttf") end
+function readers.ttc(specification) return opentypereader(specification,"ttf") end
+function readers.woff(specification)
+ checkconversion(specification)
+ opentypereader(specification,"")
+end
+function otf.scriptandlanguage(tfmdata,attr)
+ local properties=tfmdata.properties
+ return properties.script or "dflt",properties.language or "dflt"
+end
+local function justset(coverage,unicode,replacement)
+ coverage[unicode]=replacement
+end
+otf.coverup={
+ stepkey="steps",
+ actions={
+ chainsubstitution=justset,
+ chainposition=justset,
+ substitution=justset,
+ alternate=justset,
+ multiple=justset,
+ kern=justset,
+ pair=justset,
+ single=justset,
+ ligature=function(coverage,unicode,ligature)
+ local first=ligature[1]
+ local tree=coverage[first]
+ if not tree then
+ tree={}
+ coverage[first]=tree
+ end
+ for i=2,#ligature do
+ local l=ligature[i]
+ local t=tree[l]
+ if not t then
+ t={}
+ tree[l]=t
+ end
+ tree=t
+ end
+ tree.ligature=unicode
+ end,
+ },
+ register=function(coverage,featuretype,format)
+ return {
+ format=format,
+ coverage=coverage,
+ }
+ end
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-oto']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local concat,unpack=table.concat,table.unpack
+local insert,remove=table.insert,table.remove
+local format,gmatch,gsub,find,match,lower,strip=string.format,string.gmatch,string.gsub,string.find,string.match,string.lower,string.strip
+local type,next,tonumber,tostring,rawget=type,next,tonumber,tostring,rawget
+local trace_baseinit=false trackers.register("otf.baseinit",function(v) trace_baseinit=v end)
+local trace_singles=false trackers.register("otf.singles",function(v) trace_singles=v end)
+local trace_multiples=false trackers.register("otf.multiples",function(v) trace_multiples=v end)
+local trace_alternatives=false trackers.register("otf.alternatives",function(v) trace_alternatives=v end)
+local trace_ligatures=false trackers.register("otf.ligatures",function(v) trace_ligatures=v end)
+local trace_kerns=false trackers.register("otf.kerns",function(v) trace_kerns=v end)
+local trace_preparing=false trackers.register("otf.preparing",function(v) trace_preparing=v end)
+local report_prepare=logs.reporter("fonts","otf prepare")
+local fonts=fonts
+local otf=fonts.handlers.otf
+local otffeatures=otf.features
+local registerotffeature=otffeatures.register
+otf.defaultbasealternate="none"
+local getprivate=fonts.constructors.getprivate
+local wildcard="*"
+local default="dflt"
+local formatters=string.formatters
+local f_unicode=formatters["%U"]
+local f_uniname=formatters["%U (%s)"]
+local f_unilist=formatters["% t (% t)"]
+local function gref(descriptions,n)
+ if type(n)=="number" then
+ local name=descriptions[n].name
+ if name then
+ return f_uniname(n,name)
+ else
+ return f_unicode(n)
+ end
+ elseif n then
+ local num={}
+ local nam={}
+ local j=0
+ for i=1,#n do
+ local ni=n[i]
+ if tonumber(ni) then
+ j=j+1
+ local di=descriptions[ni]
+ num[j]=f_unicode(ni)
+ nam[j]=di and di.name or "-"
+ end
+ end
+ return f_unilist(num,nam)
+ else
+ return "<error in base mode tracing>"
+ end
+end
+local function cref(feature,sequence)
+ return formatters["feature %a, type %a, chain lookup %a"](feature,sequence.type,sequence.name)
+end
+local function report_substitution(feature,sequence,descriptions,unicode,substitution)
+ if unicode==substitution then
+ report_prepare("%s: base substitution %s maps onto itself",
+ cref(feature,sequence),
+ gref(descriptions,unicode))
+ else
+ report_prepare("%s: base substitution %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ gref(descriptions,substitution))
+ end
+end
+local function report_alternate(feature,sequence,descriptions,unicode,replacement,value,comment)
+ if unicode==replacement then
+ report_prepare("%s: base alternate %s maps onto itself",
+ cref(feature,sequence),
+ gref(descriptions,unicode))
+ else
+ report_prepare("%s: base alternate %s => %s (%S => %S)",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ replacement and gref(descriptions,replacement),
+ value,
+ comment)
+ end
+end
+local function report_ligature(feature,sequence,descriptions,unicode,ligature)
+ report_prepare("%s: base ligature %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,ligature),
+ gref(descriptions,unicode))
+end
+local function report_kern(feature,sequence,descriptions,unicode,otherunicode,value)
+ report_prepare("%s: base kern %s + %s => %S",
+ cref(feature,sequence),
+ gref(descriptions,unicode),
+ gref(descriptions,otherunicode),
+ value)
+end
+local basehash,basehashes,applied={},1,{}
+local function registerbasehash(tfmdata)
+ local properties=tfmdata.properties
+ local hash=concat(applied," ")
+ local base=basehash[hash]
+ if not base then
+ basehashes=basehashes+1
+ base=basehashes
+ basehash[hash]=base
+ end
+ properties.basehash=base
+ properties.fullname=(properties.fullname or properties.name).."-"..base
+ applied={}
+end
+local function registerbasefeature(feature,value)
+ applied[#applied+1]=feature.."="..tostring(value)
+end
+local function makefake(tfmdata,name,present)
+ local private=getprivate(tfmdata)
+ local character={ intermediate=true,ligatures={} }
+ resources.unicodes[name]=private
+ tfmdata.characters[private]=character
+ tfmdata.descriptions[private]={ name=name }
+ present[name]=private
+ return character
+end
+local function make_1(present,tree,name)
+ for k,v in next,tree do
+ if k=="ligature" then
+ present[name]=v
+ else
+ make_1(present,v,name.."_"..k)
+ end
+ end
+end
+local function make_2(present,tfmdata,characters,tree,name,preceding,unicode,done)
+ for k,v in next,tree do
+ if k=="ligature" then
+ local character=characters[preceding]
+ if not character then
+ if trace_baseinit then
+ report_prepare("weird ligature in lookup %a, current %C, preceding %C",sequence.name,v,preceding)
+ end
+ character=makefake(tfmdata,name,present)
+ end
+ local ligatures=character.ligatures
+ if ligatures then
+ ligatures[unicode]={ char=v }
+ else
+ character.ligatures={ [unicode]={ char=v } }
+ end
+ if done then
+ local d=done[name]
+ if not d then
+ done[name]={ "dummy",v }
+ else
+ d[#d+1]=v
+ end
+ end
+ else
+ local code=present[name] or unicode
+ local name=name.."_"..k
+ make_2(present,tfmdata,characters,v,name,code,k,done)
+ end
+ end
+end
+local function preparesubstitutions(tfmdata,feature,value,validlookups,lookuplist)
+ local characters=tfmdata.characters
+ local descriptions=tfmdata.descriptions
+ local resources=tfmdata.resources
+ local changed=tfmdata.changed
+ local ligatures={}
+ local alternate=tonumber(value) or true and 1
+ local defaultalt=otf.defaultbasealternate
+ local trace_singles=trace_baseinit and trace_singles
+ local trace_alternatives=trace_baseinit and trace_alternatives
+ local trace_ligatures=trace_baseinit and trace_ligatures
+ if not changed then
+ changed={}
+ tfmdata.changed=changed
+ end
+ for i=1,#lookuplist do
+ local sequence=lookuplist[i]
+ local steps=sequence.steps
+ local kind=sequence.type
+ if kind=="gsub_single" then
+ for i=1,#steps do
+ for unicode,data in next,steps[i].coverage do
+ if unicode~=data then
+ changed[unicode]=data
+ end
+ if trace_singles then
+ report_substitution(feature,sequence,descriptions,unicode,data)
+ end
+ end
+ end
+ elseif kind=="gsub_alternate" then
+ for i=1,#steps do
+ for unicode,data in next,steps[i].coverage do
+ local replacement=data[alternate]
+ if replacement then
+ if unicode~=replacement then
+ changed[unicode]=replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,"normal")
+ end
+ elseif defaultalt=="first" then
+ replacement=data[1]
+ if unicode~=replacement then
+ changed[unicode]=replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,defaultalt)
+ end
+ elseif defaultalt=="last" then
+ replacement=data[#data]
+ if unicode~=replacement then
+ changed[unicode]=replacement
+ end
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,defaultalt)
+ end
+ else
+ if trace_alternatives then
+ report_alternate(feature,sequence,descriptions,unicode,replacement,value,"unknown")
+ end
+ end
+ end
+ end
+ elseif kind=="gsub_ligature" then
+ for i=1,#steps do
+ for unicode,data in next,steps[i].coverage do
+ ligatures[#ligatures+1]={ unicode,data,"" }
+ if trace_ligatures then
+ report_ligature(feature,sequence,descriptions,unicode,data)
+ end
+ end
+ end
+ end
+ end
+ local nofligatures=#ligatures
+ if nofligatures>0 then
+ local characters=tfmdata.characters
+ local present={}
+ local done=trace_baseinit and trace_ligatures and {}
+ for i=1,nofligatures do
+ local ligature=ligatures[i]
+ local unicode=ligature[1]
+ local tree=ligature[2]
+ make_1(present,tree,"ctx_"..unicode)
+ end
+ for i=1,nofligatures do
+ local ligature=ligatures[i]
+ local unicode=ligature[1]
+ local tree=ligature[2]
+ local lookupname=ligature[3]
+ make_2(present,tfmdata,characters,tree,"ctx_"..unicode,unicode,unicode,done,sequence)
+ end
+ end
+end
+local function preparepositionings(tfmdata,feature,value,validlookups,lookuplist)
+ local characters=tfmdata.characters
+ local descriptions=tfmdata.descriptions
+ local resources=tfmdata.resources
+ local properties=tfmdata.properties
+ local traceindeed=trace_baseinit and trace_kerns
+ for i=1,#lookuplist do
+ local sequence=lookuplist[i]
+ local steps=sequence.steps
+ local kind=sequence.type
+ local format=sequence.format
+ if kind=="gpos_pair" then
+ for i=1,#steps do
+ local step=steps[i]
+ local format=step.format
+ if format=="kern" or format=="move" then
+ for unicode,data in next,steps[i].coverage do
+ local character=characters[unicode]
+ local kerns=character.kerns
+ if not kerns then
+ kerns={}
+ character.kerns=kerns
+ end
+ if traceindeed then
+ for otherunicode,kern in next,data do
+ if not kerns[otherunicode] and kern~=0 then
+ kerns[otherunicode]=kern
+ report_kern(feature,sequence,descriptions,unicode,otherunicode,kern)
+ end
+ end
+ else
+ for otherunicode,kern in next,data do
+ if not kerns[otherunicode] and kern~=0 then
+ kerns[otherunicode]=kern
+ end
+ end
+ end
+ end
+ else
+ for unicode,data in next,steps[i].coverage do
+ local character=characters[unicode]
+ local kerns=character.kerns
+ for otherunicode,kern in next,data do
+ local other=kern[2]
+ if other==true or (not other and not (kerns and kerns[otherunicode])) then
+ local kern=kern[1]
+ if kern==true then
+ elseif kern[1]~=0 or kern[2]~=0 or kern[4]~=0 then
+ else
+ kern=kern[3]
+ if kern~=0 then
+ if kerns then
+ kerns[otherunicode]=kern
+ else
+ kerns={ [otherunicode]=kern }
+ character.kerns=kerns
+ end
+ if traceindeed then
+ report_kern(feature,sequence,descriptions,unicode,otherunicode,kern)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local function initializehashes(tfmdata)
+end
+local function checkmathreplacements(tfmdata,fullname,fixitalics)
+ if tfmdata.mathparameters then
+ local characters=tfmdata.characters
+ local changed=tfmdata.changed
+ if next(changed) then
+ if trace_preparing or trace_baseinit then
+ report_prepare("checking math replacements for %a",fullname)
+ end
+ for unicode,replacement in next,changed do
+ local u=characters[unicode]
+ local r=characters[replacement]
+ if u and r then
+ local n=u.next
+ local v=u.vert_variants
+ local h=u.horiz_variants
+ if fixitalics then
+ local ui=u.italic
+ if ui and not r.italic then
+ if trace_preparing then
+ report_prepare("using %i units of italic correction from %C for %U",ui,unicode,replacement)
+ end
+ r.italic=ui
+ end
+ end
+ if n and not r.next then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","incremental step",unicode,replacement)
+ end
+ r.next=n
+ end
+ if v and not r.vert_variants then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","vertical variants",unicode,replacement)
+ end
+ r.vert_variants=v
+ end
+ if h and not r.horiz_variants then
+ if trace_preparing then
+ report_prepare("forcing %s for %C substituted by %U","horizontal variants",unicode,replacement)
+ end
+ r.horiz_variants=h
+ end
+ else
+ if trace_preparing then
+ report_prepare("error replacing %C by %U",unicode,replacement)
+ end
+ end
+ end
+ end
+ end
+end
+local function featuresinitializer(tfmdata,value)
+ if true then
+ local starttime=trace_preparing and os.clock()
+ local features=tfmdata.shared.features
+ local fullname=tfmdata.properties.fullname or "?"
+ if features then
+ initializehashes(tfmdata)
+ local collectlookups=otf.collectlookups
+ local rawdata=tfmdata.shared.rawdata
+ local properties=tfmdata.properties
+ local script=properties.script
+ local language=properties.language
+ local rawresources=rawdata.resources
+ local rawfeatures=rawresources and rawresources.features
+ local basesubstitutions=rawfeatures and rawfeatures.gsub
+ local basepositionings=rawfeatures and rawfeatures.gpos
+ local substitutionsdone=false
+ local positioningsdone=false
+ if basesubstitutions or basepositionings then
+ local sequences=tfmdata.resources.sequences
+ for s=1,#sequences do
+ local sequence=sequences[s]
+ local sfeatures=sequence.features
+ if sfeatures then
+ local order=sequence.order
+ if order then
+ for i=1,#order do
+ local feature=order[i]
+ local value=features[feature]
+ if value then
+ local validlookups,lookuplist=collectlookups(rawdata,feature,script,language)
+ if not validlookups then
+ elseif basesubstitutions and basesubstitutions[feature] then
+ if trace_preparing then
+ report_prepare("filtering base %s feature %a for %a with value %a","sub",feature,fullname,value)
+ end
+ preparesubstitutions(tfmdata,feature,value,validlookups,lookuplist)
+ registerbasefeature(feature,value)
+ substitutionsdone=true
+ elseif basepositionings and basepositionings[feature] then
+ if trace_preparing then
+ report_prepare("filtering base %a feature %a for %a with value %a","pos",feature,fullname,value)
+ end
+ preparepositionings(tfmdata,feature,value,validlookups,lookuplist)
+ registerbasefeature(feature,value)
+ positioningsdone=true
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if substitutionsdone then
+ checkmathreplacements(tfmdata,fullname,features.fixitalics)
+ end
+ registerbasehash(tfmdata)
+ end
+ if trace_preparing then
+ report_prepare("preparation time is %0.3f seconds for %a",os.clock()-starttime,fullname)
+ end
+ end
+end
+registerotffeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ base=featuresinitializer,
+ }
+}
+otf.basemodeinitializer=featuresinitializer
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-otj']={
+ version=1.001,
+ comment="companion to font-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+if not nodes.properties then return end
+local next,rawget,tonumber=next,rawget,tonumber
+local fastcopy=table.fastcopy
+local registertracker=trackers.register
+local registerdirective=directives.register
+local trace_injections=false registertracker("fonts.injections",function(v) trace_injections=v end)
+local trace_marks=false registertracker("fonts.injections.marks",function(v) trace_marks=v end)
+local trace_cursive=false registertracker("fonts.injections.cursive",function(v) trace_cursive=v end)
+local trace_spaces=false registertracker("fonts.injections.spaces",function(v) trace_spaces=v end)
+local report_injections=logs.reporter("fonts","injections")
+local report_spaces=logs.reporter("fonts","spaces")
+local attributes,nodes,node=attributes,nodes,node
+fonts=fonts
+local hashes=fonts.hashes
+local fontdata=hashes.identifiers
+local fontmarks=hashes.marks
+nodes.injections=nodes.injections or {}
+local injections=nodes.injections
+local tracers=nodes.tracers
+local setcolor=tracers and tracers.colors.set
+local resetcolor=tracers and tracers.colors.reset
+local nodecodes=nodes.nodecodes
+local glyph_code=nodecodes.glyph
+local disc_code=nodecodes.disc
+local kern_code=nodecodes.kern
+local glue_code=nodecodes.glue
+local nuts=nodes.nuts
+local nodepool=nuts.pool
+local tonode=nuts.tonode
+local tonut=nuts.tonut
+local setfield=nuts.setfield
+local getnext=nuts.getnext
+local getprev=nuts.getprev
+local getid=nuts.getid
+local getfont=nuts.getfont
+local getchar=nuts.getchar
+local getoffsets=nuts.getoffsets
+local getboth=nuts.getboth
+local getdisc=nuts.getdisc
+local setdisc=nuts.setdisc
+local setoffsets=nuts.setoffsets
+local ischar=nuts.ischar
+local getkern=nuts.getkern
+local setkern=nuts.setkern
+local setlink=nuts.setlink
+local setwidth=nuts.setwidth
+local getwidth=nuts.getwidth
+local nextchar=nuts.traversers.char
+local nextglue=nuts.traversers.glue
+local insert_node_before=nuts.insert_before
+local insert_node_after=nuts.insert_after
+local properties=nodes.properties.data
+local fontkern=nuts.pool and nuts.pool.fontkern
+local italickern=nuts.pool and nuts.pool.italickern
+local useitalickerns=false
+directives.register("fonts.injections.useitalics",function(v)
+ if v then
+ report_injections("using italics for space kerns (tracing only)")
+ end
+ useitalickerns=v
+end)
+do if not fontkern then
+ local thekern=nuts.new("kern",0)
+ local setkern=nuts.setkern
+ local copy_node=nuts.copy_node
+ fontkern=function(k)
+ local n=copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+end end
+do if not italickern then
+ local thekern=nuts.new("kern",3)
+ local setkern=nuts.setkern
+ local copy_node=nuts.copy_node
+ italickern=function(k)
+ local n=copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+end end
+function injections.installnewkern() end
+local nofregisteredkerns=0
+local nofregisteredpositions=0
+local nofregisteredmarks=0
+local nofregisteredcursives=0
+local keepregisteredcounts=false
+function injections.keepcounts()
+ keepregisteredcounts=true
+end
+function injections.resetcounts()
+ nofregisteredkerns=0
+ nofregisteredpositions=0
+ nofregisteredmarks=0
+ nofregisteredcursives=0
+ keepregisteredcounts=false
+end
+function injections.reset(n)
+ local p=rawget(properties,n)
+ if p then
+ p.injections=false
+ else
+ properties[n]=false
+ end
+end
+function injections.copy(target,source)
+ local sp=rawget(properties,source)
+ if sp then
+ local tp=rawget(properties,target)
+ local si=sp.injections
+ if si then
+ si=fastcopy(si)
+ if tp then
+ tp.injections=si
+ else
+ properties[target]={
+ injections=si,
+ }
+ end
+ elseif tp then
+ tp.injections=false
+ else
+ properties[target]={ injections={} }
+ end
+ else
+ local tp=rawget(properties,target)
+ if tp then
+ tp.injections=false
+ else
+ properties[target]=false
+ end
+ end
+end
+function injections.setligaindex(n,index)
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections
+ if i then
+ i.ligaindex=index
+ else
+ p.injections={
+ ligaindex=index
+ }
+ end
+ else
+ properties[n]={
+ injections={
+ ligaindex=index
+ }
+ }
+ end
+end
+function injections.getligaindex(n,default)
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections
+ if i then
+ return i.ligaindex or default
+ end
+ end
+ return default
+end
+function injections.setcursive(start,nxt,factor,rlmode,exit,entry,tfmstart,tfmnext,r2lflag)
+ local dx=factor*(exit[1]-entry[1])
+ local dy=-factor*(exit[2]-entry[2])
+ local ws=tfmstart.width
+ local wn=tfmnext.width
+ nofregisteredcursives=nofregisteredcursives+1
+ if rlmode<0 then
+ dx=-(dx+wn)
+ else
+ dx=dx-ws
+ end
+ if dx==0 then
+ dx=0
+ end
+ local p=rawget(properties,start)
+ if p then
+ local i=p.injections
+ if i then
+ i.cursiveanchor=true
+ else
+ p.injections={
+ cursiveanchor=true,
+ }
+ end
+ else
+ properties[start]={
+ injections={
+ cursiveanchor=true,
+ },
+ }
+ end
+ local p=rawget(properties,nxt)
+ if p then
+ local i=p.injections
+ if i then
+ i.cursivex=dx
+ i.cursivey=dy
+ else
+ p.injections={
+ cursivex=dx,
+ cursivey=dy,
+ }
+ end
+ else
+ properties[nxt]={
+ injections={
+ cursivex=dx,
+ cursivey=dy,
+ },
+ }
+ end
+ return dx,dy,nofregisteredcursives
+end
+function injections.setposition(kind,current,factor,rlmode,spec,injection)
+ local x=factor*(spec[1] or 0)
+ local y=factor*(spec[2] or 0)
+ local w=factor*(spec[3] or 0)
+ local h=factor*(spec[4] or 0)
+ if x~=0 or w~=0 or y~=0 or h~=0 then
+ local yoffset=y-h
+ local leftkern=x
+ local rightkern=w-x
+ if leftkern~=0 or rightkern~=0 or yoffset~=0 then
+ nofregisteredpositions=nofregisteredpositions+1
+ if rlmode and rlmode<0 then
+ leftkern,rightkern=rightkern,leftkern
+ end
+ if not injection then
+ injection="injections"
+ end
+ local p=rawget(properties,current)
+ if p then
+ local i=p[injection]
+ if i then
+ if leftkern~=0 then
+ i.leftkern=(i.leftkern or 0)+leftkern
+ end
+ if rightkern~=0 then
+ i.rightkern=(i.rightkern or 0)+rightkern
+ end
+ if yoffset~=0 then
+ i.yoffset=(i.yoffset or 0)+yoffset
+ end
+ elseif leftkern~=0 or rightkern~=0 then
+ p[injection]={
+ leftkern=leftkern,
+ rightkern=rightkern,
+ yoffset=yoffset,
+ }
+ else
+ p[injection]={
+ yoffset=yoffset,
+ }
+ end
+ elseif leftkern~=0 or rightkern~=0 then
+ properties[current]={
+ [injection]={
+ leftkern=leftkern,
+ rightkern=rightkern,
+ yoffset=yoffset,
+ },
+ }
+ else
+ properties[current]={
+ [injection]={
+ yoffset=yoffset,
+ },
+ }
+ end
+ return x,y,w,h,nofregisteredpositions
+ end
+ end
+ return x,y,w,h
+end
+function injections.setkern(current,factor,rlmode,x,injection)
+ local dx=factor*x
+ if dx~=0 then
+ nofregisteredkerns=nofregisteredkerns+1
+ local p=rawget(properties,current)
+ if not injection then
+ injection="injections"
+ end
+ if p then
+ local i=p[injection]
+ if i then
+ i.leftkern=dx+(i.leftkern or 0)
+ else
+ p[injection]={
+ leftkern=dx,
+ }
+ end
+ else
+ properties[current]={
+ [injection]={
+ leftkern=dx,
+ },
+ }
+ end
+ return dx,nofregisteredkerns
+ else
+ return 0,0
+ end
+end
+function injections.setmove(current,factor,rlmode,x,injection)
+ local dx=factor*x
+ if dx~=0 then
+ nofregisteredkerns=nofregisteredkerns+1
+ local p=rawget(properties,current)
+ if not injection then
+ injection="injections"
+ end
+ if rlmode and rlmode<0 then
+ if p then
+ local i=p[injection]
+ if i then
+ i.rightkern=dx+(i.rightkern or 0)
+ else
+ p[injection]={
+ rightkern=dx,
+ }
+ end
+ else
+ properties[current]={
+ [injection]={
+ rightkern=dx,
+ },
+ }
+ end
+ else
+ if p then
+ local i=p[injection]
+ if i then
+ i.leftkern=dx+(i.leftkern or 0)
+ else
+ p[injection]={
+ leftkern=dx,
+ }
+ end
+ else
+ properties[current]={
+ [injection]={
+ leftkern=dx,
+ },
+ }
+ end
+ end
+ return dx,nofregisteredkerns
+ else
+ return 0,0
+ end
+end
+function injections.setmark(start,base,factor,rlmode,ba,ma,tfmbase,mkmk,checkmark)
+ local dx=factor*(ba[1]-ma[1])
+ local dy=factor*(ba[2]-ma[2])
+ nofregisteredmarks=nofregisteredmarks+1
+ if rlmode>=0 then
+ dx=tfmbase.width-dx
+ end
+ local p=rawget(properties,start)
+ if p then
+ local i=p.injections
+ if i then
+ if i.markmark then
+ else
+ i.markx=dx
+ i.marky=dy
+ i.markdir=rlmode or 0
+ i.markbase=nofregisteredmarks
+ i.markbasenode=base
+ i.markmark=mkmk
+ i.checkmark=checkmark
+ end
+ else
+ p.injections={
+ markx=dx,
+ marky=dy,
+ markdir=rlmode or 0,
+ markbase=nofregisteredmarks,
+ markbasenode=base,
+ markmark=mkmk,
+ checkmark=checkmark,
+ }
+ end
+ else
+ properties[start]={
+ injections={
+ markx=dx,
+ marky=dy,
+ markdir=rlmode or 0,
+ markbase=nofregisteredmarks,
+ markbasenode=base,
+ markmark=mkmk,
+ checkmark=checkmark,
+ },
+ }
+ end
+ return dx,dy,nofregisteredmarks
+end
+local function dir(n)
+ return (n and n<0 and "r-to-l") or (n and n>0 and "l-to-r") or "unset"
+end
+local function showchar(n,nested)
+ local char=getchar(n)
+ report_injections("%wfont %s, char %U, glyph %c",nested and 2 or 0,getfont(n),char,char)
+end
+local function show(n,what,nested,symbol)
+ if n then
+ local p=rawget(properties,n)
+ if p then
+ local i=p[what]
+ if i then
+ local leftkern=i.leftkern or 0
+ local rightkern=i.rightkern or 0
+ local yoffset=i.yoffset or 0
+ local markx=i.markx or 0
+ local marky=i.marky or 0
+ local markdir=i.markdir or 0
+ local markbase=i.markbase or 0
+ local cursivex=i.cursivex or 0
+ local cursivey=i.cursivey or 0
+ local ligaindex=i.ligaindex or 0
+ local cursbase=i.cursiveanchor
+ local margin=nested and 4 or 2
+ if rightkern~=0 or yoffset~=0 then
+ report_injections("%w%s pair: lx %p, rx %p, dy %p",margin,symbol,leftkern,rightkern,yoffset)
+ elseif leftkern~=0 then
+ report_injections("%w%s kern: dx %p",margin,symbol,leftkern)
+ end
+ if markx~=0 or marky~=0 or markbase~=0 then
+ report_injections("%w%s mark: dx %p, dy %p, dir %s, base %s",margin,symbol,markx,marky,markdir,markbase~=0 and "yes" or "no")
+ end
+ if cursivex~=0 or cursivey~=0 then
+ if cursbase then
+ report_injections("%w%s curs: base dx %p, dy %p",margin,symbol,cursivex,cursivey)
+ else
+ report_injections("%w%s curs: dx %p, dy %p",margin,symbol,cursivex,cursivey)
+ end
+ elseif cursbase then
+ report_injections("%w%s curs: base",margin,symbol)
+ end
+ if ligaindex~=0 then
+ report_injections("%w%s liga: index %i",margin,symbol,ligaindex)
+ end
+ end
+ end
+ end
+end
+local function showsub(n,what,where)
+ report_injections("begin subrun: %s",where)
+ for n in nextchar,n do
+ showchar(n,where)
+ show(n,what,where," ")
+ end
+ report_injections("end subrun")
+end
+local function trace(head,where)
+ report_injections()
+ report_injections("begin run %s: %s kerns, %s positions, %s marks and %s cursives registered",
+ where or "",nofregisteredkerns,nofregisteredpositions,nofregisteredmarks,nofregisteredcursives)
+ local n=head
+ while n do
+ local id=getid(n)
+ if id==glyph_code then
+ showchar(n)
+ show(n,"injections",false," ")
+ show(n,"preinjections",false,"<")
+ show(n,"postinjections",false,">")
+ show(n,"replaceinjections",false,"=")
+ show(n,"emptyinjections",false,"*")
+ elseif id==disc_code then
+ local pre,post,replace=getdisc(n)
+ if pre then
+ showsub(pre,"preinjections","pre")
+ end
+ if post then
+ showsub(post,"postinjections","post")
+ end
+ if replace then
+ showsub(replace,"replaceinjections","replace")
+ end
+ show(n,"emptyinjections",false,"*")
+ end
+ n=getnext(n)
+ end
+ report_injections("end run")
+end
+local function show_result(head)
+ local current=head
+ local skipping=false
+ while current do
+ local id=getid(current)
+ if id==glyph_code then
+ local w=getwidth(current)
+ local x,y=getoffsets(current)
+ report_injections("char: %C, width %p, xoffset %p, yoffset %p",getchar(current),w,x,y)
+ skipping=false
+ elseif id==kern_code then
+ report_injections("kern: %p",getkern(current))
+ skipping=false
+ elseif not skipping then
+ report_injections()
+ skipping=true
+ end
+ current=getnext(current)
+ end
+ report_injections()
+end
+local function inject_kerns_only(head,where)
+ if trace_injections then
+ trace(head,"kerns")
+ end
+ local current=head
+ local prev=nil
+ local next=nil
+ local prevdisc=nil
+ local pre=nil
+ local post=nil
+ local replace=nil
+ local pretail=nil
+ local posttail=nil
+ local replacetail=nil
+ while current do
+ local next=getnext(current)
+ local char,id=ischar(current)
+ if char then
+ local p=rawget(properties,current)
+ if p then
+ local i=p.injections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ head=insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if prevdisc then
+ local done=false
+ if post then
+ local i=p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(posttail,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ if replace then
+ local i=p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(replacetail,fontkern(leftkern))
+ done=true
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=fontkern(leftkern)
+ done=true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ prevdisc=nil
+ elseif char==false then
+ prevdisc=nil
+ elseif id==disc_code then
+ pre,post,replace,pretail,posttail,replacetail=getdisc(current,true)
+ local done=false
+ if pre then
+ for n in nextchar,pre do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.preinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ pre=insert_node_before(pre,n,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if post then
+ for n in nextchar,post do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ post=insert_node_before(post,n,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ for n in nextchar,replace do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=insert_node_before(replace,n,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevdisc=current
+ else
+ prevdisc=nil
+ end
+ prev=current
+ current=next
+ end
+ if keepregisteredcounts then
+ keepregisteredcounts=false
+ else
+ nofregisteredkerns=0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+local function inject_positions_only(head,where)
+ if trace_injections then
+ trace(head,"positions")
+ end
+ local current=head
+ local prev=nil
+ local next=nil
+ local prevdisc=nil
+ local prevglyph=nil
+ local pre=nil
+ local post=nil
+ local replace=nil
+ local pretail=nil
+ local posttail=nil
+ local replacetail=nil
+ while current do
+ local next=getnext(current)
+ local char,id=ischar(current)
+ if char then
+ local p=rawget(properties,current)
+ if p then
+ local i=p.injections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(current,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ local rightkern=i.rightkern
+ if leftkern and leftkern~=0 then
+ if rightkern and leftkern==-rightkern then
+ setoffsets(current,leftkern,false)
+ rightkern=0
+ else
+ head=insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if rightkern and rightkern~=0 then
+ insert_node_after(head,current,fontkern(rightkern))
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ if next and getid(next)==disc_code then
+ if replace then
+ else
+ replace=fontkern(rightkern)
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if prevdisc then
+ local done=false
+ if post then
+ local i=p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(posttail,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ if replace then
+ local i=p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(replacetail,fontkern(leftkern))
+ done=true
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=fontkern(leftkern)
+ done=true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ prevdisc=nil
+ prevglyph=current
+ elseif char==false then
+ prevdisc=nil
+ prevglyph=current
+ elseif id==disc_code then
+ pre,post,replace,pretail,posttail,replacetail=getdisc(current,true)
+ local done=false
+ if pre then
+ for n in nextchar,pre do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.preinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ pre=insert_node_before(pre,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(pre,n,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if post then
+ for n in nextchar,post do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.postinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ post=insert_node_before(post,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(post,n,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ for n in nextchar,replace do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.replaceinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=insert_node_before(replace,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(replace,n,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if prevglyph then
+ if pre then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.preinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ pre=insert_node_before(pre,pre,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ if replace then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.replaceinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ replace=insert_node_before(replace,replace,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevglyph=nil
+ prevdisc=current
+ else
+ prevglyph=nil
+ prevdisc=nil
+ end
+ prev=current
+ current=next
+ end
+ if keepregisteredcounts then
+ keepregisteredcounts=false
+ else
+ nofregisteredpositions=0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+local function showoffset(n,flag)
+ local x,y=getoffsets(n)
+ if x~=0 or y~=0 then
+ setcolor(n,"darkgray")
+ end
+end
+local function inject_everything(head,where)
+ if trace_injections then
+ trace(head,"everything")
+ end
+ local hascursives=nofregisteredcursives>0
+ local hasmarks=nofregisteredmarks>0
+ local current=head
+ local last=nil
+ local prev=nil
+ local next=nil
+ local prevdisc=nil
+ local prevglyph=nil
+ local pre=nil
+ local post=nil
+ local replace=nil
+ local pretail=nil
+ local posttail=nil
+ local replacetail=nil
+ local cursiveanchor=nil
+ local minc=0
+ local maxc=0
+ local glyphs={}
+ local marks={}
+ local nofmarks=0
+ local function processmark(p,n,pn)
+ local px,py=getoffsets(p)
+ local nx,ny=getoffsets(n)
+ local ox=0
+ local rightkern=nil
+ local pp=rawget(properties,p)
+ if pp then
+ pp=pp.injections
+ if pp then
+ rightkern=pp.rightkern
+ end
+ end
+ local markdir=pn.markdir
+ if rightkern then
+ ox=px-(pn.markx or 0)-rightkern
+ if markdir and markdir<0 then
+ if not pn.markmark then
+ ox=ox+(pn.leftkern or 0)
+ end
+ else
+ if false then
+ local leftkern=pp.leftkern
+ if leftkern then
+ ox=ox-leftkern
+ end
+ end
+ end
+ else
+ ox=px-(pn.markx or 0)
+ if markdir and markdir<0 then
+ if not pn.markmark then
+ local leftkern=pn.leftkern
+ if leftkern then
+ ox=ox+leftkern
+ end
+ end
+ end
+ if pn.checkmark then
+ local wn=getwidth(n)
+ if wn and wn~=0 then
+ wn=wn/2
+ if trace_injections then
+ report_injections("correcting non zero width mark %C",getchar(n))
+ end
+ insert_node_before(n,n,fontkern(-wn))
+ insert_node_after(n,n,fontkern(-wn))
+ end
+ end
+ end
+ local oy=ny+py+(pn.marky or 0)
+ if not pn.markmark then
+ local yoffset=pn.yoffset
+ if yoffset then
+ oy=oy+yoffset
+ end
+ end
+ setoffsets(n,ox,oy)
+ if trace_marks then
+ showoffset(n,true)
+ end
+ end
+ while current do
+ local next=getnext(current)
+ local char,id=ischar(current)
+ if char then
+ local p=rawget(properties,current)
+ if p then
+ local i=p.injections
+ if i then
+ local pm=i.markbasenode
+ if pm then
+ nofmarks=nofmarks+1
+ marks[nofmarks]=current
+ else
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(current,false,yoffset)
+ end
+ if hascursives then
+ local cursivex=i.cursivex
+ if cursivex then
+ if cursiveanchor then
+ if cursivex~=0 then
+ i.leftkern=(i.leftkern or 0)+cursivex
+ end
+ if maxc==0 then
+ minc=1
+ maxc=1
+ glyphs[1]=cursiveanchor
+ else
+ maxc=maxc+1
+ glyphs[maxc]=cursiveanchor
+ end
+ properties[cursiveanchor].cursivedy=i.cursivey
+ last=current
+ else
+ maxc=0
+ end
+ elseif maxc>0 then
+ local nx,ny=getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ setoffsets(ti,false,ny)
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ maxc=0
+ cursiveanchor=nil
+ end
+ if i.cursiveanchor then
+ cursiveanchor=current
+ else
+ if maxc>0 then
+ local nx,ny=getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ setoffsets(ti,false,ny)
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ maxc=0
+ end
+ cursiveanchor=nil
+ end
+ end
+ local leftkern=i.leftkern
+ local rightkern=i.rightkern
+ if leftkern and leftkern~=0 then
+ if rightkern and leftkern==-rightkern then
+ setoffsets(current,leftkern,false)
+ rightkern=0
+ else
+ head=insert_node_before(head,current,fontkern(leftkern))
+ end
+ end
+ if rightkern and rightkern~=0 then
+ insert_node_after(head,current,fontkern(rightkern))
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ if next and getid(next)==disc_code then
+ if replace then
+ else
+ replace=fontkern(rightkern)
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if prevdisc then
+ if p then
+ local done=false
+ if post then
+ local i=p.postinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(posttail,fontkern(leftkern))
+ done=true
+ end
+ end
+ end
+ if replace then
+ local i=p.replaceinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ setlink(replacetail,fontkern(leftkern))
+ done=true
+ end
+ end
+ else
+ local i=p.emptyinjections
+ if i then
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=fontkern(leftkern)
+ done=true
+ end
+ end
+ end
+ if done then
+ setdisc(prevdisc,pre,post,replace)
+ end
+ end
+ end
+ else
+ if hascursives and maxc>0 then
+ local nx,ny=getoffsets(current)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ local xi,yi=getoffsets(ti)
+ setoffsets(ti,xi,yi+ny)
+ end
+ maxc=0
+ cursiveanchor=nil
+ end
+ end
+ prevdisc=nil
+ prevglyph=current
+ elseif char==false then
+ prevdisc=nil
+ prevglyph=current
+ elseif id==disc_code then
+ pre,post,replace,pretail,posttail,replacetail=getdisc(current,true)
+ local done=false
+ if pre then
+ for n in nextchar,pre do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.preinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ pre=insert_node_before(pre,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(pre,n,fontkern(rightkern))
+ done=true
+ end
+ if hasmarks then
+ local pm=i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if post then
+ for n in nextchar,post do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.postinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ post=insert_node_before(post,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(post,n,fontkern(rightkern))
+ done=true
+ end
+ if hasmarks then
+ local pm=i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if replace then
+ for n in nextchar,replace do
+ local p=rawget(properties,n)
+ if p then
+ local i=p.injections or p.replaceinjections
+ if i then
+ local yoffset=i.yoffset
+ if yoffset and yoffset~=0 then
+ setoffsets(n,false,yoffset)
+ end
+ local leftkern=i.leftkern
+ if leftkern and leftkern~=0 then
+ replace=insert_node_before(replace,n,fontkern(leftkern))
+ done=true
+ end
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ insert_node_after(replace,n,fontkern(rightkern))
+ done=true
+ end
+ if hasmarks then
+ local pm=i.markbasenode
+ if pm then
+ processmark(pm,n,i)
+ end
+ end
+ end
+ end
+ end
+ end
+ if prevglyph then
+ if pre then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.preinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ pre=insert_node_before(pre,pre,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ if replace then
+ local p=rawget(properties,prevglyph)
+ if p then
+ local i=p.replaceinjections
+ if i then
+ local rightkern=i.rightkern
+ if rightkern and rightkern~=0 then
+ replace=insert_node_before(replace,replace,fontkern(rightkern))
+ done=true
+ end
+ end
+ end
+ end
+ end
+ if done then
+ setdisc(current,pre,post,replace)
+ end
+ prevglyph=nil
+ prevdisc=current
+ else
+ prevglyph=nil
+ prevdisc=nil
+ end
+ prev=current
+ current=next
+ end
+ if hascursives and maxc>0 then
+ local nx,ny=getoffsets(last)
+ for i=maxc,minc,-1 do
+ local ti=glyphs[i]
+ ny=ny+properties[ti].cursivedy
+ setoffsets(ti,false,ny)
+ if trace_cursive then
+ showoffset(ti)
+ end
+ end
+ end
+ if nofmarks>0 then
+ for i=1,nofmarks do
+ local m=marks[i]
+ local p=rawget(properties,m)
+ local i=p.injections
+ local b=i.markbasenode
+ processmark(b,m,i)
+ end
+ elseif hasmarks then
+ end
+ if keepregisteredcounts then
+ keepregisteredcounts=false
+ else
+ nofregisteredkerns=0
+ nofregisteredpositions=0
+ nofregisteredmarks=0
+ nofregisteredcursives=0
+ end
+ if trace_injections then
+ show_result(head)
+ end
+ return head
+end
+local triggers=false
+function nodes.injections.setspacekerns(font,sequence)
+ if triggers then
+ triggers[font]=sequence
+ else
+ triggers={ [font]=sequence }
+ end
+end
+local getthreshold
+if context then
+
+--removed
+
+else
+ injections.threshold=0
+ getthreshold=function(font)
+ local p=fontdata[font].parameters
+ local f=p.factor
+ local s=p.spacing
+ local t=injections.threshold*(s and s.width or p.space or 0)-2
+ return t>0 and t or 0,f
+ end
+end
+injections.getthreshold=getthreshold
+function injections.isspace(n,threshold,id)
+ if (id or getid(n))==glue_code then
+ local w=getwidth(n)
+ if threshold and w>threshold then
+ return 32
+ end
+ end
+end
+local getspaceboth=getboth
+function injections.installgetspaceboth(gb)
+ getspaceboth=gb or getboth
+end
+local function injectspaces(head)
+ if not triggers then
+ return head
+ end
+ local lastfont=nil
+ local spacekerns=nil
+ local leftkerns=nil
+ local rightkerns=nil
+ local factor=0
+ local threshold=0
+ local leftkern=false
+ local rightkern=false
+ local function updatefont(font,trig)
+ leftkerns=trig.left
+ rightkerns=trig.right
+ lastfont=font
+ threshold,
+ factor=getthreshold(font)
+ end
+ for n in nextglue,head do
+ local prev,next=getspaceboth(n)
+ local prevchar=prev and ischar(prev)
+ local nextchar=next and ischar(next)
+ if nextchar then
+ local font=getfont(next)
+ local trig=triggers[font]
+ if trig then
+ if lastfont~=font then
+ updatefont(font,trig)
+ end
+ if rightkerns then
+ rightkern=rightkerns[nextchar]
+ end
+ end
+ end
+ if prevchar then
+ local font=getfont(prev)
+ local trig=triggers[font]
+ if trig then
+ if lastfont~=font then
+ updatefont(font,trig)
+ end
+ if leftkerns then
+ leftkern=leftkerns[prevchar]
+ end
+ end
+ end
+ if leftkern then
+ local old=getwidth(n)
+ if old>threshold then
+ if rightkern then
+ if useitalickerns then
+ local lnew=leftkern*factor
+ local rnew=rightkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p + %p] %C",prevchar,lnew,old,rnew,nextchar)
+ end
+ head=insert_node_before(head,n,italickern(lnew))
+ insert_node_after(head,n,italickern(rnew))
+ else
+ local new=old+(leftkern+rightkern)*factor
+ if trace_spaces then
+ report_spaces("%C [%p -> %p] %C",prevchar,old,new,nextchar)
+ end
+ setwidth(n,new)
+ end
+ rightkern=false
+ else
+ if useitalickerns then
+ local new=leftkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p]",prevchar,old,new)
+ end
+ insert_node_after(head,n,italickern(new))
+ else
+ local new=old+leftkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p -> %p]",prevchar,old,new)
+ end
+ setwidth(n,new)
+ end
+ end
+ end
+ leftkern=false
+ elseif rightkern then
+ local old=getwidth(n)
+ if old>threshold then
+ if useitalickerns then
+ local new=rightkern*factor
+ if trace_spaces then
+ report_spaces("%C [%p + %p]",nextchar,old,new)
+ end
+ insert_node_after(head,n,italickern(new))
+ else
+ local new=old+rightkern*factor
+ if trace_spaces then
+ report_spaces("[%p -> %p] %C",nextchar,old,new)
+ end
+ setwidth(n,new)
+ end
+ end
+ rightkern=false
+ end
+ end
+ triggers=false
+ return head
+end
+function injections.handler(head,where)
+ if triggers then
+ head=injectspaces(head)
+ end
+ if nofregisteredmarks>0 or nofregisteredcursives>0 then
+ if trace_injections then
+ report_injections("injection variant %a","everything")
+ end
+ return inject_everything(head,where)
+ elseif nofregisteredpositions>0 then
+ if trace_injections then
+ report_injections("injection variant %a","positions")
+ end
+ return inject_positions_only(head,where)
+ elseif nofregisteredkerns>0 then
+ if trace_injections then
+ report_injections("injection variant %a","kerns")
+ end
+ return inject_kerns_only(head,where)
+ else
+ return head
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-ota']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local type=type
+if not trackers then trackers={ register=function() end } end
+local fonts,nodes,node=fonts,nodes,node
+local allocate=utilities.storage.allocate
+local otf=fonts.handlers.otf
+local analyzers=fonts.analyzers
+local initializers=allocate()
+local methods=allocate()
+analyzers.initializers=initializers
+analyzers.methods=methods
+local a_state=attributes.private('state')
+local nuts=nodes.nuts
+local tonut=nuts.tonut
+local getnext=nuts.getnext
+local getprev=nuts.getprev
+local getprev=nuts.getprev
+local getprop=nuts.getprop
+local setprop=nuts.setprop
+local getsubtype=nuts.getsubtype
+local getchar=nuts.getchar
+local ischar=nuts.ischar
+local end_of_math=nuts.end_of_math
+local nodecodes=nodes.nodecodes
+local disc_code=nodecodes.disc
+local math_code=nodecodes.math
+local fontdata=fonts.hashes.identifiers
+local categories=characters and characters.categories or {}
+local chardata=characters and characters.data
+local otffeatures=fonts.constructors.features.otf
+local registerotffeature=otffeatures.register
+local s_init=1 local s_rphf=7
+local s_medi=2 local s_half=8
+local s_fina=3 local s_pref=9
+local s_isol=4 local s_blwf=10
+local s_mark=5 local s_pstf=11
+local s_rest=6
+local states=allocate {
+ init=s_init,
+ medi=s_medi,
+ med2=s_medi,
+ fina=s_fina,
+ fin2=s_fina,
+ fin3=s_fina,
+ isol=s_isol,
+ mark=s_mark,
+ rest=s_rest,
+ rphf=s_rphf,
+ half=s_half,
+ pref=s_pref,
+ blwf=s_blwf,
+ pstf=s_pstf,
+}
+local features=allocate {
+ init=s_init,
+ medi=s_medi,
+ med2=s_medi,
+ fina=s_fina,
+ fin2=s_fina,
+ fin3=s_fina,
+ isol=s_isol,
+ rphf=s_rphf,
+ half=s_half,
+ pref=s_pref,
+ blwf=s_blwf,
+ pstf=s_pstf,
+}
+analyzers.states=states
+analyzers.features=features
+analyzers.useunicodemarks=false
+function analyzers.setstate(head,font)
+ local useunicodemarks=analyzers.useunicodemarks
+ local tfmdata=fontdata[font]
+ local descriptions=tfmdata.descriptions
+ local first,last,current,n,done=nil,nil,head,0,false
+ current=tonut(current)
+ while current do
+ local char,id=ischar(current,font)
+ if char and not getprop(current,a_state) then
+ done=true
+ local d=descriptions[char]
+ if d then
+ if d.class=="mark" then
+ done=true
+ setprop(current,a_state,s_mark)
+ elseif useunicodemarks and categories[char]=="mn" then
+ done=true
+ setprop(current,a_state,s_mark)
+ elseif n==0 then
+ first,last,n=current,current,1
+ setprop(current,a_state,s_init)
+ else
+ last,n=current,n+1
+ setprop(current,a_state,s_medi)
+ end
+ else
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first,last,n=nil,nil,0
+ end
+ elseif char==false then
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first,last,n=nil,nil,0
+ if id==math_code then
+ current=end_of_math(current)
+ end
+ elseif id==disc_code then
+ setprop(current,a_state,s_medi)
+ last=current
+ else
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ first,last,n=nil,nil,0
+ if id==math_code then
+ current=end_of_math(current)
+ end
+ end
+ current=getnext(current)
+ end
+ if first and first==last then
+ setprop(last,a_state,s_isol)
+ elseif last then
+ setprop(last,a_state,s_fina)
+ end
+ return head,done
+end
+local function analyzeinitializer(tfmdata,value)
+ local script,language=otf.scriptandlanguage(tfmdata)
+ local action=initializers[script]
+ if not action then
+ elseif type(action)=="function" then
+ return action(tfmdata,value)
+ else
+ local action=action[language]
+ if action then
+ return action(tfmdata,value)
+ end
+ end
+end
+local function analyzeprocessor(head,font,attr)
+ local tfmdata=fontdata[font]
+ local script,language=otf.scriptandlanguage(tfmdata,attr)
+ local action=methods[script]
+ if not action then
+ elseif type(action)=="function" then
+ return action(head,font,attr)
+ else
+ action=action[language]
+ if action then
+ return action(head,font,attr)
+ end
+ end
+ return head,false
+end
+registerotffeature {
+ name="analyze",
+ description="analysis of character classes",
+ default=true,
+ initializers={
+ node=analyzeinitializer,
+ },
+ processors={
+ position=1,
+ node=analyzeprocessor,
+ }
+}
+methods.latn=analyzers.setstate
+local arab_warned={}
+local function warning(current,what)
+ local char=getchar(current)
+ if not arab_warned[char] then
+ log.report("analyze","arab: character %C has no %a class",char,what)
+ arab_warned[char]=true
+ end
+end
+local mappers=allocate {
+ l=s_init,
+ d=s_medi,
+ c=s_medi,
+ r=s_fina,
+ u=s_isol,
+}
+local classifiers=characters.classifiers
+if not classifiers then
+ local f_arabic,l_arabic=characters.blockrange("arabic")
+ local f_syriac,l_syriac=characters.blockrange("syriac")
+ local f_mandiac,l_mandiac=characters.blockrange("mandiac")
+ local f_nko,l_nko=characters.blockrange("nko")
+ local f_ext_a,l_ext_a=characters.blockrange("arabicextendeda")
+ classifiers=table.setmetatableindex(function(t,k)
+ if type(k)=="number" then
+ local c=chardata[k]
+ local v=false
+ if c then
+ local arabic=c.arabic
+ if arabic then
+ v=mappers[arabic]
+ if not v then
+ log.report("analyze","error in mapping arabic %C",k)
+ v=false
+ end
+ elseif (k>=f_arabic and k<=l_arabic) or
+ (k>=f_syriac and k<=l_syriac) or
+ (k>=f_mandiac and k<=l_mandiac) or
+ (k>=f_nko and k<=l_nko) or
+ (k>=f_ext_a and k<=l_ext_a) then
+ if categories[k]=="mn" then
+ v=s_mark
+ else
+ v=s_rest
+ end
+ end
+ end
+ t[k]=v
+ return v
+ end
+ end)
+ characters.classifiers=classifiers
+end
+function methods.arab(head,font,attr)
+ local first,last,c_first,c_last
+ local current=head
+ local done=false
+ current=tonut(current)
+ while current do
+ local char,id=ischar(current,font)
+ if char and not getprop(current,a_state) then
+ done=true
+ local classifier=classifiers[char]
+ if not classifier then
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ elseif classifier==s_mark then
+ setprop(current,a_state,s_mark)
+ elseif classifier==s_isol then
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ setprop(current,a_state,s_isol)
+ elseif classifier==s_medi then
+ if first then
+ last=current
+ c_last=classifier
+ setprop(current,a_state,s_medi)
+ else
+ setprop(current,a_state,s_init)
+ first=current
+ c_first=classifier
+ end
+ elseif classifier==s_fina then
+ if last then
+ if getprop(last,a_state)~=s_init then
+ setprop(last,a_state,s_medi)
+ end
+ setprop(current,a_state,s_fina)
+ first,last=nil,nil
+ elseif first then
+ setprop(current,a_state,s_fina)
+ first=nil
+ else
+ setprop(current,a_state,s_isol)
+ end
+ else
+ setprop(current,a_state,s_rest)
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ end
+ else
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ first,last=nil,nil
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ first=nil
+ end
+ if id==math_code then
+ current=end_of_math(current)
+ end
+ end
+ current=getnext(current)
+ end
+ if last then
+ if c_last==s_medi or c_last==s_fina then
+ setprop(last,a_state,s_fina)
+ else
+ warning(last,"fina")
+ setprop(last,a_state,s_error)
+ end
+ elseif first then
+ if c_first==s_medi or c_first==s_fina then
+ setprop(first,a_state,s_isol)
+ else
+ warning(first,"isol")
+ setprop(first,a_state,s_error)
+ end
+ end
+ return head,done
+end
+methods.syrc=methods.arab
+methods.mand=methods.arab
+methods.nko=methods.arab
+directives.register("otf.analyze.useunicodemarks",function(v)
+ analyzers.useunicodemarks=v
+end)
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-ots']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+}
+local type,next,tonumber=type,next,tonumber
+local random=math.random
+local formatters=string.formatters
+local insert=table.insert
+local registertracker=trackers.register
+local logs=logs
+local trackers=trackers
+local nodes=nodes
+local attributes=attributes
+local fonts=fonts
+local otf=fonts.handlers.otf
+local tracers=nodes.tracers
+local trace_singles=false registertracker("otf.singles",function(v) trace_singles=v end)
+local trace_multiples=false registertracker("otf.multiples",function(v) trace_multiples=v end)
+local trace_alternatives=false registertracker("otf.alternatives",function(v) trace_alternatives=v end)
+local trace_ligatures=false registertracker("otf.ligatures",function(v) trace_ligatures=v end)
+local trace_contexts=false registertracker("otf.contexts",function(v) trace_contexts=v end)
+local trace_marks=false registertracker("otf.marks",function(v) trace_marks=v end)
+local trace_kerns=false registertracker("otf.kerns",function(v) trace_kerns=v end)
+local trace_cursive=false registertracker("otf.cursive",function(v) trace_cursive=v end)
+local trace_preparing=false registertracker("otf.preparing",function(v) trace_preparing=v end)
+local trace_bugs=false registertracker("otf.bugs",function(v) trace_bugs=v end)
+local trace_details=false registertracker("otf.details",function(v) trace_details=v end)
+local trace_steps=false registertracker("otf.steps",function(v) trace_steps=v end)
+local trace_skips=false registertracker("otf.skips",function(v) trace_skips=v end)
+local trace_plugins=false registertracker("otf.plugins",function(v) trace_plugins=v end)
+local trace_chains=false registertracker("otf.chains",function(v) trace_chains=v end)
+local trace_kernruns=false registertracker("otf.kernruns",function(v) trace_kernruns=v end)
+local trace_compruns=false registertracker("otf.compruns",function(v) trace_compruns=v end)
+local trace_testruns=false registertracker("otf.testruns",function(v) trace_testruns=v end)
+local forcediscretionaries=false
+local forcepairadvance=false
+directives.register("otf.forcediscretionaries",function(v)
+ forcediscretionaries=v
+end)
+directives.register("otf.forcepairadvance",function(v)
+ forcepairadvance=v
+end)
+local report_direct=logs.reporter("fonts","otf direct")
+local report_subchain=logs.reporter("fonts","otf subchain")
+local report_chain=logs.reporter("fonts","otf chain")
+local report_process=logs.reporter("fonts","otf process")
+local report_warning=logs.reporter("fonts","otf warning")
+local report_run=logs.reporter("fonts","otf run")
+registertracker("otf.substitutions","otf.singles","otf.multiples","otf.alternatives","otf.ligatures")
+registertracker("otf.positions","otf.marks","otf.kerns","otf.cursive")
+registertracker("otf.actions","otf.substitutions","otf.positions")
+registertracker("otf.sample","otf.steps","otf.substitutions","otf.positions","otf.analyzing")
+registertracker("otf.sample.silent","otf.steps=silent","otf.substitutions","otf.positions","otf.analyzing")
+local nuts=nodes.nuts
+local getfield=nuts.getfield
+local getnext=nuts.getnext
+local setnext=nuts.setnext
+local getprev=nuts.getprev
+local setprev=nuts.setprev
+local getboth=nuts.getboth
+local setboth=nuts.setboth
+local getid=nuts.getid
+local getprop=nuts.getprop
+local setprop=nuts.setprop
+local getsubtype=nuts.getsubtype
+local setsubtype=nuts.setsubtype
+local getchar=nuts.getchar
+local setchar=nuts.setchar
+local getdisc=nuts.getdisc
+local setdisc=nuts.setdisc
+local setlink=nuts.setlink
+local getcomponents=nuts.getcomponents
+local setcomponents=nuts.setcomponents
+local getwidth=nuts.getwidth
+local getattr=nuts.getattr
+local getglyphdata=nuts.getglyphdata
+local ischar=nuts.ischar
+local isglyph=nuts.isglyph
+local usesfont=nuts.uses_font
+local insert_node_after=nuts.insert_after
+local copy_node=nuts.copy
+local copy_node_list=nuts.copy_list
+local remove_node=nuts.remove
+local find_node_tail=nuts.tail
+local flush_node_list=nuts.flush_list
+local flush_node=nuts.flush_node
+local end_of_math=nuts.end_of_math
+local setmetatable=setmetatable
+local setmetatableindex=table.setmetatableindex
+local nextnode=nuts.traversers.node
+local nodecodes=nodes.nodecodes
+local glyphcodes=nodes.glyphcodes
+local disccodes=nodes.disccodes
+local glyph_code=nodecodes.glyph
+local glue_code=nodecodes.glue
+local disc_code=nodecodes.disc
+local math_code=nodecodes.math
+local dir_code=nodecodes.dir
+local localpar_code=nodecodes.localpar
+local discretionarydisc_code=disccodes.discretionary
+local ligatureglyph_code=glyphcodes.ligature
+local a_state=attributes.private('state')
+local a_noligature=attributes.private("noligature")
+local injections=nodes.injections
+local setmark=injections.setmark
+local setcursive=injections.setcursive
+local setkern=injections.setkern
+local setmove=injections.setmove
+local setposition=injections.setposition
+local resetinjection=injections.reset
+local copyinjection=injections.copy
+local setligaindex=injections.setligaindex
+local getligaindex=injections.getligaindex
+local fontdata=fonts.hashes.identifiers
+local fontfeatures=fonts.hashes.features
+local otffeatures=fonts.constructors.features.otf
+local registerotffeature=otffeatures.register
+local onetimemessage=fonts.loggers.onetimemessage or function() end
+local getrandom=utilities and utilities.randomizer and utilities.randomizer.get
+otf.defaultnodealternate="none"
+local tfmdata=false
+local characters=false
+local descriptions=false
+local marks=false
+local classes=false
+local currentfont=false
+local factor=0
+local threshold=0
+local checkmarks=false
+local discs=false
+local spaces=false
+local sweepnode=nil
+local sweephead={}
+local notmatchpre={}
+local notmatchpost={}
+local notmatchreplace={}
+local handlers={}
+local isspace=injections.isspace
+local getthreshold=injections.getthreshold
+local checkstep=(tracers and tracers.steppers.check) or function() end
+local registerstep=(tracers and tracers.steppers.register) or function() end
+local registermessage=(tracers and tracers.steppers.message) or function() end
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_direct(...)
+end
+local function logwarning(...)
+ report_direct(...)
+end
+local gref do
+ local f_unicode=formatters["U+%X"]
+ local f_uniname=formatters["U+%X (%s)"]
+ local f_unilist=formatters["% t"]
+ gref=function(n)
+ if type(n)=="number" then
+ local description=descriptions[n]
+ local name=description and description.name
+ if name then
+ return f_uniname(n,name)
+ else
+ return f_unicode(n)
+ end
+ elseif n then
+ local t={}
+ for i=1,#n do
+ local ni=n[i]
+ if tonumber(ni) then
+ local di=descriptions[ni]
+ local nn=di and di.name
+ if nn then
+ t[#t+1]=f_uniname(ni,nn)
+ else
+ t[#t+1]=f_unicode(ni)
+ end
+ end
+ end
+ return f_unilist(t)
+ else
+ return "<error in node mode tracing>"
+ end
+ end
+end
+local function cref(dataset,sequence,index)
+ if not dataset then
+ return "no valid dataset"
+ end
+ local merged=sequence.merged and "merged " or ""
+ if index then
+ return formatters["feature %a, type %a, %schain lookup %a, index %a"](
+ dataset[4],sequence.type,merged,sequence.name,index)
+ else
+ return formatters["feature %a, type %a, %schain lookup %a"](
+ dataset[4],sequence.type,merged,sequence.name)
+ end
+end
+local function pref(dataset,sequence)
+ return formatters["feature %a, type %a, %slookup %a"](
+ dataset[4],sequence.type,sequence.merged and "merged " or "",sequence.name)
+end
+local function mref(rlmode)
+ if not rlmode or rlmode>=0 then
+ return "l2r"
+ else
+ return "r2l"
+ end
+end
+local function flattendisk(head,disc)
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local prev,next=getboth(disc)
+ local ishead=head==disc
+ setdisc(disc)
+ flush_node(disc)
+ if pre then
+ flush_node_list(pre)
+ end
+ if post then
+ flush_node_list(post)
+ end
+ if ishead then
+ if replace then
+ if next then
+ setlink(replacetail,next)
+ end
+ return replace,replace
+ elseif next then
+ return next,next
+ else
+ end
+ else
+ if replace then
+ if next then
+ setlink(replacetail,next)
+ end
+ setlink(prev,replace)
+ return head,replace
+ else
+ setlink(prev,next)
+ return head,next
+ end
+ end
+end
+local function appenddisc(disc,list)
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local posthead=list
+ local replacehead=copy_node_list(list)
+ if post then
+ setlink(posttail,posthead)
+ else
+ post=posthead
+ end
+ if replace then
+ setlink(replacetail,replacehead)
+ else
+ replace=replacehead
+ end
+ setdisc(disc,pre,post,replace)
+end
+local copy_no_components=nuts.copy_no_components
+local copy_only_glyphs=nuts.copy_only_glyphs
+local set_components=setcomponents
+local take_components=getcomponents
+local function count_components(start,marks)
+ local char=isglyph(start)
+ if char then
+ if getsubtype(start)==ligatureglyph_code then
+ local i=0
+ local components=getcomponents(start)
+ while components do
+ i=i+count_components(components,marks)
+ components=getnext(components)
+ end
+ return i
+ elseif not marks[char] then
+ return 1
+ end
+ end
+ return 0
+end
+local function markstoligature(head,start,stop,char)
+ if start==stop and getchar(start)==char then
+ return head,start
+ else
+ local prev=getprev(start)
+ local next=getnext(stop)
+ setprev(start)
+ setnext(stop)
+ local base=copy_no_components(start,copyinjection)
+ if head==start then
+ head=base
+ end
+ resetinjection(base)
+ setchar(base,char)
+ setsubtype(base,ligatureglyph_code)
+ set_components(base,start)
+ setlink(prev,base,next)
+ return head,base
+ end
+end
+local function toligature(head,start,stop,char,dataset,sequence,skiphash,discfound,hasmarks)
+ if getattr(start,a_noligature)==1 then
+ return head,start
+ end
+ if start==stop and getchar(start)==char then
+ resetinjection(start)
+ setchar(start,char)
+ return head,start
+ end
+ local prev=getprev(start)
+ local next=getnext(stop)
+ local comp=start
+ setprev(start)
+ setnext(stop)
+ local base=copy_no_components(start,copyinjection)
+ if start==head then
+ head=base
+ end
+ resetinjection(base)
+ setchar(base,char)
+ setsubtype(base,ligatureglyph_code)
+ set_components(base,comp)
+ setlink(prev,base,next)
+ if not discfound then
+ local deletemarks=not skiphash or hasmarks
+ local components=start
+ local baseindex=0
+ local componentindex=0
+ local head=base
+ local current=base
+ while start do
+ local char=getchar(start)
+ if not marks[char] then
+ baseindex=baseindex+componentindex
+ componentindex=count_components(start,marks)
+ elseif not deletemarks then
+ setligaindex(start,baseindex+getligaindex(start,componentindex))
+ if trace_marks then
+ logwarning("%s: keep mark %s, gets index %s",pref(dataset,sequence),gref(char),getligaindex(start))
+ end
+ local n=copy_node(start)
+ copyinjection(n,start)
+ head,current=insert_node_after(head,current,n)
+ elseif trace_marks then
+ logwarning("%s: delete mark %s",pref(dataset,sequence),gref(char))
+ end
+ start=getnext(start)
+ end
+ local start=getnext(current)
+ while start do
+ local char=ischar(start)
+ if char then
+ if marks[char] then
+ setligaindex(start,baseindex+getligaindex(start,componentindex))
+ if trace_marks then
+ logwarning("%s: set mark %s, gets index %s",pref(dataset,sequence),gref(char),getligaindex(start))
+ end
+ start=getnext(start)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ else
+ local discprev,discnext=getboth(discfound)
+ if discprev and discnext then
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(discfound,true)
+ if not replace then
+ local prev=getprev(base)
+ local comp=take_components(base)
+ local copied=copy_only_glyphs(comp)
+ if pre then
+ setlink(discprev,pre)
+ else
+ setnext(discprev)
+ end
+ pre=comp
+ if post then
+ setlink(posttail,discnext)
+ setprev(post)
+ else
+ post=discnext
+ setprev(discnext)
+ end
+ setlink(prev,discfound,next)
+ setboth(base)
+ set_components(base,copied)
+ replace=base
+ if forcediscretionaries then
+ setdisc(discfound,pre,post,replace,discretionarydisc_code)
+ else
+ setdisc(discfound,pre,post,replace)
+ end
+ base=prev
+ end
+ end
+ end
+ return head,base
+end
+local function multiple_glyphs(head,start,multiple,skiphash,what,stop)
+ local nofmultiples=#multiple
+ if nofmultiples>0 then
+ resetinjection(start)
+ setchar(start,multiple[1])
+ if nofmultiples>1 then
+ local sn=getnext(start)
+ for k=2,nofmultiples do
+ local n=copy_node(start)
+ resetinjection(n)
+ setchar(n,multiple[k])
+ insert_node_after(head,start,n)
+ start=n
+ end
+ if what==true then
+ elseif what>1 then
+ local m=multiple[nofmultiples]
+ for i=2,what do
+ local n=copy_node(start)
+ resetinjection(n)
+ setchar(n,m)
+ insert_node_after(head,start,n)
+ start=n
+ end
+ end
+ end
+ return head,start,true
+ else
+ if trace_multiples then
+ logprocess("no multiple for %s",gref(getchar(start)))
+ end
+ return head,start,false
+ end
+end
+local function get_alternative_glyph(start,alternatives,value)
+ local n=#alternatives
+ if n==1 then
+ return alternatives[1],trace_alternatives and "1 (only one present)"
+ elseif value=="random" then
+ local r=getrandom and getrandom("glyph",1,n) or random(1,n)
+ return alternatives[r],trace_alternatives and formatters["value %a, taking %a"](value,r)
+ elseif value=="first" then
+ return alternatives[1],trace_alternatives and formatters["value %a, taking %a"](value,1)
+ elseif value=="last" then
+ return alternatives[n],trace_alternatives and formatters["value %a, taking %a"](value,n)
+ end
+ value=value==true and 1 or tonumber(value)
+ if type(value)~="number" then
+ return alternatives[1],trace_alternatives and formatters["invalid value %s, taking %a"](value,1)
+ end
+ if value>n then
+ local defaultalt=otf.defaultnodealternate
+ if defaultalt=="first" then
+ return alternatives[n],trace_alternatives and formatters["invalid value %s, taking %a"](value,1)
+ elseif defaultalt=="last" then
+ return alternatives[1],trace_alternatives and formatters["invalid value %s, taking %a"](value,n)
+ else
+ return false,trace_alternatives and formatters["invalid value %a, %s"](value,"out of range")
+ end
+ elseif value==0 then
+ return getchar(start),trace_alternatives and formatters["invalid value %a, %s"](value,"no change")
+ elseif value<1 then
+ return alternatives[1],trace_alternatives and formatters["invalid value %a, taking %a"](value,1)
+ else
+ return alternatives[value],trace_alternatives and formatters["value %a, taking %a"](value,value)
+ end
+end
+function handlers.gsub_single(head,start,dataset,sequence,replacement)
+ if trace_singles then
+ logprocess("%s: replacing %s by single %s",pref(dataset,sequence),gref(getchar(start)),gref(replacement))
+ end
+ resetinjection(start)
+ setchar(start,replacement)
+ return head,start,true
+end
+function handlers.gsub_alternate(head,start,dataset,sequence,alternative)
+ local kind=dataset[4]
+ local what=dataset[1]
+ local value=what==true and tfmdata.shared.features[kind] or what
+ local choice,comment=get_alternative_glyph(start,alternative,value)
+ if choice then
+ if trace_alternatives then
+ logprocess("%s: replacing %s by alternative %a to %s, %s",pref(dataset,sequence),gref(getchar(start)),gref(choice),comment)
+ end
+ resetinjection(start)
+ setchar(start,choice)
+ else
+ if trace_alternatives then
+ logwarning("%s: no variant %a for %s, %s",pref(dataset,sequence),value,gref(getchar(start)),comment)
+ end
+ end
+ return head,start,true
+end
+function handlers.gsub_multiple(head,start,dataset,sequence,multiple,rlmode,skiphash)
+ if trace_multiples then
+ logprocess("%s: replacing %s by multiple %s",pref(dataset,sequence),gref(getchar(start)),gref(multiple))
+ end
+ return multiple_glyphs(head,start,multiple,skiphash,dataset[1])
+end
+function handlers.gsub_ligature(head,start,dataset,sequence,ligature,rlmode,skiphash)
+ local current=getnext(start)
+ if not current then
+ return head,start,false,nil
+ end
+ local stop=nil
+ local startchar=getchar(start)
+ if skiphash and skiphash[startchar] then
+ while current do
+ local char=ischar(current,currentfont)
+ if char then
+ local lg=ligature[char]
+ if lg then
+ stop=current
+ ligature=lg
+ current=getnext(current)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if stop then
+ local lig=ligature.ligature
+ if lig then
+ if trace_ligatures then
+ local stopchar=getchar(stop)
+ head,start=markstoligature(head,start,stop,lig)
+ logprocess("%s: replacing %s upto %s by ligature %s case 1",pref(dataset,sequence),gref(startchar),gref(stopchar),gref(getchar(start)))
+ else
+ head,start=markstoligature(head,start,stop,lig)
+ end
+ return head,start,true,false
+ else
+ end
+ end
+ else
+ local discfound=false
+ local hasmarks=marks[startchar]
+ while current do
+ local char,id=ischar(current,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ current=getnext(current)
+ else
+ local lg=ligature[char]
+ if lg then
+ if marks[char] then
+ hasmarks=true
+ end
+ stop=current
+ ligature=lg
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ elseif char==false then
+ break
+ elseif id==disc_code then
+ discfound=current
+ break
+ else
+ break
+ end
+ end
+ if discfound then
+ local pre,post,replace=getdisc(discfound)
+ local match
+ if replace then
+ local char=ischar(replace,currentfont)
+ if char and ligature[char] then
+ match=true
+ end
+ end
+ if not match and pre then
+ local char=ischar(pre,currentfont)
+ if char and ligature[char] then
+ match=true
+ end
+ end
+ if not match and not pre or not replace then
+ local n=getnext(discfound)
+ local char=ischar(n,currentfont)
+ if char and ligature[char] then
+ match=true
+ end
+ end
+ if match then
+ local ishead=head==start
+ local prev=getprev(start)
+ if stop then
+ setnext(stop)
+ local copy=copy_node_list(start)
+ local tail=stop
+ local liat=find_node_tail(copy)
+ if pre then
+ setlink(liat,pre)
+ end
+ if replace then
+ setlink(tail,replace)
+ end
+ pre=copy
+ replace=start
+ else
+ setnext(start)
+ local copy=copy_node(start)
+ if pre then
+ setlink(copy,pre)
+ end
+ if replace then
+ setlink(start,replace)
+ end
+ pre=copy
+ replace=start
+ end
+ setdisc(discfound,pre,post,replace)
+ if prev then
+ setlink(prev,discfound)
+ else
+ setprev(discfound)
+ head=discfound
+ end
+ start=discfound
+ return head,start,true,true
+ end
+ end
+ local lig=ligature.ligature
+ if lig then
+ if stop then
+ if trace_ligatures then
+ local stopchar=getchar(stop)
+ head,start=toligature(head,start,stop,lig,dataset,sequence,skiphash,false,hasmarks)
+ logprocess("%s: replacing %s upto %s by ligature %s case 2",pref(dataset,sequence),gref(startchar),gref(stopchar),gref(lig))
+ else
+ head,start=toligature(head,start,stop,lig,dataset,sequence,skiphash,false,hasmarks)
+ end
+ else
+ resetinjection(start)
+ setchar(start,lig)
+ if trace_ligatures then
+ logprocess("%s: replacing %s by (no real) ligature %s case 3",pref(dataset,sequence),gref(startchar),gref(lig))
+ end
+ end
+ return head,start,true,false
+ else
+ end
+ end
+ return head,start,false,false
+end
+function handlers.gpos_single(head,start,dataset,sequence,kerns,rlmode,skiphash,step,injection)
+ local startchar=getchar(start)
+ local format=step.format
+ if format=="single" or type(kerns)=="table" then
+ local dx,dy,w,h=setposition(0,start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s xy (%p,%p) and wh (%p,%p)",pref(dataset,sequence),gref(startchar),format,dx,dy,w,h)
+ end
+ else
+ local k=(format=="move" and setmove or setkern)(start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s %p",pref(dataset,sequence),gref(startchar),format,k)
+ end
+ end
+ return head,start,true
+end
+function handlers.gpos_pair(head,start,dataset,sequence,kerns,rlmode,skiphash,step,injection)
+ local snext=getnext(start)
+ if not snext then
+ return head,start,false
+ else
+ local prev=start
+ while snext do
+ local nextchar=ischar(snext,currentfont)
+ if nextchar then
+ if skiphash and skiphash[nextchar] then
+ prev=snext
+ snext=getnext(snext)
+ else
+ local krn=kerns[nextchar]
+ if not krn then
+ break
+ end
+ local format=step.format
+ if format=="pair" then
+ local a=krn[1]
+ local b=krn[2]
+ if a==true then
+ elseif a then
+ local x,y,w,h=setposition(1,start,factor,rlmode,a,injection)
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting first of pair %s and %s by xy (%p,%p) and wh (%p,%p) as %s",pref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h,injection or "injections")
+ end
+ end
+ if b==true then
+ start=snext
+ elseif b then
+ local x,y,w,h=setposition(2,snext,factor,rlmode,b,injection)
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting second of pair %s and %s by xy (%p,%p) and wh (%p,%p) as %s",pref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h,injection or "injections")
+ end
+ start=snext
+ elseif forcepairadvance then
+ start=snext
+ end
+ return head,start,true
+ elseif krn~=0 then
+ local k=(format=="move" and setmove or setkern)(snext,factor,rlmode,krn,injection)
+ if trace_kerns then
+ logprocess("%s: inserting %s %p between %s and %s as %s",pref(dataset,sequence),format,k,gref(getchar(prev)),gref(nextchar),injection or "injections")
+ end
+ return head,start,true
+ else
+ break
+ end
+ end
+ else
+ break
+ end
+ end
+ return head,start,false
+ end
+end
+function handlers.gpos_mark2base(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basechar %s => (%p,%p)",
+ pref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ elseif trace_bugs then
+ logwarning("%s: mark %s is not anchored to %s",pref(dataset,sequence),gref(markchar),gref(basechar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: nothing preceding, case %i",pref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: nothing preceding, case %i",pref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head,start,false
+end
+function handlers.gpos_mark2ligature(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local index=getligaindex(start)
+ ba=ba[index]
+ if ba then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, index %s, bound %s, anchoring mark %s to baselig %s at index %s => (%p,%p)",
+ pref(dataset,sequence),index,bound,gref(markchar),gref(basechar),index,dx,dy)
+ end
+ return head,start,true
+ else
+ if trace_bugs then
+ logwarning("%s: no matching anchors for mark %s and baselig %s with index %a",pref(dataset,sequence),gref(markchar),gref(basechar),index)
+ end
+ end
+ end
+ elseif trace_bugs then
+ onetimemessage(currentfont,basechar,"no base anchors",report_fonts)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",pref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",pref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head,start,false
+end
+function handlers.gpos_mark2mark(head,start,dataset,sequence,markanchors,rlmode,skiphash)
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local base=getprev(start)
+ local slc=getligaindex(start)
+ if slc then
+ while base do
+ local blc=getligaindex(base)
+ if blc and blc~=slc then
+ base=getprev(base)
+ else
+ break
+ end
+ end
+ end
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],true,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basemark %s => (%p,%p)",
+ pref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",pref(dataset,sequence),gref(markchar))
+ end
+ return head,start,false
+end
+function handlers.gpos_cursive(head,start,dataset,sequence,exitanchors,rlmode,skiphash,step)
+ local startchar=getchar(start)
+ if marks[startchar] then
+ if trace_cursive then
+ logprocess("%s: ignoring cursive for mark %s",pref(dataset,sequence),gref(startchar))
+ end
+ else
+ local nxt=getnext(start)
+ while nxt do
+ local nextchar=ischar(nxt,currentfont)
+ if not nextchar then
+ break
+ elseif marks[nextchar] then
+ nxt=getnext(nxt)
+ else
+ local exit=exitanchors[3]
+ if exit then
+ local entry=exitanchors[1][nextchar]
+ if entry then
+ entry=entry[2]
+ if entry then
+ local r2lflag=sequence.flags[4]
+ local dx,dy,bound=setcursive(start,nxt,factor,rlmode,exit,entry,characters[startchar],characters[nextchar],r2lflag)
+ if trace_cursive then
+ logprocess("%s: moving %s to %s cursive (%p,%p) using bound %s in %s mode",pref(dataset,sequence),gref(startchar),gref(nextchar),dx,dy,bound,mref(rlmode))
+ end
+ return head,start,true
+ end
+ end
+ end
+ break
+ end
+ end
+ end
+ return head,start,false
+end
+local chainprocs={}
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_subchain(...)
+end
+local logwarning=report_subchain
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_chain(...)
+end
+local logwarning=report_chain
+local function reversesub(head,start,stop,dataset,sequence,replacements,rlmode,skiphash)
+ local char=getchar(start)
+ local replacement=replacements[char]
+ if replacement then
+ if trace_singles then
+ logprocess("%s: single reverse replacement of %s by %s",cref(dataset,sequence),gref(char),gref(replacement))
+ end
+ resetinjection(start)
+ setchar(start,replacement)
+ return head,start,true
+ else
+ return head,start,false
+ end
+end
+chainprocs.reversesub=reversesub
+local function reportzerosteps(dataset,sequence)
+ logwarning("%s: no steps",cref(dataset,sequence))
+end
+local function reportmoresteps(dataset,sequence)
+ logwarning("%s: more than 1 step",cref(dataset,sequence))
+end
+local function getmapping(dataset,sequence,currentlookup)
+ local steps=currentlookup.steps
+ local nofsteps=currentlookup.nofsteps
+ if nofsteps==0 then
+ reportzerosteps(dataset,sequence)
+ currentlookup.mapping=false
+ return false
+ else
+ if nofsteps>1 then
+ reportmoresteps(dataset,sequence)
+ end
+ local mapping=steps[1].coverage
+ currentlookup.mapping=mapping
+ currentlookup.format=steps[1].format
+ return mapping
+ end
+end
+function chainprocs.gsub_remove(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ if trace_chains then
+ logprocess("%s: removing character %s",cref(dataset,sequence,chainindex),gref(getchar(start)))
+ end
+ head,start=remove_node(head,start,true)
+ return head,getprev(start),true
+end
+function chainprocs.gsub_single(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local current=start
+ while current do
+ local currentchar=ischar(current)
+ if currentchar then
+ local replacement=mapping[currentchar]
+ if not replacement or replacement=="" then
+ if trace_bugs then
+ logwarning("%s: no single for %s",cref(dataset,sequence,chainindex),gref(currentchar))
+ end
+ else
+ if trace_singles then
+ logprocess("%s: replacing single %s by %s",cref(dataset,sequence,chainindex),gref(currentchar),gref(replacement))
+ end
+ resetinjection(current)
+ setchar(current,replacement)
+ end
+ return head,start,true
+ elseif currentchar==false then
+ break
+ elseif current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gsub_alternate(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local kind=dataset[4]
+ local what=dataset[1]
+ local value=what==true and tfmdata.shared.features[kind] or what
+ local current=start
+ while current do
+ local currentchar=ischar(current)
+ if currentchar then
+ local alternatives=mapping[currentchar]
+ if alternatives then
+ local choice,comment=get_alternative_glyph(current,alternatives,value)
+ if choice then
+ if trace_alternatives then
+ logprocess("%s: replacing %s by alternative %a to %s, %s",cref(dataset,sequence),gref(currentchar),choice,gref(choice),comment)
+ end
+ resetinjection(start)
+ setchar(start,choice)
+ else
+ if trace_alternatives then
+ logwarning("%s: no variant %a for %s, %s",cref(dataset,sequence),value,gref(currentchar),comment)
+ end
+ end
+ end
+ return head,start,true
+ elseif currentchar==false then
+ break
+ elseif current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gsub_multiple(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local replacement=mapping[startchar]
+ if not replacement or replacement=="" then
+ if trace_bugs then
+ logwarning("%s: no multiple for %s",cref(dataset,sequence),gref(startchar))
+ end
+ else
+ if trace_multiples then
+ logprocess("%s: replacing %s by multiple characters %s",cref(dataset,sequence),gref(startchar),gref(replacement))
+ end
+ return multiple_glyphs(head,start,replacement,skiphash,dataset[1],stop)
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gsub_ligature(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local ligatures=mapping[startchar]
+ if not ligatures then
+ if trace_bugs then
+ logwarning("%s: no ligatures starting with %s",cref(dataset,sequence,chainindex),gref(startchar))
+ end
+ else
+ local hasmarks=marks[startchar]
+ local current=getnext(start)
+ local discfound=false
+ local last=stop
+ local nofreplacements=1
+ while current do
+ local id=getid(current)
+ if id==disc_code then
+ if not discfound then
+ discfound=current
+ end
+ if current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ else
+ local schar=getchar(current)
+ if skiphash and skiphash[schar] then
+ current=getnext(current)
+ else
+ local lg=ligatures[schar]
+ if lg then
+ ligatures=lg
+ last=current
+ nofreplacements=nofreplacements+1
+ if marks[char] then
+ hasmarks=true
+ end
+ if current==stop then
+ break
+ else
+ current=getnext(current)
+ end
+ else
+ break
+ end
+ end
+ end
+ end
+ local ligature=ligatures.ligature
+ if ligature then
+ if chainindex then
+ stop=last
+ end
+ if trace_ligatures then
+ if start==stop then
+ logprocess("%s: replacing character %s by ligature %s case 3",cref(dataset,sequence,chainindex),gref(startchar),gref(ligature))
+ else
+ logprocess("%s: replacing character %s upto %s by ligature %s case 4",cref(dataset,sequence,chainindex),gref(startchar),gref(getchar(stop)),gref(ligature))
+ end
+ end
+ head,start=toligature(head,start,stop,ligature,dataset,sequence,skiphash,discfound,hasmarks)
+ return head,start,true,nofreplacements,discfound
+ elseif trace_bugs then
+ if start==stop then
+ logwarning("%s: replacing character %s by ligature fails",cref(dataset,sequence,chainindex),gref(startchar))
+ else
+ logwarning("%s: replacing character %s upto %s by ligature fails",cref(dataset,sequence,chainindex),gref(startchar),gref(getchar(stop)))
+ end
+ end
+ end
+ end
+ return head,start,false,0,false
+end
+function chainprocs.gpos_single(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local kerns=mapping[startchar]
+ if kerns then
+ local format=currentlookup.format
+ if format=="single" then
+ local dx,dy,w,h=setposition(0,start,factor,rlmode,kerns)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),format,dx,dy,w,h)
+ end
+ else
+ local k=(format=="move" and setmove or setkern)(start,factor,rlmode,kerns,injection)
+ if trace_kerns then
+ logprocess("%s: shifting single %s by %s %p",cref(dataset,sequence),gref(startchar),format,k)
+ end
+ end
+ return head,start,true
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_pair(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local snext=getnext(start)
+ if snext then
+ local startchar=getchar(start)
+ local kerns=mapping[startchar]
+ if kerns then
+ local prev=start
+ while snext do
+ local nextchar=ischar(snext,currentfont)
+ if not nextchar then
+ break
+ end
+ if skiphash and skiphash[nextchar] then
+ prev=snext
+ snext=getnext(snext)
+ else
+ local krn=kerns[nextchar]
+ if not krn then
+ break
+ end
+ local format=currentlookup.format
+ if format=="pair" then
+ local a=krn[1]
+ local b=krn[2]
+ if a==true then
+ elseif a then
+ local x,y,w,h=setposition(1,start,factor,rlmode,a,"injections")
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting first of pair %s and %s by (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h)
+ end
+ end
+ if b==true then
+ start=snext
+ elseif b then
+ local x,y,w,h=setposition(2,snext,factor,rlmode,b,"injections")
+ if trace_kerns then
+ local startchar=getchar(start)
+ logprocess("%s: shifting second of pair %s and %s by (%p,%p) and correction (%p,%p)",cref(dataset,sequence),gref(startchar),gref(nextchar),x,y,w,h)
+ end
+ start=snext
+ elseif forcepairadvance then
+ start=snext
+ end
+ return head,start,true
+ elseif krn~=0 then
+ local k=(format=="move" and setmove or setkern)(snext,factor,rlmode,krn)
+ if trace_kerns then
+ logprocess("%s: inserting %s %p between %s and %s",cref(dataset,sequence),format,k,gref(getchar(prev)),gref(nextchar))
+ end
+ return head,start,true
+ else
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_mark2base(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local markanchors=mapping[markchar]
+ if markanchors then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",pref(dataset,sequence),gref(markchar),2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basechar %s => (%p,%p)",
+ cref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no char, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_mark2ligature(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local markanchors=mapping[markchar]
+ if markanchors then
+ local base=getprev(start)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if marks[basechar] then
+ while base do
+ base=getprev(base)
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ if not marks[basechar] then
+ break
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",cref(dataset,sequence),markchar,1)
+ end
+ return head,start,false
+ end
+ else
+ if trace_bugs then
+ logwarning("%s: no base for mark %s, case %i",cref(dataset,sequence),markchar,2)
+ end
+ return head,start,false
+ end
+ end
+ end
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local index=getligaindex(start)
+ ba=ba[index]
+ if ba then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],false,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to baselig %s at index %s => (%p,%p)",
+ cref(dataset,sequence),a or bound,gref(markchar),gref(basechar),index,dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s, prev node is no char, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s, prev node is no char, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s, mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s, mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_mark2mark(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local markchar=getchar(start)
+ if marks[markchar] then
+ local markanchors=mapping[markchar]
+ if markanchors then
+ local base=getprev(start)
+ local slc=getligaindex(start)
+ if slc then
+ while base do
+ local blc=getligaindex(base)
+ if blc and blc~=slc then
+ base=getprev(base)
+ else
+ break
+ end
+ end
+ end
+ if base then
+ local basechar=ischar(base,currentfont)
+ if basechar then
+ local ba=markanchors[1][basechar]
+ if ba then
+ local ma=markanchors[2]
+ if ma then
+ local dx,dy,bound=setmark(start,base,factor,rlmode,ba,ma,characters[basechar],true,checkmarks)
+ if trace_marks then
+ logprocess("%s, bound %s, anchoring mark %s to basemark %s => (%p,%p)",
+ cref(dataset,sequence),bound,gref(markchar),gref(basechar),dx,dy)
+ end
+ return head,start,true
+ end
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no mark, case %i",cref(dataset,sequence),1)
+ end
+ elseif trace_bugs then
+ logwarning("%s: prev node is no mark, case %i",cref(dataset,sequence),2)
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s has no anchors",cref(dataset,sequence),gref(markchar))
+ end
+ elseif trace_bugs then
+ logwarning("%s: mark %s is no mark",cref(dataset,sequence),gref(markchar))
+ end
+ end
+ return head,start,false
+end
+function chainprocs.gpos_cursive(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash,chainindex)
+ local mapping=currentlookup.mapping
+ if mapping==nil then
+ mapping=getmapping(dataset,sequence,currentlookup)
+ end
+ if mapping then
+ local startchar=getchar(start)
+ local exitanchors=mapping[startchar]
+ if exitanchors then
+ if marks[startchar] then
+ if trace_cursive then
+ logprocess("%s: ignoring cursive for mark %s",pref(dataset,sequence),gref(startchar))
+ end
+ else
+ local nxt=getnext(start)
+ while nxt do
+ local nextchar=ischar(nxt,currentfont)
+ if not nextchar then
+ break
+ elseif marks[nextchar] then
+ nxt=getnext(nxt)
+ else
+ local exit=exitanchors[3]
+ if exit then
+ local entry=exitanchors[1][nextchar]
+ if entry then
+ entry=entry[2]
+ if entry then
+ local r2lflag=sequence.flags[4]
+ local dx,dy,bound=setcursive(start,nxt,factor,rlmode,exit,entry,characters[startchar],characters[nextchar],r2lflag)
+ if trace_cursive then
+ logprocess("%s: moving %s to %s cursive (%p,%p) using bound %s in %s mode",pref(dataset,sequence),gref(startchar),gref(nextchar),dx,dy,bound,mref(rlmode))
+ end
+ return head,start,true
+ end
+ end
+ elseif trace_bugs then
+ onetimemessage(currentfont,startchar,"no entry anchors",report_fonts)
+ end
+ break
+ end
+ end
+ end
+ elseif trace_cursive and trace_details then
+ logprocess("%s, cursive %s is already done",pref(dataset,sequence),gref(getchar(start)),alreadydone)
+ end
+ end
+ return head,start,false
+end
+local function show_skip(dataset,sequence,char,ck,class)
+ logwarning("%s: skipping char %s, class %a, rule %a, lookuptype %a",cref(dataset,sequence),gref(char),class,ck[1],ck[8] or ck[2])
+end
+local userkern=nuts.pool and nuts.pool.newkern
+do if not userkern then
+ local thekern=nuts.new("kern",1)
+ local setkern=nuts.setkern
+ userkern=function(k)
+ local n=copy_node(thekern)
+ setkern(n,k)
+ return n
+ end
+end end
+local function checked(head)
+ local current=head
+ while current do
+ if getid(current)==glue_code then
+ local kern=userkern(getwidth(current))
+ if head==current then
+ local next=getnext(current)
+ if next then
+ setlink(kern,next)
+ end
+ flush_node(current)
+ head=kern
+ current=next
+ else
+ local prev,next=getboth(current)
+ setlink(prev,kern,next)
+ flush_node(current)
+ current=next
+ end
+ else
+ current=getnext(current)
+ end
+ end
+ return head
+end
+local function setdiscchecked(d,pre,post,replace)
+ if pre then pre=checked(pre) end
+ if post then post=checked(post) end
+ if replace then replace=checked(replace) end
+ setdisc(d,pre,post,replace)
+end
+local noflags={ false,false,false,false }
+local function chainrun(head,start,last,dataset,sequence,rlmode,skiphash,ck)
+ local size=ck[5]-ck[4]+1
+ local chainlookups=ck[6]
+ local done=false
+ if chainlookups then
+ if size==1 then
+ local chainlookup=chainlookups[1]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local chainkind=chainstep.type
+ local chainproc=chainprocs[chainkind]
+ if chainproc then
+ local ok
+ head,start,ok=chainproc(head,start,last,dataset,sequence,chainstep,rlmode,skiphash)
+ if ok then
+ done=true
+ end
+ else
+ logprocess("%s: %s is not yet supported (1)",cref(dataset,sequence),chainkind)
+ end
+ end
+ else
+ local i=1
+ local laststart=start
+ local nofchainlookups=#chainlookups
+ while start do
+ if skiphash then
+ while start do
+ local char=ischar(start,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ end
+ local chainlookup=chainlookups[i]
+ if chainlookup then
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local chainkind=chainstep.type
+ local chainproc=chainprocs[chainkind]
+ if chainproc then
+ local ok,n
+ head,start,ok,n=chainproc(head,start,last,dataset,sequence,chainstep,rlmode,skiphash,i)
+ if ok then
+ done=true
+ if n and n>1 and i+n>nofchainlookups then
+ i=size
+ break
+ end
+ end
+ else
+ logprocess("%s: %s is not yet supported (2)",cref(dataset,sequence),chainkind)
+ end
+ end
+ else
+ end
+ i=i+1
+ if i>size or not start then
+ break
+ elseif start then
+ laststart=start
+ start=getnext(start)
+ end
+ end
+ if not start then
+ start=laststart
+ end
+ end
+ else
+ local replacements=ck[7]
+ if replacements then
+ head,start,done=reversesub(head,start,last,dataset,sequence,replacements,rlmode,skiphash)
+ else
+ done=true
+ if trace_contexts then
+ logprocess("%s: skipping match",cref(dataset,sequence))
+ end
+ end
+ end
+ return head,start,done
+end
+local function chaindisk(head,start,dataset,sequence,rlmode,skiphash,ck)
+ if not start then
+ return head,start,false
+ end
+ local startishead=start==head
+ local seq=ck[3]
+ local f=ck[4]
+ local l=ck[5]
+ local s=#seq
+ local done=false
+ local sweepnode=sweepnode
+ local sweeptype=sweeptype
+ local sweepoverflow=false
+ local keepdisc=not sweepnode
+ local lookaheaddisc=nil
+ local backtrackdisc=nil
+ local current=start
+ local last=start
+ local prev=getprev(start)
+ local hasglue=false
+ local i=f
+ while i<=l do
+ local id=getid(current)
+ if id==glyph_code then
+ i=i+1
+ last=current
+ current=getnext(current)
+ elseif id==glue_code then
+ i=i+1
+ last=current
+ current=getnext(current)
+ hasglue=true
+ elseif id==disc_code then
+ if keepdisc then
+ keepdisc=false
+ lookaheaddisc=current
+ local replace=getfield(current,"replace")
+ if not replace then
+ sweepoverflow=true
+ sweepnode=current
+ current=getnext(current)
+ else
+ while replace and i<=l do
+ if getid(replace)==glyph_code then
+ i=i+1
+ end
+ replace=getnext(replace)
+ end
+ current=getnext(replace)
+ end
+ last=current
+ else
+ head,current=flattendisk(head,current)
+ end
+ else
+ last=current
+ current=getnext(current)
+ end
+ if current then
+ elseif sweepoverflow then
+ break
+ elseif sweeptype=="post" or sweeptype=="replace" then
+ current=getnext(sweepnode)
+ if current then
+ sweeptype=nil
+ sweepoverflow=true
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if sweepoverflow then
+ local prev=current and getprev(current)
+ if not current or prev~=sweepnode then
+ local head=getnext(sweepnode)
+ local tail=nil
+ if prev then
+ tail=prev
+ setprev(current,sweepnode)
+ else
+ tail=find_node_tail(head)
+ end
+ setnext(sweepnode,current)
+ setprev(head)
+ setnext(tail)
+ appenddisc(sweepnode,head)
+ end
+ end
+ if l<s then
+ local i=l
+ local t=sweeptype=="post" or sweeptype=="replace"
+ while current and i<s do
+ local id=getid(current)
+ if id==glyph_code then
+ i=i+1
+ current=getnext(current)
+ elseif id==glue_code then
+ i=i+1
+ current=getnext(current)
+ hasglue=true
+ elseif id==disc_code then
+ if keepdisc then
+ keepdisc=false
+ if notmatchpre[current]~=notmatchreplace[current] then
+ lookaheaddisc=current
+ end
+ local replace=getfield(current,"replace")
+ while replace and i<s do
+ if getid(replace)==glyph_code then
+ i=i+1
+ end
+ replace=getnext(replace)
+ end
+ current=getnext(current)
+ elseif notmatchpre[current]~=notmatchreplace[current] then
+ head,current=flattendisk(head,current)
+ else
+ current=getnext(current)
+ end
+ else
+ current=getnext(current)
+ end
+ if not current and t then
+ current=getnext(sweepnode)
+ if current then
+ sweeptype=nil
+ end
+ end
+ end
+ end
+ if f>1 then
+ local current=prev
+ local i=f
+ local t=sweeptype=="pre" or sweeptype=="replace"
+ if not current and t and current==checkdisk then
+ current=getprev(sweepnode)
+ end
+ while current and i>1 do
+ local id=getid(current)
+ if id==glyph_code then
+ i=i-1
+ elseif id==glue_code then
+ i=i-1
+ hasglue=true
+ elseif id==disc_code then
+ if keepdisc then
+ keepdisc=false
+ if notmatchpost[current]~=notmatchreplace[current] then
+ backtrackdisc=current
+ end
+ local replace=getfield(current,"replace")
+ while replace and i>1 do
+ if getid(replace)==glyph_code then
+ i=i-1
+ end
+ replace=getnext(replace)
+ end
+ elseif notmatchpost[current]~=notmatchreplace[current] then
+ head,current=flattendisk(head,current)
+ end
+ end
+ current=getprev(current)
+ if t and current==checkdisk then
+ current=getprev(sweepnode)
+ end
+ end
+ end
+ local done=false
+ if lookaheaddisc then
+ local cf=start
+ local cl=getprev(lookaheaddisc)
+ local cprev=getprev(start)
+ local insertedmarks=0
+ while cprev do
+ local char=ischar(cf,currentfont)
+ if char and marks[char] then
+ insertedmarks=insertedmarks+1
+ cf=cprev
+ startishead=cf==head
+ cprev=getprev(cprev)
+ else
+ break
+ end
+ end
+ setlink(cprev,lookaheaddisc)
+ setprev(cf)
+ setnext(cl)
+ if startishead then
+ head=lookaheaddisc
+ end
+ local pre,post,replace=getdisc(lookaheaddisc)
+ local new=copy_node_list(cf)
+ local cnew=new
+ if pre then
+ setlink(find_node_tail(cf),pre)
+ end
+ if replace then
+ local tail=find_node_tail(new)
+ setlink(tail,replace)
+ end
+ for i=1,insertedmarks do
+ cnew=getnext(cnew)
+ end
+ cl=start
+ local clast=cnew
+ for i=f,l do
+ cl=getnext(cl)
+ clast=getnext(clast)
+ end
+ if not notmatchpre[lookaheaddisc] then
+ local ok=false
+ cf,start,ok=chainrun(cf,start,cl,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if not notmatchreplace[lookaheaddisc] then
+ local ok=false
+ new,cnew,ok=chainrun(new,cnew,clast,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if hasglue then
+ setdiscchecked(lookaheaddisc,cf,post,new)
+ else
+ setdisc(lookaheaddisc,cf,post,new)
+ end
+ start=getprev(lookaheaddisc)
+ sweephead[cf]=getnext(clast) or false
+ sweephead[new]=getnext(cl) or false
+ elseif backtrackdisc then
+ local cf=getnext(backtrackdisc)
+ local cl=start
+ local cnext=getnext(start)
+ local insertedmarks=0
+ while cnext do
+ local char=ischar(cnext,currentfont)
+ if char and marks[char] then
+ insertedmarks=insertedmarks+1
+ cl=cnext
+ cnext=getnext(cnext)
+ else
+ break
+ end
+ end
+ setlink(backtrackdisc,cnext)
+ setprev(cf)
+ setnext(cl)
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(backtrackdisc,true)
+ local new=copy_node_list(cf)
+ local cnew=find_node_tail(new)
+ for i=1,insertedmarks do
+ cnew=getprev(cnew)
+ end
+ local clast=cnew
+ for i=f,l do
+ clast=getnext(clast)
+ end
+ if not notmatchpost[backtrackdisc] then
+ local ok=false
+ cf,start,ok=chainrun(cf,start,last,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if not notmatchreplace[backtrackdisc] then
+ local ok=false
+ new,cnew,ok=chainrun(new,cnew,clast,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ if post then
+ setlink(posttail,cf)
+ else
+ post=cf
+ end
+ if replace then
+ setlink(replacetail,new)
+ else
+ replace=new
+ end
+ if hasglue then
+ setdiscchecked(backtrackdisc,pre,post,replace)
+ else
+ setdisc(backtrackdisc,pre,post,replace)
+ end
+ start=getprev(backtrackdisc)
+ sweephead[post]=getnext(clast) or false
+ sweephead[replace]=getnext(last) or false
+ else
+ local ok=false
+ head,start,ok=chainrun(head,start,last,dataset,sequence,rlmode,skiphash,ck)
+ if ok then
+ done=true
+ end
+ end
+ return head,start,done
+end
+local function chaintrac(head,start,dataset,sequence,rlmode,skiphash,ck,match,discseen,sweepnode)
+ local rule=ck[1]
+ local lookuptype=ck[8] or ck[2]
+ local nofseq=#ck[3]
+ local first=ck[4]
+ local last=ck[5]
+ local char=getchar(start)
+ logwarning("%s: rule %s %s at char %s for (%s,%s,%s) chars, lookuptype %a, %sdisc seen, %ssweeping",
+ cref(dataset,sequence),rule,match and "matches" or "nomatch",
+ gref(char),first-1,last-first+1,nofseq-last,lookuptype,
+ discseen and "" or "no ",sweepnode and "" or "not ")
+end
+local function handle_contextchain(head,start,dataset,sequence,contexts,rlmode,skiphash)
+ local sweepnode=sweepnode
+ local sweeptype=sweeptype
+ local postreplace
+ local prereplace
+ local checkdisc
+ local discseen
+ if sweeptype then
+ if sweeptype=="replace" then
+ postreplace=true
+ prereplace=true
+ else
+ postreplace=sweeptype=="post"
+ prereplace=sweeptype=="pre"
+ end
+ checkdisc=getprev(head)
+ end
+ local currentfont=currentfont
+ local skipped
+ local startprev,
+ startnext=getboth(start)
+ local done
+ local nofcontexts=contexts.n
+ local startchar=nofcontext==1 or ischar(start,currentfont)
+ for k=1,nofcontexts do
+ local ck=contexts[k]
+ local seq=ck[3]
+ local f=ck[4]
+ if not startchar or not seq[f][startchar] then
+ goto next
+ end
+ local s=seq.n
+ local l=ck[5]
+ local current=start
+ local last=start
+ if l>f then
+ local discfound
+ local n=f+1
+ last=startnext
+ while n<=l do
+ if postreplace and not last then
+ last=getnext(sweepnode)
+ sweeptype=nil
+ end
+ if last then
+ local char,id=ischar(last,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped=true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ last=getnext(last)
+ elseif seq[n][char] then
+ if n<l then
+ last=getnext(last)
+ end
+ n=n+1
+ elseif discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char==false then
+ if discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif id==disc_code then
+ discseen=true
+ discfound=last
+ notmatchpre[last]=nil
+ notmatchpost[last]=true
+ notmatchreplace[last]=nil
+ local pre,post,replace=getdisc(last)
+ if pre then
+ local n=n
+ while pre do
+ if seq[n][getchar(pre)] then
+ n=n+1
+ if n>l then
+ break
+ end
+ pre=getnext(pre)
+ else
+ notmatchpre[last]=true
+ break
+ end
+ end
+ else
+ notmatchpre[last]=true
+ end
+ if replace then
+ while replace do
+ if seq[n][getchar(replace)] then
+ n=n+1
+ if n>l then
+ break
+ end
+ replace=getnext(replace)
+ else
+ notmatchreplace[last]=true
+ if notmatchpre[last] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ if notmatchpre[last] then
+ goto next
+ end
+ end
+ last=getnext(last)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ end
+ if f>1 then
+ if startprev then
+ local prev=startprev
+ if prereplace and prev==checkdisc then
+ prev=getprev(sweepnode)
+ end
+ if prev then
+ local discfound
+ local n=f-1
+ while n>=1 do
+ if prev then
+ local char,id=ischar(prev,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped=true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ prev=getprev(prev)
+ elseif seq[n][char] then
+ if n>1 then
+ prev=getprev(prev)
+ end
+ n=n-1
+ elseif discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpost[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char==false then
+ if discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpost[discfound] then
+ goto next
+ end
+ else
+ goto next
+ end
+ break
+ elseif id==disc_code then
+ discseen=true
+ discfound=prev
+ notmatchpre[prev]=true
+ notmatchpost[prev]=nil
+ notmatchreplace[prev]=nil
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(prev,true)
+ if pre~=start and post~=start and replace~=start then
+ if post then
+ local n=n
+ while posttail do
+ if seq[n][getchar(posttail)] then
+ n=n-1
+ if posttail==post or n<1 then
+ break
+ else
+ posttail=getprev(posttail)
+ end
+ else
+ notmatchpost[prev]=true
+ break
+ end
+ end
+ if n>=1 then
+ notmatchpost[prev]=true
+ end
+ else
+ notmatchpost[prev]=true
+ end
+ if replace then
+ while replacetail do
+ if seq[n][getchar(replacetail)] then
+ n=n-1
+ if replacetail==replace or n<1 then
+ break
+ else
+ replacetail=getprev(replacetail)
+ end
+ else
+ notmatchreplace[prev]=true
+ if notmatchpost[prev] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ else
+ end
+ end
+ prev=getprev(prev)
+ elseif id==glue_code then
+ local sn=seq[n]
+ if (sn[32] and spaces[prev]) or sn[0xFFFC] then
+ n=n-1
+ prev=getprev(prev)
+ else
+ goto next
+ end
+ elseif seq[n][0xFFFC] then
+ n=n-1
+ prev=getprev(prev)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ if s>l then
+ local current=last and getnext(last)
+ if not current and postreplace then
+ current=getnext(sweepnode)
+ end
+ if current then
+ local discfound
+ local n=l+1
+ while n<=s do
+ if current then
+ local char,id=ischar(current,currentfont)
+ if char then
+ if skiphash and skiphash[char] then
+ skipped=true
+ if trace_skips then
+ show_skip(dataset,sequence,char,ck,classes[char])
+ end
+ current=getnext(current)
+ elseif seq[n][char] then
+ if n<s then
+ current=getnext(current)
+ end
+ n=n+1
+ elseif discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif char==false then
+ if discfound then
+ notmatchreplace[discfound]=true
+ if notmatchpre[discfound] then
+ goto next
+ else
+ break
+ end
+ else
+ goto next
+ end
+ elseif id==disc_code then
+ discseen=true
+ discfound=current
+ notmatchpre[current]=nil
+ notmatchpost[current]=true
+ notmatchreplace[current]=nil
+ local pre,post,replace=getdisc(current)
+ if pre then
+ local n=n
+ while pre do
+ if seq[n][getchar(pre)] then
+ n=n+1
+ if n>s then
+ break
+ else
+ pre=getnext(pre)
+ end
+ else
+ notmatchpre[current]=true
+ break
+ end
+ end
+ if n<=s then
+ notmatchpre[current]=true
+ end
+ else
+ notmatchpre[current]=true
+ end
+ if replace then
+ while replace do
+ if seq[n][getchar(replace)] then
+ n=n+1
+ if n>s then
+ break
+ else
+ replace=getnext(replace)
+ end
+ else
+ notmatchreplace[current]=true
+ if notmatchpre[current] then
+ goto next
+ else
+ break
+ end
+ end
+ end
+ else
+ end
+ current=getnext(current)
+ elseif id==glue_code then
+ local sn=seq[n]
+ if (sn[32] and spaces[current]) or sn[0xFFFC] then
+ n=n+1
+ current=getnext(current)
+ else
+ goto next
+ end
+ elseif seq[n][0xFFFC] then
+ n=n+1
+ current=getnext(current)
+ else
+ goto next
+ end
+ else
+ goto next
+ end
+ end
+ else
+ goto next
+ end
+ end
+ if trace_contexts then
+ chaintrac(head,start,dataset,sequence,rlmode,skipped and skiphash,ck,true,discseen,sweepnode)
+ end
+ if discseen or sweepnode then
+ head,start,done=chaindisk(head,start,dataset,sequence,rlmode,skipped and skiphash,ck)
+ else
+ head,start,done=chainrun(head,start,last,dataset,sequence,rlmode,skipped and skiphash,ck)
+ end
+ if done then
+ break
+ end
+ ::next::
+ end
+ if discseen then
+ notmatchpre={}
+ notmatchpost={}
+ notmatchreplace={}
+ end
+ return head,start,done
+end
+handlers.gsub_context=handle_contextchain
+handlers.gsub_contextchain=handle_contextchain
+handlers.gsub_reversecontextchain=handle_contextchain
+handlers.gpos_contextchain=handle_contextchain
+handlers.gpos_context=handle_contextchain
+local function chained_contextchain(head,start,stop,dataset,sequence,currentlookup,rlmode,skiphash)
+ local steps=currentlookup.steps
+ local nofsteps=currentlookup.nofsteps
+ if nofsteps>1 then
+ reportmoresteps(dataset,sequence)
+ end
+ local l=steps[1].coverage[getchar(start)]
+ if l then
+ return handle_contextchain(head,start,dataset,sequence,l,rlmode,skiphash)
+ else
+ return head,start,false
+ end
+end
+chainprocs.gsub_context=chained_contextchain
+chainprocs.gsub_contextchain=chained_contextchain
+chainprocs.gsub_reversecontextchain=chained_contextchain
+chainprocs.gpos_contextchain=chained_contextchain
+chainprocs.gpos_context=chained_contextchain
+local missing=setmetatableindex("table")
+local logwarning=report_process
+local resolved={}
+local function logprocess(...)
+ if trace_steps then
+ registermessage(...)
+ if trace_steps=="silent" then
+ return
+ end
+ end
+ report_process(...)
+end
+local sequencelists=setmetatableindex(function(t,font)
+ local sequences=fontdata[font].resources.sequences
+ if not sequences or not next(sequences) then
+ sequences=false
+ end
+ t[font]=sequences
+ return sequences
+end)
+do
+ local autofeatures=fonts.analyzers.features
+ local featuretypes=otf.tables.featuretypes
+ local defaultscript=otf.features.checkeddefaultscript
+ local defaultlanguage=otf.features.checkeddefaultlanguage
+ local wildcard="*"
+ local default="dflt"
+ local function initialize(sequence,script,language,enabled,autoscript,autolanguage)
+ local features=sequence.features
+ if features then
+ local order=sequence.order
+ if order then
+ local featuretype=featuretypes[sequence.type or "unknown"]
+ for i=1,#order do
+ local kind=order[i]
+ local valid=enabled[kind]
+ if valid then
+ local scripts=features[kind]
+ local languages=scripts and (
+ scripts[script] or
+ scripts[wildcard] or
+ (autoscript and defaultscript(featuretype,autoscript,scripts))
+ )
+ local enabled=languages and (
+ languages[language] or
+ languages[wildcard] or
+ (autolanguage and defaultlanguage(featuretype,autolanguage,languages))
+ )
+ if enabled then
+ return { valid,autofeatures[kind] or false,sequence,kind }
+ end
+ end
+ end
+ else
+ end
+ end
+ return false
+ end
+ function otf.dataset(tfmdata,font)
+ local shared=tfmdata.shared
+ local properties=tfmdata.properties
+ local language=properties.language or "dflt"
+ local script=properties.script or "dflt"
+ local enabled=shared.features
+ local autoscript=enabled and enabled.autoscript
+ local autolanguage=enabled and enabled.autolanguage
+ local res=resolved[font]
+ if not res then
+ res={}
+ resolved[font]=res
+ end
+ local rs=res[script]
+ if not rs then
+ rs={}
+ res[script]=rs
+ end
+ local rl=rs[language]
+ if not rl then
+ rl={
+ }
+ rs[language]=rl
+ local sequences=tfmdata.resources.sequences
+ if sequences then
+ for s=1,#sequences do
+ local v=enabled and initialize(sequences[s],script,language,enabled,autoscript,autolanguage)
+ if v then
+ rl[#rl+1]=v
+ end
+ end
+ end
+ end
+ return rl
+ end
+end
+local function report_disc(what,n)
+ report_run("%s: %s > %s",what,n,languages.serializediscretionary(n))
+end
+local function kernrun(disc,k_run,font,attr,...)
+ if trace_kernruns then
+ report_disc("kern",disc)
+ end
+ local prev,next=getboth(disc)
+ local nextstart=next
+ local done=false
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local prevmarks=prev
+ while prevmarks do
+ local char=ischar(prevmarks,font)
+ if char and marks[char] then
+ prevmarks=getprev(prevmarks)
+ else
+ break
+ end
+ end
+ if prev and not ischar(prev,font) then
+ prev=false
+ end
+ if next and not ischar(next,font) then
+ next=false
+ end
+ if pre then
+ if k_run(pre,"injections",nil,font,attr,...) then
+ done=true
+ end
+ if prev then
+ setlink(prev,pre)
+ if k_run(prevmarks,"preinjections",pre,font,attr,...) then
+ done=true
+ end
+ setprev(pre)
+ setlink(prev,disc)
+ end
+ end
+ if post then
+ if k_run(post,"injections",nil,font,attr,...) then
+ done=true
+ end
+ if next then
+ setlink(posttail,next)
+ if k_run(posttail,"postinjections",next,font,attr,...) then
+ done=true
+ end
+ setnext(posttail)
+ setlink(disc,next)
+ end
+ end
+ if replace then
+ if k_run(replace,"injections",nil,font,attr,...) then
+ done=true
+ end
+ if prev then
+ setlink(prev,replace)
+ if k_run(prevmarks,"replaceinjections",replace,font,attr,...) then
+ done=true
+ end
+ setprev(replace)
+ setlink(prev,disc)
+ end
+ if next then
+ setlink(replacetail,next)
+ if k_run(replacetail,"replaceinjections",next,font,attr,...) then
+ done=true
+ end
+ setnext(replacetail)
+ setlink(disc,next)
+ end
+ elseif prev and next then
+ setlink(prev,next)
+ if k_run(prevmarks,"emptyinjections",next,font,attr,...) then
+ done=true
+ end
+ setlink(prev,disc,next)
+ end
+ if done and trace_testruns then
+ report_disc("done",disc)
+ end
+ return nextstart,done
+end
+local function comprun(disc,c_run,...)
+ if trace_compruns then
+ report_disc("comp",disc)
+ end
+ local pre,post,replace=getdisc(disc)
+ local renewed=false
+ if pre then
+ sweepnode=disc
+ sweeptype="pre"
+ local new,done=c_run(pre,...)
+ if done then
+ pre=new
+ renewed=true
+ end
+ end
+ if post then
+ sweepnode=disc
+ sweeptype="post"
+ local new,done=c_run(post,...)
+ if done then
+ post=new
+ renewed=true
+ end
+ end
+ if replace then
+ sweepnode=disc
+ sweeptype="replace"
+ local new,done=c_run(replace,...)
+ if done then
+ replace=new
+ renewed=true
+ end
+ end
+ sweepnode=nil
+ sweeptype=nil
+ if renewed then
+ if trace_testruns then
+ report_disc("done",disc)
+ end
+ setdisc(disc,pre,post,replace)
+ end
+ return getnext(disc),renewed
+end
+local function testrun(disc,t_run,c_run,...)
+ if trace_testruns then
+ report_disc("test",disc)
+ end
+ local prev,next=getboth(disc)
+ if not next then
+ return
+ end
+ local pre,post,replace,pretail,posttail,replacetail=getdisc(disc,true)
+ local renewed=false
+ if (post or replace) then
+ if post then
+ setlink(posttail,next)
+ else
+ post=next
+ end
+ if replace then
+ setlink(replacetail,next)
+ else
+ replace=next
+ end
+ local d_post=t_run(post,next,...)
+ local d_replace=t_run(replace,next,...)
+ if d_post>0 or d_replace>0 then
+ local d=d_replace>d_post and d_replace or d_post
+ local head=getnext(disc)
+ local tail=head
+ for i=2,d do
+ local nx=getnext(tail)
+ local id=getid(nx)
+ if id==disc_code then
+ head,tail=flattendisk(head,nx)
+ elseif id==glyph_code then
+ tail=nx
+ else
+ break
+ end
+ end
+ next=getnext(tail)
+ setnext(tail)
+ setprev(head)
+ local new=copy_node_list(head)
+ if posttail then
+ setlink(posttail,head)
+ else
+ post=head
+ end
+ if replacetail then
+ setlink(replacetail,new)
+ else
+ replace=new
+ end
+ else
+ if posttail then
+ setnext(posttail)
+ else
+ post=nil
+ end
+ if replacetail then
+ setnext(replacetail)
+ else
+ replace=nil
+ end
+ end
+ setlink(disc,next)
+ end
+ if trace_testruns then
+ report_disc("more",disc)
+ end
+ if pre then
+ sweepnode=disc
+ sweeptype="pre"
+ local new,ok=c_run(pre,...)
+ if ok then
+ pre=new
+ renewed=true
+ end
+ end
+ if post then
+ sweepnode=disc
+ sweeptype="post"
+ local new,ok=c_run(post,...)
+ if ok then
+ post=new
+ renewed=true
+ end
+ end
+ if replace then
+ sweepnode=disc
+ sweeptype="replace"
+ local new,ok=c_run(replace,...)
+ if ok then
+ replace=new
+ renewed=true
+ end
+ end
+ sweepnode=nil
+ sweeptype=nil
+ if renewed then
+ setdisc(disc,pre,post,replace)
+ if trace_testruns then
+ report_disc("done",disc)
+ end
+ end
+ return getnext(disc),renewed
+end
+local nesting=0
+local function c_run_single(head,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ local done=false
+ local sweep=sweephead[head]
+ if sweep then
+ start=sweep
+ sweephead[head]=false
+ else
+ start=head
+ end
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ if not a or (a==attr) then
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ done=true
+ end
+ end
+ if start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif char==false then
+ return head,done
+ elseif sweep then
+ return head,done
+ else
+ start=getnext(start)
+ end
+ end
+ return head,done
+end
+local function t_run_single(start,stop,font,attr,lookupcache)
+ local lastd=nil
+ while start~=stop do
+ local char=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ local startnext=getnext(start)
+ if not a or (a==attr) then
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local s=startnext
+ local ss=nil
+ local sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+ local l=nil
+ local d=0
+ while s do
+ local char=ischar(s,font)
+ if char then
+ local lg=lookupmatch[char]
+ if lg then
+ if sstop then
+ d=1
+ elseif d>0 then
+ d=d+1
+ end
+ l=lg
+ s=getnext(s)
+ sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+lookupmatch=lg
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if l and l.ligature then
+ lastd=d
+ end
+ else
+ end
+ else
+ end
+ if lastd then
+ return lastd
+ end
+ start=startnext
+ else
+ break
+ end
+ end
+ return 0
+end
+local function k_run_single(sub,injection,last,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ local a
+ if attr then
+ a=getglyphdata(sub)
+ end
+ if not a or (a==attr) then
+ for n in nextnode,sub do
+ if n==last then
+ break
+ end
+ local char=ischar(n)
+ if char then
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local h,d,ok=handler(sub,n,dataset,sequence,lookupmatch,rlmode,skiphash,step,injection)
+ if ok then
+ return true
+ end
+ end
+ end
+ end
+ end
+end
+local function c_run_multiple(head,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ local done=false
+ local sweep=sweephead[head]
+ if sweep then
+ start=sweep
+ sweephead[head]=false
+ else
+ start=head
+ end
+ while start do
+ local char=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ if not a or (a==attr) then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ done=true
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif char==false then
+ return head,done
+ elseif sweep then
+ return head,done
+ else
+ start=getnext(start)
+ end
+ end
+ return head,done
+end
+local function t_run_multiple(start,stop,font,attr,steps,nofsteps)
+ local lastd=nil
+ while start~=stop do
+ local char=ischar(start,font)
+ if char then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ local startnext=getnext(start)
+ if not a or (a==attr) then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local s=startnext
+ local ss=nil
+ local sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+ local l=nil
+ local d=0
+ while s do
+ local char=ischar(s)
+ if char then
+ local lg=lookupmatch[char]
+ if lg then
+ if sstop then
+ d=1
+ elseif d>0 then
+ d=d+1
+ end
+ l=lg
+ s=getnext(s)
+ sstop=s==stop
+ if not s then
+ s=ss
+ ss=nil
+ end
+ while getid(s)==disc_code do
+ ss=getnext(s)
+ s=getfield(s,"replace")
+ if not s then
+ s=ss
+ ss=nil
+ end
+ end
+lookupmatch=lg
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if l and l.ligature then
+ lastd=d
+ end
+ end
+ end
+ else
+ end
+ if lastd then
+ return lastd
+ end
+ start=startnext
+ else
+ break
+ end
+ end
+ return 0
+end
+local function k_run_multiple(sub,injection,last,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ local a
+ if attr then
+ a=getglyphdata(sub)
+ end
+ if not a or (a==attr) then
+ for n in nextnode,sub do
+ if n==last then
+ break
+ end
+ local char=ischar(n)
+ if char then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local h,d,ok=handler(sub,n,dataset,sequence,lookupmatch,rlmode,skiphash,step,injection)
+ if ok then
+ return true
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local txtdirstate,pardirstate do
+ local getdirection=nuts.getdirection
+ local lefttoright=0
+ local righttoleft=1
+ txtdirstate=function(start,stack,top,rlparmode)
+ local dir,pop=getdirection(start)
+ if pop then
+ if top==1 then
+ return 0,rlparmode
+ else
+ top=top-1
+ if stack[top]==righttoleft then
+ return top,-1
+ else
+ return top,1
+ end
+ end
+ elseif dir==lefttoright then
+ top=top+1
+ stack[top]=lefttoright
+ return top,1
+ elseif dir==righttoleft then
+ top=top+1
+ stack[top]=righttoleft
+ return top,-1
+ else
+ return top,rlparmode
+ end
+ end
+ pardirstate=function(start)
+ local dir=getdirection(start)
+ if dir==lefttoright then
+ return 1,1
+ elseif dir==righttoleft then
+ return -1,-1
+ elseif dir=="TLT" then
+ return 1,1
+ elseif dir=="TRT" then
+ return -1,-1
+ else
+ return 0,0
+ end
+ end
+end
+otf.helpers=otf.helpers or {}
+otf.helpers.txtdirstate=txtdirstate
+otf.helpers.pardirstate=pardirstate
+do
+ local fastdisc=true
+ local testdics=false
+ directives.register("otf.fastdisc",function(v) fastdisc=v end)
+ local otfdataset=nil
+ local getfastdisc={ __index=function(t,k)
+ local v=usesfont(k,currentfont)
+ t[k]=v
+ return v
+ end }
+ local getfastspace={ __index=function(t,k)
+ local v=isspace(k,threshold) or false
+ t[k]=v
+ return v
+ end }
+ function otf.featuresprocessor(head,font,attr,direction,n)
+ local sequences=sequencelists[font]
+ nesting=nesting+1
+ if nesting==1 then
+ currentfont=font
+ tfmdata=fontdata[font]
+ descriptions=tfmdata.descriptions
+ characters=tfmdata.characters
+ local resources=tfmdata.resources
+ marks=resources.marks
+ classes=resources.classes
+ threshold,
+ factor=getthreshold(font)
+ checkmarks=tfmdata.properties.checkmarks
+ if not otfdataset then
+ otfdataset=otf.dataset
+ end
+ discs=fastdisc and n and n>1 and setmetatable({},getfastdisc)
+ spaces=setmetatable({},getfastspace)
+ elseif currentfont~=font then
+ report_warning("nested call with a different font, level %s, quitting",nesting)
+ nesting=nesting-1
+ return head,false
+ end
+ if trace_steps then
+ checkstep(head)
+ end
+ local initialrl=0
+ if getid(head)==localpar_code and getsubtype(head)==0 then
+ initialrl=pardirstate(head)
+ elseif direction==1 or direction=="TRT" then
+ initialrl=-1
+ end
+ local datasets=otfdataset(tfmdata,font,attr)
+ local dirstack={ nil }
+ sweephead={}
+ for s=1,#datasets do
+ local dataset=datasets[s]
+ local attribute=dataset[2]
+ local sequence=dataset[3]
+ local rlparmode=initialrl
+ local topstack=0
+ local typ=sequence.type
+ local gpossing=typ=="gpos_single" or typ=="gpos_pair"
+ local forcetestrun=typ=="gsub_ligature"
+ local handler=handlers[typ]
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ local skiphash=sequence.skiphash
+ if not steps then
+ local h,ok=handler(head,dataset,sequence,initialrl,font,attr)
+ if h and h~=head then
+ head=h
+ end
+ elseif typ=="gsub_reversecontextchain" then
+ local start=find_node_tail(head)
+ local rlmode=0
+ local merged=steps.merged
+ while start do
+ local char=ischar(start,font)
+ if char then
+ local m=merged[char]
+ if m then
+ local a
+ if attr then
+ a=getglyphdata(start)
+ end
+ if not a or (a==attr) then
+ for i=m[1],m[2] do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ break
+ end
+ end
+ end
+ if start then
+ start=getprev(start)
+ end
+ else
+ start=getprev(start)
+ end
+ else
+ start=getprev(start)
+ end
+ else
+ start=getprev(start)
+ end
+ end
+ else
+ local start=head
+ local rlmode=initialrl
+ if nofsteps==1 then
+ local step=steps[1]
+ local lookupcache=step.coverage
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local a
+ if attr then
+ if getglyphdata(start)==attr and (not attribute or getprop(start,a_state)==attribute) then
+ a=true
+ end
+ elseif not attribute or getprop(start,a_state)==attribute then
+ a=true
+ end
+ if a then
+ local ok,df
+ head,start,ok,df=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if df then
+ elseif start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ end
+ elseif char==false or id==glue_code then
+ start=getnext(start)
+ elseif id==disc_code then
+ if not discs or discs[start]==true then
+ local ok
+ if gpossing then
+ start,ok=kernrun(start,k_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ elseif forcetestrun then
+ start,ok=testrun(start,t_run_single,c_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ else
+ start,ok=comprun(start,c_run_single,font,attr,lookupcache,step,dataset,sequence,rlmode,skiphash,handler)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif id==math_code then
+ start=getnext(end_of_math(start))
+ elseif id==dir_code then
+ topstack,rlmode=txtdirstate(start,dirstack,topstack,rlparmode)
+ start=getnext(start)
+ else
+ start=getnext(start)
+ end
+ end
+ else
+ local merged=steps.merged
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ local m=merged[char]
+ if m then
+ local a
+ if attr then
+ if getglyphdata(start)==attr and (not attribute or getprop(start,a_state)==attribute) then
+ a=true
+ end
+ elseif not attribute or getprop(start,a_state)==attribute then
+ a=true
+ end
+ if a then
+ local ok,df
+ for i=m[1],m[2] do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ head,start,ok,df=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if df then
+ break
+ elseif ok then
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if df then
+ elseif start then
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ else
+ start=getnext(start)
+ end
+ end
+ elseif char==false or id==glue_code then
+ start=getnext(start)
+ elseif id==disc_code then
+ if not discs or discs[start]==true then
+ local ok
+ if gpossing then
+ start,ok=kernrun(start,k_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ elseif forcetestrun then
+ start,ok=testrun(start,t_run_multiple,c_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ else
+ start,ok=comprun(start,c_run_multiple,font,attr,steps,nofsteps,dataset,sequence,rlmode,skiphash,handler)
+ end
+ else
+ start=getnext(start)
+ end
+ elseif id==math_code then
+ start=getnext(end_of_math(start))
+ elseif id==dir_code then
+ topstack,rlmode=txtdirstate(start,dirstack,topstack,rlparmode)
+ start=getnext(start)
+ else
+ start=getnext(start)
+ end
+ end
+ end
+ end
+ if trace_steps then
+ registerstep(head)
+ end
+ end
+ nesting=nesting-1
+ return head
+ end
+ function otf.datasetpositionprocessor(head,font,direction,dataset)
+ currentfont=font
+ tfmdata=fontdata[font]
+ descriptions=tfmdata.descriptions
+ characters=tfmdata.characters
+ local resources=tfmdata.resources
+ marks=resources.marks
+ classes=resources.classes
+ threshold,
+ factor=getthreshold(font)
+ checkmarks=tfmdata.properties.checkmarks
+ if type(dataset)=="number" then
+ dataset=otfdataset(tfmdata,font,0)[dataset]
+ end
+ local sequence=dataset[3]
+ local typ=sequence.type
+ local handler=handlers[typ]
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ local done=false
+ local dirstack={ nil }
+ local start=head
+ local initialrl=(direction==1 or direction=="TRT") and -1 or 0
+ local rlmode=initialrl
+ local rlparmode=initialrl
+ local topstack=0
+ local merged=steps.merged
+ local position=0
+ while start do
+ local char,id=ischar(start,font)
+ if char then
+ position=position+1
+ local m=merged[char]
+ if m then
+ if skiphash and skiphash[char] then
+ start=getnext(start)
+ else
+ for i=m[1],m[2] do
+ local step=steps[i]
+ local lookupcache=step.coverage
+ local lookupmatch=lookupcache[char]
+ if lookupmatch then
+ local ok
+ head,start,ok=handler(head,start,dataset,sequence,lookupmatch,rlmode,skiphash,step)
+ if ok then
+ break
+ elseif not start then
+ break
+ end
+ end
+ end
+ if start then
+ start=getnext(start)
+ end
+ end
+ else
+ start=getnext(start)
+ end
+ elseif char==false or id==glue_code then
+ start=getnext(start)
+ elseif id==math_code then
+ start=getnext(end_of_math(start))
+ elseif id==dir_code then
+ topstack,rlmode=txtdirstate(start,dirstack,topstack,rlparmode)
+ start=getnext(start)
+ else
+ start=getnext(start)
+ end
+ end
+ return head
+ end
+end
+local plugins={}
+otf.plugins=plugins
+local report=logs.reporter("fonts")
+function otf.registerplugin(name,f)
+ if type(name)=="string" and type(f)=="function" then
+ plugins[name]={ name,f }
+ report()
+ report("plugin %a has been loaded, please be aware of possible side effects",name)
+ report()
+ if logs.pushtarget then
+ logs.pushtarget("log")
+ end
+ report("Plugins are not officially supported unless stated otherwise. This is because")
+ report("they bypass the regular font handling and therefore some features in ConTeXt")
+ report("(especially those related to fonts) might not work as expected or might not work")
+ report("at all. Some plugins are for testing and development only and might change")
+ report("whenever we feel the need for it.")
+ report()
+ if logs.poptarget then
+ logs.poptarget()
+ end
+ end
+end
+function otf.plugininitializer(tfmdata,value)
+ if type(value)=="string" then
+ tfmdata.shared.plugin=plugins[value]
+ end
+end
+function otf.pluginprocessor(head,font,attr,direction)
+ local s=fontdata[font].shared
+ local p=s and s.plugin
+ if p then
+ if trace_plugins then
+ report_process("applying plugin %a",p[1])
+ end
+ return p[2](head,font,attr,direction)
+ else
+ return head,false
+ end
+end
+function otf.featuresinitializer(tfmdata,value)
+end
+registerotffeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ position=1,
+ node=otf.featuresinitializer,
+ plug=otf.plugininitializer,
+ },
+ processors={
+ node=otf.featuresprocessor,
+ plug=otf.pluginprocessor,
+ }
+}
+otf.handlers=handlers
+local setspacekerns=nodes.injections.setspacekerns if not setspacekerns then os.exit() end
+local tag="kern"
+if fontfeatures then
+ function handlers.trigger_space_kerns(head,dataset,sequence,initialrl,font,attr)
+ local features=fontfeatures[font]
+ local enabled=features and features.spacekern and features[tag]
+ if enabled then
+ setspacekerns(font,sequence)
+ end
+ return head,enabled
+ end
+else
+ function handlers.trigger_space_kerns(head,dataset,sequence,initialrl,font,attr)
+ local shared=fontdata[font].shared
+ local features=shared and shared.features
+ local enabled=features and features.spacekern and features[tag]
+ if enabled then
+ setspacekerns(font,sequence)
+ end
+ return head,enabled
+ end
+end
+local function hasspacekerns(data)
+ local resources=data.resources
+ local sequences=resources.sequences
+ local validgpos=resources.features.gpos
+ if validgpos and sequences then
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ if steps and sequence.features[tag] then
+ local kind=sequence.type
+ if kind=="gpos_pair" or kind=="gpos_single" then
+ for i=1,#steps do
+ local step=steps[i]
+ local coverage=step.coverage
+ local rules=step.rules
+ if rules then
+ elseif not coverage then
+ elseif kind=="gpos_single" then
+ elseif kind=="gpos_pair" then
+ local format=step.format
+ if format=="move" or format=="kern" then
+ local kerns=coverage[32]
+ if kerns then
+ return true
+ end
+ for k,v in next,coverage do
+ if v[32] then
+ return true
+ end
+ end
+ elseif format=="pair" then
+ local kerns=coverage[32]
+ if kerns then
+ for k,v in next,kerns do
+ local one=v[1]
+ if one and one~=true then
+ return true
+ end
+ end
+ end
+ for k,v in next,coverage do
+ local kern=v[32]
+ if kern then
+ local one=kern[1]
+ if one and one~=true then
+ return true
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ return false
+end
+otf.readers.registerextender {
+ name="spacekerns",
+ action=function(data)
+ data.properties.hasspacekerns=hasspacekerns(data)
+ end
+}
+local function spaceinitializer(tfmdata,value)
+ local resources=tfmdata.resources
+ local spacekerns=resources and resources.spacekerns
+ if value and spacekerns==nil then
+ local rawdata=tfmdata.shared and tfmdata.shared.rawdata
+ local properties=rawdata.properties
+ if properties and properties.hasspacekerns then
+ local sequences=resources.sequences
+ local validgpos=resources.features.gpos
+ if validgpos and sequences then
+ local left={}
+ local right={}
+ local last=0
+ local feat=nil
+ for i=1,#sequences do
+ local sequence=sequences[i]
+ local steps=sequence.steps
+ if steps then
+ local kern=sequence.features[tag]
+ if kern then
+ local kind=sequence.type
+ if kind=="gpos_pair" or kind=="gpos_single" then
+ if feat then
+ for script,languages in next,kern do
+ local f=feat[script]
+ if f then
+ for l in next,languages do
+ f[l]=true
+ end
+ else
+ feat[script]=languages
+ end
+ end
+ else
+ feat=kern
+ end
+ for i=1,#steps do
+ local step=steps[i]
+ local coverage=step.coverage
+ local rules=step.rules
+ if rules then
+ elseif not coverage then
+ elseif kind=="gpos_single" then
+ elseif kind=="gpos_pair" then
+ local format=step.format
+ if format=="move" or format=="kern" then
+ local kerns=coverage[32]
+ if kerns then
+ for k,v in next,kerns do
+ right[k]=v
+ end
+ end
+ for k,v in next,coverage do
+ local kern=v[32]
+ if kern then
+ left[k]=kern
+ end
+ end
+ elseif format=="pair" then
+ local kerns=coverage[32]
+ if kerns then
+ for k,v in next,kerns do
+ local one=v[1]
+ if one and one~=true then
+ right[k]=one[3]
+ end
+ end
+ end
+ for k,v in next,coverage do
+ local kern=v[32]
+ if kern then
+ local one=kern[1]
+ if one and one~=true then
+ left[k]=one[3]
+ end
+ end
+ end
+ end
+ end
+ end
+ last=i
+ end
+ else
+ end
+ end
+ end
+ left=next(left) and left or false
+ right=next(right) and right or false
+ if left or right then
+ spacekerns={
+ left=left,
+ right=right,
+ }
+ if last>0 then
+ local triggersequence={
+ features={ [tag]=feat or { dflt={ dflt=true,} } },
+ flags=noflags,
+ name="trigger_space_kerns",
+ order={ tag },
+ type="trigger_space_kerns",
+ left=left,
+ right=right,
+ }
+ insert(sequences,last,triggersequence)
+ end
+ end
+ end
+ end
+ resources.spacekerns=spacekerns
+ end
+ return spacekerns
+end
+registerotffeature {
+ name="spacekern",
+ description="space kern injection",
+ default=true,
+ initializers={
+ node=spaceinitializer,
+ },
+}
+local function markinitializer(tfmdata,value)
+ local properties=tfmdata.properties
+ properties.checkmarks=value
+end
+registerotffeature {
+ name="checkmarks",
+ description="check mark widths",
+ default=true,
+ initializers={
+ node=markinitializer,
+ },
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-osd']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Kai Eigner, TAT Zetwerk / Hans Hagen, PRAGMA ADE",
+ copyright="TAT Zetwerk / PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local insert,imerge,copy,tohash=table.insert,table.imerge,table.copy,table.tohash
+local next,type=next,type
+local report=logs.reporter("otf","devanagari")
+fonts=fonts or {}
+fonts.analyzers=fonts.analyzers or {}
+fonts.analyzers.methods=fonts.analyzers.methods or { node={ otf={} } }
+local otf=fonts.handlers.otf
+local handlers=otf.handlers
+local methods=fonts.analyzers.methods
+local otffeatures=fonts.constructors.features.otf
+local registerotffeature=otffeatures.register
+local nuts=nodes.nuts
+local getnext=nuts.getnext
+local getprev=nuts.getprev
+local getboth=nuts.getboth
+local getid=nuts.getid
+local getchar=nuts.getchar
+local getfont=nuts.getfont
+local getsubtype=nuts.getsubtype
+local setlink=nuts.setlink
+local setnext=nuts.setnext
+local setprev=nuts.setprev
+local setchar=nuts.setchar
+local getprop=nuts.getprop
+local setprop=nuts.setprop
+local ischar=nuts.ischar
+local insert_node_after=nuts.insert_after
+local copy_node=nuts.copy
+local remove_node=nuts.remove
+local flush_list=nuts.flush_list
+local flush_node=nuts.flush_node
+local copyinjection=nodes.injections.copy
+local unsetvalue=attributes.unsetvalue
+local fontdata=fonts.hashes.identifiers
+local a_state=attributes.private('state')
+local a_syllabe=attributes.private('syllabe')
+local dotted_circle=0x25CC
+local c_nbsp=0x00A0
+local c_zwnj=0x200C
+local c_zwj=0x200D
+local states=fonts.analyzers.states
+local s_rphf=states.rphf
+local s_half=states.half
+local s_pref=states.pref
+local s_blwf=states.blwf
+local s_pstf=states.pstf
+local s_init=states.init
+local replace_all_nbsp=nil
+replace_all_nbsp=function(head)
+ replace_all_nbsp=typesetters and typesetters.characters and typesetters.characters.replacenbspaces or function(head)
+ return head
+ end
+ return replace_all_nbsp(head)
+end
+local processcharacters=nil
+if context then
+
+--removed
+
+else
+ function processcharacters(head,font)
+ local processors=fontdata[font].shared.processes
+ for i=1,#processors do
+ head=processors[i](head,font,0)
+ end
+ return head
+ end
+end
+local indicgroups=characters and characters.indicgroups
+if not indicgroups and characters then
+ local indic={
+ c={},
+ i={},
+ d={},
+ m={},
+ s={},
+ o={},
+ }
+ local indicmarks={
+ l={},
+ t={},
+ b={},
+ r={},
+ s={},
+ }
+ local indicclasses={
+ nukta={},
+ halant={},
+ ra={},
+ anudatta={},
+ }
+ local indicorders={
+ bp={},
+ ap={},
+ bs={},
+ as={},
+ bh={},
+ ah={},
+ bm={},
+ am={},
+ }
+ for k,v in next,characters.data do
+ local i=v.indic
+ if i then
+ indic[i][k]=true
+ i=v.indicmark
+ if i then
+ if i=="s" then
+ local s=v.specials
+ indicmarks[i][k]={ s[2],s[3] }
+ else
+ indicmarks[i][k]=true
+ end
+ end
+ i=v.indicclass
+ if i then
+ indicclasses[i][k]=true
+ end
+ i=v.indicorder
+ if i then
+ indicorders[i][k]=true
+ end
+ end
+ end
+ indicgroups={
+ consonant=indic.c,
+ independent_vowel=indic.i,
+ dependent_vowel=indic.d,
+ vowel_modifier=indic.m,
+ stress_tone_mark=indic.s,
+ pre_mark=indicmarks.l,
+ above_mark=indicmarks.t,
+ below_mark=indicmarks.b,
+ post_mark=indicmarks.r,
+ twopart_mark=indicmarks.s,
+ nukta=indicclasses.nukta,
+ halant=indicclasses.halant,
+ ra=indicclasses.ra,
+ anudatta=indicclasses.anudatta,
+ before_postscript=indicorders.bp,
+ after_postscript=indicorders.ap,
+ before_half=indicorders.bh,
+ after_half=indicorders.ah,
+ before_subscript=indicorders.bs,
+ after_subscript=indicorders.as,
+ before_main=indicorders.bm,
+ after_main=indicorders.am,
+ }
+ indic=nil
+ indicmarks=nil
+ indicclasses=nil
+ indicorders=nil
+ characters.indicgroups=indicgroups
+end
+local consonant=indicgroups.consonant
+local independent_vowel=indicgroups.independent_vowel
+local dependent_vowel=indicgroups.dependent_vowel
+local vowel_modifier=indicgroups.vowel_modifier
+local stress_tone_mark=indicgroups.stress_tone_mark
+local pre_mark=indicgroups.pre_mark
+local above_mark=indicgroups.above_mark
+local below_mark=indicgroups.below_mark
+local post_mark=indicgroups.post_mark
+local twopart_mark=indicgroups.twopart_mark
+local nukta=indicgroups.nukta
+local halant=indicgroups.halant
+local ra=indicgroups.ra
+local anudatta=indicgroups.anudatta
+local before_postscript=indicgroups.before_postscript
+local after_postscript=indicgroups.after_postscript
+local before_half=indicgroups.before_half
+local after_half=indicgroups.after_half
+local before_subscript=indicgroups.before_subscript
+local after_subscript=indicgroups.after_subscript
+local before_main=indicgroups.before_main
+local after_main=indicgroups.after_main
+local mark_four=table.merged (
+ pre_mark,
+ above_mark,
+ below_mark,
+ post_mark
+)
+local mark_above_below_post=table.merged (
+ above_mark,
+ below_mark,
+ post_mark
+)
+local zw_char={
+ [c_zwnj]=true,
+ [c_zwj ]=true,
+}
+local dflt_true={
+ dflt=true,
+}
+local two_defaults={}
+local one_defaults={}
+local false_flags={ false,false,false,false }
+local sequence_reorder_matras={
+ features={ dv01=two_defaults },
+ flags=false_flags,
+ name="dv01_reorder_matras",
+ order={ "dv01" },
+ type="devanagari_reorder_matras",
+ nofsteps=1,
+ steps={
+ {
+ coverage=pre_mark,
+ }
+ }
+}
+local sequence_reorder_reph={
+ features={ dv02=two_defaults },
+ flags=false_flags,
+ name="dv02_reorder_reph",
+ order={ "dv02" },
+ type="devanagari_reorder_reph",
+ nofsteps=1,
+ steps={
+ {
+ coverage={},
+ }
+ }
+}
+local sequence_reorder_pre_base_reordering_consonants={
+ features={ dv03=one_defaults },
+ flags=false_flags,
+ name="dv03_reorder_pre_base_reordering_consonants",
+ order={ "dv03" },
+ type="devanagari_reorder_pre_base_reordering_consonants",
+ nofsteps=1,
+ steps={
+ {
+ coverage={},
+ }
+ }
+}
+local sequence_remove_joiners={
+ features={ dv04=one_defaults },
+ flags=false_flags,
+ name="dv04_remove_joiners",
+ order={ "dv04" },
+ type="devanagari_remove_joiners",
+ nofsteps=1,
+ steps={
+ {
+ coverage=zw_char,
+ },
+ }
+}
+local basic_shaping_forms={
+ akhn=true,
+ blwf=true,
+ cjct=true,
+ half=true,
+ nukt=true,
+ pref=true,
+ pstf=true,
+ rkrf=true,
+ rphf=true,
+ vatu=true,
+ locl=true,
+}
+local valid={
+ abvs=true,
+ akhn=true,
+ blwf=true,
+ calt=true,
+ cjct=true,
+ half=true,
+ haln=true,
+ nukt=true,
+ pref=true,
+ pres=true,
+ pstf=true,
+ psts=true,
+ rkrf=true,
+ rphf=true,
+ vatu=true,
+ pres=true,
+ abvs=true,
+ blws=true,
+ psts=true,
+ haln=true,
+ calt=true,
+ locl=true,
+}
+local scripts={}
+local scripts_one={ "deva","mlym","beng","gujr","guru","knda","orya","taml","telu" }
+local scripts_two={ "dev2","mlm2","bng2","gjr2","gur2","knd2","ory2","tml2","tel2" }
+local nofscripts=#scripts_one
+for i=1,nofscripts do
+ local one=scripts_one[i]
+ local two=scripts_two[i]
+ scripts[one]=true
+ scripts[two]=true
+ two_defaults[two]=dflt_true
+ one_defaults[one]=dflt_true
+ one_defaults[two]=dflt_true
+end
+local function valid_one(s) for i=1,nofscripts do if s[scripts_one[i]] then return true end end end
+local function valid_two(s) for i=1,nofscripts do if s[scripts_two[i]] then return true end end end
+local function initializedevanagi(tfmdata)
+ local script,language=otf.scriptandlanguage(tfmdata,attr)
+ if scripts[script] then
+ local resources=tfmdata.resources
+ local devanagari=resources.devanagari
+ if not devanagari then
+ report("adding devanagari features to font")
+ local gsubfeatures=resources.features.gsub
+ local sequences=resources.sequences
+ local sharedfeatures=tfmdata.shared.features
+ gsubfeatures["dv01"]=two_defaults
+ gsubfeatures["dv02"]=two_defaults
+ gsubfeatures["dv03"]=one_defaults
+ gsubfeatures["dv04"]=one_defaults
+ local reorder_pre_base_reordering_consonants=copy(sequence_reorder_pre_base_reordering_consonants)
+ local reorder_reph=copy(sequence_reorder_reph)
+ local reorder_matras=copy(sequence_reorder_matras)
+ local remove_joiners=copy(sequence_remove_joiners)
+ local lastmatch=0
+ for s=1,#sequences do
+ local features=sequences[s].features
+ if features then
+ for k,v in next,features do
+ if k=="locl" then
+ local steps=sequences[s].steps
+ local nofsteps=sequences[s].nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,pre_mark do
+ local locl=coverage[k]
+ if locl then
+ if #locl>0 then
+ for j=1,#locl do
+ local ck=locl[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ locl=coverage[k]
+ end
+ end
+ end
+ end
+ end
+ end
+ if locl then
+ reorder_matras.steps[1].coverage[locl]=true
+ end
+ end
+ end
+ end
+ end
+ end
+ if basic_shaping_forms[k] then
+ lastmatch=lastmatch+1
+ if s~=lastmatch then
+ table.insert(sequences,lastmatch,table.remove(sequences,s))
+ end
+ end
+ end
+ end
+ end
+ local insertindex=lastmatch+1
+ if tfmdata.properties.language then
+ dflt_true[tfmdata.properties.language]=true
+ end
+ insert(sequences,insertindex,reorder_pre_base_reordering_consonants)
+ insert(sequences,insertindex,reorder_reph)
+ insert(sequences,insertindex,reorder_matras)
+ insert(sequences,insertindex,remove_joiners)
+ local blwfcache={}
+ local vatucache={}
+ local pstfcache={}
+ local seqsubset={}
+ local rephstep={
+ coverage={}
+ }
+ local devanagari={
+ reph=false,
+ vattu=false,
+ blwfcache=blwfcache,
+ vatucache=vatucache,
+ pstfcache=pstfcache,
+ seqsubset=seqsubset,
+ reorderreph=rephstep,
+ }
+ reorder_reph.steps={ rephstep }
+ local pre_base_reordering_consonants={}
+ reorder_pre_base_reordering_consonants.steps[1].coverage=pre_base_reordering_consonants
+ resources.devanagari=devanagari
+ for s=1,#sequences do
+ local sequence=sequences[s]
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ local features=sequence.features
+ local has_rphf=features.rphf
+ local has_blwf=features.blwf
+ local has_vatu=features.vatu
+ local has_pstf=features.pstf
+ if has_rphf and has_rphf[script] then
+ devanagari.reph=true
+ elseif (has_blwf and has_blwf[script] ) or (has_vatu and has_vatu[script] ) then
+ devanagari.vattu=true
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,coverage do
+ for h,w in next,halant do
+ if v[h] then
+ if not blwfcache[k] then
+ blwfcache[k]=v
+ end
+ end
+ if has_vatu and has_vatu[script] and not vatucache[k] then
+ vatucache[k]=v
+ end
+ end
+ end
+ end
+ end
+ elseif has_pstf and has_pstf[script] then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,coverage do
+ if not pstfcache[k] then
+ pstfcache[k]=v
+ end
+ end
+ for k,v in next,ra do
+ local r=coverage[k]
+ if r then
+ local found=false
+ if #r>0 then
+ for j=1,#r do
+ local ck=r[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups and chainlookups[f] then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local h=coverage[k]
+ if h then
+ for k,v in next,h do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k,v in next,r do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ for kind,spec in next,features do
+ if valid[kind] and valid_two(spec)then
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local reph,rephbase=false,false
+ if kind=="rphf" then
+ for k,v in next,ra do
+ local r=coverage[k]
+ if r then
+ rephbase=k
+ local h=false
+ if #r>0 then
+ for j=1,#r do
+ local ck=r[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local r=coverage[k]
+ if r then
+ for k,v in next,halant do
+ local h=r[k]
+ if h then
+ reph=h.ligature or false
+ break
+ end
+ end
+ if h then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k,v in next,halant do
+ local h=r[k]
+ if h then
+ reph=h.ligature or false
+ break
+ end
+ end
+ end
+ if reph then
+ break
+ end
+ end
+ end
+ end
+ seqsubset[#seqsubset+1]={ kind,coverage,reph,rephbase }
+ end
+ end
+ end
+ if kind=="pref" then
+ local steps=sequence.steps
+ local nofsteps=sequence.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ for k,v in next,halant do
+ local h=coverage[k]
+ if h then
+ local found=false
+ if #h>0 then
+ for j=1,#h do
+ local ck=h[j]
+ local f=ck[4]
+ local chainlookups=ck[6]
+ if chainlookups then
+ local chainlookup=chainlookups[f]
+ for j=1,#chainlookup do
+ local chainstep=chainlookup[j]
+ local steps=chainstep.steps
+ local nofsteps=chainstep.nofsteps
+ for i=1,nofsteps do
+ local step=steps[i]
+ local coverage=step.coverage
+ if coverage then
+ local h=coverage[k]
+ if h then
+ for k,v in next,h do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ for k,v in next,h do
+ found=v and v.ligature
+ if found then
+ pre_base_reordering_consonants[found]=true
+ break
+ end
+ end
+ end
+ if found then
+ break
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if two_defaults[script] then
+ sharedfeatures["dv01"]=true
+ sharedfeatures["dv02"]=true
+ sharedfeatures["dv03"]=true
+ sharedfeatures["dv04"]=true
+ elseif one_defaults[script] then
+ sharedfeatures["dv03"]=true
+ sharedfeatures["dv04"]=true
+ end
+ if script=="mlym" or script=="taml" then
+ devanagari.left_matra_before_base=true
+ end
+ end
+ end
+end
+registerotffeature {
+ name="devanagari",
+ description="inject additional features",
+ default=true,
+ initializers={
+ node=initializedevanagi,
+ },
+}
+local show_syntax_errors=false
+local function inject_syntax_error(head,current,char)
+ local signal=copy_node(current)
+ copyinjection(signal,current)
+ if pre_mark[char] then
+ setchar(signal,dotted_circle)
+ else
+ setchar(current,dotted_circle)
+ end
+ return insert_node_after(head,current,signal)
+end
+local function initialize_one(font,attr)
+ local tfmdata=fontdata[font]
+ local datasets=otf.dataset(tfmdata,font,attr)
+ local devanagaridata=datasets.devanagari
+ if not devanagaridata then
+ devanagaridata={
+ reph=false,
+ vattu=false,
+ blwfcache={},
+ vatucache={},
+ pstfcache={},
+ }
+ datasets.devanagari=devanagaridata
+ local resources=tfmdata.resources
+ local devanagari=resources.devanagari
+ for s=1,#datasets do
+ local dataset=datasets[s]
+ if dataset and dataset[1] then
+ local kind=dataset[4]
+ if kind=="rphf" then
+ devanagaridata.reph=true
+ elseif kind=="blwf" or kind=="vatu" then
+ devanagaridata.vattu=true
+ devanagaridata.blwfcache=devanagari.blwfcache
+ devanagaridata.vatucache=devanagari.vatucache
+ devanagaridata.pstfcache=devanagari.pstfcache
+ end
+ end
+ end
+ end
+ return devanagaridata.reph,devanagaridata.vattu,devanagaridata.blwfcache,devanagaridata.vatucache,devanagaridata.pstfcache
+end
+local function contextchain(contexts,n)
+ local char=getchar(n)
+ for k=1,#contexts do
+ local ck=contexts[k]
+ local seq=ck[3]
+ local f=ck[4]
+ local l=ck[5]
+ if (l-f)==1 and seq[f+1][char] then
+ local ok=true
+ local c=n
+ for i=l+1,#seq do
+ c=getnext(c)
+ if not c or not seq[i][ischar(c)] then
+ ok=false
+ break
+ end
+ end
+ if ok then
+ c=getprev(n)
+ for i=1,f-1 do
+ c=getprev(c)
+ if not c or not seq[f-i][ischar(c)] then
+ ok=false
+ end
+ end
+ end
+ if ok then
+ return true
+ end
+ end
+ end
+ return false
+end
+local function order_matras(c)
+ local cn=getnext(c)
+ local char=getchar(cn)
+ while dependent_vowel[char] do
+ local next=getnext(cn)
+ local cc=c
+ local cchar=getchar(cc)
+ while cc~=cn do
+ if (above_mark[char] and (below_mark[cchar] or post_mark[cchar])) or (below_mark[char] and (post_mark[cchar])) then
+ local prev,next=getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ setnext(getprev(cc),cn)
+ setprev(cn,getprev(cc))
+ setnext(cn,cc)
+ setprev(cc,cn)
+ break
+ end
+ cc=getnext(cc)
+ cchar=getchar(cc)
+ end
+ cn=next
+ char=getchar(cn)
+ end
+end
+local function reorder_one(head,start,stop,font,attr,nbspaces)
+ local reph,vattu,blwfcache,vatucache,pstfcache=initialize_one(font,attr)
+ local devanagari=fontdata[font].resources.devanagari
+ local current=start
+ local n=getnext(start)
+ local base=nil
+ local firstcons=nil
+ local lastcons=nil
+ local basefound=false
+ if reph and ra[getchar(start)] and halant[getchar(n)] then
+ if n==stop then
+ return head,stop,nbspaces
+ end
+ if getchar(getnext(n))==c_zwj then
+ current=start
+ else
+ current=getnext(n)
+ setprop(start,a_state,s_rphf)
+ end
+ end
+ if getchar(current)==c_nbsp then
+ if current==stop then
+ stop=getprev(stop)
+ head=remove_node(head,current)
+ flush_node(current)
+ return head,stop,nbspaces
+ else
+ nbspaces=nbspaces+1
+ base=current
+ firstcons=current
+ lastcons=current
+ current=getnext(current)
+ if current~=stop then
+ local char=getchar(current)
+ if nukta[char] then
+ current=getnext(current)
+ char=getchar(current)
+ end
+ if char==c_zwj and current~=stop then
+ local next=getnext(current)
+ if next~=stop and halant[getchar(next)] then
+ current=next
+ next=getnext(current)
+ local tmp=next and getnext(next) or nil
+ local changestop=next==stop
+ local tempcurrent=copy_node(next)
+ copyinjection(tempcurrent,next)
+ local nextcurrent=copy_node(current)
+ copyinjection(nextcurrent,current)
+ setlink(tempcurrent,nextcurrent)
+ setprop(tempcurrent,a_state,s_blwf)
+ tempcurrent=processcharacters(tempcurrent,font)
+ setprop(tempcurrent,a_state,unsetvalue)
+ if getchar(next)==getchar(tempcurrent) then
+ flush_list(tempcurrent)
+ if show_syntax_errors then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ else
+ setchar(current,getchar(tempcurrent))
+ local freenode=getnext(current)
+ setlink(current,tmp)
+ flush_node(freenode)
+ flush_list(tempcurrent)
+ if changestop then
+ stop=current
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ while not basefound do
+ local char=getchar(current)
+ if consonant[char] then
+ setprop(current,a_state,s_half)
+ if not firstcons then
+ firstcons=current
+ end
+ lastcons=current
+ if not base then
+ base=current
+ elseif blwfcache[char] then
+ setprop(current,a_state,s_blwf)
+ elseif pstfcache[char] then
+ setprop(current,a_state,s_pstf)
+ else
+ base=current
+ end
+ end
+ basefound=current==stop
+ current=getnext(current)
+ end
+ if base~=lastcons then
+ local np=base
+ local n=getnext(base)
+ local ch=getchar(n)
+ if nukta[ch] then
+ np=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if halant[ch] then
+ if lastcons~=stop then
+ local ln=getnext(lastcons)
+ if nukta[getchar(ln)] then
+ lastcons=ln
+ end
+ end
+ local nn=getnext(n)
+ local ln=getnext(lastcons)
+ setlink(np,nn)
+ setnext(lastcons,n)
+ if ln then
+ setprev(ln,n)
+ end
+ setnext(n,ln)
+ setprev(n,lastcons)
+ if lastcons==stop then
+ stop=n
+ end
+ end
+ end
+ n=getnext(start)
+ if n~=stop and ra[getchar(start)] and halant[getchar(n)] and not zw_char[getchar(getnext(n))] then
+ local matra=base
+ if base~=stop then
+ local next=getnext(base)
+ if dependent_vowel[getchar(next)] then
+ matra=next
+ end
+ end
+ local sp=getprev(start)
+ local nn=getnext(n)
+ local mn=getnext(matra)
+ setlink(sp,nn)
+ setlink(matra,start)
+ setlink(n,mn)
+ if head==start then
+ head=nn
+ end
+ start=nn
+ if matra==stop then
+ stop=n
+ end
+ end
+ local current=start
+ while current~=stop do
+ local next=getnext(current)
+ if next~=stop and halant[getchar(next)] and getchar(getnext(next))==c_zwnj then
+ setprop(current,a_state,unsetvalue)
+ end
+ current=next
+ end
+ if base~=stop and getprop(base,a_state) then
+ local next=getnext(base)
+ if halant[getchar(next)] and not (next~=stop and getchar(getnext(next))==c_zwj) then
+ setprop(base,a_state,unsetvalue)
+ end
+ end
+ local current,allreordered,moved=start,false,{ [base]=true }
+ local a,b,p,bn=base,base,base,getnext(base)
+ if base~=stop and nukta[getchar(bn)] then
+ a,b,p=bn,bn,bn
+ end
+ while not allreordered do
+ local c=current
+ local n=getnext(current)
+ local l=nil
+ if c~=stop then
+ local ch=getchar(n)
+ if nukta[ch] then
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if c~=stop then
+ if halant[ch] then
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ local tpm=twopart_mark[ch]
+ while tpm do
+ local extra=copy_node(n)
+ copyinjection(extra,n)
+ ch=tpm[1]
+ setchar(n,ch)
+ setchar(extra,tpm[2])
+ head=insert_node_after(head,current,extra)
+ tpm=twopart_mark[ch]
+ end
+ while c~=stop and dependent_vowel[ch] do
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if c~=stop then
+ if vowel_modifier[ch] then
+ c=n
+ n=getnext(n)
+ ch=getchar(n)
+ end
+ if c~=stop and stress_tone_mark[ch] then
+ c=n
+ n=getnext(n)
+ end
+ end
+ end
+ end
+ local bp=getprev(firstcons)
+ local cn=getnext(current)
+ local last=getnext(c)
+ while cn~=last do
+ if pre_mark[getchar(cn)] then
+ if devanagari.left_matra_before_base then
+ local prev,next=getboth(cn)
+ setlink(prev,next)
+ if cn==stop then
+ stop=getprev(cn)
+ end
+ if base==start then
+ if head==start then
+ head=cn
+ end
+ start=cn
+ end
+ setlink(getprev(base),cn)
+ setlink(cn,base)
+ cn=next
+ else
+ if bp then
+ setnext(bp,cn)
+ end
+ local prev,next=getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ if cn==stop then
+ stop=prev
+ end
+ setprev(cn,bp)
+ setlink(cn,firstcons)
+ if firstcons==start then
+ if head==start then
+ head=cn
+ end
+ start=cn
+ end
+ cn=next
+ end
+ elseif current~=base and dependent_vowel[getchar(cn)] then
+ local prev,next=getboth(cn)
+ if next then
+ setprev(next,prev)
+ end
+ setnext(prev,next)
+ if cn==stop then
+ stop=prev
+ end
+ setlink(b,cn,getnext(b))
+ order_matras(cn)
+ cn=next
+ elseif current==base and dependent_vowel[getchar(cn)] then
+ local cnn=getnext(cn)
+ order_matras(cn)
+ cn=cnn
+ while cn~=last and dependent_vowel[getchar(cn)] do
+ cn=getnext(cn)
+ end
+ else
+ cn=getnext(cn)
+ end
+ end
+ allreordered=c==stop
+ current=getnext(c)
+ end
+ if reph or vattu then
+ local current,cns=start,nil
+ while current~=stop do
+ local c=current
+ local n=getnext(current)
+ if ra[getchar(current)] and halant[getchar(n)] then
+ c=n
+ n=getnext(n)
+ local b,bn=base,base
+ while bn~=stop do
+ local next=getnext(bn)
+ if dependent_vowel[getchar(next)] then
+ b=next
+ end
+ bn=next
+ end
+ if getprop(current,a_state)==s_rphf then
+ if b~=current then
+ if current==start then
+ if head==start then
+ head=n
+ end
+ start=n
+ end
+ if b==stop then
+ stop=c
+ end
+ local prev=getprev(current)
+ setlink(prev,n)
+ local next=getnext(b)
+ setlink(c,next)
+ setlink(b,current)
+ end
+ elseif cns and getnext(cns)~=current then
+ local cp=getprev(current)
+ local cnsn=getnext(cns)
+ setlink(cp,n)
+ setlink(cns,current)
+ setlink(c,cnsn)
+ if c==stop then
+ stop=cp
+ break
+ end
+ current=getprev(n)
+ end
+ else
+ local char=getchar(current)
+ if consonant[char] then
+ cns=current
+ local next=getnext(cns)
+ if halant[getchar(next)] then
+ cns=next
+ end
+ if not vatucache[char] then
+ next=getnext(cns)
+ while dependent_vowel[getchar(next)] do
+ cns=next
+ next=getnext(cns)
+ end
+ end
+ elseif char==c_nbsp then
+ nbspaces=nbspaces+1
+ cns=current
+ local next=getnext(cns)
+ if halant[getchar(next)] then
+ cns=next
+ end
+ if not vatucache[char] then
+ next=getnext(cns)
+ while dependent_vowel[getchar(next)] do
+ cns=next
+ next=getnext(cns)
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ if getchar(base)==c_nbsp then
+ nbspaces=nbspaces-1
+ if base==stop then
+ stop=getprev(stop)
+ end
+ head=remove_node(head,base)
+ flush_node(base)
+ end
+ return head,stop,nbspaces
+end
+function handlers.devanagari_reorder_matras(head,start)
+ local current=start
+ local startfont=getfont(start)
+ local startattr=getprop(start,a_syllabe)
+ while current do
+ local char=ischar(current,startfont)
+ local next=getnext(current)
+ if char and getprop(current,a_syllabe)==startattr then
+ if halant[char] then
+ if next then
+ local char=ischar(next,startfont)
+ if char and zw_char[char] and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ end
+ end
+ local startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ start=startnext
+ break
+ end
+ else
+ break
+ end
+ current=next
+ end
+ return head,start,true
+end
+local rephbase={}
+function handlers.devanagari_reorder_reph(head,start)
+ local current=getnext(start)
+ local startnext=nil
+ local startprev=nil
+ local startfont=getfont(start)
+ local startattr=getprop(start,a_syllabe)
+ ::step_1::
+ local char=ischar(start,startfont)
+ local rephbase=rephbase[startfont][char]
+ if char and after_subscript[rephbase] then
+ goto step_5
+ end
+ ::step_2::
+ if char and not after_postscript[rephbase] then
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ if halant[char] then
+ local next=getnext(current)
+ if next then
+ local nextchar=ischar(next,startfont)
+ if nextchar and zw_char[nextchar] and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ end
+ end
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ break
+ end
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ end
+ ::step_3::
+ if not startnext then
+ if char and after_main[rephbase] then
+ current=getnext(start)
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ if consonant[char] and not getprop(current,a_state)==s_pref then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(current,start)
+ setlink(start,getnext(current))
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ break
+ end
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ end
+ end
+ ::step_4::
+ if not startnext then
+ if char and before_postscript[rephbase] then
+ current=getnext(start)
+ local c=nil
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ if getprop(current,a_state)==s_pstf then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(getprev(current),start)
+ setlink(start,current)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ break
+ elseif not c and (vowel_modifier[char] or stress_tone_mark[char] ) then
+ c=current
+ end
+ current=getnext(current)
+ else
+ if c then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(getprev(c),start)
+ setlink(start,c)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ end
+ break
+ end
+ end
+ end
+ end
+ ::step_5::
+ if not startnext then
+ current=getnext(start)
+ local c=nil
+ while current do
+ local char=ischar(current,startfont)
+ if char and getprop(current,a_syllabe)==startattr then
+ local state=getprop(current,a_state)
+ if before_subscript[rephbase] and (state==s_blwf or state==s_pstf) then
+ c=current
+ elseif after_subscript[rephbase] and (state==s_pstf) then
+ c=current
+ end
+ current=getnext(current)
+ else
+ break
+ end
+ end
+ if c then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(getprev(c),start)
+ setlink(start,c)
+ start=startnext
+ startattr=getprop(start,a_syllabe)
+ end
+ end
+ ::step_6::
+ if not startnext then
+ current=start
+ local next=getnext(current)
+ while next do
+ local nextchar=ischar(next,startfont)
+ if nextchar and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ else
+ break
+ end
+ end
+ if start~=current then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,getnext(current))
+ setlink(current,start)
+ start=startnext
+ end
+ end
+ return head,start,true
+end
+local reordered_pre_base_reordering_consonants={}
+function handlers.devanagari_reorder_pre_base_reordering_consonants(head,start)
+ if reordered_pre_base_reordering_consonants[start] then
+ return head,start,true
+ end
+ local current=start
+ local startfont=getfont(start)
+ local startattr=getprop(start,a_syllabe)
+ while current do
+ local char=ischar(current,startfont)
+ local next=getnext(current)
+ if char and getprop(current,a_syllabe)==startattr then
+ if halant[char] then
+ if next then
+ local char=ischar(next,startfont)
+ if char and zw_char[char] and getprop(next,a_syllabe)==startattr then
+ current=next
+ next=getnext(current)
+ end
+ end
+ local startnext=getnext(start)
+ head=remove_node(head,start)
+ setlink(start,next)
+ setlink(current,start)
+ reordered_pre_base_reordering_consonants[start]=true
+ start=startnext
+ return head,start,true
+ end
+ else
+ break
+ end
+ current=next
+ end
+ local startattr=getprop(start,a_syllabe)
+ local current=getprev(start)
+ while current and getprop(current,a_syllabe)==startattr do
+ local char=ischar(current)
+ if (not dependent_vowel[char] and not getprop(current,a_state) or getprop(current,a_state)==s_init) then
+ startnext=getnext(start)
+ head=remove_node(head,start)
+ if current==head then
+ setlink(start,current)
+ head=start
+ else
+ setlink(getprev(current),start)
+ setlink(start,current)
+ end
+ reordered_pre_base_reordering_consonants[start]=true
+ start=startnext
+ break
+ end
+ current=getprev(current)
+ end
+ return head,start,true
+end
+function handlers.devanagari_remove_joiners(head,start,kind,lookupname,replacement)
+ local stop=getnext(start)
+ local font=getfont(start)
+ local last=start
+ while stop do
+ local char=ischar(stop,font)
+ if char and (char==c_zwnj or char==c_zwj) then
+ last=stop
+ stop=getnext(stop)
+ else
+ break
+ end
+ end
+ local prev=getprev(start)
+ if stop then
+ setnext(last)
+ setlink(prev,stop)
+ elseif prev then
+ setnext(prev)
+ end
+ if head==start then
+ head=stop
+ end
+ flush_list(start)
+ return head,stop,true
+end
+local function initialize_two(font,attr)
+ local devanagari=fontdata[font].resources.devanagari
+ if devanagari then
+ return devanagari.seqsubset or {},devanagari.reorderreph or {}
+ else
+ return {},{}
+ end
+end
+local function reorder_two(head,start,stop,font,attr,nbspaces)
+ local seqsubset,reorderreph=initialize_two(font,attr)
+ local halfpos=nil
+ local basepos=nil
+ local subpos=nil
+ local postpos=nil
+ reorderreph.coverage={}
+ rephbase[font]={}
+ for i=1,#seqsubset do
+ local subset=seqsubset[i]
+ local kind=subset[1]
+ local lookupcache=subset[2]
+ if kind=="rphf" then
+ reorderreph.coverage[subset[3]]=true
+ rephbase[font][subset[3]]=subset[4]
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ local afternext=next~=stop and getnext(next)
+ if afternext and zw_char[getchar(afternext)] then
+ current=afternext
+ elseif current==start then
+ setprop(current,a_state,s_rphf)
+ current=next
+ else
+ current=next
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="pref" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then
+ setprop(current,a_state,s_pref)
+ setprop(next,a_state,s_pref)
+ current=next
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="half" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if next~=stop and getchar(getnext(next))==c_zwnj then
+ current=next
+ elseif (not getprop(current,a_state)) then
+ setprop(current,a_state,s_half)
+ if not halfpos then
+ halfpos=current
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="blwf" or kind=="vatu" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then
+ setprop(current,a_state,s_blwf)
+ setprop(next,a_state,s_blwf)
+ current=next
+ subpos=current
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ elseif kind=="pstf" then
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ if current~=stop then
+ local c=getchar(current)
+ local found=lookupcache[c]
+ if found then
+ local next=getnext(current)
+ if found[getchar(next)] or contextchain(found,next) then
+ if (not getprop(current,a_state) and not getprop(next,a_state)) then
+ setprop(current,a_state,s_pstf)
+ setprop(next,a_state,s_pstf)
+ current=next
+ postpos=current
+ end
+ end
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ end
+ local current,base,firstcons=start,nil,nil
+ if getprop(start,a_state)==s_rphf then
+ current=getnext(getnext(start))
+ end
+ if current~=getnext(stop) and getchar(current)==c_nbsp then
+ if current==stop then
+ stop=getprev(stop)
+ head=remove_node(head,current)
+ flush_node(current)
+ return head,stop,nbspaces
+ else
+ nbspaces=nbspaces+1
+ base=current
+ current=getnext(current)
+ if current~=stop then
+ local char=getchar(current)
+ if nukta[char] then
+ current=getnext(current)
+ char=getchar(current)
+ end
+ if char==c_zwj then
+ local next=getnext(current)
+ if current~=stop and next~=stop and halant[getchar(next)] then
+ current=next
+ next=getnext(current)
+ local tmp=getnext(next)
+ local changestop=next==stop
+ setnext(next)
+ setprop(current,a_state,s_pref)
+ current=processcharacters(current,font)
+ setprop(current,a_state,s_blwf)
+ current=processcharacters(current,font)
+ setprop(current,a_state,s_pstf)
+ current=processcharacters(current,font)
+ setprop(current,a_state,unsetvalue)
+ if halant[getchar(current)] then
+ setnext(getnext(current),tmp)
+ if show_syntax_errors then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ else
+ setnext(current,tmp)
+ if changestop then
+ stop=current
+ end
+ end
+ end
+ end
+ end
+ end
+ else
+ local last=getnext(stop)
+ while current~=last do
+ local next=getnext(current)
+ if consonant[getchar(current)] then
+ if not (current~=stop and next~=stop and halant[getchar(next)] and getchar(getnext(next))==c_zwj) then
+ if not firstcons then
+ firstcons=current
+ end
+ local a=getprop(current,a_state)
+ if not (a==s_blwf or a==s_pstf or (a~=s_rphf and a~=s_blwf and ra[getchar(current)])) then
+ base=current
+ end
+ end
+ end
+ current=next
+ end
+ if not base then
+ base=firstcons
+ end
+ end
+ if not base then
+ if getprop(start,a_state)==s_rphf then
+ setprop(start,a_state,unsetvalue)
+ end
+ return head,stop,nbspaces
+ else
+ if getprop(base,a_state) then
+ setprop(base,a_state,unsetvalue)
+ end
+ basepos=base
+ end
+ if not halfpos then
+ halfpos=base
+ end
+ if not subpos then
+ subpos=base
+ end
+ if not postpos then
+ postpos=subpos or base
+ end
+ local moved={}
+ local current=start
+ local last=getnext(stop)
+ while current~=last do
+ local char=getchar(current)
+ local target=nil
+ local cn=getnext(current)
+ local tpm=twopart_mark[char]
+ while tpm do
+ local extra=copy_node(current)
+ copyinjection(extra,current)
+ char=tpm[1]
+ setchar(current,char)
+ setchar(extra,tpm[2])
+ head=insert_node_after(head,current,extra)
+ tpm=twopart_mark[char]
+ end
+ if not moved[current] and dependent_vowel[char] then
+ if pre_mark[char] then
+ moved[current]=true
+ local prev,next=getboth(current)
+ setlink(prev,next)
+ if current==stop then
+ stop=getprev(current)
+ end
+ local pos
+ if before_main[char] then
+ pos=basepos
+ else
+ pos=halfpos
+ end
+ local ppos=getprev(pos)
+ while ppos and getprop(ppos,a_syllabe)==getprop(pos,a_syllabe) do
+ if getprop(ppos,a_state)==s_pref then
+ pos=ppos
+ end
+ ppos=getprev(ppos)
+ end
+ local ppos=getprev(pos)
+ while ppos and getprop(ppos,a_syllabe)==getprop(pos,a_syllabe) and halant[ischar(ppos)] do
+ ppos=getprev(ppos)
+ if ppos and getprop(ppos,a_syllabe)==getprop(pos,a_syllabe) and consonant[ischar(ppos)] then
+ pos=ppos
+ ppos=getprev(ppos)
+ else
+ break
+ end
+ end
+ if pos==start then
+ if head==start then
+ head=current
+ end
+ start=current
+ end
+ setlink(getprev(pos),current)
+ setlink(current,pos)
+ elseif above_mark[char] then
+ target=basepos
+ if subpos==basepos then
+ subpos=current
+ end
+ if postpos==basepos then
+ postpos=current
+ end
+ basepos=current
+ elseif below_mark[char] then
+ target=subpos
+ if postpos==subpos then
+ postpos=current
+ end
+ subpos=current
+ elseif post_mark[char] then
+ local n=getnext(postpos)
+ while n do
+ local v=ischar(n,font)
+ if nukta[v] or stress_tone_mark[v] or vowel_modifier[v] then
+ postpos=n
+ else
+ break
+ end
+ n=getnext(n)
+ end
+ target=postpos
+ postpos=current
+ end
+ if mark_above_below_post[char] then
+ local prev=getprev(current)
+ if prev~=target then
+ local next=getnext(current)
+ setlink(prev,next)
+ if current==stop then
+ stop=prev
+ end
+ setlink(current,getnext(target))
+ setlink(target,current)
+ end
+ end
+ end
+ current=cn
+ end
+ local current=getnext(start)
+ local last=getnext(stop)
+ while current~=last do
+ local char=getchar(current)
+ local cn=getnext(current)
+ if halant[char] and ra[ischar(cn)] and getprop(cn,a_state)~=s_rphf and getprop(cn,a_state)~=s_blwf then
+ if after_main[ischar(cn)] then
+ local prev=getprev(current)
+ local next=getnext(cn)
+ local bpn=getnext(basepos)
+ while bpn and dependent_vowel[ischar(bpn)] do
+ basepos=bpn
+ bpn=getnext(bpn)
+ end
+ if basepos~=prev then
+ setlink(prev,next)
+ setlink(cn,getnext(basepos))
+ setlink(basepos,current)
+ if cn==stop then
+ stop=prev
+ end
+ cn=next
+ end
+ end
+ end
+ current=cn
+ end
+ local current=start
+ local c=nil
+ while current~=stop do
+ local char=getchar(current)
+ if halant[char] or stress_tone_mark[char] then
+ if not c then
+ c=current
+ end
+ else
+ c=nil
+ end
+ local next=getnext(current)
+ if c and nukta[getchar(next)] then
+ if head==c then
+ head=next
+ end
+ if stop==next then
+ stop=current
+ end
+ setlink(getprev(c),next)
+ local nextnext=getnext(next)
+ setnext(current,nextnext)
+ local nextnextnext=getnext(nextnext)
+ if nextnextnext then
+ setprev(nextnextnext,current)
+ end
+ setlink(nextnext,c)
+ end
+ if stop==current then break end
+ current=getnext(current)
+ end
+ if getchar(base)==c_nbsp then
+ if base==stop then
+ stop=getprev(stop)
+ end
+ nbspaces=nbspaces-1
+ head=remove_node(head,base)
+ flush_node(base)
+ end
+ return head,stop,nbspaces
+end
+local separator={}
+imerge(separator,consonant)
+imerge(separator,independent_vowel)
+imerge(separator,dependent_vowel)
+imerge(separator,vowel_modifier)
+imerge(separator,stress_tone_mark)
+for k,v in next,nukta do separator[k]=true end
+for k,v in next,halant do separator[k]=true end
+local function analyze_next_chars_one(c,font,variant)
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ if variant==1 then
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ n=getnext(n)
+ if n then
+ v=ischar(n,font)
+ end
+ end
+ if n and v then
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv then
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv then
+ if vv==c_zwj and consonant[vvv] then
+ c=nnn
+ elseif (vv==c_zwnj or vv==c_zwj) and halant[vvv] then
+ local nnnn=getnext(nnn)
+ if nnnn then
+ local vvvv=ischar(nnnn,font)
+ if vvvv and consonant[vvvv] then
+ c=nnnn
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ elseif variant==2 then
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ c=n
+ end
+ n=getnext(c)
+ if n then
+ v=ischar(n,font)
+ if v then
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv and zw_char[v] then
+ n=nn
+ v=vv
+ nn=getnext(nn)
+ vv=nn and ischar(nn,font)
+ end
+ if vv and halant[v] and consonant[vv] then
+ c=nn
+ end
+ end
+ end
+ end
+ end
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ local v=ischar(n,font)
+ if not v then
+ return c
+ end
+ local already_pre_mark
+ local already_above_mark
+ local already_below_mark
+ local already_post_mark
+ while dependent_vowel[v] do
+ local vowels=twopart_mark[v] or { v }
+ for k,v in next,vowels do
+ if pre_mark[v] and not already_pre_mark then
+ already_pre_mark=true
+ elseif above_mark[v] and not already_above_mark then
+ already_above_mark=true
+ elseif below_mark[v] and not already_below_mark then
+ already_below_mark=true
+ elseif post_mark[v] and not already_post_mark then
+ already_post_mark=true
+ else
+ return c
+ end
+ end
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if nukta[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if vowel_modifier[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ c=getnext(c)
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ return n
+ else
+ return c
+ end
+end
+local function analyze_next_chars_two(c,font)
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ c=n
+ end
+ n=c
+ while true do
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv then
+ if halant[vv] then
+ n=nn
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv and zw_char[vvv] then
+ n=nnn
+ end
+ end
+ elseif vv==c_zwnj or vv==c_zwj then
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv and halant[vvv] then
+ n=nnn
+ end
+ end
+ else
+ break
+ end
+ local nn=getnext(n)
+ if nn then
+ local vv=ischar(nn,font)
+ if vv and consonant[vv] then
+ n=nn
+ local nnn=getnext(nn)
+ if nnn then
+ local vvv=ischar(nnn,font)
+ if vvv and nukta[vvv] then
+ n=nnn
+ end
+ end
+ c=n
+ else
+ break
+ end
+ else
+ break
+ end
+ else
+ break
+ end
+ else
+ break
+ end
+ end
+ if not c then
+ return
+ end
+ local n=getnext(c)
+ if not n then
+ return c
+ end
+ local v=ischar(n,font)
+ if not v then
+ return c
+ end
+ if anudatta[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ if v==c_zwnj or v==c_zwj then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ else
+ local already_pre_mark
+ local already_above_mark
+ local already_below_mark
+ local already_post_mark
+ while dependent_vowel[v] do
+ local vowels=twopart_mark[v] or { v }
+ for k,v in next,vowels do
+ if pre_mark[v] and not already_pre_mark then
+ already_pre_mark=true
+ elseif above_mark[v] and not already_above_mark then
+ already_above_mark=true
+ elseif below_mark[v] and not already_below_mark then
+ already_below_mark=true
+ elseif post_mark[v] and not already_post_mark then
+ already_post_mark=true
+ else
+ return c
+ end
+ end
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if nukta[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if halant[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ end
+ if vowel_modifier[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ c=n
+ n=getnext(c)
+ if not n then
+ return c
+ end
+ v=ischar(n,font)
+ if not v then
+ return c
+ end
+ end
+ if stress_tone_mark[v] then
+ return n
+ else
+ return c
+ end
+end
+local function method_one(head,font,attr)
+ local current=head
+ local start=true
+ local done=false
+ local nbspaces=0
+ local syllabe=0
+ while current do
+ local char=ischar(current,font)
+ if char then
+ done=true
+ local syllablestart=current
+ local syllableend=nil
+ local c=current
+ local n=getnext(c)
+ local first=char
+ if n and ra[first] then
+ local second=ischar(n,font)
+ if second and halant[second] then
+ local n=getnext(n)
+ if n then
+ local third=ischar(n,font)
+ if third then
+ c=n
+ first=third
+ end
+ end
+ end
+ end
+ local standalone=first==c_nbsp
+ if standalone then
+ local prev=getprev(current)
+ if prev then
+ local prevchar=ischar(prev,font)
+ if not prevchar then
+ elseif not separator[prevchar] then
+ else
+ standalone=false
+ end
+ else
+ end
+ end
+ if standalone then
+ local syllableend=analyze_next_chars_one(c,font,2)
+ current=getnext(syllableend)
+ if syllablestart~=syllableend then
+ head,current,nbspaces=reorder_one(head,syllablestart,syllableend,font,attr,nbspaces)
+ current=getnext(current)
+ end
+ else
+ if consonant[char] then
+ local prevc=true
+ while prevc do
+ prevc=false
+ local n=getnext(current)
+ if not n then
+ break
+ end
+ local v=ischar(n,font)
+ if not v then
+ break
+ end
+ if nukta[v] then
+ n=getnext(n)
+ if not n then
+ break
+ end
+ v=ischar(n,font)
+ if not v then
+ break
+ end
+ end
+ if halant[v] then
+ n=getnext(n)
+ if not n then
+ break
+ end
+ v=ischar(n,font)
+ if not v then
+ break
+ end
+ if v==c_zwnj or v==c_zwj then
+ n=getnext(n)
+ if not n then
+ break
+ end
+ v=ischar(n,font)
+ if not v then
+ break
+ end
+ end
+ if consonant[v] then
+ prevc=true
+ current=n
+ end
+ end
+ end
+ local n=getnext(current)
+ if n then
+ local v=ischar(n,font)
+ if v and nukta[v] then
+ current=n
+ n=getnext(current)
+ end
+ end
+ syllableend=current
+ current=n
+ if current then
+ local v=ischar(current,font)
+ if not v then
+ elseif halant[v] then
+ local n=getnext(current)
+ if n then
+ local v=ischar(n,font)
+ if v and zw_char[v] then
+ syllableend=n
+ current=getnext(n)
+ else
+ syllableend=current
+ current=n
+ end
+ else
+ syllableend=current
+ current=n
+ end
+ else
+ if dependent_vowel[v] then
+ syllableend=current
+ current=getnext(current)
+ v=ischar(current,font)
+ end
+ if v and vowel_modifier[v] then
+ syllableend=current
+ current=getnext(current)
+ v=ischar(current,font)
+ end
+ if v and stress_tone_mark[v] then
+ syllableend=current
+ current=getnext(current)
+ end
+ end
+ end
+ if syllablestart~=syllableend then
+ if syllableend then
+ syllabe=syllabe+1
+ local c=syllablestart
+ local n=getnext(syllableend)
+ while c~=n do
+ setprop(c,a_syllabe,syllabe)
+ c=getnext(c)
+ end
+ end
+ head,current,nbspaces=reorder_one(head,syllablestart,syllableend,font,attr,nbspaces)
+ current=getnext(current)
+ end
+ elseif independent_vowel[char] then
+ syllableend=current
+ current=getnext(current)
+ if current then
+ local v=ischar(current,font)
+ if v then
+ if vowel_modifier[v] then
+ syllableend=current
+ current=getnext(current)
+ v=ischar(current,font)
+ end
+ if v and stress_tone_mark[v] then
+ syllableend=current
+ current=getnext(current)
+ end
+ end
+ end
+ else
+ if show_syntax_errors then
+ local mark=mark_four[char]
+ if mark then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ end
+ current=getnext(current)
+ end
+ end
+ else
+ current=getnext(current)
+ end
+ start=false
+ end
+ if nbspaces>0 then
+ head=replace_all_nbsp(head)
+ end
+ current=head
+ local n=0
+ while current do
+ local char=ischar(current,font)
+ if char then
+ if n==0 and not getprop(current,a_state) then
+ setprop(current,a_state,s_init)
+ end
+ n=n+1
+ else
+ n=0
+ end
+ current=getnext(current)
+ end
+ return head,done
+end
+local function method_two(head,font,attr)
+ local current=head
+ local start=true
+ local done=false
+ local syllabe=0
+ local nbspaces=0
+ while current do
+ local syllablestart=nil
+ local syllableend=nil
+ local char=ischar(current,font)
+ if char then
+ done=true
+ syllablestart=current
+ local c=current
+ local n=getnext(current)
+ if n and ra[char] then
+ local nextchar=ischar(n,font)
+ if nextchar and halant[nextchar] then
+ local n=getnext(n)
+ if n then
+ local nextnextchar=ischar(n,font)
+ if nextnextchar then
+ c=n
+ char=nextnextchar
+ end
+ end
+ end
+ end
+ if independent_vowel[char] then
+ current=analyze_next_chars_one(c,font,1)
+ syllableend=current
+ else
+ local standalone=char==c_nbsp
+ if standalone then
+ nbspaces=nbspaces+1
+ local p=getprev(current)
+ if not p then
+ elseif ischar(p,font) then
+ elseif not separator[getchar(p)] then
+ else
+ standalone=false
+ end
+ end
+ if standalone then
+ current=analyze_next_chars_one(c,font,2)
+ syllableend=current
+ elseif consonant[getchar(current)] then
+ current=analyze_next_chars_two(current,font)
+ syllableend=current
+ end
+ end
+ end
+ if syllableend then
+ syllabe=syllabe+1
+ local c=syllablestart
+ local n=getnext(syllableend)
+ while c~=n do
+ setprop(c,a_syllabe,syllabe)
+ c=getnext(c)
+ end
+ end
+ if syllableend and syllablestart~=syllableend then
+ head,current,nbspaces=reorder_two(head,syllablestart,syllableend,font,attr,nbspaces)
+ end
+ if not syllableend and show_syntax_errors then
+ local char=ischar(current,font)
+ if char and not getprop(current,a_state) then
+ local mark=mark_four[char]
+ if mark then
+ head,current=inject_syntax_error(head,current,char)
+ end
+ end
+ end
+ start=false
+ current=getnext(current)
+ end
+ if nbspaces>0 then
+ head=replace_all_nbsp(head)
+ end
+ current=head
+ local n=0
+ while current do
+ local char=ischar(current,font)
+ if char then
+ if n==0 and not getprop(current,a_state) then
+ setprop(current,a_state,s_init)
+ end
+ n=n+1
+ else
+ n=0
+ end
+ current=getnext(current)
+ end
+ return head,done
+end
+for i=1,nofscripts do
+ methods[scripts_one[i]]=method_one
+ methods[scripts_two[i]]=method_two
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-ocl']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local tostring,tonumber,next=tostring,tonumber,next
+local round,max=math.round,math.round
+local sortedkeys,sortedhash=table.sortedkeys,table.sortedhash
+local setmetatableindex=table.setmetatableindex
+local formatters=string.formatters
+local tounicode=fonts.mappings.tounicode
+local helpers=fonts.helpers
+local charcommand=helpers.commands.char
+local rightcommand=helpers.commands.right
+local leftcommand=helpers.commands.left
+local downcommand=helpers.commands.down
+local otf=fonts.handlers.otf
+local f_color=formatters["%.3f %.3f %.3f rg"]
+local f_gray=formatters["%.3f g"]
+if context then
+
+--removed
+
+else
+ local tounicode=fonts.mappings.tounicode16
+ function otf.getactualtext(s)
+ return
+ "/Span << /ActualText <feff"..s.."> >> BDC",
+ "EMC"
+ end
+end
+local sharedpalettes={}
+local hash=setmetatableindex(function(t,k)
+ local v={ "pdf","direct",k }
+ t[k]=v
+ return v
+end)
+if context then
+
+--removed
+
+else
+ function otf.registerpalette(name,values)
+ sharedpalettes[name]=values
+ for i=1,#values do
+ local v=values[i]
+ if v then
+ values[i]=hash[f_color(
+ max(round((v.r or 0)*255),255)/255,
+ max(round((v.g or 0)*255),255)/255,
+ max(round((v.b or 0)*255),255)/255
+ )]
+ end
+ end
+ end
+end
+local function convert(t,k)
+ local v={}
+ for i=1,#k do
+ local p=k[i]
+ local r,g,b=p[1],p[2],p[3]
+ if r==g and g==b then
+ v[i]=hash[f_gray(r/255)]
+ else
+ v[i]=hash[f_color(r/255,g/255,b/255)]
+ end
+ end
+ t[k]=v
+ return v
+end
+local start={ "pdf","mode","font" }
+local push={ "pdf","page","q" }
+local pop={ "pdf","page","Q" }
+local function initialize(tfmdata,kind,value)
+ if value then
+ local resources=tfmdata.resources
+ local palettes=resources.colorpalettes
+ if palettes then
+ local converted=resources.converted
+ if not converted then
+ converted=setmetatableindex(convert)
+ resources.converted=converted
+ end
+ local colorvalues=sharedpalettes[value]
+ local default=false
+ if colorvalues then
+ default=colorvalues[#colorvalues]
+ else
+ colorvalues=converted[palettes[tonumber(value) or 1] or palettes[1]] or {}
+ end
+ local classes=#colorvalues
+ if classes==0 then
+ return
+ end
+ local characters=tfmdata.characters
+ local descriptions=tfmdata.descriptions
+ local properties=tfmdata.properties
+ properties.virtualized=true
+ tfmdata.fonts={
+ { id=0 }
+ }
+ local getactualtext=otf.getactualtext
+ local b,e=getactualtext(tounicode(0xFFFD))
+ local actualb={ "pdf","page",b }
+ local actuale={ "pdf","page",e }
+ for unicode,character in next,characters do
+ local description=descriptions[unicode]
+ if description then
+ local colorlist=description.colors
+ if colorlist then
+ local u=description.unicode or characters[unicode].unicode
+ local w=character.width or 0
+ local s=#colorlist
+ local goback=w~=0 and leftcommand[w] or nil
+ local t={
+ start,
+ not u and actualb or { "pdf","page",(getactualtext(tounicode(u))) }
+ }
+ local n=2
+ local l=nil
+ local f=false
+ for i=1,s do
+ local entry=colorlist[i]
+ local v=colorvalues[entry.class] or default
+ if v and l~=v then
+ if f then
+ n=n+1 t[n]=pop
+ end
+ n=n+1 t[n]=push
+ f=true
+ n=n+1 t[n]=v
+ l=v
+ else
+ if f then
+ n=n+1 t[n]=pop
+ end
+ f=false
+ l=nil
+ end
+ n=n+1 t[n]=charcommand[entry.slot]
+ if s>1 and i<s and goback then
+ n=n+1 t[n]=goback
+ end
+ end
+ if f then
+ n=n+1 t[n]=pop
+ end
+ n=n+1 t[n]=actuale
+ character.commands=t
+ end
+ end
+ end
+ end
+ end
+end
+fonts.handlers.otf.features.register {
+ name="colr",
+ description="color glyphs",
+ manipulators={
+ base=initialize,
+ node=initialize,
+ }
+}
+do
+ local nofstreams=0
+ local f_name=formatters[ [[pdf-glyph-%05i]] ]
+ local f_used=context and formatters[ [[original:///%s]] ] or formatters[ [[%s]] ]
+ local hashed={}
+ local cache={}
+ local openpdf=pdfe.new
+ function otf.storepdfdata(pdf)
+ local done=hashed[pdf]
+ if not done then
+ nofstreams=nofstreams+1
+ local f=f_name(nofstreams)
+ local n=openpdf(pdf,#pdf,f)
+ done=f_used(n)
+ hashed[pdf]=done
+ end
+ return done
+ end
+end
+local function pdftovirtual(tfmdata,pdfshapes,kind)
+ if not tfmdata or not pdfshapes or not kind then
+ return
+ end
+ local characters=tfmdata.characters
+ local properties=tfmdata.properties
+ local parameters=tfmdata.parameters
+ local hfactor=parameters.hfactor
+ properties.virtualized=true
+ tfmdata.fonts={
+ { id=0 }
+ }
+ local getactualtext=otf.getactualtext
+ local storepdfdata=otf.storepdfdata
+ local b,e=getactualtext(tounicode(0xFFFD))
+ local actualb={ "pdf","page",b }
+ local actuale={ "pdf","page",e }
+ local vfimage=lpdf and lpdf.vfimage or function(wd,ht,dp,data,name)
+ local name=storepdfdata(data)
+ return { "image",{ filename=name,width=wd,height=ht,depth=dp } }
+ end
+ for unicode,character in sortedhash(characters) do
+ local index=character.index
+ if index then
+ local pdf=pdfshapes[index]
+ local typ=type(pdf)
+ local data=nil
+ local dx=nil
+ local dy=nil
+ if typ=="table" then
+ data=pdf.data
+ dx=pdf.dx or 0
+ dy=pdf.dy or 0
+ elseif typ=="string" then
+ data=pdf
+ dx=0
+ dy=0
+ end
+ if data then
+ local bt=unicode and getactualtext(unicode)
+ local wd=character.width or 0
+ local ht=character.height or 0
+ local dp=character.depth or 0
+ character.commands={
+ not unicode and actualb or { "pdf","page",(getactualtext(unicode)) },
+ downcommand[dp+dy*hfactor],
+ rightcommand[dx*hfactor],
+ vfimage(wd,ht,dp,data,name),
+ actuale,
+ }
+ character[kind]=true
+ end
+ end
+ end
+end
+local otfsvg=otf.svg or {}
+otf.svg=otfsvg
+otf.svgenabled=true
+do
+ local report_svg=logs.reporter("fonts","svg conversion")
+ local loaddata=io.loaddata
+ local savedata=io.savedata
+ local remove=os.remove
+ if context and xml.convert then
+ local xmlconvert=xml.convert
+ local xmlfirst=xml.first
+ function otfsvg.filterglyph(entry,index)
+ local svg=xmlconvert(entry.data)
+ local root=svg and xmlfirst(svg,"/svg[@id='glyph"..index.."']")
+ local data=root and tostring(root)
+ return data
+ end
+ else
+ function otfsvg.filterglyph(entry,index)
+ return entry.data
+ end
+ end
+ local runner=sandbox and sandbox.registerrunner {
+ name="otfsvg",
+ program="inkscape",
+ method="pipeto",
+ template="--shell > temp-otf-svg-shape.log",
+ reporter=report_svg,
+ }
+ if not runner then
+ runner=function()
+ return io.open("inkscape --shell > temp-otf-svg-shape.log","w")
+ end
+ end
+ function otfsvg.topdf(svgshapes)
+ local pdfshapes={}
+ local inkscape=runner()
+ if inkscape then
+ local nofshapes=#svgshapes
+ local f_svgfile=formatters["temp-otf-svg-shape-%i.svg"]
+ local f_pdffile=formatters["temp-otf-svg-shape-%i.pdf"]
+ local f_convert=formatters["%s --export-pdf=%s\n"]
+ local filterglyph=otfsvg.filterglyph
+ local nofdone=0
+ report_svg("processing %i svg containers",nofshapes)
+ statistics.starttiming()
+ for i=1,nofshapes do
+ local entry=svgshapes[i]
+ for index=entry.first,entry.last do
+ local data=filterglyph(entry,index)
+ if data and data~="" then
+ local svgfile=f_svgfile(index)
+ local pdffile=f_pdffile(index)
+ savedata(svgfile,data)
+ inkscape:write(f_convert(svgfile,pdffile))
+ pdfshapes[index]=true
+ nofdone=nofdone+1
+ if nofdone%100==0 then
+ report_svg("%i shapes processed",nofdone)
+ end
+ end
+ end
+ end
+ inkscape:write("quit\n")
+ inkscape:close()
+ report_svg("processing %i pdf results",nofshapes)
+ for index in next,pdfshapes do
+ local svgfile=f_svgfile(index)
+ local pdffile=f_pdffile(index)
+ pdfshapes[index]=loaddata(pdffile)
+ remove(svgfile)
+ remove(pdffile)
+ end
+ statistics.stoptiming()
+ if statistics.elapsedseconds then
+ report_svg("svg conversion time %s",statistics.elapsedseconds() or "-")
+ end
+ end
+ return pdfshapes
+ end
+end
+local function initializesvg(tfmdata,kind,value)
+ if value and otf.svgenabled then
+ local svg=tfmdata.properties.svg
+ local hash=svg and svg.hash
+ local timestamp=svg and svg.timestamp
+ if not hash then
+ return
+ end
+ local pdffile=containers.read(otf.pdfcache,hash)
+ local pdfshapes=pdffile and pdffile.pdfshapes
+ if not pdfshapes or pdffile.timestamp~=timestamp then
+ local svgfile=containers.read(otf.svgcache,hash)
+ local svgshapes=svgfile and svgfile.svgshapes
+ pdfshapes=svgshapes and otfsvg.topdf(svgshapes) or {}
+ containers.write(otf.pdfcache,hash,{
+ pdfshapes=pdfshapes,
+ timestamp=timestamp,
+ })
+ end
+ pdftovirtual(tfmdata,pdfshapes,"svg")
+ end
+end
+fonts.handlers.otf.features.register {
+ name="svg",
+ description="svg glyphs",
+ manipulators={
+ base=initializesvg,
+ node=initializesvg,
+ }
+}
+local otfpng=otf.png or {}
+otf.png=otfpng
+otf.pngenabled=true
+do
+ local report_png=logs.reporter("fonts","png conversion")
+ local loaddata=io.loaddata
+ local savedata=io.savedata
+ local remove=os.remove
+ local runner=sandbox and sandbox.registerrunner {
+ name="otfpng",
+ program="gm",
+ template="convert -quality 100 temp-otf-png-shape.png temp-otf-png-shape.pdf > temp-otf-svg-shape.log",
+ }
+ if not runner then
+ runner=function()
+ return os.execute("gm convert -quality 100 temp-otf-png-shape.png temp-otf-png-shape.pdf > temp-otf-svg-shape.log")
+ end
+ end
+ function otfpng.topdf(pngshapes)
+ local pdfshapes={}
+ local pngfile="temp-otf-png-shape.png"
+ local pdffile="temp-otf-png-shape.pdf"
+ local nofdone=0
+ local indices=sortedkeys(pngshapes)
+ local nofindices=#indices
+ report_png("processing %i png containers",nofindices)
+ statistics.starttiming()
+ for i=1,nofindices do
+ local index=indices[i]
+ local entry=pngshapes[index]
+ local data=entry.data
+ local x=entry.x
+ local y=entry.y
+ savedata(pngfile,data)
+ runner()
+ pdfshapes[index]={
+ x=x~=0 and x or nil,
+ y=y~=0 and y or nil,
+ data=loaddata(pdffile),
+ }
+ nofdone=nofdone+1
+ if nofdone%100==0 then
+ report_png("%i shapes processed",nofdone)
+ end
+ end
+ report_png("processing %i pdf results",nofindices)
+ remove(pngfile)
+ remove(pdffile)
+ statistics.stoptiming()
+ if statistics.elapsedseconds then
+ report_png("png conversion time %s",statistics.elapsedseconds() or "-")
+ end
+ return pdfshapes
+ end
+end
+local function initializepng(tfmdata,kind,value)
+ if value and otf.pngenabled then
+ local png=tfmdata.properties.png
+ local hash=png and png.hash
+ local timestamp=png and png.timestamp
+ if not hash then
+ return
+ end
+ local pdffile=containers.read(otf.pdfcache,hash)
+ local pdfshapes=pdffile and pdffile.pdfshapes
+ if not pdfshapes or pdffile.timestamp~=timestamp then
+ local pngfile=containers.read(otf.pngcache,hash)
+ local pngshapes=pngfile and pngfile.pngshapes
+ pdfshapes=pngshapes and otfpng.topdf(pngshapes) or {}
+ containers.write(otf.pdfcache,hash,{
+ pdfshapes=pdfshapes,
+ timestamp=timestamp,
+ })
+ end
+ pdftovirtual(tfmdata,pdfshapes,"png")
+ end
+end
+fonts.handlers.otf.features.register {
+ name="sbix",
+ description="sbix glyphs",
+ manipulators={
+ base=initializepng,
+ node=initializepng,
+ }
+}
+fonts.handlers.otf.features.register {
+ name="cblc",
+ description="cblc glyphs",
+ manipulators={
+ base=initializepng,
+ node=initializepng,
+ }
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-otc']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local insert,sortedkeys,sortedhash,tohash=table.insert,table.sortedkeys,table.sortedhash,table.tohash
+local type,next,tonumber=type,next,tonumber
+local lpegmatch=lpeg.match
+local utfbyte,utflen=utf.byte,utf.len
+local sortedhash=table.sortedhash
+local trace_loading=false trackers.register("otf.loading",function(v) trace_loading=v end)
+local report_otf=logs.reporter("fonts","otf loading")
+local fonts=fonts
+local otf=fonts.handlers.otf
+local registerotffeature=otf.features.register
+local setmetatableindex=table.setmetatableindex
+local checkmerge=fonts.helpers.checkmerge
+local checkflags=fonts.helpers.checkflags
+local checksteps=fonts.helpers.checksteps
+local normalized={
+ substitution="substitution",
+ single="substitution",
+ ligature="ligature",
+ alternate="alternate",
+ multiple="multiple",
+ kern="kern",
+ pair="pair",
+ single="single",
+ chainsubstitution="chainsubstitution",
+ chainposition="chainposition",
+}
+local types={
+ substitution="gsub_single",
+ ligature="gsub_ligature",
+ alternate="gsub_alternate",
+ multiple="gsub_multiple",
+ kern="gpos_pair",
+ pair="gpos_pair",
+ single="gpos_single",
+ chainsubstitution="gsub_contextchain",
+ chainposition="gpos_contextchain",
+}
+local names={
+ gsub_single="gsub",
+ gsub_multiple="gsub",
+ gsub_alternate="gsub",
+ gsub_ligature="gsub",
+ gsub_context="gsub",
+ gsub_contextchain="gsub",
+ gsub_reversecontextchain="gsub",
+ gpos_single="gpos",
+ gpos_pair="gpos",
+ gpos_cursive="gpos",
+ gpos_mark2base="gpos",
+ gpos_mark2ligature="gpos",
+ gpos_mark2mark="gpos",
+ gpos_context="gpos",
+ gpos_contextchain="gpos",
+}
+setmetatableindex(types,function(t,k) t[k]=k return k end)
+local everywhere={ ["*"]={ ["*"]=true } }
+local noflags={ false,false,false,false }
+local function getrange(sequences,category)
+ local count=#sequences
+ local first=nil
+ local last=nil
+ for i=1,count do
+ local t=sequences[i].type
+ if t and names[t]==category then
+ if not first then
+ first=i
+ end
+ last=i
+ end
+ end
+ return first or 1,last or count
+end
+local function validspecification(specification,name)
+ local dataset=specification.dataset
+ if dataset then
+ elseif specification[1] then
+ dataset=specification
+ specification={ dataset=dataset }
+ else
+ dataset={ { data=specification.data } }
+ specification.data=nil
+ specification.dataset=dataset
+ end
+ local first=dataset[1]
+ if first then
+ first=first.data
+ end
+ if not first then
+ report_otf("invalid feature specification, no dataset")
+ return
+ end
+ if type(name)~="string" then
+ name=specification.name or first.name
+ end
+ if type(name)~="string" then
+ report_otf("invalid feature specification, no name")
+ return
+ end
+ local n=#dataset
+ if n>0 then
+ for i=1,n do
+ setmetatableindex(dataset[i],specification)
+ end
+ return specification,name
+ end
+end
+local function addfeature(data,feature,specifications)
+ if not specifications then
+ report_otf("missing specification")
+ return
+ end
+ local descriptions=data.descriptions
+ local resources=data.resources
+ local features=resources.features
+ local sequences=resources.sequences
+ if not features or not sequences then
+ report_otf("missing specification")
+ return
+ end
+ local alreadydone=resources.alreadydone
+ if not alreadydone then
+ alreadydone={}
+ resources.alreadydone=alreadydone
+ end
+ if alreadydone[specifications] then
+ return
+ else
+ alreadydone[specifications]=true
+ end
+ local fontfeatures=resources.features or everywhere
+ local unicodes=resources.unicodes
+ local splitter=lpeg.splitter(" ",unicodes)
+ local done=0
+ local skip=0
+ local aglunicodes=false
+ local specifications=validspecification(specifications,feature)
+ if not specifications then
+ return
+ end
+ local p=lpeg.P("P")*(lpeg.patterns.hexdigit^1/function(s) return tonumber(s,16) end)*lpeg.P(-1)
+ local function tounicode(code)
+ if not code then
+ return
+ end
+ if type(code)=="number" then
+ return code
+ end
+ local u=unicodes[code]
+ if u then
+ return u
+ end
+ if utflen(code)==1 then
+ u=utfbyte(code)
+ if u then
+ return u
+ end
+ end
+ local u=lpegmatch(p,code)
+ if u then
+ return u
+ end
+ if not aglunicodes then
+ aglunicodes=fonts.encodings.agl.unicodes
+ end
+ local u=aglunicodes[code]
+ if u then
+ return u
+ end
+ end
+ local coverup=otf.coverup
+ local coveractions=coverup.actions
+ local stepkey=coverup.stepkey
+ local register=coverup.register
+ local function prepare_substitution(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ else
+ if type(replacement)=="table" then
+ replacement=replacement[1]
+ end
+ replacement=tounicode(replacement)
+ if replacement and descriptions[replacement] then
+ cover(coverage,unicode,replacement)
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function prepare_alternate(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ elseif type(replacement)=="table" then
+ local r={}
+ for i=1,#replacement do
+ local u=tounicode(replacement[i])
+ r[i]=(nocheck or descriptions[u]) and u or unicode
+ end
+ cover(coverage,unicode,r)
+ done=done+1
+ else
+ local u=tounicode(replacement)
+ if u then
+ cover(coverage,unicode,{ u })
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function prepare_multiple(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ elseif type(replacement)=="table" then
+ local r={}
+ local n=0
+ for i=1,#replacement do
+ local u=tounicode(replacement[i])
+ if nocheck or descriptions[u] then
+ n=n+1
+ r[n]=u
+ end
+ end
+ if n>0 then
+ cover(coverage,unicode,r)
+ done=done+1
+ else
+ skip=skip+1
+ end
+ else
+ local u=tounicode(replacement)
+ if u then
+ cover(coverage,unicode,{ u })
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function prepare_ligature(list,featuretype,nocheck)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ for code,ligature in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if not nocheck and not description then
+ skip=skip+1
+ else
+ if type(ligature)=="string" then
+ ligature={ lpegmatch(splitter,ligature) }
+ end
+ local present=true
+ for i=1,#ligature do
+ local l=ligature[i]
+ local u=tounicode(l)
+ if nocheck or descriptions[u] then
+ ligature[i]=u
+ else
+ present=false
+ break
+ end
+ end
+ if present then
+ cover(coverage,unicode,ligature)
+ done=done+1
+ else
+ skip=skip+1
+ end
+ end
+ end
+ return coverage
+ end
+ local function resetspacekerns()
+ data.properties.hasspacekerns=true
+ data.resources .spacekerns=nil
+ end
+ local function prepare_kern(list,featuretype)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ local isspace=false
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if description and type(replacement)=="table" then
+ local r={}
+ for k,v in next,replacement do
+ local u=tounicode(k)
+ if u then
+ r[u]=v
+ if u==32 then
+ isspace=true
+ end
+ end
+ end
+ if next(r) then
+ cover(coverage,unicode,r)
+ done=done+1
+ if unicode==32 then
+ isspace=true
+ end
+ else
+ skip=skip+1
+ end
+ else
+ skip=skip+1
+ end
+ end
+ if isspace then
+ resetspacekerns()
+ end
+ return coverage
+ end
+ local function prepare_pair(list,featuretype)
+ local coverage={}
+ local cover=coveractions[featuretype]
+ if cover then
+ for code,replacement in next,list do
+ local unicode=tounicode(code)
+ local description=descriptions[unicode]
+ if description and type(replacement)=="table" then
+ local r={}
+ for k,v in next,replacement do
+ local u=tounicode(k)
+ if u then
+ r[u]=v
+ if u==32 then
+ isspace=true
+ end
+ end
+ end
+ if next(r) then
+ cover(coverage,unicode,r)
+ done=done+1
+ if unicode==32 then
+ isspace=true
+ end
+ else
+ skip=skip+1
+ end
+ else
+ skip=skip+1
+ end
+ end
+ if isspace then
+ resetspacekerns()
+ end
+ else
+ report_otf("unknown cover type %a",featuretype)
+ end
+ return coverage
+ end
+ local prepare_single=prepare_pair
+ local function prepare_chain(list,featuretype,sublookups)
+ local rules=list.rules
+ local coverage={}
+ if rules then
+ local rulehash={}
+ local rulesize=0
+ local lookuptype=types[featuretype]
+ for nofrules=1,#rules do
+ local rule=rules[nofrules]
+ local current=rule.current
+ local before=rule.before
+ local after=rule.after
+ local replacements=rule.replacements or false
+ local sequence={}
+ local nofsequences=0
+ if before then
+ for n=1,#before do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=before[n]
+ end
+ end
+ local start=nofsequences+1
+ for n=1,#current do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=current[n]
+ end
+ local stop=nofsequences
+ if after then
+ for n=1,#after do
+ nofsequences=nofsequences+1
+ sequence[nofsequences]=after[n]
+ end
+ end
+ local lookups=rule.lookups or false
+ local subtype=nil
+ if lookups and sublookups then
+ for k,v in sortedhash(lookups) do
+ local t=type(v)
+ if t=="table" then
+ for i=1,#v do
+ local vi=v[i]
+ if type(vi)~="table" then
+ v[i]={ vi }
+ end
+ end
+ elseif t=="number" then
+ local lookup=sublookups[v]
+ if lookup then
+ lookups[k]={ lookup }
+ if not subtype then
+ subtype=lookup.type
+ end
+ elseif v==0 then
+ lookups[k]={ { type="gsub_remove" } }
+ else
+ lookups[k]=false
+ end
+ else
+ lookups[k]=false
+ end
+ end
+ end
+ if nofsequences>0 then
+ local hashed={}
+ for i=1,nofsequences do
+ local t={}
+ local s=sequence[i]
+ for i=1,#s do
+ local u=tounicode(s[i])
+ if u then
+ t[u]=true
+ end
+ end
+ hashed[i]=t
+ end
+ sequence=hashed
+ rulesize=rulesize+1
+ rulehash[rulesize]={
+ nofrules,
+ lookuptype,
+ sequence,
+ start,
+ stop,
+ lookups,
+ replacements,
+ subtype,
+ }
+ for unic in sortedhash(sequence[start]) do
+ local cu=coverage[unic]
+ if not cu then
+ coverage[unic]=rulehash
+ end
+ end
+ sequence.n=nofsequences
+ end
+ end
+ rulehash.n=rulesize
+ end
+ return coverage
+ end
+ local dataset=specifications.dataset
+ local function report(name,category,position,first,last,sequences)
+ report_otf("injecting name %a of category %a at position %i in [%i,%i] of [%i,%i]",
+ name,category,position,first,last,1,#sequences)
+ end
+ local function inject(specification,sequences,sequence,first,last,category,name)
+ local position=specification.position or false
+ if not position then
+ position=specification.prepend
+ if position==true then
+ if trace_loading then
+ report(name,category,first,first,last,sequences)
+ end
+ insert(sequences,first,sequence)
+ return
+ end
+ end
+ if not position then
+ position=specification.append
+ if position==true then
+ if trace_loading then
+ report(name,category,last+1,first,last,sequences)
+ end
+ insert(sequences,last+1,sequence)
+ return
+ end
+ end
+ local kind=type(position)
+ if kind=="string" then
+ local index=false
+ for i=first,last do
+ local s=sequences[i]
+ local f=s.features
+ if f then
+ for k in sortedhash(f) do
+ if k==position then
+ index=i
+ break
+ end
+ end
+ if index then
+ break
+ end
+ end
+ end
+ if index then
+ position=index
+ else
+ position=last+1
+ end
+ elseif kind=="number" then
+ if position<0 then
+ position=last-position+1
+ end
+ if position>last then
+ position=last+1
+ elseif position<first then
+ position=first
+ end
+ else
+ position=last+1
+ end
+ if trace_loading then
+ report(name,category,position,first,last,sequences)
+ end
+ insert(sequences,position,sequence)
+ end
+ for s=1,#dataset do
+ local specification=dataset[s]
+ local valid=specification.valid
+ local feature=specification.name or feature
+ if not feature or feature=="" then
+ report_otf("no valid name given for extra feature")
+ elseif not valid or valid(data,specification,feature) then
+ local initialize=specification.initialize
+ if initialize then
+ specification.initialize=initialize(specification,data) and initialize or nil
+ end
+ local askedfeatures=specification.features or everywhere
+ local askedsteps=specification.steps or specification.subtables or { specification.data } or {}
+ local featuretype=normalized[specification.type or "substitution"] or "substitution"
+ local featureflags=specification.flags or noflags
+ local nocheck=specification.nocheck
+ local futuresteps=specification.futuresteps
+ local featureorder=specification.order or { feature }
+ local featurechain=(featuretype=="chainsubstitution" or featuretype=="chainposition") and 1 or 0
+ local nofsteps=0
+ local steps={}
+ local sublookups=specification.lookups
+ local category=nil
+ checkflags(specification,resources)
+ if sublookups then
+ local s={}
+ for i=1,#sublookups do
+ local specification=sublookups[i]
+ local askedsteps=specification.steps or specification.subtables or { specification.data } or {}
+ local featuretype=normalized[specification.type or "substitution"] or "substitution"
+ local featureflags=specification.flags or noflags
+ local nofsteps=0
+ local steps={}
+ for i=1,#askedsteps do
+ local list=askedsteps[i]
+ local coverage=nil
+ local format=nil
+ if featuretype=="substitution" then
+ coverage=prepare_substitution(list,featuretype,nocheck)
+ elseif featuretype=="ligature" then
+ coverage=prepare_ligature(list,featuretype,nocheck)
+ elseif featuretype=="alternate" then
+ coverage=prepare_alternate(list,featuretype,nocheck)
+ elseif featuretype=="multiple" then
+ coverage=prepare_multiple(list,featuretype,nocheck)
+ elseif featuretype=="kern" or featuretype=="move" then
+ format=featuretype
+ coverage=prepare_kern(list,featuretype)
+ elseif featuretype=="pair" then
+ format="pair"
+ coverage=prepare_pair(list,featuretype)
+ elseif featuretype=="single" then
+ format="single"
+ coverage=prepare_single(list,featuretype)
+ end
+ if coverage and next(coverage) then
+ nofsteps=nofsteps+1
+ steps[nofsteps]=register(coverage,featuretype,format,feature,nofsteps,descriptions,resources)
+ end
+ end
+ checkmerge(specification)
+ checksteps(specification)
+ s[i]={
+ [stepkey]=steps,
+ nofsteps=nofsteps,
+ flags=featureflags,
+ type=types[featuretype],
+ }
+ end
+ sublookups=s
+ end
+ for i=1,#askedsteps do
+ local list=askedsteps[i]
+ local coverage=nil
+ local format=nil
+ if featuretype=="substitution" then
+ category="gsub"
+ coverage=prepare_substitution(list,featuretype,nocheck)
+ elseif featuretype=="ligature" then
+ category="gsub"
+ coverage=prepare_ligature(list,featuretype,nocheck)
+ elseif featuretype=="alternate" then
+ category="gsub"
+ coverage=prepare_alternate(list,featuretype,nocheck)
+ elseif featuretype=="multiple" then
+ category="gsub"
+ coverage=prepare_multiple(list,featuretype,nocheck)
+ elseif featuretype=="kern" or featuretype=="move" then
+ category="gpos"
+ format=featuretype
+ coverage=prepare_kern(list,featuretype)
+ elseif featuretype=="pair" then
+ category="gpos"
+ format="pair"
+ coverage=prepare_pair(list,featuretype)
+ elseif featuretype=="single" then
+ category="gpos"
+ format="single"
+ coverage=prepare_single(list,featuretype)
+ elseif featuretype=="chainsubstitution" then
+ category="gsub"
+ coverage=prepare_chain(list,featuretype,sublookups)
+ elseif featuretype=="chainposition" then
+ category="gpos"
+ coverage=prepare_chain(list,featuretype,sublookups)
+ else
+ report_otf("not registering feature %a, unknown category",feature)
+ return
+ end
+ if coverage and next(coverage) then
+ nofsteps=nofsteps+1
+ steps[nofsteps]=register(coverage,featuretype,format,feature,nofsteps,descriptions,resources)
+ end
+ end
+ if nofsteps>0 then
+ for k,v in next,askedfeatures do
+ if v[1] then
+ askedfeatures[k]=tohash(v)
+ end
+ end
+ if featureflags[1] then featureflags[1]="mark" end
+ if featureflags[2] then featureflags[2]="ligature" end
+ if featureflags[3] then featureflags[3]="base" end
+ local steptype=types[featuretype]
+ local sequence={
+ chain=featurechain,
+ features={ [feature]=askedfeatures },
+ flags=featureflags,
+ name=feature,
+ order=featureorder,
+ [stepkey]=steps,
+ nofsteps=nofsteps,
+ type=steptype,
+ }
+ checkflags(sequence,resources)
+ checkmerge(sequence)
+ checksteps(sequence)
+ local first,last=getrange(sequences,category)
+ inject(specification,sequences,sequence,first,last,category,feature)
+ local features=fontfeatures[category]
+ if not features then
+ features={}
+ fontfeatures[category]=features
+ end
+ local k=features[feature]
+ if not k then
+ k={}
+ features[feature]=k
+ end
+ for script,languages in next,askedfeatures do
+ local kk=k[script]
+ if not kk then
+ kk={}
+ k[script]=kk
+ end
+ for language,value in next,languages do
+ kk[language]=value
+ end
+ end
+ end
+ end
+ end
+ if trace_loading then
+ report_otf("registering feature %a, affected glyphs %a, skipped glyphs %a",feature,done,skip)
+ end
+end
+otf.enhancers.addfeature=addfeature
+local extrafeatures={}
+local knownfeatures={}
+function otf.addfeature(name,specification)
+ if type(name)=="table" then
+ specification=name
+ end
+ if type(specification)~="table" then
+ report_otf("invalid feature specification, no valid table")
+ return
+ end
+ specification,name=validspecification(specification,name)
+ if name and specification then
+ local slot=knownfeatures[name]
+ if not slot then
+ slot=#extrafeatures+1
+ knownfeatures[name]=slot
+ elseif specification.overload==false then
+ slot=#extrafeatures+1
+ knownfeatures[name]=slot
+ else
+ end
+ specification.name=name
+ extrafeatures[slot]=specification
+ end
+end
+local function enhance(data,filename,raw)
+ for slot=1,#extrafeatures do
+ local specification=extrafeatures[slot]
+ addfeature(data,specification.name,specification)
+ end
+end
+otf.enhancers.enhance=enhance
+otf.enhancers.register("check extra features",enhance)
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-onr']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local fonts,logs,trackers,resolvers=fonts,logs,trackers,resolvers
+local next,type,tonumber,rawget,rawset=next,type,tonumber,rawget,rawset
+local match,lower,gsub,strip,find=string.match,string.lower,string.gsub,string.strip,string.find
+local char,byte,sub=string.char,string.byte,string.sub
+local abs=math.abs
+local bxor,rshift=bit32.bxor,bit32.rshift
+local P,S,R,V,Cmt,C,Ct,Cs,Carg,Cf,Cg,Cc=lpeg.P,lpeg.S,lpeg.R,lpeg.V,lpeg.Cmt,lpeg.C,lpeg.Ct,lpeg.Cs,lpeg.Carg,lpeg.Cf,lpeg.Cg,lpeg.Cc
+local lpegmatch,patterns=lpeg.match,lpeg.patterns
+local trace_indexing=false trackers.register("afm.indexing",function(v) trace_indexing=v end)
+local trace_loading=false trackers.register("afm.loading",function(v) trace_loading=v end)
+local report_afm=logs.reporter("fonts","afm loading")
+local report_pfb=logs.reporter("fonts","pfb loading")
+local handlers=fonts.handlers
+local afm=handlers.afm or {}
+handlers.afm=afm
+local readers=afm.readers or {}
+afm.readers=readers
+afm.version=1.513
+local get_indexes,get_shapes
+do
+ local decrypt
+ do
+ local r,c1,c2,n=0,0,0,0
+ local function step(c)
+ local cipher=byte(c)
+ local plain=bxor(cipher,rshift(r,8))
+ r=((cipher+r)*c1+c2)%65536
+ return char(plain)
+ end
+ decrypt=function(binary,initial,seed)
+ r,c1,c2,n=initial,52845,22719,seed
+ binary=gsub(binary,".",step)
+ return sub(binary,n+1)
+ end
+ end
+ local charstrings=P("/CharStrings")
+ local subroutines=P("/Subrs")
+ local encoding=P("/Encoding")
+ local dup=P("dup")
+ local put=P("put")
+ local array=P("array")
+ local name=P("/")*C((R("az","AZ","09")+S("-_."))^1)
+ local digits=R("09")^1
+ local cardinal=digits/tonumber
+ local spaces=P(" ")^1
+ local spacing=patterns.whitespace^0
+ local routines,vector,chars,n,m
+ local initialize=function(str,position,size)
+ n=0
+ m=size
+ return position+1
+ end
+ local setroutine=function(str,position,index,size,filename)
+ if routines[index] then
+ return false
+ end
+ local forward=position+size
+ local stream=decrypt(sub(str,position+1,forward),4330,4)
+ routines[index]={ byte(stream,1,#stream) }
+ n=n+1
+ if n>=m then
+ return #str
+ end
+ return forward+1
+ end
+ local setvector=function(str,position,name,size,filename)
+ local forward=position+tonumber(size)
+ if n>=m then
+ return #str
+ elseif forward<#str then
+ if n==0 and name~=".notdef" then
+ report_pfb("reserving .notdef at index 0 in %a",filename)
+ n=n+1
+ end
+ vector[n]=name
+ n=n+1
+ return forward
+ else
+ return #str
+ end
+ end
+ local setshapes=function(str,position,name,size,filename)
+ local forward=position+tonumber(size)
+ local stream=sub(str,position+1,forward)
+ if n>m then
+ return #str
+ elseif forward<#str then
+ if n==0 and name~=".notdef" then
+ report_pfb("reserving .notdef at index 0 in %a",filename)
+ n=n+1
+ end
+ vector[n]=name
+ n=n+1
+ chars [n]=decrypt(stream,4330,4)
+ return forward
+ else
+ return #str
+ end
+ end
+ local p_rd=spacing*(P("RD")+P("-|"))
+ local p_np=spacing*(P("NP")+P("|"))
+ local p_nd=spacing*(P("ND")+P("|"))
+ local p_filterroutines=
+ (1-subroutines)^0*subroutines*spaces*Cmt(cardinal,initialize)*(Cmt(cardinal*spaces*cardinal*p_rd*Carg(1),setroutine)*p_np+(1-p_nd))^1
+ local p_filtershapes=
+ (1-charstrings)^0*charstrings*spaces*Cmt(cardinal,initialize)*(Cmt(name*spaces*cardinal*p_rd*Carg(1),setshapes)*p_nd+P(1))^1
+ local p_filternames=Ct (
+ (1-charstrings)^0*charstrings*spaces*Cmt(cardinal,initialize)*(Cmt(name*spaces*cardinal*Carg(1),setvector)+P(1))^1
+ )
+ local p_filterencoding=(1-encoding)^0*encoding*spaces*digits*spaces*array*(1-dup)^0*Cf(
+ Ct("")*Cg(spacing*dup*spaces*cardinal*spaces*name*spaces*put)^1
+,rawset)
+ local key=spacing*P("/")*R("az","AZ")
+ local str=spacing*Cs { (P("(")/"")*((1-P("\\(")-P("\\)")-S("()"))+V(1))^0*(P(")")/"") }
+ local num=spacing*(R("09")+S("+-."))^1/tonumber
+ local arr=spacing*Ct (S("[{")*(num)^0*spacing*S("]}"))
+ local boo=spacing*(P("true")*Cc(true)+P("false")*Cc(false))
+ local nam=spacing*P("/")*Cs(R("az","AZ")^1)
+ local p_filtermetadata=(
+ P("/")*Carg(1)*((
+ C("version")*str+C("Copyright")*str+C("Notice")*str+C("FullName")*str+C("FamilyName")*str+C("Weight")*str+C("ItalicAngle")*num+C("isFixedPitch")*boo+C("UnderlinePosition")*num+C("UnderlineThickness")*num+C("FontName")*nam+C("FontMatrix")*arr+C("FontBBox")*arr
+ ) )/function(t,k,v) t[lower(k)]=v end+P(1)
+ )^0*Carg(1)
+ local function loadpfbvector(filename,shapestoo,streams)
+ local data=io.loaddata(resolvers.findfile(filename))
+ if not data then
+ report_pfb("no data in %a",filename)
+ return
+ end
+ if not (find(data,"!PS-AdobeFont-",1,true) or find(data,"%!FontType1",1,true)) then
+ report_pfb("no font in %a",filename)
+ return
+ end
+ local ascii,binary=match(data,"(.*)eexec%s+......(.*)")
+ if not binary then
+ report_pfb("no binary data in %a",filename)
+ return
+ end
+ binary=decrypt(binary,55665,4)
+ local names={}
+ local encoding=lpegmatch(p_filterencoding,ascii)
+ local metadata=lpegmatch(p_filtermetadata,ascii,1,{})
+ local glyphs={}
+ routines,vector,chars={},{},{}
+ if shapestoo or streams then
+ lpegmatch(p_filterroutines,binary,1,filename)
+ lpegmatch(p_filtershapes,binary,1,filename)
+ local data={
+ dictionaries={
+ {
+ charstrings=chars,
+ charset=vector,
+ subroutines=routines,
+ }
+ },
+ }
+ fonts.handlers.otf.readers.parsecharstrings(false,data,glyphs,true,"cff",streams,true)
+ else
+ lpegmatch(p_filternames,binary,1,filename)
+ end
+ names=vector
+ routines,vector,chars=nil,nil,nil
+ return names,encoding,glyphs,metadata
+ end
+ local pfb=handlers.pfb or {}
+ handlers.pfb=pfb
+ pfb.loadvector=loadpfbvector
+ get_indexes=function(data,pfbname)
+ local vector=loadpfbvector(pfbname)
+ if vector then
+ local characters=data.characters
+ if trace_loading then
+ report_afm("getting index data from %a",pfbname)
+ end
+ for index=0,#vector do
+ local name=vector[index]
+ local char=characters[name]
+ if char then
+ if trace_indexing then
+ report_afm("glyph %a has index %a",name,index)
+ end
+ char.index=index
+ else
+ if trace_indexing then
+ report_afm("glyph %a has index %a but no data",name,index)
+ end
+ end
+ end
+ end
+ end
+ get_shapes=function(pfbname)
+ local vector,encoding,glyphs=loadpfbvector(pfbname,true)
+ return glyphs
+ end
+end
+local spacer=patterns.spacer
+local whitespace=patterns.whitespace
+local lineend=patterns.newline
+local spacing=spacer^0
+local number=spacing*S("+-")^-1*(R("09")+S("."))^1/tonumber
+local name=spacing*C((1-whitespace)^1)
+local words=spacing*((1-lineend)^1/strip)
+local rest=(1-lineend)^0
+local fontdata=Carg(1)
+local semicolon=spacing*P(";")
+local plus=spacing*P("plus")*number
+local minus=spacing*P("minus")*number
+local function addkernpair(data,one,two,value)
+ local chr=data.characters[one]
+ if chr then
+ local kerns=chr.kerns
+ if kerns then
+ kerns[two]=tonumber(value)
+ else
+ chr.kerns={ [two]=tonumber(value) }
+ end
+ end
+end
+local p_kernpair=(fontdata*P("KPX")*name*name*number)/addkernpair
+local chr=false
+local ind=0
+local function start(data,version)
+ data.metadata.afmversion=version
+ ind=0
+ chr={}
+end
+local function stop()
+ ind=0
+ chr=false
+end
+local function setindex(i)
+ if i<0 then
+ ind=ind+1
+ else
+ ind=i
+ end
+ chr={
+ index=ind
+ }
+end
+local function setwidth(width)
+ chr.width=width
+end
+local function setname(data,name)
+ data.characters[name]=chr
+end
+local function setboundingbox(boundingbox)
+ chr.boundingbox=boundingbox
+end
+local function setligature(plus,becomes)
+ local ligatures=chr.ligatures
+ if ligatures then
+ ligatures[plus]=becomes
+ else
+ chr.ligatures={ [plus]=becomes }
+ end
+end
+local p_charmetric=((
+ P("C")*number/setindex+P("WX")*number/setwidth+P("N")*fontdata*name/setname+P("B")*Ct((number)^4)/setboundingbox+P("L")*(name)^2/setligature
+ )*semicolon )^1
+local p_charmetrics=P("StartCharMetrics")*number*(p_charmetric+(1-P("EndCharMetrics")))^0*P("EndCharMetrics")
+local p_kernpairs=P("StartKernPairs")*number*(p_kernpair+(1-P("EndKernPairs" )))^0*P("EndKernPairs" )
+local function set_1(data,key,a) data.metadata[lower(key)]=a end
+local function set_2(data,key,a,b) data.metadata[lower(key)]={ a,b } end
+local function set_3(data,key,a,b,c) data.metadata[lower(key)]={ a,b,c } end
+local p_parameters=P(false)+fontdata*((P("FontName")+P("FullName")+P("FamilyName"))/lower)*words/function(data,key,value)
+ data.metadata[key]=value
+ end+fontdata*((P("Weight")+P("Version"))/lower)*name/function(data,key,value)
+ data.metadata[key]=value
+ end+fontdata*P("IsFixedPitch")*name/function(data,pitch)
+ data.metadata.monospaced=toboolean(pitch,true)
+ end+fontdata*P("FontBBox")*Ct(number^4)/function(data,boundingbox)
+ data.metadata.boundingbox=boundingbox
+ end+fontdata*((P("CharWidth")+P("CapHeight")+P("XHeight")+P("Descender")+P("Ascender")+P("ItalicAngle"))/lower)*number/function(data,key,value)
+ data.metadata[key]=value
+ end+P("Comment")*spacing*(P(false)+(fontdata*C("DESIGNSIZE")*number*rest)/set_1
++(fontdata*C("TFM designsize")*number*rest)/set_1+(fontdata*C("DesignSize")*number*rest)/set_1+(fontdata*C("CODINGSCHEME")*words*rest)/set_1
++(fontdata*C("CHECKSUM")*number*words*rest)/set_1
++(fontdata*C("SPACE")*number*plus*minus*rest)/set_3
++(fontdata*C("QUAD")*number*rest)/set_1
++(fontdata*C("EXTRASPACE")*number*rest)/set_1
++(fontdata*C("NUM")*number*number*number*rest)/set_3
++(fontdata*C("DENOM")*number*number*rest)/set_2
++(fontdata*C("SUP")*number*number*number*rest)/set_3
++(fontdata*C("SUB")*number*number*rest)/set_2
++(fontdata*C("SUPDROP")*number*rest)/set_1
++(fontdata*C("SUBDROP")*number*rest)/set_1
++(fontdata*C("DELIM")*number*number*rest)/set_2
++(fontdata*C("AXISHEIGHT")*number*rest)/set_1
+ )
+local fullparser=(P("StartFontMetrics")*fontdata*name/start )*(p_charmetrics+p_kernpairs+p_parameters+(1-P("EndFontMetrics")) )^0*(P("EndFontMetrics")/stop )
+local infoparser=(P("StartFontMetrics")*fontdata*name/start )*(p_parameters+(1-P("EndFontMetrics")) )^0*(P("EndFontMetrics")/stop )
+local function read(filename,parser)
+ local afmblob=io.loaddata(filename)
+ if afmblob then
+ local data={
+ resources={
+ filename=resolvers.unresolve(filename),
+ version=afm.version,
+ creator="context mkiv",
+ },
+ properties={
+ hasitalics=false,
+ },
+ goodies={},
+ metadata={
+ filename=file.removesuffix(file.basename(filename))
+ },
+ characters={
+ },
+ descriptions={
+ },
+ }
+ if trace_loading then
+ report_afm("parsing afm file %a",filename)
+ end
+ lpegmatch(parser,afmblob,1,data)
+ return data
+ else
+ if trace_loading then
+ report_afm("no valid afm file %a",filename)
+ end
+ return nil
+ end
+end
+function readers.loadfont(afmname,pfbname)
+ local data=read(resolvers.findfile(afmname),fullparser)
+ if data then
+ if not pfbname or pfbname=="" then
+ pfbname=resolvers.findfile(file.replacesuffix(file.nameonly(afmname),"pfb"))
+ end
+ if pfbname and pfbname~="" then
+ data.resources.filename=resolvers.unresolve(pfbname)
+ get_indexes(data,pfbname)
+ return data
+ else
+ report_afm("no pfb file for %a",afmname)
+ end
+ end
+end
+function readers.loadshapes(filename)
+ local fullname=resolvers.findfile(filename) or ""
+ if fullname=="" then
+ return {
+ filename="not found: "..filename,
+ glyphs={}
+ }
+ else
+ return {
+ filename=fullname,
+ format="opentype",
+ glyphs=get_shapes(fullname) or {},
+ units=1000,
+ }
+ end
+end
+function readers.getinfo(filename)
+ local data=read(resolvers.findfile(filename),infoparser)
+ if data then
+ return data.metadata
+ end
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-one']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local fonts,logs,trackers,containers,resolvers=fonts,logs,trackers,containers,resolvers
+local next,type,tonumber,rawget=next,type,tonumber,rawget
+local match,gsub=string.match,string.gsub
+local abs=math.abs
+local P,S,R,Cmt,C,Ct,Cs,Carg=lpeg.P,lpeg.S,lpeg.R,lpeg.Cmt,lpeg.C,lpeg.Ct,lpeg.Cs,lpeg.Carg
+local lpegmatch,patterns=lpeg.match,lpeg.patterns
+local sortedhash=table.sortedhash
+local trace_features=false trackers.register("afm.features",function(v) trace_features=v end)
+local trace_indexing=false trackers.register("afm.indexing",function(v) trace_indexing=v end)
+local trace_loading=false trackers.register("afm.loading",function(v) trace_loading=v end)
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local report_afm=logs.reporter("fonts","afm loading")
+local setmetatableindex=table.setmetatableindex
+local derivetable=table.derive
+local findbinfile=resolvers.findbinfile
+local privateoffset=fonts.constructors and fonts.constructors.privateoffset or 0xF0000
+local definers=fonts.definers
+local readers=fonts.readers
+local constructors=fonts.constructors
+local afm=constructors.handlers.afm
+local pfb=constructors.handlers.pfb
+local otf=fonts.handlers.otf
+local otfreaders=otf.readers
+local otfenhancers=otf.enhancers
+local afmfeatures=constructors.features.afm
+local registerafmfeature=afmfeatures.register
+local afmenhancers=constructors.enhancers.afm
+local registerafmenhancer=afmenhancers.register
+afm.version=1.513
+afm.cache=containers.define("fonts","one",afm.version,true)
+afm.autoprefixed=true
+afm.helpdata={}
+afm.syncspace=true
+local overloads=fonts.mappings.overloads
+local applyruntimefixes=fonts.treatments and fonts.treatments.applyfixes
+function afm.load(filename)
+ filename=resolvers.findfile(filename,'afm') or ""
+ if filename~="" and not fonts.names.ignoredfile(filename) then
+ local name=file.removesuffix(file.basename(filename))
+ local data=containers.read(afm.cache,name)
+ local attr=lfs.attributes(filename)
+ local size=attr and attr.size or 0
+ local time=attr and attr.modification or 0
+ local pfbfile=file.replacesuffix(name,"pfb")
+ local pfbname=resolvers.findfile(pfbfile,"pfb") or ""
+ if pfbname=="" then
+ pfbname=resolvers.findfile(file.basename(pfbfile),"pfb") or ""
+ end
+ local pfbsize=0
+ local pfbtime=0
+ if pfbname~="" then
+ local attr=lfs.attributes(pfbname)
+ pfbsize=attr.size or 0
+ pfbtime=attr.modification or 0
+ end
+ if not data or data.size~=size or data.time~=time or data.pfbsize~=pfbsize or data.pfbtime~=pfbtime then
+ report_afm("reading %a",filename)
+ data=afm.readers.loadfont(filename,pfbname)
+ if data then
+ afmenhancers.apply(data,filename)
+ fonts.mappings.addtounicode(data,filename)
+ otfreaders.stripredundant(data)
+ otfreaders.pack(data)
+ data.size=size
+ data.time=time
+ data.pfbsize=pfbsize
+ data.pfbtime=pfbtime
+ report_afm("saving %a in cache",name)
+ data=containers.write(afm.cache,name,data)
+ data=containers.read(afm.cache,name)
+ end
+ end
+ if data then
+ otfreaders.unpack(data)
+ otfreaders.expand(data)
+ otfreaders.addunicodetable(data)
+ otfenhancers.apply(data,filename,data)
+ if applyruntimefixes then
+ applyruntimefixes(filename,data)
+ end
+ end
+ return data
+ end
+end
+local uparser=fonts.mappings.makenameparser()
+local function enhance_unify_names(data,filename)
+ local unicodevector=fonts.encodings.agl.unicodes
+ local unicodes={}
+ local names={}
+ local private=data.private or privateoffset
+ local descriptions=data.descriptions
+ for name,blob in sortedhash(data.characters) do
+ local code=unicodevector[name]
+ if not code then
+ code=lpegmatch(uparser,name)
+ if type(code)~="number" then
+ code=private
+ private=private+1
+ report_afm("assigning private slot %U for unknown glyph name %a",code,name)
+ end
+ end
+ local index=blob.index
+ unicodes[name]=code
+ names[name]=index
+ blob.name=name
+ descriptions[code]={
+ boundingbox=blob.boundingbox,
+ width=blob.width,
+ kerns=blob.kerns,
+ index=index,
+ name=name,
+ }
+ end
+ for unicode,description in next,descriptions do
+ local kerns=description.kerns
+ if kerns then
+ local krn={}
+ for name,kern in next,kerns do
+ local unicode=unicodes[name]
+ if unicode then
+ krn[unicode]=kern
+ else
+ end
+ end
+ description.kerns=krn
+ end
+ end
+ data.characters=nil
+ data.private=private
+ local resources=data.resources
+ local filename=resources.filename or file.removesuffix(file.basename(filename))
+ resources.filename=resolvers.unresolve(filename)
+ resources.unicodes=unicodes
+ resources.marks={}
+end
+local everywhere={ ["*"]={ ["*"]=true } }
+local noflags={ false,false,false,false }
+local function enhance_normalize_features(data)
+ local ligatures=setmetatableindex("table")
+ local kerns=setmetatableindex("table")
+ local extrakerns=setmetatableindex("table")
+ for u,c in next,data.descriptions do
+ local l=c.ligatures
+ local k=c.kerns
+ local e=c.extrakerns
+ if l then
+ ligatures[u]=l
+ for u,v in next,l do
+ l[u]={ ligature=v }
+ end
+ c.ligatures=nil
+ end
+ if k then
+ kerns[u]=k
+ for u,v in next,k do
+ k[u]=v
+ end
+ c.kerns=nil
+ end
+ if e then
+ extrakerns[u]=e
+ for u,v in next,e do
+ e[u]=v
+ end
+ c.extrakerns=nil
+ end
+ end
+ local features={
+ gpos={},
+ gsub={},
+ }
+ local sequences={
+ }
+ if next(ligatures) then
+ features.gsub.liga=everywhere
+ data.properties.hasligatures=true
+ sequences[#sequences+1]={
+ features={
+ liga=everywhere,
+ },
+ flags=noflags,
+ name="s_s_0",
+ nofsteps=1,
+ order={ "liga" },
+ type="gsub_ligature",
+ steps={
+ {
+ coverage=ligatures,
+ },
+ },
+ }
+ end
+ if next(kerns) then
+ features.gpos.kern=everywhere
+ data.properties.haskerns=true
+ sequences[#sequences+1]={
+ features={
+ kern=everywhere,
+ },
+ flags=noflags,
+ name="p_s_0",
+ nofsteps=1,
+ order={ "kern" },
+ type="gpos_pair",
+ steps={
+ {
+ format="kern",
+ coverage=kerns,
+ },
+ },
+ }
+ end
+ if next(extrakerns) then
+ features.gpos.extrakerns=everywhere
+ data.properties.haskerns=true
+ sequences[#sequences+1]={
+ features={
+ extrakerns=everywhere,
+ },
+ flags=noflags,
+ name="p_s_1",
+ nofsteps=1,
+ order={ "extrakerns" },
+ type="gpos_pair",
+ steps={
+ {
+ format="kern",
+ coverage=extrakerns,
+ },
+ },
+ }
+ end
+ data.resources.features=features
+ data.resources.sequences=sequences
+end
+local function enhance_fix_names(data)
+ for k,v in next,data.descriptions do
+ local n=v.name
+ local r=overloads[n]
+ if r then
+ local name=r.name
+ if trace_indexing then
+ report_afm("renaming characters %a to %a",n,name)
+ end
+ v.name=name
+ v.unicode=r.unicode
+ end
+ end
+end
+local addthem=function(rawdata,ligatures)
+ if ligatures then
+ local descriptions=rawdata.descriptions
+ local resources=rawdata.resources
+ local unicodes=resources.unicodes
+ for ligname,ligdata in next,ligatures do
+ local one=descriptions[unicodes[ligname]]
+ if one then
+ for _,pair in next,ligdata do
+ local two=unicodes[pair[1]]
+ local three=unicodes[pair[2]]
+ if two and three then
+ local ol=one.ligatures
+ if ol then
+ if not ol[two] then
+ ol[two]=three
+ end
+ else
+ one.ligatures={ [two]=three }
+ end
+ end
+ end
+ end
+ end
+ end
+end
+local function enhance_add_ligatures(rawdata)
+ addthem(rawdata,afm.helpdata.ligatures)
+end
+local function enhance_add_extra_kerns(rawdata)
+ local descriptions=rawdata.descriptions
+ local resources=rawdata.resources
+ local unicodes=resources.unicodes
+ local function do_it_left(what)
+ if what then
+ for unicode,description in next,descriptions do
+ local kerns=description.kerns
+ if kerns then
+ local extrakerns
+ for complex,simple in next,what do
+ complex=unicodes[complex]
+ simple=unicodes[simple]
+ if complex and simple then
+ local ks=kerns[simple]
+ if ks and not kerns[complex] then
+ if extrakerns then
+ extrakerns[complex]=ks
+ else
+ extrakerns={ [complex]=ks }
+ end
+ end
+ end
+ end
+ if extrakerns then
+ description.extrakerns=extrakerns
+ end
+ end
+ end
+ end
+ end
+ local function do_it_copy(what)
+ if what then
+ for complex,simple in next,what do
+ complex=unicodes[complex]
+ simple=unicodes[simple]
+ if complex and simple then
+ local complexdescription=descriptions[complex]
+ if complexdescription then
+ local simpledescription=descriptions[complex]
+ if simpledescription then
+ local extrakerns
+ local kerns=simpledescription.kerns
+ if kerns then
+ for unicode,kern in next,kerns do
+ if extrakerns then
+ extrakerns[unicode]=kern
+ else
+ extrakerns={ [unicode]=kern }
+ end
+ end
+ end
+ local extrakerns=simpledescription.extrakerns
+ if extrakerns then
+ for unicode,kern in next,extrakerns do
+ if extrakerns then
+ extrakerns[unicode]=kern
+ else
+ extrakerns={ [unicode]=kern }
+ end
+ end
+ end
+ if extrakerns then
+ complexdescription.extrakerns=extrakerns
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ do_it_left(afm.helpdata.leftkerned)
+ do_it_left(afm.helpdata.bothkerned)
+ do_it_copy(afm.helpdata.bothkerned)
+ do_it_copy(afm.helpdata.rightkerned)
+end
+local function adddimensions(data)
+ if data then
+ for unicode,description in next,data.descriptions do
+ local bb=description.boundingbox
+ if bb then
+ local ht=bb[4]
+ local dp=-bb[2]
+ if ht==0 or ht<0 then
+ else
+ description.height=ht
+ end
+ if dp==0 or dp<0 then
+ else
+ description.depth=dp
+ end
+ end
+ end
+ end
+end
+local function copytotfm(data)
+ if data and data.descriptions then
+ local metadata=data.metadata
+ local resources=data.resources
+ local properties=derivetable(data.properties)
+ local descriptions=derivetable(data.descriptions)
+ local goodies=derivetable(data.goodies)
+ local characters={}
+ local parameters={}
+ local unicodes=resources.unicodes
+ for unicode,description in next,data.descriptions do
+ characters[unicode]={}
+ end
+ local filename=constructors.checkedfilename(resources)
+ local fontname=metadata.fontname or metadata.fullname
+ local fullname=metadata.fullname or metadata.fontname
+ local endash=0x2013
+ local emdash=0x2014
+ local space=0x0020
+ local spacer="space"
+ local spaceunits=500
+ local monospaced=metadata.monospaced
+ local charwidth=metadata.charwidth
+ local italicangle=metadata.italicangle
+ local charxheight=metadata.xheight and metadata.xheight>0 and metadata.xheight
+ properties.monospaced=monospaced
+ parameters.italicangle=italicangle
+ parameters.charwidth=charwidth
+ parameters.charxheight=charxheight
+ local d_endash=descriptions[endash]
+ local d_emdash=descriptions[emdash]
+ local d_space=descriptions[space]
+ if not d_space or d_space==0 then
+ d_space=d_endash
+ end
+ if d_space then
+ spaceunits,spacer=d_space.width or 0,"space"
+ end
+ if properties.monospaced then
+ if spaceunits==0 and d_emdash then
+ spaceunits,spacer=d_emdash.width or 0,"emdash"
+ end
+ else
+ if spaceunits==0 and d_endash then
+ spaceunits,spacer=d_emdash.width or 0,"endash"
+ end
+ end
+ if spaceunits==0 and charwidth then
+ spaceunits,spacer=charwidth or 0,"charwidth"
+ end
+ if spaceunits==0 then
+ spaceunits=tonumber(spaceunits) or 500
+ end
+ if spaceunits==0 then
+ spaceunits=500
+ end
+ parameters.slant=0
+ parameters.space=spaceunits
+ parameters.space_stretch=500
+ parameters.space_shrink=333
+ parameters.x_height=400
+ parameters.quad=1000
+ if italicangle and italicangle~=0 then
+ parameters.italicangle=italicangle
+ parameters.italicfactor=math.cos(math.rad(90+italicangle))
+ parameters.slant=- math.tan(italicangle*math.pi/180)
+ end
+ if monospaced then
+ parameters.space_stretch=0
+ parameters.space_shrink=0
+ elseif afm.syncspace then
+ parameters.space_stretch=spaceunits/2
+ parameters.space_shrink=spaceunits/3
+ end
+ parameters.extra_space=parameters.space_shrink
+ if charxheight then
+ parameters.x_height=charxheight
+ else
+ local x=0x0078
+ if x then
+ local x=descriptions[x]
+ if x then
+ parameters.x_height=x.height
+ end
+ end
+ end
+ if metadata.sup then
+ local dummy={ 0,0,0 }
+ parameters[ 1]=metadata.designsize or 0
+ parameters[ 2]=metadata.checksum or 0
+ parameters[ 3],
+ parameters[ 4],
+ parameters[ 5]=unpack(metadata.space or dummy)
+ parameters[ 6]=metadata.quad or 0
+ parameters[ 7]=metadata.extraspace or 0
+ parameters[ 8],
+ parameters[ 9],
+ parameters[10]=unpack(metadata.num or dummy)
+ parameters[11],
+ parameters[12]=unpack(metadata.denom or dummy)
+ parameters[13],
+ parameters[14],
+ parameters[15]=unpack(metadata.sup or dummy)
+ parameters[16],
+ parameters[17]=unpack(metadata.sub or dummy)
+ parameters[18]=metadata.supdrop or 0
+ parameters[19]=metadata.subdrop or 0
+ parameters[20],
+ parameters[21]=unpack(metadata.delim or dummy)
+ parameters[22]=metadata.axisheight or 0
+ end
+ parameters.designsize=(metadata.designsize or 10)*65536
+ parameters.ascender=abs(metadata.ascender or 0)
+ parameters.descender=abs(metadata.descender or 0)
+ parameters.units=1000
+ properties.spacer=spacer
+ properties.encodingbytes=2
+ properties.format=fonts.formats[filename] or "type1"
+ properties.filename=filename
+ properties.fontname=fontname
+ properties.fullname=fullname
+ properties.psname=fullname
+ properties.name=filename or fullname or fontname
+ properties.private=properties.private or data.private or privateoffset
+ if next(characters) then
+ return {
+ characters=characters,
+ descriptions=descriptions,
+ parameters=parameters,
+ resources=resources,
+ properties=properties,
+ goodies=goodies,
+ }
+ end
+ end
+ return nil
+end
+function afm.setfeatures(tfmdata,features)
+ local okay=constructors.initializefeatures("afm",tfmdata,features,trace_features,report_afm)
+ if okay then
+ return constructors.collectprocessors("afm",tfmdata,features,trace_features,report_afm)
+ else
+ return {}
+ end
+end
+local function addtables(data)
+ local resources=data.resources
+ local lookuptags=resources.lookuptags
+ local unicodes=resources.unicodes
+ if not lookuptags then
+ lookuptags={}
+ resources.lookuptags=lookuptags
+ end
+ setmetatableindex(lookuptags,function(t,k)
+ local v=type(k)=="number" and ("lookup "..k) or k
+ t[k]=v
+ return v
+ end)
+ if not unicodes then
+ unicodes={}
+ resources.unicodes=unicodes
+ setmetatableindex(unicodes,function(t,k)
+ setmetatableindex(unicodes,nil)
+ for u,d in next,data.descriptions do
+ local n=d.name
+ if n then
+ t[n]=u
+ end
+ end
+ return rawget(t,k)
+ end)
+ end
+ constructors.addcoreunicodes(unicodes)
+end
+local function afmtotfm(specification)
+ local afmname=specification.filename or specification.name
+ if specification.forced=="afm" or specification.format=="afm" then
+ if trace_loading then
+ report_afm("forcing afm format for %a",afmname)
+ end
+ else
+ local tfmname=findbinfile(afmname,"ofm") or ""
+ if tfmname~="" then
+ if trace_loading then
+ report_afm("fallback from afm to tfm for %a",afmname)
+ end
+ return
+ end
+ end
+ if afmname~="" then
+ local features=constructors.checkedfeatures("afm",specification.features.normal)
+ specification.features.normal=features
+ constructors.hashinstance(specification,true)
+ specification=definers.resolve(specification)
+ local cache_id=specification.hash
+ local tfmdata=containers.read(constructors.cache,cache_id)
+ if not tfmdata then
+ local rawdata=afm.load(afmname)
+ if rawdata and next(rawdata) then
+ addtables(rawdata)
+ adddimensions(rawdata)
+ tfmdata=copytotfm(rawdata)
+ if tfmdata and next(tfmdata) then
+ local shared=tfmdata.shared
+ if not shared then
+ shared={}
+ tfmdata.shared=shared
+ end
+ shared.rawdata=rawdata
+ shared.dynamics={}
+ tfmdata.changed={}
+ shared.features=features
+ shared.processes=afm.setfeatures(tfmdata,features)
+ end
+ elseif trace_loading then
+ report_afm("no (valid) afm file found with name %a",afmname)
+ end
+ tfmdata=containers.write(constructors.cache,cache_id,tfmdata)
+ end
+ return tfmdata
+ end
+end
+local function read_from_afm(specification)
+ local tfmdata=afmtotfm(specification)
+ if tfmdata then
+ tfmdata.properties.name=specification.name
+ tfmdata=constructors.scale(tfmdata,specification)
+ local allfeatures=tfmdata.shared.features or specification.features.normal
+ constructors.applymanipulators("afm",tfmdata,allfeatures,trace_features,report_afm)
+ fonts.loggers.register(tfmdata,'afm',specification)
+ end
+ return tfmdata
+end
+registerafmfeature {
+ name="mode",
+ description="mode",
+ initializers={
+ base=otf.modeinitializer,
+ node=otf.modeinitializer,
+ }
+}
+registerafmfeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ node=otf.nodemodeinitializer,
+ base=otf.basemodeinitializer,
+ },
+ processors={
+ node=otf.featuresprocessor,
+ }
+}
+fonts.formats.afm="type1"
+fonts.formats.pfb="type1"
+local function check_afm(specification,fullname)
+ local foundname=findbinfile(fullname,'afm') or ""
+ if foundname=="" then
+ foundname=fonts.names.getfilename(fullname,"afm") or ""
+ end
+ if fullname and foundname=="" and afm.autoprefixed then
+ local encoding,shortname=match(fullname,"^(.-)%-(.*)$")
+ if encoding and shortname and fonts.encodings.known[encoding] then
+ shortname=findbinfile(shortname,'afm') or ""
+ if shortname~="" then
+ foundname=shortname
+ if trace_defining then
+ report_afm("stripping encoding prefix from filename %a",afmname)
+ end
+ end
+ end
+ end
+ if foundname~="" then
+ specification.filename=foundname
+ specification.format="afm"
+ return read_from_afm(specification)
+ end
+end
+function readers.afm(specification,method)
+ local fullname=specification.filename or ""
+ local tfmdata=nil
+ if fullname=="" then
+ local forced=specification.forced or ""
+ if forced~="" then
+ tfmdata=check_afm(specification,specification.name.."."..forced)
+ end
+ if not tfmdata then
+ local check_tfm=readers.check_tfm
+ method=(check_tfm and (method or definers.method or "afm or tfm")) or "afm"
+ if method=="tfm" then
+ tfmdata=check_tfm(specification,specification.name)
+ elseif method=="afm" then
+ tfmdata=check_afm(specification,specification.name)
+ elseif method=="tfm or afm" then
+ tfmdata=check_tfm(specification,specification.name) or check_afm(specification,specification.name)
+ else
+ tfmdata=check_afm(specification,specification.name) or check_tfm(specification,specification.name)
+ end
+ end
+ else
+ tfmdata=check_afm(specification,fullname)
+ end
+ return tfmdata
+end
+function readers.pfb(specification,method)
+ local original=specification.specification
+ if trace_defining then
+ report_afm("using afm reader for %a",original)
+ end
+ specification.forced="afm"
+ local function swap(name)
+ local value=specification[swap]
+ if value then
+ specification[swap]=gsub("%.pfb",".afm",1)
+ end
+ end
+ swap("filename")
+ swap("fullname")
+ swap("forcedname")
+ swap("specification")
+ return readers.afm(specification,method)
+end
+registerafmenhancer("unify names",enhance_unify_names)
+registerafmenhancer("add ligatures",enhance_add_ligatures)
+registerafmenhancer("add extra kerns",enhance_add_extra_kerns)
+registerafmenhancer("normalize features",enhance_normalize_features)
+registerafmenhancer("check extra features",otfenhancers.enhance)
+registerafmenhancer("fix names",enhance_fix_names)
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-afk']={
+ version=1.001,
+ comment="companion to font-lib.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files",
+ dataonly=true,
+}
+local allocate=utilities.storage.allocate
+fonts.handlers.afm.helpdata={
+ ligatures=allocate {
+ ['f']={
+ { 'f','ff' },
+ { 'i','fi' },
+ { 'l','fl' },
+ },
+ ['ff']={
+ { 'i','ffi' }
+ },
+ ['fi']={
+ { 'i','fii' }
+ },
+ ['fl']={
+ { 'i','fli' }
+ },
+ ['s']={
+ { 't','st' }
+ },
+ ['i']={
+ { 'j','ij' }
+ },
+ },
+ texligatures=allocate {
+ ['quoteleft']={
+ { 'quoteleft','quotedblleft' }
+ },
+ ['quoteright']={
+ { 'quoteright','quotedblright' }
+ },
+ ['hyphen']={
+ { 'hyphen','endash' }
+ },
+ ['endash']={
+ { 'hyphen','emdash' }
+ }
+ },
+ leftkerned=allocate {
+ AEligature="A",aeligature="a",
+ OEligature="O",oeligature="o",
+ IJligature="I",ijligature="i",
+ AE="A",ae="a",
+ OE="O",oe="o",
+ IJ="I",ij="i",
+ Ssharp="S",ssharp="s",
+ },
+ rightkerned=allocate {
+ AEligature="E",aeligature="e",
+ OEligature="E",oeligature="e",
+ IJligature="J",ijligature="j",
+ AE="E",ae="e",
+ OE="E",oe="e",
+ IJ="J",ij="j",
+ Ssharp="S",ssharp="s",
+ },
+ bothkerned=allocate {
+ Acircumflex="A",acircumflex="a",
+ Ccircumflex="C",ccircumflex="c",
+ Ecircumflex="E",ecircumflex="e",
+ Gcircumflex="G",gcircumflex="g",
+ Hcircumflex="H",hcircumflex="h",
+ Icircumflex="I",icircumflex="i",
+ Jcircumflex="J",jcircumflex="j",
+ Ocircumflex="O",ocircumflex="o",
+ Scircumflex="S",scircumflex="s",
+ Ucircumflex="U",ucircumflex="u",
+ Wcircumflex="W",wcircumflex="w",
+ Ycircumflex="Y",ycircumflex="y",
+ Agrave="A",agrave="a",
+ Egrave="E",egrave="e",
+ Igrave="I",igrave="i",
+ Ograve="O",ograve="o",
+ Ugrave="U",ugrave="u",
+ Ygrave="Y",ygrave="y",
+ Atilde="A",atilde="a",
+ Itilde="I",itilde="i",
+ Otilde="O",otilde="o",
+ Utilde="U",utilde="u",
+ Ntilde="N",ntilde="n",
+ Adiaeresis="A",adiaeresis="a",Adieresis="A",adieresis="a",
+ Ediaeresis="E",ediaeresis="e",Edieresis="E",edieresis="e",
+ Idiaeresis="I",idiaeresis="i",Idieresis="I",idieresis="i",
+ Odiaeresis="O",odiaeresis="o",Odieresis="O",odieresis="o",
+ Udiaeresis="U",udiaeresis="u",Udieresis="U",udieresis="u",
+ Ydiaeresis="Y",ydiaeresis="y",Ydieresis="Y",ydieresis="y",
+ Aacute="A",aacute="a",
+ Cacute="C",cacute="c",
+ Eacute="E",eacute="e",
+ Iacute="I",iacute="i",
+ Lacute="L",lacute="l",
+ Nacute="N",nacute="n",
+ Oacute="O",oacute="o",
+ Racute="R",racute="r",
+ Sacute="S",sacute="s",
+ Uacute="U",uacute="u",
+ Yacute="Y",yacute="y",
+ Zacute="Z",zacute="z",
+ Dstroke="D",dstroke="d",
+ Hstroke="H",hstroke="h",
+ Tstroke="T",tstroke="t",
+ Cdotaccent="C",cdotaccent="c",
+ Edotaccent="E",edotaccent="e",
+ Gdotaccent="G",gdotaccent="g",
+ Idotaccent="I",idotaccent="i",
+ Zdotaccent="Z",zdotaccent="z",
+ Amacron="A",amacron="a",
+ Emacron="E",emacron="e",
+ Imacron="I",imacron="i",
+ Omacron="O",omacron="o",
+ Umacron="U",umacron="u",
+ Ccedilla="C",ccedilla="c",
+ Kcedilla="K",kcedilla="k",
+ Lcedilla="L",lcedilla="l",
+ Ncedilla="N",ncedilla="n",
+ Rcedilla="R",rcedilla="r",
+ Scedilla="S",scedilla="s",
+ Tcedilla="T",tcedilla="t",
+ Ohungarumlaut="O",ohungarumlaut="o",
+ Uhungarumlaut="U",uhungarumlaut="u",
+ Aogonek="A",aogonek="a",
+ Eogonek="E",eogonek="e",
+ Iogonek="I",iogonek="i",
+ Uogonek="U",uogonek="u",
+ Aring="A",aring="a",
+ Uring="U",uring="u",
+ Abreve="A",abreve="a",
+ Ebreve="E",ebreve="e",
+ Gbreve="G",gbreve="g",
+ Ibreve="I",ibreve="i",
+ Obreve="O",obreve="o",
+ Ubreve="U",ubreve="u",
+ Ccaron="C",ccaron="c",
+ Dcaron="D",dcaron="d",
+ Ecaron="E",ecaron="e",
+ Lcaron="L",lcaron="l",
+ Ncaron="N",ncaron="n",
+ Rcaron="R",rcaron="r",
+ Scaron="S",scaron="s",
+ Tcaron="T",tcaron="t",
+ Zcaron="Z",zcaron="z",
+ dotlessI="I",dotlessi="i",
+ dotlessJ="J",dotlessj="j",
+ AEligature="AE",aeligature="ae",AE="AE",ae="ae",
+ OEligature="OE",oeligature="oe",OE="OE",oe="oe",
+ IJligature="IJ",ijligature="ij",IJ="IJ",ij="ij",
+ Lstroke="L",lstroke="l",Lslash="L",lslash="l",
+ Ostroke="O",ostroke="o",Oslash="O",oslash="o",
+ Ssharp="SS",ssharp="ss",
+ Aumlaut="A",aumlaut="a",
+ Eumlaut="E",eumlaut="e",
+ Iumlaut="I",iumlaut="i",
+ Oumlaut="O",oumlaut="o",
+ Uumlaut="U",uumlaut="u",
+ }
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-fonts-tfm']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type=next,type
+local match,format=string.match,string.format
+local concat,sortedhash=table.concat,table.sortedhash
+local idiv=number.idiv
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local trace_features=false trackers.register("tfm.features",function(v) trace_features=v end)
+local report_defining=logs.reporter("fonts","defining")
+local report_tfm=logs.reporter("fonts","tfm loading")
+local findbinfile=resolvers.findbinfile
+local setmetatableindex=table.setmetatableindex
+local fonts=fonts
+local handlers=fonts.handlers
+local helpers=fonts.helpers
+local readers=fonts.readers
+local constructors=fonts.constructors
+local encodings=fonts.encodings
+local tfm=constructors.handlers.tfm
+tfm.version=1.000
+tfm.maxnestingdepth=5
+tfm.maxnestingsize=65536*1024
+local otf=fonts.handlers.otf
+local otfenhancers=otf.enhancers
+local tfmfeatures=constructors.features.tfm
+local registertfmfeature=tfmfeatures.register
+local tfmenhancers=constructors.enhancers.tfm
+local registertfmenhancer=tfmenhancers.register
+local charcommand=helpers.commands.char
+constructors.resolvevirtualtoo=false
+fonts.formats.tfm="type1"
+fonts.formats.ofm="type1"
+function tfm.setfeatures(tfmdata,features)
+ local okay=constructors.initializefeatures("tfm",tfmdata,features,trace_features,report_tfm)
+ if okay then
+ return constructors.collectprocessors("tfm",tfmdata,features,trace_features,report_tfm)
+ else
+ return {}
+ end
+end
+local depth={}
+local loadtfm=font.read_tfm
+local loadvf=font.read_vf
+local function read_from_tfm(specification)
+ local filename=specification.filename
+ local size=specification.size
+ depth[filename]=(depth[filename] or 0)+1
+ if trace_defining then
+ report_defining("loading tfm file %a at size %s",filename,size)
+ end
+ local tfmdata=loadtfm(filename,size)
+ if tfmdata then
+ local features=specification.features and specification.features.normal or {}
+ local features=constructors.checkedfeatures("tfm",features)
+ specification.features.normal=features
+ local newtfmdata=(depth[filename]==1) and tfm.reencode(tfmdata,specification)
+ if newtfmdata then
+ tfmdata=newtfmdata
+ end
+ local resources=tfmdata.resources or {}
+ local properties=tfmdata.properties or {}
+ local parameters=tfmdata.parameters or {}
+ local shared=tfmdata.shared or {}
+ shared.features=features
+ shared.resources=resources
+ properties.name=tfmdata.name
+ properties.fontname=tfmdata.fontname
+ properties.psname=tfmdata.psname
+ properties.fullname=tfmdata.fullname
+ properties.filename=specification.filename
+ properties.format=tfmdata.format or fonts.formats.tfm
+ properties.usedbitmap=tfmdata.usedbitmap
+ tfmdata.properties=properties
+ tfmdata.resources=resources
+ tfmdata.parameters=parameters
+ tfmdata.shared=shared
+ shared.rawdata={ resources=resources }
+ shared.features=features
+ if newtfmdata then
+ if not resources.marks then
+ resources.marks={}
+ end
+ if not resources.sequences then
+ resources.sequences={}
+ end
+ if not resources.features then
+ resources.features={
+ gsub={},
+ gpos={},
+ }
+ end
+ if not tfmdata.changed then
+ tfmdata.changed={}
+ end
+ if not tfmdata.descriptions then
+ tfmdata.descriptions=tfmdata.characters
+ end
+ otf.readers.addunicodetable(tfmdata)
+ tfmenhancers.apply(tfmdata,filename)
+ constructors.applymanipulators("tfm",tfmdata,features,trace_features,report_tfm)
+ otf.readers.unifymissing(tfmdata)
+ fonts.mappings.addtounicode(tfmdata,filename)
+ tfmdata.tounicode=1
+ local tounicode=fonts.mappings.tounicode
+ for unicode,v in next,tfmdata.characters do
+ local u=v.unicode
+ if u then
+ v.tounicode=tounicode(u)
+ end
+ end
+ if tfmdata.usedbitmap then
+ tfm.addtounicode(tfmdata)
+ end
+ end
+ shared.processes=next(features) and tfm.setfeatures(tfmdata,features) or nil
+ if size<0 then
+ size=idiv(65536*-size,100)
+ end
+ parameters.factor=1
+ parameters.units=1000
+ parameters.size=size
+ parameters.slant=parameters.slant or parameters[1] or 0
+ parameters.space=parameters.space or parameters[2] or 0
+ parameters.space_stretch=parameters.space_stretch or parameters[3] or 0
+ parameters.space_shrink=parameters.space_shrink or parameters[4] or 0
+ parameters.x_height=parameters.x_height or parameters[5] or 0
+ parameters.quad=parameters.quad or parameters[6] or 0
+ parameters.extra_space=parameters.extra_space or parameters[7] or 0
+ constructors.enhanceparameters(parameters)
+ properties.private=properties.private or tfmdata.private or privateoffset
+ if newtfmdata then
+ elseif constructors.resolvevirtualtoo then
+ fonts.loggers.register(tfmdata,file.suffix(filename),specification)
+ local vfname=findbinfile(specification.name,'ovf')
+ if vfname and vfname~="" then
+ local vfdata=loadvf(vfname,size)
+ if vfdata then
+ local chars=tfmdata.characters
+ for k,v in next,vfdata.characters do
+ chars[k].commands=v.commands
+ end
+ properties.virtualized=true
+ tfmdata.fonts=vfdata.fonts
+ tfmdata.type="virtual"
+ local fontlist=vfdata.fonts
+ local name=file.nameonly(filename)
+ for i=1,#fontlist do
+ local n=fontlist[i].name
+ local s=fontlist[i].size
+ local d=depth[filename]
+ s=constructors.scaled(s,vfdata.designsize)
+ if d>tfm.maxnestingdepth then
+ report_defining("too deeply nested virtual font %a with size %a, max nesting depth %s",n,s,tfm.maxnestingdepth)
+ fontlist[i]={ id=0 }
+ elseif (d>1) and (s>tfm.maxnestingsize) then
+ report_defining("virtual font %a exceeds size %s",n,s)
+ fontlist[i]={ id=0 }
+ else
+ local t,id=constructors.readanddefine(n,s)
+ fontlist[i]={ id=id }
+ end
+ end
+ end
+ end
+ end
+ properties.haskerns=true
+ properties.hasligatures=true
+ properties.hasitalics=true
+ resources.unicodes={}
+ resources.lookuptags={}
+ depth[filename]=depth[filename]-1
+ return tfmdata
+ else
+ depth[filename]=depth[filename]-1
+ end
+end
+local function check_tfm(specification,fullname)
+ local foundname=findbinfile(fullname,'tfm') or ""
+ if foundname=="" then
+ foundname=findbinfile(fullname,'ofm') or ""
+ end
+ if foundname=="" then
+ foundname=fonts.names.getfilename(fullname,"tfm") or ""
+ end
+ if foundname~="" then
+ specification.filename=foundname
+ specification.format="ofm"
+ return read_from_tfm(specification)
+ elseif trace_defining then
+ report_defining("loading tfm with name %a fails",specification.name)
+ end
+end
+readers.check_tfm=check_tfm
+function readers.tfm(specification)
+ local fullname=specification.filename or ""
+ if fullname=="" then
+ local forced=specification.forced or ""
+ if forced~="" then
+ fullname=specification.name.."."..forced
+ else
+ fullname=specification.name
+ end
+ end
+ return check_tfm(specification,fullname)
+end
+readers.ofm=readers.tfm
+do
+ local outfiles={}
+ local tfmcache=table.setmetatableindex(function(t,tfmdata)
+ local id=font.define(tfmdata)
+ t[tfmdata]=id
+ return id
+ end)
+ local encdone=table.setmetatableindex("table")
+ function tfm.reencode(tfmdata,specification)
+ local features=specification.features
+ if not features then
+ return
+ end
+ local features=features.normal
+ if not features then
+ return
+ end
+ local tfmfile=file.basename(tfmdata.name)
+ local encfile=features.reencode
+ local pfbfile=features.pfbfile
+ local bitmap=features.bitmap
+ if not encfile then
+ return
+ end
+ local pfbfile=outfiles[tfmfile]
+ if pfbfile==nil then
+ if bitmap then
+ pfbfile=false
+ elseif type(pfbfile)~="string" then
+ pfbfile=tfmfile
+ end
+ if type(pfbfile)=="string" then
+ pfbfile=file.addsuffix(pfbfile,"pfb")
+ report_tfm("using type1 shapes from %a for %a",pfbfile,tfmfile)
+ else
+ report_tfm("using bitmap shapes for %a",tfmfile)
+ pfbfile=false
+ end
+ outfiles[tfmfile]=pfbfile
+ end
+ local encoding=false
+ local vector=false
+ if type(pfbfile)=="string" then
+ local pfb=constructors.handlers.pfb
+ if pfb and pfb.loadvector then
+ local v,e=pfb.loadvector(pfbfile)
+ if v then
+ vector=v
+ end
+ if e then
+ encoding=e
+ end
+ end
+ end
+ if type(encfile)=="string" and encfile~="auto" then
+ encoding=fonts.encodings.load(file.addsuffix(encfile,"enc"))
+ if encoding then
+ encoding=encoding.vector
+ end
+ end
+ if not encoding then
+ report_tfm("bad encoding for %a, quitting",tfmfile)
+ return
+ end
+ local unicoding=fonts.encodings.agl and fonts.encodings.agl.unicodes
+ local virtualid=tfmcache[tfmdata]
+ local tfmdata=table.copy(tfmdata)
+ local characters={}
+ local originals=tfmdata.characters
+ local indices={}
+ local parentfont={ "font",1 }
+ local private=tfmdata.privateoffset or constructors.privateoffset
+ local reported=encdone[tfmfile][encfile]
+ local backmap=vector and table.swapped(vector)
+ local done={}
+ for index,name in sortedhash(encoding) do
+ local unicode=unicoding[name]
+ local original=originals[index]
+ if original then
+ if unicode then
+ original.unicode=unicode
+ else
+ unicode=private
+ private=private+1
+ if not reported then
+ report_tfm("glyph %a in font %a with encoding %a gets unicode %U",name,tfmfile,encfile,unicode)
+ end
+ end
+ characters[unicode]=original
+ indices[index]=unicode
+ original.name=name
+ if backmap then
+ original.index=backmap[name]
+ else
+ original.commands={ parentfont,charcommand[index] }
+ original.oindex=index
+ end
+ done[name]=true
+ elseif not done[name] then
+ report_tfm("bad index %a in font %a with name %a",index,tfmfile,name)
+ end
+ end
+ encdone[tfmfile][encfile]=true
+ for k,v in next,characters do
+ local kerns=v.kerns
+ if kerns then
+ local t={}
+ for k,v in next,kerns do
+ local i=indices[k]
+ if i then
+ t[i]=v
+ end
+ end
+ v.kerns=next(t) and t or nil
+ end
+ local ligatures=v.ligatures
+ if ligatures then
+ local t={}
+ for k,v in next,ligatures do
+ local i=indices[k]
+ if i then
+ t[i]=v
+ v.char=indices[v.char]
+ end
+ end
+ v.ligatures=next(t) and t or nil
+ end
+ end
+ tfmdata.fonts={ { id=virtualid } }
+ tfmdata.characters=characters
+ tfmdata.fullname=tfmdata.fullname or tfmdata.name
+ tfmdata.psname=file.nameonly(pfbfile or tfmdata.name)
+ tfmdata.filename=pfbfile
+ tfmdata.encodingbytes=2
+ tfmdata.format="type1"
+ tfmdata.tounicode=1
+ tfmdata.embedding="subset"
+ tfmdata.usedbitmap=bitmap and virtualid
+ tfmdata.private=private
+ return tfmdata
+ end
+end
+do
+ local template=[[
+/CIDInit /ProcSet findresource begin
+ 12 dict begin
+ begincmap
+ /CIDSystemInfo << /Registry (TeX) /Ordering (bitmap-%s) /Supplement 0 >> def
+ /CMapName /TeX-bitmap-%s def
+ /CMapType 2 def
+ 1 begincodespacerange
+ <00> <FF>
+ endcodespacerange
+ %s beginbfchar
+%s
+ endbfchar
+ endcmap
+CMapName currentdict /CMap defineresource pop end
+end
+end
+]]
+ local flushstreamobject=lpdf and lpdf.flushstreamobject
+ local setfontattributes=lpdf and lpdf.setfontattributes
+ if not flushstreamobject then
+ flushstreamobject=function(data)
+ return pdf.obj { immediate=true,type="stream",string=data }
+ end
+ end
+ if not setfontattributes then
+ setfontattributes=function(id,data)
+ return pdf.setfontattributes(id,data)
+ end
+ end
+ function tfm.addtounicode(tfmdata)
+ local id=tfmdata.usedbitmap
+ local map={}
+ local char={}
+ for k,v in next,tfmdata.characters do
+ local index=v.oindex
+ local tounicode=v.tounicode
+ if index and tounicode then
+ map[index]=tounicode
+ end
+ end
+ for k,v in sortedhash(map) do
+ char[#char+1]=format("<%02X> <%s>",k,v)
+ end
+ char=concat(char,"\n")
+ local stream=format(template,id,id,#char,char)
+ local reference=flushstreamobject(stream,nil,true)
+ setfontattributes(id,format("/ToUnicode %i 0 R",reference))
+ end
+end
+do
+ local everywhere={ ["*"]={ ["*"]=true } }
+ local noflags={ false,false,false,false }
+ local function enhance_normalize_features(data)
+ local ligatures=setmetatableindex("table")
+ local kerns=setmetatableindex("table")
+ local characters=data.characters
+ for u,c in next,characters do
+ local l=c.ligatures
+ local k=c.kerns
+ if l then
+ ligatures[u]=l
+ for u,v in next,l do
+ l[u]={ ligature=v.char }
+ end
+ c.ligatures=nil
+ end
+ if k then
+ kerns[u]=k
+ for u,v in next,k do
+ k[u]=v
+ end
+ c.kerns=nil
+ end
+ end
+ for u,l in next,ligatures do
+ for k,v in next,l do
+ local vl=v.ligature
+ local dl=ligatures[vl]
+ if dl then
+ for kk,vv in next,dl do
+ v[kk]=vv
+ end
+ end
+ end
+ end
+ local features={
+ gpos={},
+ gsub={},
+ }
+ local sequences={
+ }
+ if next(ligatures) then
+ features.gsub.liga=everywhere
+ data.properties.hasligatures=true
+ sequences[#sequences+1]={
+ features={
+ liga=everywhere,
+ },
+ flags=noflags,
+ name="s_s_0",
+ nofsteps=1,
+ order={ "liga" },
+ type="gsub_ligature",
+ steps={
+ {
+ coverage=ligatures,
+ },
+ },
+ }
+ end
+ if next(kerns) then
+ features.gpos.kern=everywhere
+ data.properties.haskerns=true
+ sequences[#sequences+1]={
+ features={
+ kern=everywhere,
+ },
+ flags=noflags,
+ name="p_s_0",
+ nofsteps=1,
+ order={ "kern" },
+ type="gpos_pair",
+ steps={
+ {
+ format="kern",
+ coverage=kerns,
+ },
+ },
+ }
+ end
+ data.resources.features=features
+ data.resources.sequences=sequences
+ data.shared.resources=data.shared.resources or resources
+ end
+ registertfmenhancer("normalize features",enhance_normalize_features)
+ registertfmenhancer("check extra features",otfenhancers.enhance)
+end
+registertfmfeature {
+ name="mode",
+ description="mode",
+ initializers={
+ base=otf.modeinitializer,
+ node=otf.modeinitializer,
+ }
+}
+registertfmfeature {
+ name="features",
+ description="features",
+ default=true,
+ initializers={
+ base=otf.basemodeinitializer,
+ node=otf.nodemodeinitializer,
+ },
+ processors={
+ node=otf.featuresprocessor,
+ }
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-lua']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end)
+local report_lua=logs.reporter("fonts","lua loading")
+local fonts=fonts
+local readers=fonts.readers
+fonts.formats.lua="lua"
+local function check_lua(specification,fullname)
+ local fullname=resolvers.findfile(fullname) or ""
+ if fullname~="" then
+ local loader=loadfile(fullname)
+ loader=loader and loader()
+ return loader and loader(specification)
+ end
+end
+readers.check_lua=check_lua
+function readers.lua(specification)
+ local original=specification.specification
+ if trace_defining then
+ report_lua("using lua reader for %a",original)
+ end
+ local fullname=specification.filename or ""
+ if fullname=="" then
+ local forced=specification.forced or ""
+ if forced~="" then
+ fullname=specification.name.."."..forced
+ else
+ fullname=specification.name
+ end
+ end
+ return check_lua(specification,fullname)
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-def']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local lower,gsub=string.lower,string.gsub
+local tostring,next=tostring,next
+local lpegmatch=lpeg.match
+local suffixonly,removesuffix,basename=file.suffix,file.removesuffix,file.basename
+local formatters=string.formatters
+local sortedhash,sortedkeys=table.sortedhash,table.sortedkeys
+local allocate=utilities.storage.allocate
+local trace_defining=false trackers .register("fonts.defining",function(v) trace_defining=v end)
+local directive_embedall=false directives.register("fonts.embedall",function(v) directive_embedall=v end)
+trackers.register("fonts.loading","fonts.defining","otf.loading","afm.loading","tfm.loading")
+local report_defining=logs.reporter("fonts","defining")
+local fonts=fonts
+local fontdata=fonts.hashes.identifiers
+local readers=fonts.readers
+local definers=fonts.definers
+local specifiers=fonts.specifiers
+local constructors=fonts.constructors
+local fontgoodies=fonts.goodies
+readers.sequence=allocate { 'otf','ttf','afm','tfm','lua' }
+local variants=allocate()
+specifiers.variants=variants
+definers.methods=definers.methods or {}
+local internalized=allocate()
+local lastdefined=nil
+local loadedfonts=constructors.loadedfonts
+local designsizes=constructors.designsizes
+local resolvefile=fontgoodies and fontgoodies.filenames and fontgoodies.filenames.resolve or function(s) return s end
+local function makespecification(specification,lookup,name,sub,method,detail,size)
+ size=size or 655360
+ if not lookup or lookup=="" then
+ lookup=definers.defaultlookup
+ end
+ if trace_defining then
+ report_defining("specification %a, lookup %a, name %a, sub %a, method %a, detail %a",
+ specification,lookup,name,sub,method,detail)
+ end
+ local t={
+ lookup=lookup,
+ specification=specification,
+ size=size,
+ name=name,
+ sub=sub,
+ method=method,
+ detail=detail,
+ resolved="",
+ forced="",
+ features={},
+ }
+ return t
+end
+definers.makespecification=makespecification
+if context then
+
+--removed
+
+end
+definers.resolvers=definers.resolvers or {}
+local resolvers=definers.resolvers
+function resolvers.file(specification)
+ local name=resolvefile(specification.name)
+ local suffix=lower(suffixonly(name))
+ if fonts.formats[suffix] then
+ specification.forced=suffix
+ specification.forcedname=name
+ specification.name=removesuffix(name)
+ else
+ specification.name=name
+ end
+end
+function resolvers.name(specification)
+ local resolve=fonts.names.resolve
+ if resolve then
+ local resolved,sub,subindex,instance=resolve(specification.name,specification.sub,specification)
+ if resolved then
+ specification.resolved=resolved
+ specification.sub=sub
+ specification.subindex=subindex
+ if instance then
+ specification.instance=instance
+ local features=specification.features
+ if not features then
+ features={}
+ specification.features=features
+ end
+ local normal=features.normal
+ if not normal then
+ normal={}
+ features.normal=normal
+ end
+ normal.instance=instance
+ end
+ local suffix=lower(suffixonly(resolved))
+ if fonts.formats[suffix] then
+ specification.forced=suffix
+ specification.forcedname=resolved
+ specification.name=removesuffix(resolved)
+ else
+ specification.name=resolved
+ end
+ end
+ else
+ resolvers.file(specification)
+ end
+end
+function resolvers.spec(specification)
+ local resolvespec=fonts.names.resolvespec
+ if resolvespec then
+ local resolved,sub,subindex=resolvespec(specification.name,specification.sub,specification)
+ if resolved then
+ specification.resolved=resolved
+ specification.sub=sub
+ specification.subindex=subindex
+ specification.forced=lower(suffixonly(resolved))
+ specification.forcedname=resolved
+ specification.name=removesuffix(resolved)
+ end
+ else
+ resolvers.name(specification)
+ end
+end
+function definers.resolve(specification)
+ if not specification.resolved or specification.resolved=="" then
+ local r=resolvers[specification.lookup]
+ if r then
+ r(specification)
+ end
+ end
+ if specification.forced=="" then
+ specification.forced=nil
+ specification.forcedname=nil
+ end
+ specification.hash=lower(specification.name..' @ '..constructors.hashfeatures(specification))
+ if specification.sub and specification.sub~="" then
+ specification.hash=specification.sub..' @ '..specification.hash
+ end
+ return specification
+end
+function definers.applypostprocessors(tfmdata)
+ local postprocessors=tfmdata.postprocessors
+ if postprocessors then
+ local properties=tfmdata.properties
+ for i=1,#postprocessors do
+ local extrahash=postprocessors[i](tfmdata)
+ if type(extrahash)=="string" and extrahash~="" then
+ extrahash=gsub(lower(extrahash),"[^a-z]","-")
+ properties.fullname=formatters["%s-%s"](properties.fullname,extrahash)
+ end
+ end
+ end
+ return tfmdata
+end
+local function checkembedding(tfmdata)
+ local properties=tfmdata.properties
+ local embedding
+ if directive_embedall then
+ embedding="full"
+ elseif properties and properties.filename and constructors.dontembed[properties.filename] then
+ embedding="no"
+ else
+ embedding="subset"
+ end
+ if properties then
+ properties.embedding=embedding
+ else
+ tfmdata.properties={ embedding=embedding }
+ end
+ tfmdata.embedding=embedding
+end
+local function checkfeatures(tfmdata)
+ local resources=tfmdata.resources
+ local shared=tfmdata.shared
+ if resources and shared then
+ local features=resources.features
+ local usedfeatures=shared.features
+ if features and usedfeatures then
+ local usedlanguage=usedfeatures.language or "dflt"
+ local usedscript=usedfeatures.script or "dflt"
+ local function check(what)
+ if what then
+ local foundlanguages={}
+ for feature,scripts in next,what do
+ if usedscript=="auto" or scripts["*"] then
+ elseif not scripts[usedscript] then
+ else
+ for script,languages in next,scripts do
+ if languages["*"] then
+ elseif context and not languages[usedlanguage] then
+ report_defining("font %!font:name!, feature %a, script %a, no language %a",
+ tfmdata,feature,script,usedlanguage)
+ end
+ end
+ end
+ for script,languages in next,scripts do
+ for language in next,languages do
+ foundlanguages[language]=true
+ end
+ end
+ end
+ if false then
+ foundlanguages["*"]=nil
+ foundlanguages=sortedkeys(foundlanguages)
+ for feature,scripts in sortedhash(what) do
+ for script,languages in next,scripts do
+ if not languages["*"] then
+ for i=1,#foundlanguages do
+ local language=foundlanguages[i]
+ if context and not languages[language] then
+ report_defining("font %!font:name!, feature %a, script %a, no language %a",
+ tfmdata,feature,script,language)
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ check(features.gsub)
+ check(features.gpos)
+ end
+ end
+end
+function definers.loadfont(specification)
+ local hash=constructors.hashinstance(specification)
+ local tfmdata=loadedfonts[hash]
+ if not tfmdata then
+ local forced=specification.forced or ""
+ if forced~="" then
+ local reader=readers[lower(forced)]
+ tfmdata=reader and reader(specification)
+ if not tfmdata then
+ report_defining("forced type %a of %a not found",forced,specification.name)
+ end
+ else
+ local sequence=readers.sequence
+ for s=1,#sequence do
+ local reader=sequence[s]
+ if readers[reader] then
+ if trace_defining then
+ report_defining("trying (reader sequence driven) type %a for %a with file %a",reader,specification.name,specification.filename)
+ end
+ tfmdata=readers[reader](specification)
+ if tfmdata then
+ break
+ else
+ specification.filename=nil
+ end
+ end
+ end
+ end
+ if tfmdata then
+ tfmdata=definers.applypostprocessors(tfmdata)
+ checkembedding(tfmdata)
+ loadedfonts[hash]=tfmdata
+ designsizes[specification.hash]=tfmdata.parameters.designsize
+ checkfeatures(tfmdata)
+ end
+ end
+ if not tfmdata then
+ report_defining("font with asked name %a is not found using lookup %a",specification.name,specification.lookup)
+ end
+ return tfmdata
+end
+function constructors.readanddefine(name,size)
+ local specification=definers.analyze(name,size)
+ local method=specification.method
+ if method and variants[method] then
+ specification=variants[method](specification)
+ end
+ specification=definers.resolve(specification)
+ local hash=constructors.hashinstance(specification)
+ local id=definers.registered(hash)
+ if not id then
+ local tfmdata=definers.loadfont(specification)
+ if tfmdata then
+ tfmdata.properties.hash=hash
+ id=font.define(tfmdata)
+ definers.register(tfmdata,id)
+ else
+ id=0
+ end
+ end
+ return fontdata[id],id
+end
+function definers.current()
+ return lastdefined
+end
+function definers.registered(hash)
+ local id=internalized[hash]
+ return id,id and fontdata[id]
+end
+function definers.register(tfmdata,id)
+ if tfmdata and id then
+ local hash=tfmdata.properties.hash
+ if not hash then
+ report_defining("registering font, id %a, name %a, invalid hash",id,tfmdata.properties.filename or "?")
+ elseif not internalized[hash] then
+ internalized[hash]=id
+ if trace_defining then
+ report_defining("registering font, id %s, hash %a",id,hash)
+ end
+ fontdata[id]=tfmdata
+ end
+ end
+end
+function definers.read(specification,size,id)
+ statistics.starttiming(fonts)
+ if type(specification)=="string" then
+ specification=definers.analyze(specification,size)
+ end
+ local method=specification.method
+ if method and variants[method] then
+ specification=variants[method](specification)
+ end
+ specification=definers.resolve(specification)
+ local hash=constructors.hashinstance(specification)
+ local tfmdata=definers.registered(hash)
+ if tfmdata then
+ if trace_defining then
+ report_defining("already hashed: %s",hash)
+ end
+ else
+ tfmdata=definers.loadfont(specification)
+ if tfmdata then
+ if trace_defining then
+ report_defining("loaded and hashed: %s",hash)
+ end
+ tfmdata.properties.hash=hash
+ if id then
+ definers.register(tfmdata,id)
+ end
+ else
+ if trace_defining then
+ report_defining("not loaded and hashed: %s",hash)
+ end
+ end
+ end
+ lastdefined=tfmdata or id
+ if not tfmdata then
+ report_defining("unknown font %a, loading aborted",specification.name)
+ elseif trace_defining and type(tfmdata)=="table" then
+ local properties=tfmdata.properties or {}
+ local parameters=tfmdata.parameters or {}
+ report_defining("using %a font with id %a, name %a, size %a, bytes %a, encoding %a, fullname %a, filename %a",
+ properties.format or "unknown",id or "-",properties.name,parameters.size,properties.encodingbytes,
+ properties.encodingname,properties.fullname,basename(properties.filename))
+ end
+ statistics.stoptiming(fonts)
+ return tfmdata
+end
+function font.getfont(id)
+ return fontdata[id]
+end
+callbacks.register('define_font',definers.read,"definition of fonts (tfmdata preparation)")
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-fonts-def']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local fonts=fonts
+fonts.constructors.namemode="specification"
+function fonts.definers.getspecification(str)
+ return "",str,"",":",str
+end
+local list={}
+local function issome () list.lookup='name' end
+local function isfile () list.lookup='file' end
+local function isname () list.lookup='name' end
+local function thename(s) list.name=s end
+local function issub (v) list.sub=v end
+local function iscrap (s) list.crap=string.lower(s) end
+local function iskey (k,v) list[k]=v end
+local function istrue (s) list[s]=true end
+local function isfalse(s) list[s]=false end
+local P,S,R,C,Cs=lpeg.P,lpeg.S,lpeg.R,lpeg.C,lpeg.Cs
+local spaces=P(" ")^0
+local namespec=Cs((P("{")/"")*(1-S("}"))^0*(P("}")/"")+(1-S("/:("))^0)
+local crapspec=spaces*P("/")*(((1-P(":"))^0)/iscrap)*spaces
+local filename_1=P("file:")/isfile*(namespec/thename)
+local filename_2=P("[")*P(true)/isfile*(((1-P("]"))^0)/thename)*P("]")
+local fontname_1=P("name:")/isname*(namespec/thename)
+local fontname_2=P(true)/issome*(namespec/thename)
+local sometext=R("az","AZ","09")^1
+local somekey=R("az","AZ","09")^1
+local somevalue=(P("{")/"")*(1-P("}"))^0*(P("}")/"")+(1-S(";"))^1
+local truevalue=P("+")*spaces*(sometext/istrue)
+local falsevalue=P("-")*spaces*(sometext/isfalse)
+local keyvalue=(C(somekey)*spaces*P("=")*spaces*C(somevalue))/iskey
+local somevalue=sometext/istrue
+local subvalue=P("(")*(C(P(1-S("()"))^1)/issub)*P(")")
+local option=spaces*(keyvalue+falsevalue+truevalue+somevalue)*spaces
+local options=P(":")*spaces*(P(";")^0*option)^0
+local pattern=(filename_1+filename_2+fontname_1+fontname_2)*subvalue^0*crapspec^0*options^0
+function fonts.definers.analyze(str,size)
+ local specification=fonts.definers.makespecification(str,nil,nil,nil,":",nil,size)
+ list={}
+ lpeg.match(pattern,str)
+ list.crap=nil
+ if list.name then
+ specification.name=list.name
+ list.name=nil
+ end
+ if list.lookup then
+ specification.lookup=list.lookup
+ list.lookup=nil
+ end
+ if list.sub then
+ specification.sub=list.sub
+ list.sub=nil
+ end
+ specification.features.normal=fonts.handlers.otf.features.normalize(list)
+ list=nil
+ return specification
+end
+function fonts.definers.applypostprocessors(tfmdata)
+ local postprocessors=tfmdata.postprocessors
+ if postprocessors then
+ for i=1,#postprocessors do
+ local extrahash=postprocessors[i](tfmdata)
+ if type(extrahash)=="string" and extrahash~="" then
+ extrahash=string.gsub(lower(extrahash),"[^a-z]","-")
+ tfmdata.properties.fullname=format("%s-%s",tfmdata.properties.fullname,extrahash)
+ end
+ end
+ end
+ return tfmdata
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-fonts-ext']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local byte=string.byte
+local fonts=fonts
+local handlers=fonts.handlers
+local otf=handlers.otf
+local afm=handlers.afm
+local registerotffeature=otf.features.register
+local registerafmfeature=afm.features.register
+function fonts.loggers.onetimemessage() end
+fonts.protrusions=fonts.protrusions or {}
+fonts.protrusions.setups=fonts.protrusions.setups or {}
+local setups=fonts.protrusions.setups
+setups['default']={
+ factor=1,
+ left=1,
+ right=1,
+ [0x002C]={ 0,1 },
+ [0x002E]={ 0,1 },
+ [0x003A]={ 0,1 },
+ [0x003B]={ 0,1 },
+ [0x002D]={ 0,1 },
+ [0x2013]={ 0,0.50 },
+ [0x2014]={ 0,0.33 },
+ [0x3001]={ 0,1 },
+ [0x3002]={ 0,1 },
+ [0x060C]={ 0,1 },
+ [0x061B]={ 0,1 },
+ [0x06D4]={ 0,1 },
+}
+local function initializeprotrusion(tfmdata,value)
+ if value then
+ local setup=setups[value]
+ if setup then
+ local factor,left,right=setup.factor or 1,setup.left or 1,setup.right or 1
+ local emwidth=tfmdata.parameters.quad
+ tfmdata.parameters.protrusion={
+ auto=true,
+ }
+ for i,chr in next,tfmdata.characters do
+ local v,pl,pr=setup[i],nil,nil
+ if v then
+ pl,pr=v[1],v[2]
+ end
+ if pl and pl~=0 then chr.left_protruding=left*pl*factor end
+ if pr and pr~=0 then chr.right_protruding=right*pr*factor end
+ end
+ end
+ end
+end
+local specification={
+ name="protrusion",
+ description="shift characters into the left and or right margin",
+ initializers={
+ base=initializeprotrusion,
+ node=initializeprotrusion,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+fonts.expansions=fonts.expansions or {}
+fonts.expansions.setups=fonts.expansions.setups or {}
+local setups=fonts.expansions.setups
+setups['default']={
+ stretch=2,
+ shrink=2,
+ step=.5,
+ factor=1,
+ [byte('A')]=0.5,[byte('B')]=0.7,[byte('C')]=0.7,[byte('D')]=0.5,[byte('E')]=0.7,
+ [byte('F')]=0.7,[byte('G')]=0.5,[byte('H')]=0.7,[byte('K')]=0.7,[byte('M')]=0.7,
+ [byte('N')]=0.7,[byte('O')]=0.5,[byte('P')]=0.7,[byte('Q')]=0.5,[byte('R')]=0.7,
+ [byte('S')]=0.7,[byte('U')]=0.7,[byte('W')]=0.7,[byte('Z')]=0.7,
+ [byte('a')]=0.7,[byte('b')]=0.7,[byte('c')]=0.7,[byte('d')]=0.7,[byte('e')]=0.7,
+ [byte('g')]=0.7,[byte('h')]=0.7,[byte('k')]=0.7,[byte('m')]=0.7,[byte('n')]=0.7,
+ [byte('o')]=0.7,[byte('p')]=0.7,[byte('q')]=0.7,[byte('s')]=0.7,[byte('u')]=0.7,
+ [byte('w')]=0.7,[byte('z')]=0.7,
+ [byte('2')]=0.7,[byte('3')]=0.7,[byte('6')]=0.7,[byte('8')]=0.7,[byte('9')]=0.7,
+}
+local function initializeexpansion(tfmdata,value)
+ if value then
+ local setup=setups[value]
+ if setup then
+ local factor=setup.factor or 1
+ tfmdata.parameters.expansion={
+ stretch=10*(setup.stretch or 0),
+ shrink=10*(setup.shrink or 0),
+ step=10*(setup.step or 0),
+ auto=true,
+ }
+ for i,chr in next,tfmdata.characters do
+ local v=setup[i]
+ if v and v~=0 then
+ chr.expansion_factor=v*factor
+ else
+ chr.expansion_factor=factor
+ end
+ end
+ end
+ end
+end
+local specification={
+ name="expansion",
+ description="apply hz optimization",
+ initializers={
+ base=initializeexpansion,
+ node=initializeexpansion,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+if not otf.features.normalize then
+ otf.features.normalize=function(t)
+ if t.rand then
+ t.rand="random"
+ end
+ return t
+ end
+end
+function fonts.helpers.nametoslot(name)
+ local t=type(name)
+ if t=="string" then
+ local tfmdata=fonts.hashes.identifiers[currentfont()]
+ local shared=tfmdata and tfmdata.shared
+ local fntdata=shared and shared.rawdata
+ return fntdata and fntdata.resources.unicodes[name]
+ elseif t=="number" then
+ return n
+ end
+end
+fonts.encodings=fonts.encodings or {}
+local reencodings={}
+fonts.encodings.reencodings=reencodings
+local function specialreencode(tfmdata,value)
+ local encoding=value and reencodings[value]
+ if encoding then
+ local temp={}
+ local char=tfmdata.characters
+ for k,v in next,encoding do
+ temp[k]=char[v]
+ end
+ for k,v in next,temp do
+ char[k]=temp[k]
+ end
+ return string.format("reencoded:%s",value)
+ end
+end
+local function initialize(tfmdata,value)
+ tfmdata.postprocessors=tfmdata.postprocessors or {}
+ table.insert(tfmdata.postprocessors,
+ function(tfmdata)
+ return specialreencode(tfmdata,value)
+ end
+ )
+end
+registerotffeature {
+ name="reencode",
+ description="reencode characters",
+ manipulators={
+ base=initialize,
+ node=initialize,
+ }
+}
+local function initialize(tfmdata,key,value)
+ if value then
+ tfmdata.mathparameters=nil
+ end
+end
+registerotffeature {
+ name="ignoremathconstants",
+ description="ignore math constants table",
+ initializers={
+ base=initialize,
+ node=initialize,
+ }
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-imp-tex']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next=next
+local fonts=fonts
+local otf=fonts.handlers.otf
+local registerotffeature=otf.features.register
+local addotffeature=otf.addfeature
+local specification={
+ type="ligature",
+ order={ "tlig" },
+ prepend=true,
+ data={
+ [0x2013]={ 0x002D,0x002D },
+ [0x2014]={ 0x002D,0x002D,0x002D },
+ },
+}
+addotffeature("tlig",specification)
+registerotffeature {
+ name="tlig",
+ description="tex ligatures",
+}
+local specification={
+ type="substitution",
+ order={ "trep" },
+ prepend=true,
+ data={
+ [0x0027]=0x2019,
+ },
+}
+addotffeature("trep",specification)
+registerotffeature {
+ name="trep",
+ description="tex replacements",
+}
+local anum_arabic={
+ [0x0030]=0x0660,
+ [0x0031]=0x0661,
+ [0x0032]=0x0662,
+ [0x0033]=0x0663,
+ [0x0034]=0x0664,
+ [0x0035]=0x0665,
+ [0x0036]=0x0666,
+ [0x0037]=0x0667,
+ [0x0038]=0x0668,
+ [0x0039]=0x0669,
+}
+local anum_persian={
+ [0x0030]=0x06F0,
+ [0x0031]=0x06F1,
+ [0x0032]=0x06F2,
+ [0x0033]=0x06F3,
+ [0x0034]=0x06F4,
+ [0x0035]=0x06F5,
+ [0x0036]=0x06F6,
+ [0x0037]=0x06F7,
+ [0x0038]=0x06F8,
+ [0x0039]=0x06F9,
+}
+local function valid(data)
+ local features=data.resources.features
+ if features then
+ for k,v in next,features do
+ for k,v in next,v do
+ if v.arab then
+ return true
+ end
+ end
+ end
+ end
+end
+local specification={
+ {
+ type="substitution",
+ features={ arab={ urd=true,dflt=true } },
+ order={ "anum" },
+ data=anum_arabic,
+ valid=valid,
+ },
+ {
+ type="substitution",
+ features={ arab={ urd=true } },
+ order={ "anum" },
+ data=anum_persian,
+ valid=valid,
+ },
+}
+addotffeature("anum",specification)
+registerotffeature {
+ name="anum",
+ description="arabic digits",
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-imp-ligatures']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local lpegmatch=lpeg.match
+local utfsplit=utf.split
+local settings_to_array=utilities.parsers.settings_to_array
+local fonts=fonts
+local otf=fonts.handlers.otf
+local registerotffeature=otf.features.register
+local addotffeature=otf.addfeature
+local lookups={}
+local protect={}
+local revert={}
+local zwjchar=0x200C
+local zwj={ zwjchar }
+addotffeature {
+ name="blockligatures",
+ type="chainsubstitution",
+ nocheck=true,
+ prepend=true,
+ future=true,
+ lookups={
+ {
+ type="multiple",
+ data=lookups,
+ },
+ },
+ data={
+ rules=protect,
+ }
+}
+addotffeature {
+ name="blockligatures",
+ type="chainsubstitution",
+ nocheck=true,
+ append=true,
+ overload=false,
+ lookups={
+ {
+ type="ligature",
+ data=lookups,
+ },
+ },
+ data={
+ rules=revert,
+ }
+}
+registerotffeature {
+ name='blockligatures',
+ description='block certain ligatures',
+}
+local splitter=lpeg.splitat(":")
+local function blockligatures(str)
+ local t=settings_to_array(str)
+ for i=1,#t do
+ local ti=t[i]
+ local before,current,after=lpegmatch(splitter,ti)
+ if current and after then
+ if before then
+ before=utfsplit(before)
+ for i=1,#before do
+ before[i]={ before[i] }
+ end
+ end
+ if current then
+ current=utfsplit(current)
+ end
+ if after then
+ after=utfsplit(after)
+ for i=1,#after do
+ after[i]={ after[i] }
+ end
+ end
+ else
+ before=nil
+ current=utfsplit(ti)
+ after=nil
+ end
+ if #current>1 then
+ local one=current[1]
+ local two=current[2]
+ lookups[one]={ one,zwjchar }
+ local one={ one }
+ local two={ two }
+ local new=#protect+1
+ protect[new]={
+ before=before,
+ current={ one,two },
+ after=after,
+ lookups={ 1 },
+ }
+ revert[new]={
+ current={ one,zwj },
+ after={ two },
+ lookups={ 1 },
+ }
+ end
+ end
+end
+otf.helpers.blockligatures=blockligatures
+if context then
+
+--removed
+
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-imp-italics']={
+ version=1.001,
+ comment="companion to font-ini.mkiv and hand-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next=next
+local fonts=fonts
+local handlers=fonts.handlers
+local registerotffeature=handlers.otf.features.register
+local registerafmfeature=handlers.afm.features.register
+local function initialize(tfmdata,key,value)
+ for unicode,character in next,tfmdata.characters do
+ local olditalic=character.italic
+ if olditalic and olditalic~=0 then
+ character.width=character.width+olditalic
+ character.italic=0
+ end
+ end
+end
+local specification={
+ name="italicwidths",
+ description="add italic to width",
+ manipulators={
+ base=initialize,
+ node=initialize,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initialize(tfmdata,value)
+ if value then
+ local parameters=tfmdata.parameters
+ local italicangle=parameters.italicangle
+ if italicangle and italicangle~=0 then
+ local properties=tfmdata.properties
+ local factor=tonumber(value) or 1
+ properties.hasitalics=true
+ properties.autoitalicamount=factor*(parameters.uwidth or 40)/2
+ end
+ end
+end
+local specification={
+ name="itlc",
+ description="italic correction",
+ initializers={
+ base=initialize,
+ node=initialize,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+if context then
+
+--removed
+
+end
+if context then
+ local letter=characters.is_letter
+ local always=true
+ local function collapseitalics(tfmdata,key,value)
+ local threshold=value==true and 100 or tonumber(value)
+ if threshold and threshold>0 then
+ if threshold>100 then
+ threshold=100
+ end
+ for unicode,data in next,tfmdata.characters do
+ if always or letter[unicode] or letter[data.unicode] then
+ local italic=data.italic
+ if italic and italic~=0 then
+ local width=data.width
+ if width and width~=0 then
+ local delta=threshold*italic/100
+ data.width=width+delta
+ data.italic=italic-delta
+ end
+ end
+ end
+ end
+ end
+ end
+ local dimensions_specification={
+ name="collapseitalics",
+ description="collapse italics",
+ manipulators={
+ base=collapseitalics,
+ node=collapseitalics,
+ }
+ }
+ registerotffeature(dimensions_specification)
+ registerafmfeature(dimensions_specification)
+end
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['font-imp-effects']={
+ version=1.001,
+ comment="companion to font-ini.mkiv",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+local next,type,tonumber=next,type,tonumber
+local is_boolean=string.is_boolean
+local fonts=fonts
+local handlers=fonts.handlers
+local registerotffeature=handlers.otf.features.register
+local registerafmfeature=handlers.afm.features.register
+local settings_to_hash=utilities.parsers.settings_to_hash_colon_too
+local helpers=fonts.helpers
+local prependcommands=helpers.prependcommands
+local charcommand=helpers.commands.char
+local leftcommand=helpers.commands.left
+local rightcommand=helpers.commands.right
+local upcommand=helpers.commands.up
+local downcommand=helpers.commands.down
+local dummycommand=helpers.commands.dummy
+local report_effect=logs.reporter("fonts","effect")
+local report_slant=logs.reporter("fonts","slant")
+local report_extend=logs.reporter("fonts","extend")
+local report_squeeze=logs.reporter("fonts","squeeze")
+local trace=false
+trackers.register("fonts.effect",function(v) trace=v end)
+trackers.register("fonts.slant",function(v) trace=v end)
+trackers.register("fonts.extend",function(v) trace=v end)
+trackers.register("fonts.squeeze",function(v) trace=v end)
+local function initializeslant(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ elseif value>1 then
+ value=1
+ elseif value<-1 then
+ value=-1
+ end
+ if trace then
+ report_slant("applying %0.3f",value)
+ end
+ tfmdata.parameters.slantfactor=value
+end
+local specification={
+ name="slant",
+ description="slant glyphs",
+ initializers={
+ base=initializeslant,
+ node=initializeslant,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initializeextend(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ elseif value>10 then
+ value=10
+ elseif value<-10 then
+ value=-10
+ end
+ if trace then
+ report_extend("applying %0.3f",value)
+ end
+ tfmdata.parameters.extendfactor=value
+end
+local specification={
+ name="extend",
+ description="scale glyphs horizontally",
+ initializers={
+ base=initializeextend,
+ node=initializeextend,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initializesqueeze(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ elseif value>10 then
+ value=10
+ elseif value<-10 then
+ value=-10
+ end
+ if trace then
+ report_squeeze("applying %0.3f",value)
+ end
+ tfmdata.parameters.squeezefactor=value
+end
+local specification={
+ name="squeeze",
+ description="scale glyphs vertically",
+ initializers={
+ base=initializesqueeze,
+ node=initializesqueeze,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local effects={
+ inner=0,
+ normal=0,
+ outer=1,
+ outline=1,
+ both=2,
+ hidden=3,
+}
+local function initializeeffect(tfmdata,value)
+ local spec
+ if type(value)=="number" then
+ spec={ width=value }
+ else
+ spec=settings_to_hash(value)
+ end
+ local effect=spec.effect or "both"
+ local width=tonumber(spec.width) or 0
+ local mode=effects[effect]
+ if not mode then
+ report_effect("invalid effect %a",effect)
+ elseif width==0 and mode==0 then
+ report_effect("invalid width %a for effect %a",width,effect)
+ else
+ local parameters=tfmdata.parameters
+ local properties=tfmdata.properties
+ parameters.mode=mode
+ parameters.width=width*1000
+ if is_boolean(spec.auto)==true then
+ local squeeze=1-width/20
+ local average=(1-squeeze)*width*100
+ spec.squeeze=squeeze
+ spec.extend=1+width/2
+ spec.wdelta=average
+ spec.hdelta=average/2
+ spec.ddelta=average/2
+ spec.vshift=average/2
+ end
+ local factor=tonumber(spec.factor) or 0
+ local hfactor=tonumber(spec.hfactor) or factor
+ local vfactor=tonumber(spec.vfactor) or factor
+ local delta=tonumber(spec.delta) or 1
+ local wdelta=tonumber(spec.wdelta) or delta
+ local hdelta=tonumber(spec.hdelta) or delta
+ local ddelta=tonumber(spec.ddelta) or hdelta
+ local vshift=tonumber(spec.vshift) or 0
+ local slant=spec.slant
+ local extend=spec.extend
+ local squeeze=spec.squeeze
+ if slant then
+ initializeslant(tfmdata,slant)
+ end
+ if extend then
+ initializeextend(tfmdata,extend)
+ end
+ if squeeze then
+ initializesqueeze(tfmdata,squeeze)
+ end
+ properties.effect={
+ effect=effect,
+ width=width,
+ factor=factor,
+ hfactor=hfactor,
+ vfactor=vfactor,
+ wdelta=wdelta,
+ hdelta=hdelta,
+ ddelta=ddelta,
+ vshift=vshift,
+ slant=tfmdata.parameters.slantfactor,
+ extend=tfmdata.parameters.extendfactor,
+ squeeze=tfmdata.parameters.squeezefactor,
+ }
+ end
+end
+local rules={
+ "RadicalRuleThickness",
+ "OverbarRuleThickness",
+ "FractionRuleThickness",
+ "UnderbarRuleThickness",
+}
+local function setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze)
+ if delta~=0 then
+ for i=1,#rules do
+ local name=rules[i]
+ local value=mathparameters[name]
+ if value then
+ mathparameters[name]=(squeeze or 1)*(value+dx)
+ end
+ end
+ end
+end
+local function setmathcharacters(tfmdata,characters,mathparameters,dx,dy,squeeze,wdelta,hdelta,ddelta)
+ local function wdpatch(char)
+ if wsnap~=0 then
+ char.width=char.width+wdelta/2
+ end
+ end
+ local function htpatch(char)
+ if hsnap~=0 then
+ local height=char.height
+ if height then
+ char.height=char.height+2*dy
+ end
+ end
+ end
+ local character=characters[0x221A]
+ if character and character.next then
+ local char=character
+ local next=character.next
+ wdpatch(char)
+ htpatch(char)
+ while next do
+ char=characters[next]
+ wdpatch(char)
+ htpatch(char)
+ next=char.next
+ end
+ if char then
+ local v=char.vert_variants
+ if v then
+ local top=v[#v]
+ if top then
+ local char=characters[top.glyph]
+ htpatch(char)
+ end
+ end
+ end
+ end
+end
+local function manipulateeffect(tfmdata)
+ local effect=tfmdata.properties.effect
+ if effect then
+ local characters=tfmdata.characters
+ local parameters=tfmdata.parameters
+ local mathparameters=tfmdata.mathparameters
+ local multiplier=effect.width*100
+ local factor=parameters.factor
+ local hfactor=parameters.hfactor
+ local vfactor=parameters.vfactor
+ local wdelta=effect.wdelta*hfactor*multiplier
+ local hdelta=effect.hdelta*vfactor*multiplier
+ local ddelta=effect.ddelta*vfactor*multiplier
+ local vshift=effect.vshift*vfactor*multiplier
+ local squeeze=effect.squeeze
+ local hshift=wdelta/2
+ local dx=multiplier*vfactor
+ local dy=vshift
+ local factor=(1+effect.factor)*factor
+ local hfactor=(1+effect.hfactor)*hfactor
+ local vfactor=(1+effect.vfactor)*vfactor
+ local vshift=vshift~=0 and upcommand[vshift] or false
+ for unicode,character in next,characters do
+ local oldwidth=character.width
+ local oldheight=character.height
+ local olddepth=character.depth
+ if oldwidth and oldwidth>0 then
+ character.width=oldwidth+wdelta
+ local commands=character.commands
+ local hshift=rightcommand[hshift]
+ if vshift then
+ if commands then
+ prependcommands (commands,
+ hshift,
+ vshift
+ )
+ else
+ character.commands={
+ hshift,
+ vshift,
+ charcommand[unicode]
+ }
+ end
+ else
+ if commands then
+ prependcommands (commands,
+ hshift
+ )
+ else
+ character.commands={
+ hshift,
+ charcommand[unicode]
+ }
+ end
+ end
+ end
+ if oldheight and oldheight>0 then
+ character.height=oldheight+hdelta
+ end
+ if olddepth and olddepth>0 then
+ character.depth=olddepth+ddelta
+ end
+ end
+ if mathparameters then
+ setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze)
+ setmathcharacters(tfmdata,characters,mathparameters,dx,dy,squeeze,wdelta,hdelta,ddelta)
+ end
+ parameters.factor=factor
+ parameters.hfactor=hfactor
+ parameters.vfactor=vfactor
+ if trace then
+ report_effect("applying")
+ report_effect(" effect : %s",effect.effect)
+ report_effect(" width : %s => %s",effect.width,multiplier)
+ report_effect(" factor : %s => %s",effect.factor,factor )
+ report_effect(" hfactor : %s => %s",effect.hfactor,hfactor)
+ report_effect(" vfactor : %s => %s",effect.vfactor,vfactor)
+ report_effect(" wdelta : %s => %s",effect.wdelta,wdelta)
+ report_effect(" hdelta : %s => %s",effect.hdelta,hdelta)
+ report_effect(" ddelta : %s => %s",effect.ddelta,ddelta)
+ end
+ end
+end
+local specification={
+ name="effect",
+ description="apply effects to glyphs",
+ initializers={
+ base=initializeeffect,
+ node=initializeeffect,
+ },
+ manipulators={
+ base=manipulateeffect,
+ node=manipulateeffect,
+ },
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+local function initializeoutline(tfmdata,value)
+ value=tonumber(value)
+ if not value then
+ value=0
+ else
+ value=tonumber(value) or 0
+ end
+ local parameters=tfmdata.parameters
+ local properties=tfmdata.properties
+ parameters.mode=effects.outline
+ parameters.width=value*1000
+ properties.effect={
+ effect=effect,
+ width=width,
+ }
+end
+local specification={
+ name="outline",
+ description="outline glyphs",
+ initializers={
+ base=initializeoutline,
+ node=initializeoutline,
+ }
+}
+registerotffeature(specification)
+registerafmfeature(specification)
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+
+fonts.handlers.otf.addfeature {
+ ["dataset"]={
+ {
+ ["data"]={
+ ["À"]={ "A","̀" },
+ ["Á"]={ "A","́" },
+ ["Â"]={ "A","̂" },
+ ["Ã"]={ "A","̃" },
+ ["Ä"]={ "A","̈" },
+ ["Å"]={ "A","̊" },
+ ["Ç"]={ "C","̧" },
+ ["È"]={ "E","̀" },
+ ["É"]={ "E","́" },
+ ["Ê"]={ "E","̂" },
+ ["Ë"]={ "E","̈" },
+ ["Ì"]={ "I","̀" },
+ ["Í"]={ "I","́" },
+ ["Î"]={ "I","̂" },
+ ["Ï"]={ "I","̈" },
+ ["Ñ"]={ "N","̃" },
+ ["Ò"]={ "O","̀" },
+ ["Ó"]={ "O","́" },
+ ["Ô"]={ "O","̂" },
+ ["Õ"]={ "O","̃" },
+ ["Ö"]={ "O","̈" },
+ ["Ù"]={ "U","̀" },
+ ["Ú"]={ "U","́" },
+ ["Û"]={ "U","̂" },
+ ["Ü"]={ "U","̈" },
+ ["Ý"]={ "Y","́" },
+ ["à"]={ "a","̀" },
+ ["á"]={ "a","́" },
+ ["â"]={ "a","̂" },
+ ["ã"]={ "a","̃" },
+ ["ä"]={ "a","̈" },
+ ["å"]={ "a","̊" },
+ ["ç"]={ "c","̧" },
+ ["è"]={ "e","̀" },
+ ["é"]={ "e","́" },
+ ["ê"]={ "e","̂" },
+ ["ë"]={ "e","̈" },
+ ["ì"]={ "i","̀" },
+ ["í"]={ "i","́" },
+ ["î"]={ "i","̂" },
+ ["ï"]={ "i","̈" },
+ ["ñ"]={ "n","̃" },
+ ["ò"]={ "o","̀" },
+ ["ó"]={ "o","́" },
+ ["ô"]={ "o","̂" },
+ ["õ"]={ "o","̃" },
+ ["ö"]={ "o","̈" },
+ ["ù"]={ "u","̀" },
+ ["ú"]={ "u","́" },
+ ["û"]={ "u","̂" },
+ ["ü"]={ "u","̈" },
+ ["ý"]={ "y","́" },
+ ["ÿ"]={ "y","̈" },
+ ["Ā"]={ "A","̄" },
+ ["ā"]={ "a","̄" },
+ ["Ă"]={ "A","̆" },
+ ["ă"]={ "a","̆" },
+ ["Ą"]={ "A","̨" },
+ ["ą"]={ "a","̨" },
+ ["Ć"]={ "C","́" },
+ ["ć"]={ "c","́" },
+ ["Ĉ"]={ "C","̂" },
+ ["ĉ"]={ "c","̂" },
+ ["Ċ"]={ "C","̇" },
+ ["ċ"]={ "c","̇" },
+ ["Č"]={ "C","̌" },
+ ["č"]={ "c","̌" },
+ ["Ď"]={ "D","̌" },
+ ["ď"]={ "d","̌" },
+ ["Ē"]={ "E","̄" },
+ ["ē"]={ "e","̄" },
+ ["Ĕ"]={ "E","̆" },
+ ["ĕ"]={ "e","̆" },
+ ["Ė"]={ "E","̇" },
+ ["ė"]={ "e","̇" },
+ ["Ę"]={ "E","̨" },
+ ["ę"]={ "e","̨" },
+ ["Ě"]={ "E","̌" },
+ ["ě"]={ "e","̌" },
+ ["Ĝ"]={ "G","̂" },
+ ["ĝ"]={ "g","̂" },
+ ["Ğ"]={ "G","̆" },
+ ["ğ"]={ "g","̆" },
+ ["Ġ"]={ "G","̇" },
+ ["ġ"]={ "g","̇" },
+ ["Ģ"]={ "G","̧" },
+ ["ģ"]={ "g","̧" },
+ ["Ĥ"]={ "H","̂" },
+ ["ĥ"]={ "h","̂" },
+ ["Ĩ"]={ "I","̃" },
+ ["ĩ"]={ "i","̃" },
+ ["Ī"]={ "I","̄" },
+ ["ī"]={ "i","̄" },
+ ["Ĭ"]={ "I","̆" },
+ ["ĭ"]={ "i","̆" },
+ ["Į"]={ "I","̨" },
+ ["į"]={ "i","̨" },
+ ["İ"]={ "I","̇" },
+ ["Ĵ"]={ "J","̂" },
+ ["ĵ"]={ "j","̂" },
+ ["Ķ"]={ "K","̧" },
+ ["ķ"]={ "k","̧" },
+ ["Ĺ"]={ "L","́" },
+ ["ĺ"]={ "l","́" },
+ ["Ļ"]={ "L","̧" },
+ ["ļ"]={ "l","̧" },
+ ["Ľ"]={ "L","̌" },
+ ["ľ"]={ "l","̌" },
+ ["Ń"]={ "N","́" },
+ ["ń"]={ "n","́" },
+ ["Ņ"]={ "N","̧" },
+ ["ņ"]={ "n","̧" },
+ ["Ň"]={ "N","̌" },
+ ["ň"]={ "n","̌" },
+ ["Ō"]={ "O","̄" },
+ ["ō"]={ "o","̄" },
+ ["Ŏ"]={ "O","̆" },
+ ["ŏ"]={ "o","̆" },
+ ["Ő"]={ "O","̋" },
+ ["ő"]={ "o","̋" },
+ ["Ŕ"]={ "R","́" },
+ ["ŕ"]={ "r","́" },
+ ["Ŗ"]={ "R","̧" },
+ ["ŗ"]={ "r","̧" },
+ ["Ř"]={ "R","̌" },
+ ["ř"]={ "r","̌" },
+ ["Ś"]={ "S","́" },
+ ["ś"]={ "s","́" },
+ ["Ŝ"]={ "S","̂" },
+ ["ŝ"]={ "s","̂" },
+ ["Ş"]={ "S","̧" },
+ ["ş"]={ "s","̧" },
+ ["Š"]={ "S","̌" },
+ ["š"]={ "s","̌" },
+ ["Ţ"]={ "T","̧" },
+ ["ţ"]={ "t","̧" },
+ ["Ť"]={ "T","̌" },
+ ["ť"]={ "t","̌" },
+ ["Ũ"]={ "U","̃" },
+ ["ũ"]={ "u","̃" },
+ ["Ū"]={ "U","̄" },
+ ["ū"]={ "u","̄" },
+ ["Ŭ"]={ "U","̆" },
+ ["ŭ"]={ "u","̆" },
+ ["Ů"]={ "U","̊" },
+ ["ů"]={ "u","̊" },
+ ["Ű"]={ "U","̋" },
+ ["ű"]={ "u","̋" },
+ ["Ų"]={ "U","̨" },
+ ["ų"]={ "u","̨" },
+ ["Ŵ"]={ "W","̂" },
+ ["ŵ"]={ "w","̂" },
+ ["Ŷ"]={ "Y","̂" },
+ ["ŷ"]={ "y","̂" },
+ ["Ÿ"]={ "Y","̈" },
+ ["Ź"]={ "Z","́" },
+ ["ź"]={ "z","́" },
+ ["Ż"]={ "Z","̇" },
+ ["ż"]={ "z","̇" },
+ ["Ž"]={ "Z","̌" },
+ ["ž"]={ "z","̌" },
+ ["Ơ"]={ "O","̛" },
+ ["ơ"]={ "o","̛" },
+ ["Ư"]={ "U","̛" },
+ ["ư"]={ "u","̛" },
+ ["Ǎ"]={ "A","̌" },
+ ["ǎ"]={ "a","̌" },
+ ["Ǐ"]={ "I","̌" },
+ ["ǐ"]={ "i","̌" },
+ ["Ǒ"]={ "O","̌" },
+ ["ǒ"]={ "o","̌" },
+ ["Ǔ"]={ "U","̌" },
+ ["ǔ"]={ "u","̌" },
+ ["Ǖ"]={ "Ü","̄" },
+ ["ǖ"]={ "ü","̄" },
+ ["Ǘ"]={ "Ü","́" },
+ ["ǘ"]={ "ü","́" },
+ ["Ǚ"]={ "Ü","̌" },
+ ["ǚ"]={ "ü","̌" },
+ ["Ǜ"]={ "Ü","̀" },
+ ["ǜ"]={ "ü","̀" },
+ ["Ǟ"]={ "Ä","̄" },
+ ["ǟ"]={ "ä","̄" },
+ ["Ǡ"]={ "Ȧ","̄" },
+ ["ǡ"]={ "ȧ","̄" },
+ ["Ǣ"]={ "Æ","̄" },
+ ["ǣ"]={ "æ","̄" },
+ ["Ǧ"]={ "G","̌" },
+ ["ǧ"]={ "g","̌" },
+ ["Ǩ"]={ "K","̌" },
+ ["ǩ"]={ "k","̌" },
+ ["Ǫ"]={ "O","̨" },
+ ["ǫ"]={ "o","̨" },
+ ["Ǭ"]={ "Ǫ","̄" },
+ ["ǭ"]={ "ǫ","̄" },
+ ["Ǯ"]={ "Ʒ","̌" },
+ ["ǯ"]={ "ʒ","̌" },
+ ["ǰ"]={ "j","̌" },
+ ["Ǵ"]={ "G","́" },
+ ["ǵ"]={ "g","́" },
+ ["Ǹ"]={ "N","̀" },
+ ["ǹ"]={ "n","̀" },
+ ["Ǻ"]={ "Å","́" },
+ ["ǻ"]={ "å","́" },
+ ["Ǽ"]={ "Æ","́" },
+ ["ǽ"]={ "æ","́" },
+ ["Ǿ"]={ "Ø","́" },
+ ["ǿ"]={ "ø","́" },
+ ["Ȁ"]={ "A","̏" },
+ ["ȁ"]={ "a","̏" },
+ ["Ȃ"]={ "A","̑" },
+ ["ȃ"]={ "a","̑" },
+ ["Ȅ"]={ "E","̏" },
+ ["ȅ"]={ "e","̏" },
+ ["Ȇ"]={ "E","̑" },
+ ["ȇ"]={ "e","̑" },
+ ["Ȉ"]={ "I","̏" },
+ ["ȉ"]={ "i","̏" },
+ ["Ȋ"]={ "I","̑" },
+ ["ȋ"]={ "i","̑" },
+ ["Ȍ"]={ "O","̏" },
+ ["ȍ"]={ "o","̏" },
+ ["Ȏ"]={ "O","̑" },
+ ["ȏ"]={ "o","̑" },
+ ["Ȑ"]={ "R","̏" },
+ ["ȑ"]={ "r","̏" },
+ ["Ȓ"]={ "R","̑" },
+ ["ȓ"]={ "r","̑" },
+ ["Ȕ"]={ "U","̏" },
+ ["ȕ"]={ "u","̏" },
+ ["Ȗ"]={ "U","̑" },
+ ["ȗ"]={ "u","̑" },
+ ["Ș"]={ "S","̦" },
+ ["ș"]={ "s","̦" },
+ ["Ț"]={ "T","̦" },
+ ["ț"]={ "t","̦" },
+ ["Ȟ"]={ "H","̌" },
+ ["ȟ"]={ "h","̌" },
+ ["Ȧ"]={ "A","̇" },
+ ["ȧ"]={ "a","̇" },
+ ["Ȩ"]={ "E","̧" },
+ ["ȩ"]={ "e","̧" },
+ ["Ȫ"]={ "Ö","̄" },
+ ["ȫ"]={ "ö","̄" },
+ ["Ȭ"]={ "Õ","̄" },
+ ["ȭ"]={ "õ","̄" },
+ ["Ȯ"]={ "O","̇" },
+ ["ȯ"]={ "o","̇" },
+ ["Ȱ"]={ "Ȯ","̄" },
+ ["ȱ"]={ "ȯ","̄" },
+ ["Ȳ"]={ "Y","̄" },
+ ["ȳ"]={ "y","̄" },
+ ["̈́"]={ "̈","́" },
+ ["΅"]={ "¨","́" },
+ ["Ά"]={ "Α","́" },
+ ["Έ"]={ "Ε","́" },
+ ["Ή"]={ "Η","́" },
+ ["Ί"]={ "Ι","́" },
+ ["Ό"]={ "Ο","́" },
+ ["Ύ"]={ "Υ","́" },
+ ["Ώ"]={ "Ω","́" },
+ ["ΐ"]={ "ϊ","́" },
+ ["Ϊ"]={ "Ι","̈" },
+ ["Ϋ"]={ "Υ","̈" },
+ ["ά"]={ "α","́" },
+ ["έ"]={ "ε","́" },
+ ["ή"]={ "η","́" },
+ ["ί"]={ "ι","́" },
+ ["ΰ"]={ "ϋ","́" },
+ ["ϊ"]={ "ι","̈" },
+ ["ϋ"]={ "υ","̈" },
+ ["ό"]={ "ο","́" },
+ ["ύ"]={ "υ","́" },
+ ["ώ"]={ "ω","́" },
+ ["ϓ"]={ "ϒ","́" },
+ ["ϔ"]={ "ϒ","̈" },
+ ["Ѐ"]={ "Е","̀" },
+ ["Ё"]={ "Е","̈" },
+ ["Ѓ"]={ "Г","́" },
+ ["Ї"]={ "І","̈" },
+ ["Ќ"]={ "К","́" },
+ ["Ѝ"]={ "И","̀" },
+ ["Ў"]={ "У","̆" },
+ ["Й"]={ "И","̆" },
+ ["й"]={ "и","̆" },
+ ["ѐ"]={ "е","̀" },
+ ["ё"]={ "е","̈" },
+ ["ѓ"]={ "г","́" },
+ ["ї"]={ "і","̈" },
+ ["ќ"]={ "к","́" },
+ ["ѝ"]={ "и","̀" },
+ ["ў"]={ "у","̆" },
+ ["Ѷ"]={ "Ѵ","̏" },
+ ["ѷ"]={ "ѵ","̏" },
+ ["Ӂ"]={ "Ж","̆" },
+ ["ӂ"]={ "ж","̆" },
+ ["Ӑ"]={ "А","̆" },
+ ["ӑ"]={ "а","̆" },
+ ["Ӓ"]={ "А","̈" },
+ ["ӓ"]={ "а","̈" },
+ ["Ӗ"]={ "Е","̆" },
+ ["ӗ"]={ "е","̆" },
+ ["Ӛ"]={ "Ә","̈" },
+ ["ӛ"]={ "ә","̈" },
+ ["Ӝ"]={ "Ж","̈" },
+ ["ӝ"]={ "ж","̈" },
+ ["Ӟ"]={ "З","̈" },
+ ["ӟ"]={ "з","̈" },
+ ["Ӣ"]={ "И","̄" },
+ ["ӣ"]={ "и","̄" },
+ ["Ӥ"]={ "И","̈" },
+ ["ӥ"]={ "и","̈" },
+ ["Ӧ"]={ "О","̈" },
+ ["ӧ"]={ "о","̈" },
+ ["Ӫ"]={ "Ө","̈" },
+ ["ӫ"]={ "ө","̈" },
+ ["Ӭ"]={ "Э","̈" },
+ ["ӭ"]={ "э","̈" },
+ ["Ӯ"]={ "У","̄" },
+ ["ӯ"]={ "у","̄" },
+ ["Ӱ"]={ "У","̈" },
+ ["ӱ"]={ "у","̈" },
+ ["Ӳ"]={ "У","̋" },
+ ["ӳ"]={ "у","̋" },
+ ["Ӵ"]={ "Ч","̈" },
+ ["ӵ"]={ "ч","̈" },
+ ["Ӹ"]={ "Ы","̈" },
+ ["ӹ"]={ "ы","̈" },
+ ["آ"]={ "ا","ٓ" },
+ ["أ"]={ "ا","ٔ" },
+ ["ؤ"]={ "و","ٔ" },
+ ["إ"]={ "ا","ٕ" },
+ ["ئ"]={ "ي","ٔ" },
+ ["ۀ"]={ "ە","ٔ" },
+ ["ۂ"]={ "ہ","ٔ" },
+ ["ۓ"]={ "ے","ٔ" },
+ ["ऩ"]={ "न","़" },
+ ["ऱ"]={ "र","़" },
+ ["ऴ"]={ "ळ","़" },
+ ["क़"]={ "क","़" },
+ ["ख़"]={ "ख","़" },
+ ["ग़"]={ "ग","़" },
+ ["ज़"]={ "ज","़" },
+ ["ड़"]={ "ड","़" },
+ ["ढ़"]={ "ढ","़" },
+ ["फ़"]={ "फ","़" },
+ ["य़"]={ "य","़" },
+ ["ো"]={ "ে","া" },
+ ["ৌ"]={ "ে","ৗ" },
+ ["ড়"]={ "ড","়" },
+ ["ঢ়"]={ "ঢ","়" },
+ ["য়"]={ "য","়" },
+ ["ਲ਼"]={ "ਲ","਼" },
+ ["ਸ਼"]={ "ਸ","਼" },
+ ["ਖ਼"]={ "ਖ","਼" },
+ ["ਗ਼"]={ "ਗ","਼" },
+ ["ਜ਼"]={ "ਜ","਼" },
+ ["ਫ਼"]={ "ਫ","਼" },
+ ["ୈ"]={ "େ","ୖ" },
+ ["ୋ"]={ "େ","ା" },
+ ["ୌ"]={ "େ","ୗ" },
+ ["ଡ଼"]={ "ଡ","଼" },
+ ["ଢ଼"]={ "ଢ","଼" },
+ ["ஔ"]={ "ஒ","ௗ" },
+ ["ொ"]={ "ெ","ா" },
+ ["ோ"]={ "ே","ா" },
+ ["ௌ"]={ "ெ","ௗ" },
+ ["ై"]={ "ె","ౖ" },
+ ["ೀ"]={ "ಿ","ೕ" },
+ ["ೇ"]={ "ೆ","ೕ" },
+ ["ೈ"]={ "ೆ","ೖ" },
+ ["ೊ"]={ "ೆ","ೂ" },
+ ["ೋ"]={ "ೊ","ೕ" },
+ ["ൊ"]={ "െ","ാ" },
+ ["ോ"]={ "േ","ാ" },
+ ["ൌ"]={ "െ","ൗ" },
+ ["ේ"]={ "ෙ","්" },
+ ["ො"]={ "ෙ","ා" },
+ ["ෝ"]={ "ො","්" },
+ ["ෞ"]={ "ෙ","ෟ" },
+ ["གྷ"]={ "ག","ྷ" },
+ ["ཌྷ"]={ "ཌ","ྷ" },
+ ["དྷ"]={ "ད","ྷ" },
+ ["བྷ"]={ "བ","ྷ" },
+ ["ཛྷ"]={ "ཛ","ྷ" },
+ ["ཀྵ"]={ "ཀ","ྵ" },
+ ["ཱི"]={ "ཱ","ི" },
+ ["ཱུ"]={ "ཱ","ུ" },
+ ["ྲྀ"]={ "ྲ","ྀ" },
+ ["ླྀ"]={ "ླ","ྀ" },
+ ["ཱྀ"]={ "ཱ","ྀ" },
+ ["ྒྷ"]={ "ྒ","ྷ" },
+ ["ྜྷ"]={ "ྜ","ྷ" },
+ ["ྡྷ"]={ "ྡ","ྷ" },
+ ["ྦྷ"]={ "ྦ","ྷ" },
+ ["ྫྷ"]={ "ྫ","ྷ" },
+ ["ྐྵ"]={ "ྐ","ྵ" },
+ ["ဦ"]={ "ဥ","ီ" },
+ ["ᬆ"]={ "ᬅ","ᬵ" },
+ ["ᬈ"]={ "ᬇ","ᬵ" },
+ ["ᬊ"]={ "ᬉ","ᬵ" },
+ ["ᬌ"]={ "ᬋ","ᬵ" },
+ ["ᬎ"]={ "ᬍ","ᬵ" },
+ ["ᬒ"]={ "ᬑ","ᬵ" },
+ ["ᬻ"]={ "ᬺ","ᬵ" },
+ ["ᬽ"]={ "ᬼ","ᬵ" },
+ ["ᭀ"]={ "ᬾ","ᬵ" },
+ ["ᭁ"]={ "ᬿ","ᬵ" },
+ ["ᭃ"]={ "ᭂ","ᬵ" },
+ ["Ḁ"]={ "A","̥" },
+ ["ḁ"]={ "a","̥" },
+ ["Ḃ"]={ "B","̇" },
+ ["ḃ"]={ "b","̇" },
+ ["Ḅ"]={ "B","̣" },
+ ["ḅ"]={ "b","̣" },
+ ["Ḇ"]={ "B","̱" },
+ ["ḇ"]={ "b","̱" },
+ ["Ḉ"]={ "Ç","́" },
+ ["ḉ"]={ "ç","́" },
+ ["Ḋ"]={ "D","̇" },
+ ["ḋ"]={ "d","̇" },
+ ["Ḍ"]={ "D","̣" },
+ ["ḍ"]={ "d","̣" },
+ ["Ḏ"]={ "D","̱" },
+ ["ḏ"]={ "d","̱" },
+ ["Ḑ"]={ "D","̧" },
+ ["ḑ"]={ "d","̧" },
+ ["Ḓ"]={ "D","̭" },
+ ["ḓ"]={ "d","̭" },
+ ["Ḕ"]={ "Ē","̀" },
+ ["ḕ"]={ "ē","̀" },
+ ["Ḗ"]={ "Ē","́" },
+ ["ḗ"]={ "ē","́" },
+ ["Ḙ"]={ "E","̭" },
+ ["ḙ"]={ "e","̭" },
+ ["Ḛ"]={ "E","̰" },
+ ["ḛ"]={ "e","̰" },
+ ["Ḝ"]={ "Ȩ","̆" },
+ ["ḝ"]={ "ȩ","̆" },
+ ["Ḟ"]={ "F","̇" },
+ ["ḟ"]={ "f","̇" },
+ ["Ḡ"]={ "G","̄" },
+ ["ḡ"]={ "g","̄" },
+ ["Ḣ"]={ "H","̇" },
+ ["ḣ"]={ "h","̇" },
+ ["Ḥ"]={ "H","̣" },
+ ["ḥ"]={ "h","̣" },
+ ["Ḧ"]={ "H","̈" },
+ ["ḧ"]={ "h","̈" },
+ ["Ḩ"]={ "H","̧" },
+ ["ḩ"]={ "h","̧" },
+ ["Ḫ"]={ "H","̮" },
+ ["ḫ"]={ "h","̮" },
+ ["Ḭ"]={ "I","̰" },
+ ["ḭ"]={ "i","̰" },
+ ["Ḯ"]={ "Ï","́" },
+ ["ḯ"]={ "ï","́" },
+ ["Ḱ"]={ "K","́" },
+ ["ḱ"]={ "k","́" },
+ ["Ḳ"]={ "K","̣" },
+ ["ḳ"]={ "k","̣" },
+ ["Ḵ"]={ "K","̱" },
+ ["ḵ"]={ "k","̱" },
+ ["Ḷ"]={ "L","̣" },
+ ["ḷ"]={ "l","̣" },
+ ["Ḹ"]={ "Ḷ","̄" },
+ ["ḹ"]={ "ḷ","̄" },
+ ["Ḻ"]={ "L","̱" },
+ ["ḻ"]={ "l","̱" },
+ ["Ḽ"]={ "L","̭" },
+ ["ḽ"]={ "l","̭" },
+ ["Ḿ"]={ "M","́" },
+ ["ḿ"]={ "m","́" },
+ ["Ṁ"]={ "M","̇" },
+ ["ṁ"]={ "m","̇" },
+ ["Ṃ"]={ "M","̣" },
+ ["ṃ"]={ "m","̣" },
+ ["Ṅ"]={ "N","̇" },
+ ["ṅ"]={ "n","̇" },
+ ["Ṇ"]={ "N","̣" },
+ ["ṇ"]={ "n","̣" },
+ ["Ṉ"]={ "N","̱" },
+ ["ṉ"]={ "n","̱" },
+ ["Ṋ"]={ "N","̭" },
+ ["ṋ"]={ "n","̭" },
+ ["Ṍ"]={ "Õ","́" },
+ ["ṍ"]={ "õ","́" },
+ ["Ṏ"]={ "Õ","̈" },
+ ["ṏ"]={ "õ","̈" },
+ ["Ṑ"]={ "Ō","̀" },
+ ["ṑ"]={ "ō","̀" },
+ ["Ṓ"]={ "Ō","́" },
+ ["ṓ"]={ "ō","́" },
+ ["Ṕ"]={ "P","́" },
+ ["ṕ"]={ "p","́" },
+ ["Ṗ"]={ "P","̇" },
+ ["ṗ"]={ "p","̇" },
+ ["Ṙ"]={ "R","̇" },
+ ["ṙ"]={ "r","̇" },
+ ["Ṛ"]={ "R","̣" },
+ ["ṛ"]={ "r","̣" },
+ ["Ṝ"]={ "Ṛ","̄" },
+ ["ṝ"]={ "ṛ","̄" },
+ ["Ṟ"]={ "R","̱" },
+ ["ṟ"]={ "r","̱" },
+ ["Ṡ"]={ "S","̇" },
+ ["ṡ"]={ "s","̇" },
+ ["Ṣ"]={ "S","̣" },
+ ["ṣ"]={ "s","̣" },
+ ["Ṥ"]={ "Ś","̇" },
+ ["ṥ"]={ "ś","̇" },
+ ["Ṧ"]={ "Š","̇" },
+ ["ṧ"]={ "š","̇" },
+ ["Ṩ"]={ "Ṣ","̇" },
+ ["ṩ"]={ "ṣ","̇" },
+ ["Ṫ"]={ "T","̇" },
+ ["ṫ"]={ "t","̇" },
+ ["Ṭ"]={ "T","̣" },
+ ["ṭ"]={ "t","̣" },
+ ["Ṯ"]={ "T","̱" },
+ ["ṯ"]={ "t","̱" },
+ ["Ṱ"]={ "T","̭" },
+ ["ṱ"]={ "t","̭" },
+ ["Ṳ"]={ "U","̤" },
+ ["ṳ"]={ "u","̤" },
+ ["Ṵ"]={ "U","̰" },
+ ["ṵ"]={ "u","̰" },
+ ["Ṷ"]={ "U","̭" },
+ ["ṷ"]={ "u","̭" },
+ ["Ṹ"]={ "Ũ","́" },
+ ["ṹ"]={ "ũ","́" },
+ ["Ṻ"]={ "Ū","̈" },
+ ["ṻ"]={ "ū","̈" },
+ ["Ṽ"]={ "V","̃" },
+ ["ṽ"]={ "v","̃" },
+ ["Ṿ"]={ "V","̣" },
+ ["ṿ"]={ "v","̣" },
+ ["Ẁ"]={ "W","̀" },
+ ["ẁ"]={ "w","̀" },
+ ["Ẃ"]={ "W","́" },
+ ["ẃ"]={ "w","́" },
+ ["Ẅ"]={ "W","̈" },
+ ["ẅ"]={ "w","̈" },
+ ["Ẇ"]={ "W","̇" },
+ ["ẇ"]={ "w","̇" },
+ ["Ẉ"]={ "W","̣" },
+ ["ẉ"]={ "w","̣" },
+ ["Ẋ"]={ "X","̇" },
+ ["ẋ"]={ "x","̇" },
+ ["Ẍ"]={ "X","̈" },
+ ["ẍ"]={ "x","̈" },
+ ["Ẏ"]={ "Y","̇" },
+ ["ẏ"]={ "y","̇" },
+ ["Ẑ"]={ "Z","̂" },
+ ["ẑ"]={ "z","̂" },
+ ["Ẓ"]={ "Z","̣" },
+ ["ẓ"]={ "z","̣" },
+ ["Ẕ"]={ "Z","̱" },
+ ["ẕ"]={ "z","̱" },
+ ["ẖ"]={ "h","̱" },
+ ["ẗ"]={ "t","̈" },
+ ["ẘ"]={ "w","̊" },
+ ["ẙ"]={ "y","̊" },
+ ["ẛ"]={ "ſ","̇" },
+ ["Ạ"]={ "A","̣" },
+ ["ạ"]={ "a","̣" },
+ ["Ả"]={ "A","̉" },
+ ["ả"]={ "a","̉" },
+ ["Ấ"]={ "Â","́" },
+ ["ấ"]={ "â","́" },
+ ["Ầ"]={ "Â","̀" },
+ ["ầ"]={ "â","̀" },
+ ["Ẩ"]={ "Â","̉" },
+ ["ẩ"]={ "â","̉" },
+ ["Ẫ"]={ "Â","̃" },
+ ["ẫ"]={ "â","̃" },
+ ["Ậ"]={ "Ạ","̂" },
+ ["ậ"]={ "ạ","̂" },
+ ["Ắ"]={ "Ă","́" },
+ ["ắ"]={ "ă","́" },
+ ["Ằ"]={ "Ă","̀" },
+ ["ằ"]={ "ă","̀" },
+ ["Ẳ"]={ "Ă","̉" },
+ ["ẳ"]={ "ă","̉" },
+ ["Ẵ"]={ "Ă","̃" },
+ ["ẵ"]={ "ă","̃" },
+ ["Ặ"]={ "Ạ","̆" },
+ ["ặ"]={ "ạ","̆" },
+ ["Ẹ"]={ "E","̣" },
+ ["ẹ"]={ "e","̣" },
+ ["Ẻ"]={ "E","̉" },
+ ["ẻ"]={ "e","̉" },
+ ["Ẽ"]={ "E","̃" },
+ ["ẽ"]={ "e","̃" },
+ ["Ế"]={ "Ê","́" },
+ ["ế"]={ "ê","́" },
+ ["Ề"]={ "Ê","̀" },
+ ["ề"]={ "ê","̀" },
+ ["Ể"]={ "Ê","̉" },
+ ["ể"]={ "ê","̉" },
+ ["Ễ"]={ "Ê","̃" },
+ ["ễ"]={ "ê","̃" },
+ ["Ệ"]={ "Ẹ","̂" },
+ ["ệ"]={ "ẹ","̂" },
+ ["Ỉ"]={ "I","̉" },
+ ["ỉ"]={ "i","̉" },
+ ["Ị"]={ "I","̣" },
+ ["ị"]={ "i","̣" },
+ ["Ọ"]={ "O","̣" },
+ ["ọ"]={ "o","̣" },
+ ["Ỏ"]={ "O","̉" },
+ ["ỏ"]={ "o","̉" },
+ ["Ố"]={ "Ô","́" },
+ ["ố"]={ "ô","́" },
+ ["Ồ"]={ "Ô","̀" },
+ ["ồ"]={ "ô","̀" },
+ ["Ổ"]={ "Ô","̉" },
+ ["ổ"]={ "ô","̉" },
+ ["Ỗ"]={ "Ô","̃" },
+ ["ỗ"]={ "ô","̃" },
+ ["Ộ"]={ "Ọ","̂" },
+ ["ộ"]={ "ọ","̂" },
+ ["Ớ"]={ "Ơ","́" },
+ ["ớ"]={ "ơ","́" },
+ ["Ờ"]={ "Ơ","̀" },
+ ["ờ"]={ "ơ","̀" },
+ ["Ở"]={ "Ơ","̉" },
+ ["ở"]={ "ơ","̉" },
+ ["Ỡ"]={ "Ơ","̃" },
+ ["ỡ"]={ "ơ","̃" },
+ ["Ợ"]={ "Ơ","̣" },
+ ["ợ"]={ "ơ","̣" },
+ ["Ụ"]={ "U","̣" },
+ ["ụ"]={ "u","̣" },
+ ["Ủ"]={ "U","̉" },
+ ["ủ"]={ "u","̉" },
+ ["Ứ"]={ "Ư","́" },
+ ["ứ"]={ "ư","́" },
+ ["Ừ"]={ "Ư","̀" },
+ ["ừ"]={ "ư","̀" },
+ ["Ử"]={ "Ư","̉" },
+ ["ử"]={ "ư","̉" },
+ ["Ữ"]={ "Ư","̃" },
+ ["ữ"]={ "ư","̃" },
+ ["Ự"]={ "Ư","̣" },
+ ["ự"]={ "ư","̣" },
+ ["Ỳ"]={ "Y","̀" },
+ ["ỳ"]={ "y","̀" },
+ ["Ỵ"]={ "Y","̣" },
+ ["ỵ"]={ "y","̣" },
+ ["Ỷ"]={ "Y","̉" },
+ ["ỷ"]={ "y","̉" },
+ ["Ỹ"]={ "Y","̃" },
+ ["ỹ"]={ "y","̃" },
+ ["ἀ"]={ "α","̓" },
+ ["ἁ"]={ "α","̔" },
+ ["ἂ"]={ "ἀ","̀" },
+ ["ἃ"]={ "ἁ","̀" },
+ ["ἄ"]={ "ἀ","́" },
+ ["ἅ"]={ "ἁ","́" },
+ ["ἆ"]={ "ἀ","͂" },
+ ["ἇ"]={ "ἁ","͂" },
+ ["Ἀ"]={ "Α","̓" },
+ ["Ἁ"]={ "Α","̔" },
+ ["Ἂ"]={ "Ἀ","̀" },
+ ["Ἃ"]={ "Ἁ","̀" },
+ ["Ἄ"]={ "Ἀ","́" },
+ ["Ἅ"]={ "Ἁ","́" },
+ ["Ἆ"]={ "Ἀ","͂" },
+ ["Ἇ"]={ "Ἁ","͂" },
+ ["ἐ"]={ "ε","̓" },
+ ["ἑ"]={ "ε","̔" },
+ ["ἒ"]={ "ἐ","̀" },
+ ["ἓ"]={ "ἑ","̀" },
+ ["ἔ"]={ "ἐ","́" },
+ ["ἕ"]={ "ἑ","́" },
+ ["Ἐ"]={ "Ε","̓" },
+ ["Ἑ"]={ "Ε","̔" },
+ ["Ἒ"]={ "Ἐ","̀" },
+ ["Ἓ"]={ "Ἑ","̀" },
+ ["Ἔ"]={ "Ἐ","́" },
+ ["Ἕ"]={ "Ἑ","́" },
+ ["ἠ"]={ "η","̓" },
+ ["ἡ"]={ "η","̔" },
+ ["ἢ"]={ "ἠ","̀" },
+ ["ἣ"]={ "ἡ","̀" },
+ ["ἤ"]={ "ἠ","́" },
+ ["ἥ"]={ "ἡ","́" },
+ ["ἦ"]={ "ἠ","͂" },
+ ["ἧ"]={ "ἡ","͂" },
+ ["Ἠ"]={ "Η","̓" },
+ ["Ἡ"]={ "Η","̔" },
+ ["Ἢ"]={ "Ἠ","̀" },
+ ["Ἣ"]={ "Ἡ","̀" },
+ ["Ἤ"]={ "Ἠ","́" },
+ ["Ἥ"]={ "Ἡ","́" },
+ ["Ἦ"]={ "Ἠ","͂" },
+ ["Ἧ"]={ "Ἡ","͂" },
+ ["ἰ"]={ "ι","̓" },
+ ["ἱ"]={ "ι","̔" },
+ ["ἲ"]={ "ἰ","̀" },
+ ["ἳ"]={ "ἱ","̀" },
+ ["ἴ"]={ "ἰ","́" },
+ ["ἵ"]={ "ἱ","́" },
+ ["ἶ"]={ "ἰ","͂" },
+ ["ἷ"]={ "ἱ","͂" },
+ ["Ἰ"]={ "Ι","̓" },
+ ["Ἱ"]={ "Ι","̔" },
+ ["Ἲ"]={ "Ἰ","̀" },
+ ["Ἳ"]={ "Ἱ","̀" },
+ ["Ἴ"]={ "Ἰ","́" },
+ ["Ἵ"]={ "Ἱ","́" },
+ ["Ἶ"]={ "Ἰ","͂" },
+ ["Ἷ"]={ "Ἱ","͂" },
+ ["ὀ"]={ "ο","̓" },
+ ["ὁ"]={ "ο","̔" },
+ ["ὂ"]={ "ὀ","̀" },
+ ["ὃ"]={ "ὁ","̀" },
+ ["ὄ"]={ "ὀ","́" },
+ ["ὅ"]={ "ὁ","́" },
+ ["Ὀ"]={ "Ο","̓" },
+ ["Ὁ"]={ "Ο","̔" },
+ ["Ὂ"]={ "Ὀ","̀" },
+ ["Ὃ"]={ "Ὁ","̀" },
+ ["Ὄ"]={ "Ὀ","́" },
+ ["Ὅ"]={ "Ὁ","́" },
+ ["ὐ"]={ "υ","̓" },
+ ["ὑ"]={ "υ","̔" },
+ ["ὒ"]={ "ὐ","̀" },
+ ["ὓ"]={ "ὑ","̀" },
+ ["ὔ"]={ "ὐ","́" },
+ ["ὕ"]={ "ὑ","́" },
+ ["ὖ"]={ "ὐ","͂" },
+ ["ὗ"]={ "ὑ","͂" },
+ ["Ὑ"]={ "Υ","̔" },
+ ["Ὓ"]={ "Ὑ","̀" },
+ ["Ὕ"]={ "Ὑ","́" },
+ ["Ὗ"]={ "Ὑ","͂" },
+ ["ὠ"]={ "ω","̓" },
+ ["ὡ"]={ "ω","̔" },
+ ["ὢ"]={ "ὠ","̀" },
+ ["ὣ"]={ "ὡ","̀" },
+ ["ὤ"]={ "ὠ","́" },
+ ["ὥ"]={ "ὡ","́" },
+ ["ὦ"]={ "ὠ","͂" },
+ ["ὧ"]={ "ὡ","͂" },
+ ["Ὠ"]={ "Ω","̓" },
+ ["Ὡ"]={ "Ω","̔" },
+ ["Ὢ"]={ "Ὠ","̀" },
+ ["Ὣ"]={ "Ὡ","̀" },
+ ["Ὤ"]={ "Ὠ","́" },
+ ["Ὥ"]={ "Ὡ","́" },
+ ["Ὦ"]={ "Ὠ","͂" },
+ ["Ὧ"]={ "Ὡ","͂" },
+ ["ὰ"]={ "α","̀" },
+ ["ὲ"]={ "ε","̀" },
+ ["ὴ"]={ "η","̀" },
+ ["ὶ"]={ "ι","̀" },
+ ["ὸ"]={ "ο","̀" },
+ ["ὺ"]={ "υ","̀" },
+ ["ὼ"]={ "ω","̀" },
+ ["ᾀ"]={ "ἀ","ͅ" },
+ ["ᾁ"]={ "ἁ","ͅ" },
+ ["ᾂ"]={ "ἂ","ͅ" },
+ ["ᾃ"]={ "ἃ","ͅ" },
+ ["ᾄ"]={ "ἄ","ͅ" },
+ ["ᾅ"]={ "ἅ","ͅ" },
+ ["ᾆ"]={ "ἆ","ͅ" },
+ ["ᾇ"]={ "ἇ","ͅ" },
+ ["ᾈ"]={ "Ἀ","ͅ" },
+ ["ᾉ"]={ "Ἁ","ͅ" },
+ ["ᾊ"]={ "Ἂ","ͅ" },
+ ["ᾋ"]={ "Ἃ","ͅ" },
+ ["ᾌ"]={ "Ἄ","ͅ" },
+ ["ᾍ"]={ "Ἅ","ͅ" },
+ ["ᾎ"]={ "Ἆ","ͅ" },
+ ["ᾏ"]={ "Ἇ","ͅ" },
+ ["ᾐ"]={ "ἠ","ͅ" },
+ ["ᾑ"]={ "ἡ","ͅ" },
+ ["ᾒ"]={ "ἢ","ͅ" },
+ ["ᾓ"]={ "ἣ","ͅ" },
+ ["ᾔ"]={ "ἤ","ͅ" },
+ ["ᾕ"]={ "ἥ","ͅ" },
+ ["ᾖ"]={ "ἦ","ͅ" },
+ ["ᾗ"]={ "ἧ","ͅ" },
+ ["ᾘ"]={ "Ἠ","ͅ" },
+ ["ᾙ"]={ "Ἡ","ͅ" },
+ ["ᾚ"]={ "Ἢ","ͅ" },
+ ["ᾛ"]={ "Ἣ","ͅ" },
+ ["ᾜ"]={ "Ἤ","ͅ" },
+ ["ᾝ"]={ "Ἥ","ͅ" },
+ ["ᾞ"]={ "Ἦ","ͅ" },
+ ["ᾟ"]={ "Ἧ","ͅ" },
+ ["ᾠ"]={ "ὠ","ͅ" },
+ ["ᾡ"]={ "ὡ","ͅ" },
+ ["ᾢ"]={ "ὢ","ͅ" },
+ ["ᾣ"]={ "ὣ","ͅ" },
+ ["ᾤ"]={ "ὤ","ͅ" },
+ ["ᾥ"]={ "ὥ","ͅ" },
+ ["ᾦ"]={ "ὦ","ͅ" },
+ ["ᾧ"]={ "ὧ","ͅ" },
+ ["ᾨ"]={ "Ὠ","ͅ" },
+ ["ᾩ"]={ "Ὡ","ͅ" },
+ ["ᾪ"]={ "Ὢ","ͅ" },
+ ["ᾫ"]={ "Ὣ","ͅ" },
+ ["ᾬ"]={ "Ὤ","ͅ" },
+ ["ᾭ"]={ "Ὥ","ͅ" },
+ ["ᾮ"]={ "Ὦ","ͅ" },
+ ["ᾯ"]={ "Ὧ","ͅ" },
+ ["ᾰ"]={ "α","̆" },
+ ["ᾱ"]={ "α","̄" },
+ ["ᾲ"]={ "ὰ","ͅ" },
+ ["ᾳ"]={ "α","ͅ" },
+ ["ᾴ"]={ "ά","ͅ" },
+ ["ᾶ"]={ "α","͂" },
+ ["ᾷ"]={ "ᾶ","ͅ" },
+ ["Ᾰ"]={ "Α","̆" },
+ ["Ᾱ"]={ "Α","̄" },
+ ["Ὰ"]={ "Α","̀" },
+ ["ᾼ"]={ "Α","ͅ" },
+ ["῁"]={ "¨","͂" },
+ ["ῂ"]={ "ὴ","ͅ" },
+ ["ῃ"]={ "η","ͅ" },
+ ["ῄ"]={ "ή","ͅ" },
+ ["ῆ"]={ "η","͂" },
+ ["ῇ"]={ "ῆ","ͅ" },
+ ["Ὲ"]={ "Ε","̀" },
+ ["Ὴ"]={ "Η","̀" },
+ ["ῌ"]={ "Η","ͅ" },
+ ["῍"]={ "᾿","̀" },
+ ["῎"]={ "᾿","́" },
+ ["῏"]={ "᾿","͂" },
+ ["ῐ"]={ "ι","̆" },
+ ["ῑ"]={ "ι","̄" },
+ ["ῒ"]={ "ϊ","̀" },
+ ["ῖ"]={ "ι","͂" },
+ ["ῗ"]={ "ϊ","͂" },
+ ["Ῐ"]={ "Ι","̆" },
+ ["Ῑ"]={ "Ι","̄" },
+ ["Ὶ"]={ "Ι","̀" },
+ ["῝"]={ "῾","̀" },
+ ["῞"]={ "῾","́" },
+ ["῟"]={ "῾","͂" },
+ ["ῠ"]={ "υ","̆" },
+ ["ῡ"]={ "υ","̄" },
+ ["ῢ"]={ "ϋ","̀" },
+ ["ῤ"]={ "ρ","̓" },
+ ["ῥ"]={ "ρ","̔" },
+ ["ῦ"]={ "υ","͂" },
+ ["ῧ"]={ "ϋ","͂" },
+ ["Ῠ"]={ "Υ","̆" },
+ ["Ῡ"]={ "Υ","̄" },
+ ["Ὺ"]={ "Υ","̀" },
+ ["Ῥ"]={ "Ρ","̔" },
+ ["῭"]={ "¨","̀" },
+ ["ῲ"]={ "ὼ","ͅ" },
+ ["ῳ"]={ "ω","ͅ" },
+ ["ῴ"]={ "ώ","ͅ" },
+ ["ῶ"]={ "ω","͂" },
+ ["ῷ"]={ "ῶ","ͅ" },
+ ["Ὸ"]={ "Ο","̀" },
+ ["Ὼ"]={ "Ω","̀" },
+ ["ῼ"]={ "Ω","ͅ" },
+ ["↚"]={ "←","̸" },
+ ["↛"]={ "→","̸" },
+ ["↮"]={ "↔","̸" },
+ ["⇍"]={ "⇐","̸" },
+ ["⇎"]={ "⇔","̸" },
+ ["⇏"]={ "⇒","̸" },
+ ["∄"]={ "∃","̸" },
+ ["∉"]={ "∈","̸" },
+ ["∌"]={ "∋","̸" },
+ ["∤"]={ "∣","̸" },
+ ["∦"]={ "∥","̸" },
+ ["≁"]={ "∼","̸" },
+ ["≄"]={ "≃","̸" },
+ ["≇"]={ "≅","̸" },
+ ["≉"]={ "≈","̸" },
+ ["≠"]={ "=","̸" },
+ ["≢"]={ "≡","̸" },
+ ["≭"]={ "≍","̸" },
+ ["≮"]={ "<","̸" },
+ ["≯"]={ ">","̸" },
+ ["≰"]={ "≤","̸" },
+ ["≱"]={ "≥","̸" },
+ ["≴"]={ "≲","̸" },
+ ["≵"]={ "≳","̸" },
+ ["≸"]={ "≶","̸" },
+ ["≹"]={ "≷","̸" },
+ ["⊀"]={ "≺","̸" },
+ ["⊁"]={ "≻","̸" },
+ ["⊄"]={ "⊂","̸" },
+ ["⊅"]={ "⊃","̸" },
+ ["⊈"]={ "⊆","̸" },
+ ["⊉"]={ "⊇","̸" },
+ ["⊬"]={ "⊢","̸" },
+ ["⊭"]={ "⊨","̸" },
+ ["⊮"]={ "⊩","̸" },
+ ["⊯"]={ "⊫","̸" },
+ ["⋠"]={ "≼","̸" },
+ ["⋡"]={ "≽","̸" },
+ ["⋢"]={ "⊑","̸" },
+ ["⋣"]={ "⊒","̸" },
+ ["⋪"]={ "⊲","̸" },
+ ["⋫"]={ "⊳","̸" },
+ ["⋬"]={ "⊴","̸" },
+ ["⋭"]={ "⊵","̸" },
+ ["⫝̸"]={ "⫝","̸" },
+ ["が"]={ "か","゙" },
+ ["ぎ"]={ "き","゙" },
+ ["ぐ"]={ "く","゙" },
+ ["げ"]={ "け","゙" },
+ ["ご"]={ "こ","゙" },
+ ["ざ"]={ "さ","゙" },
+ ["じ"]={ "し","゙" },
+ ["ず"]={ "す","゙" },
+ ["ぜ"]={ "せ","゙" },
+ ["ぞ"]={ "そ","゙" },
+ ["だ"]={ "た","゙" },
+ ["ぢ"]={ "ち","゙" },
+ ["づ"]={ "つ","゙" },
+ ["で"]={ "て","゙" },
+ ["ど"]={ "と","゙" },
+ ["ば"]={ "は","゙" },
+ ["ぱ"]={ "は","゚" },
+ ["び"]={ "ひ","゙" },
+ ["ぴ"]={ "ひ","゚" },
+ ["ぶ"]={ "ふ","゙" },
+ ["ぷ"]={ "ふ","゚" },
+ ["べ"]={ "へ","゙" },
+ ["ぺ"]={ "へ","゚" },
+ ["ぼ"]={ "ほ","゙" },
+ ["ぽ"]={ "ほ","゚" },
+ ["ゔ"]={ "う","゙" },
+ ["ゞ"]={ "ゝ","゙" },
+ ["ガ"]={ "カ","゙" },
+ ["ギ"]={ "キ","゙" },
+ ["グ"]={ "ク","゙" },
+ ["ゲ"]={ "ケ","゙" },
+ ["ゴ"]={ "コ","゙" },
+ ["ザ"]={ "サ","゙" },
+ ["ジ"]={ "シ","゙" },
+ ["ズ"]={ "ス","゙" },
+ ["ゼ"]={ "セ","゙" },
+ ["ゾ"]={ "ソ","゙" },
+ ["ダ"]={ "タ","゙" },
+ ["ヂ"]={ "チ","゙" },
+ ["ヅ"]={ "ツ","゙" },
+ ["デ"]={ "テ","゙" },
+ ["ド"]={ "ト","゙" },
+ ["バ"]={ "ハ","゙" },
+ ["パ"]={ "ハ","゚" },
+ ["ビ"]={ "ヒ","゙" },
+ ["ピ"]={ "ヒ","゚" },
+ ["ブ"]={ "フ","゙" },
+ ["プ"]={ "フ","゚" },
+ ["ベ"]={ "ヘ","゙" },
+ ["ペ"]={ "ヘ","゚" },
+ ["ボ"]={ "ホ","゙" },
+ ["ポ"]={ "ホ","゚" },
+ ["ヴ"]={ "ウ","゙" },
+ ["ヷ"]={ "ワ","゙" },
+ ["ヸ"]={ "ヰ","゙" },
+ ["ヹ"]={ "ヱ","゙" },
+ ["ヺ"]={ "ヲ","゙" },
+ ["ヾ"]={ "ヽ","゙" },
+ ["יִ"]={ "י","ִ" },
+ ["ײַ"]={ "ײ","ַ" },
+ ["שׁ"]={ "ש","ׁ" },
+ ["שׂ"]={ "ש","ׂ" },
+ ["שּׁ"]={ "שּ","ׁ" },
+ ["שּׂ"]={ "שּ","ׂ" },
+ ["אַ"]={ "א","ַ" },
+ ["אָ"]={ "א","ָ" },
+ ["אּ"]={ "א","ּ" },
+ ["בּ"]={ "ב","ּ" },
+ ["גּ"]={ "ג","ּ" },
+ ["דּ"]={ "ד","ּ" },
+ ["הּ"]={ "ה","ּ" },
+ ["וּ"]={ "ו","ּ" },
+ ["זּ"]={ "ז","ּ" },
+ ["טּ"]={ "ט","ּ" },
+ ["יּ"]={ "י","ּ" },
+ ["ךּ"]={ "ך","ּ" },
+ ["כּ"]={ "כ","ּ" },
+ ["לּ"]={ "ל","ּ" },
+ ["מּ"]={ "מ","ּ" },
+ ["נּ"]={ "נ","ּ" },
+ ["סּ"]={ "ס","ּ" },
+ ["ףּ"]={ "ף","ּ" },
+ ["פּ"]={ "פ","ּ" },
+ ["צּ"]={ "צ","ּ" },
+ ["קּ"]={ "ק","ּ" },
+ ["רּ"]={ "ר","ּ" },
+ ["שּ"]={ "ש","ּ" },
+ ["תּ"]={ "ת","ּ" },
+ ["וֹ"]={ "ו","ֹ" },
+ ["בֿ"]={ "ב","ֿ" },
+ ["כֿ"]={ "כ","ֿ" },
+ ["פֿ"]={ "פ","ֿ" },
+ ["𑂚"]={ "𑂙","𑂺" },
+ ["𑂜"]={ "𑂛","𑂺" },
+ ["𑂫"]={ "𑂥","𑂺" },
+ ["𑄮"]={ "𑄱","𑄧" },
+ ["𑄯"]={ "𑄲","𑄧" },
+ ["𑍋"]={ "𑍇","𑌾" },
+ ["𑍌"]={ "𑍇","𑍗" },
+ ["𑒻"]={ "𑒹","𑒺" },
+ ["𑒼"]={ "𑒹","𑒰" },
+ ["𑒾"]={ "𑒹","𑒽" },
+ ["𑖺"]={ "𑖸","𑖯" },
+ ["𑖻"]={ "𑖹","𑖯" },
+ ["𝅗𝅥"]={ "𝅗","𝅥" },
+ ["𝅘𝅥"]={ "𝅘","𝅥" },
+ ["𝅘𝅥𝅮"]={ "𝅘𝅥","𝅮" },
+ ["𝅘𝅥𝅯"]={ "𝅘𝅥","𝅯" },
+ ["𝅘𝅥𝅰"]={ "𝅘𝅥","𝅰" },
+ ["𝅘𝅥𝅱"]={ "𝅘𝅥","𝅱" },
+ ["𝅘𝅥𝅲"]={ "𝅘𝅥","𝅲" },
+ ["𝆹𝅥"]={ "𝆹","𝅥" },
+ ["𝆺𝅥"]={ "𝆺","𝅥" },
+ ["𝆹𝅥𝅮"]={ "𝆹𝅥","𝅮" },
+ ["𝆺𝅥𝅮"]={ "𝆺𝅥","𝅮" },
+ ["𝆹𝅥𝅯"]={ "𝆹𝅥","𝅯" },
+ ["𝆺𝅥𝅯"]={ "𝆺𝅥","𝅯" },
+ },
+ },
+ {
+ ["data"]={
+ ["À"]={ "A","̀" },
+ ["Á"]={ "A","́" },
+ ["Â"]={ "A","̂" },
+ ["Ã"]={ "A","̃" },
+ ["Ä"]={ "A","̈" },
+ ["Å"]={ "A","̊" },
+ ["Ç"]={ "C","̧" },
+ ["È"]={ "E","̀" },
+ ["É"]={ "E","́" },
+ ["Ê"]={ "E","̂" },
+ ["Ë"]={ "E","̈" },
+ ["Ì"]={ "I","̀" },
+ ["Í"]={ "I","́" },
+ ["Î"]={ "I","̂" },
+ ["Ï"]={ "I","̈" },
+ ["Ñ"]={ "N","̃" },
+ ["Ò"]={ "O","̀" },
+ ["Ó"]={ "O","́" },
+ ["Ô"]={ "O","̂" },
+ ["Õ"]={ "O","̃" },
+ ["Ö"]={ "O","̈" },
+ ["Ù"]={ "U","̀" },
+ ["Ú"]={ "U","́" },
+ ["Û"]={ "U","̂" },
+ ["Ü"]={ "U","̈" },
+ ["Ý"]={ "Y","́" },
+ ["à"]={ "a","̀" },
+ ["á"]={ "a","́" },
+ ["â"]={ "a","̂" },
+ ["ã"]={ "a","̃" },
+ ["ä"]={ "a","̈" },
+ ["å"]={ "a","̊" },
+ ["ç"]={ "c","̧" },
+ ["è"]={ "e","̀" },
+ ["é"]={ "e","́" },
+ ["ê"]={ "e","̂" },
+ ["ë"]={ "e","̈" },
+ ["ì"]={ "i","̀" },
+ ["í"]={ "i","́" },
+ ["î"]={ "i","̂" },
+ ["ï"]={ "i","̈" },
+ ["ñ"]={ "n","̃" },
+ ["ò"]={ "o","̀" },
+ ["ó"]={ "o","́" },
+ ["ô"]={ "o","̂" },
+ ["õ"]={ "o","̃" },
+ ["ö"]={ "o","̈" },
+ ["ù"]={ "u","̀" },
+ ["ú"]={ "u","́" },
+ ["û"]={ "u","̂" },
+ ["ü"]={ "u","̈" },
+ ["ý"]={ "y","́" },
+ ["ÿ"]={ "y","̈" },
+ ["Ā"]={ "A","̄" },
+ ["ā"]={ "a","̄" },
+ ["Ă"]={ "A","̆" },
+ ["ă"]={ "a","̆" },
+ ["Ą"]={ "A","̨" },
+ ["ą"]={ "a","̨" },
+ ["Ć"]={ "C","́" },
+ ["ć"]={ "c","́" },
+ ["Ĉ"]={ "C","̂" },
+ ["ĉ"]={ "c","̂" },
+ ["Ċ"]={ "C","̇" },
+ ["ċ"]={ "c","̇" },
+ ["Č"]={ "C","̌" },
+ ["č"]={ "c","̌" },
+ ["Ď"]={ "D","̌" },
+ ["ď"]={ "d","̌" },
+ ["Ē"]={ "E","̄" },
+ ["ē"]={ "e","̄" },
+ ["Ĕ"]={ "E","̆" },
+ ["ĕ"]={ "e","̆" },
+ ["Ė"]={ "E","̇" },
+ ["ė"]={ "e","̇" },
+ ["Ę"]={ "E","̨" },
+ ["ę"]={ "e","̨" },
+ ["Ě"]={ "E","̌" },
+ ["ě"]={ "e","̌" },
+ ["Ĝ"]={ "G","̂" },
+ ["ĝ"]={ "g","̂" },
+ ["Ğ"]={ "G","̆" },
+ ["ğ"]={ "g","̆" },
+ ["Ġ"]={ "G","̇" },
+ ["ġ"]={ "g","̇" },
+ ["Ģ"]={ "G","̧" },
+ ["ģ"]={ "g","̧" },
+ ["Ĥ"]={ "H","̂" },
+ ["ĥ"]={ "h","̂" },
+ ["Ĩ"]={ "I","̃" },
+ ["ĩ"]={ "i","̃" },
+ ["Ī"]={ "I","̄" },
+ ["ī"]={ "i","̄" },
+ ["Ĭ"]={ "I","̆" },
+ ["ĭ"]={ "i","̆" },
+ ["Į"]={ "I","̨" },
+ ["į"]={ "i","̨" },
+ ["İ"]={ "I","̇" },
+ ["Ĵ"]={ "J","̂" },
+ ["ĵ"]={ "j","̂" },
+ ["Ķ"]={ "K","̧" },
+ ["ķ"]={ "k","̧" },
+ ["Ĺ"]={ "L","́" },
+ ["ĺ"]={ "l","́" },
+ ["Ļ"]={ "L","̧" },
+ ["ļ"]={ "l","̧" },
+ ["Ľ"]={ "L","̌" },
+ ["ľ"]={ "l","̌" },
+ ["Ń"]={ "N","́" },
+ ["ń"]={ "n","́" },
+ ["Ņ"]={ "N","̧" },
+ ["ņ"]={ "n","̧" },
+ ["Ň"]={ "N","̌" },
+ ["ň"]={ "n","̌" },
+ ["Ō"]={ "O","̄" },
+ ["ō"]={ "o","̄" },
+ ["Ŏ"]={ "O","̆" },
+ ["ŏ"]={ "o","̆" },
+ ["Ő"]={ "O","̋" },
+ ["ő"]={ "o","̋" },
+ ["Ŕ"]={ "R","́" },
+ ["ŕ"]={ "r","́" },
+ ["Ŗ"]={ "R","̧" },
+ ["ŗ"]={ "r","̧" },
+ ["Ř"]={ "R","̌" },
+ ["ř"]={ "r","̌" },
+ ["Ś"]={ "S","́" },
+ ["ś"]={ "s","́" },
+ ["Ŝ"]={ "S","̂" },
+ ["ŝ"]={ "s","̂" },
+ ["Ş"]={ "S","̧" },
+ ["ş"]={ "s","̧" },
+ ["Š"]={ "S","̌" },
+ ["š"]={ "s","̌" },
+ ["Ţ"]={ "T","̧" },
+ ["ţ"]={ "t","̧" },
+ ["Ť"]={ "T","̌" },
+ ["ť"]={ "t","̌" },
+ ["Ũ"]={ "U","̃" },
+ ["ũ"]={ "u","̃" },
+ ["Ū"]={ "U","̄" },
+ ["ū"]={ "u","̄" },
+ ["Ŭ"]={ "U","̆" },
+ ["ŭ"]={ "u","̆" },
+ ["Ů"]={ "U","̊" },
+ ["ů"]={ "u","̊" },
+ ["Ű"]={ "U","̋" },
+ ["ű"]={ "u","̋" },
+ ["Ų"]={ "U","̨" },
+ ["ų"]={ "u","̨" },
+ ["Ŵ"]={ "W","̂" },
+ ["ŵ"]={ "w","̂" },
+ ["Ŷ"]={ "Y","̂" },
+ ["ŷ"]={ "y","̂" },
+ ["Ÿ"]={ "Y","̈" },
+ ["Ź"]={ "Z","́" },
+ ["ź"]={ "z","́" },
+ ["Ż"]={ "Z","̇" },
+ ["ż"]={ "z","̇" },
+ ["Ž"]={ "Z","̌" },
+ ["ž"]={ "z","̌" },
+ ["Ơ"]={ "O","̛" },
+ ["ơ"]={ "o","̛" },
+ ["Ư"]={ "U","̛" },
+ ["ư"]={ "u","̛" },
+ ["Ǎ"]={ "A","̌" },
+ ["ǎ"]={ "a","̌" },
+ ["Ǐ"]={ "I","̌" },
+ ["ǐ"]={ "i","̌" },
+ ["Ǒ"]={ "O","̌" },
+ ["ǒ"]={ "o","̌" },
+ ["Ǔ"]={ "U","̌" },
+ ["ǔ"]={ "u","̌" },
+ ["Ǖ"]={ "Ü","̄" },
+ ["ǖ"]={ "ü","̄" },
+ ["Ǘ"]={ "Ü","́" },
+ ["ǘ"]={ "ü","́" },
+ ["Ǚ"]={ "Ü","̌" },
+ ["ǚ"]={ "ü","̌" },
+ ["Ǜ"]={ "Ü","̀" },
+ ["ǜ"]={ "ü","̀" },
+ ["Ǟ"]={ "Ä","̄" },
+ ["ǟ"]={ "ä","̄" },
+ ["Ǡ"]={ "Ȧ","̄" },
+ ["ǡ"]={ "ȧ","̄" },
+ ["Ǣ"]={ "Æ","̄" },
+ ["ǣ"]={ "æ","̄" },
+ ["Ǧ"]={ "G","̌" },
+ ["ǧ"]={ "g","̌" },
+ ["Ǩ"]={ "K","̌" },
+ ["ǩ"]={ "k","̌" },
+ ["Ǫ"]={ "O","̨" },
+ ["ǫ"]={ "o","̨" },
+ ["Ǭ"]={ "Ǫ","̄" },
+ ["ǭ"]={ "ǫ","̄" },
+ ["Ǯ"]={ "Ʒ","̌" },
+ ["ǯ"]={ "ʒ","̌" },
+ ["ǰ"]={ "j","̌" },
+ ["Ǵ"]={ "G","́" },
+ ["ǵ"]={ "g","́" },
+ ["Ǹ"]={ "N","̀" },
+ ["ǹ"]={ "n","̀" },
+ ["Ǻ"]={ "Å","́" },
+ ["ǻ"]={ "å","́" },
+ ["Ǽ"]={ "Æ","́" },
+ ["ǽ"]={ "æ","́" },
+ ["Ǿ"]={ "Ø","́" },
+ ["ǿ"]={ "ø","́" },
+ ["Ȁ"]={ "A","̏" },
+ ["ȁ"]={ "a","̏" },
+ ["Ȃ"]={ "A","̑" },
+ ["ȃ"]={ "a","̑" },
+ ["Ȅ"]={ "E","̏" },
+ ["ȅ"]={ "e","̏" },
+ ["Ȇ"]={ "E","̑" },
+ ["ȇ"]={ "e","̑" },
+ ["Ȉ"]={ "I","̏" },
+ ["ȉ"]={ "i","̏" },
+ ["Ȋ"]={ "I","̑" },
+ ["ȋ"]={ "i","̑" },
+ ["Ȍ"]={ "O","̏" },
+ ["ȍ"]={ "o","̏" },
+ ["Ȏ"]={ "O","̑" },
+ ["ȏ"]={ "o","̑" },
+ ["Ȑ"]={ "R","̏" },
+ ["ȑ"]={ "r","̏" },
+ ["Ȓ"]={ "R","̑" },
+ ["ȓ"]={ "r","̑" },
+ ["Ȕ"]={ "U","̏" },
+ ["ȕ"]={ "u","̏" },
+ ["Ȗ"]={ "U","̑" },
+ ["ȗ"]={ "u","̑" },
+ ["Ș"]={ "S","̦" },
+ ["ș"]={ "s","̦" },
+ ["Ț"]={ "T","̦" },
+ ["ț"]={ "t","̦" },
+ ["Ȟ"]={ "H","̌" },
+ ["ȟ"]={ "h","̌" },
+ ["Ȧ"]={ "A","̇" },
+ ["ȧ"]={ "a","̇" },
+ ["Ȩ"]={ "E","̧" },
+ ["ȩ"]={ "e","̧" },
+ ["Ȫ"]={ "Ö","̄" },
+ ["ȫ"]={ "ö","̄" },
+ ["Ȭ"]={ "Õ","̄" },
+ ["ȭ"]={ "õ","̄" },
+ ["Ȯ"]={ "O","̇" },
+ ["ȯ"]={ "o","̇" },
+ ["Ȱ"]={ "Ȯ","̄" },
+ ["ȱ"]={ "ȯ","̄" },
+ ["Ȳ"]={ "Y","̄" },
+ ["ȳ"]={ "y","̄" },
+ ["̈́"]={ "̈","́" },
+ ["΅"]={ "¨","́" },
+ ["Ά"]={ "Α","́" },
+ ["Έ"]={ "Ε","́" },
+ ["Ή"]={ "Η","́" },
+ ["Ί"]={ "Ι","́" },
+ ["Ό"]={ "Ο","́" },
+ ["Ύ"]={ "Υ","́" },
+ ["Ώ"]={ "Ω","́" },
+ ["ΐ"]={ "ϊ","́" },
+ ["Ϊ"]={ "Ι","̈" },
+ ["Ϋ"]={ "Υ","̈" },
+ ["ά"]={ "α","́" },
+ ["έ"]={ "ε","́" },
+ ["ή"]={ "η","́" },
+ ["ί"]={ "ι","́" },
+ ["ΰ"]={ "ϋ","́" },
+ ["ϊ"]={ "ι","̈" },
+ ["ϋ"]={ "υ","̈" },
+ ["ό"]={ "ο","́" },
+ ["ύ"]={ "υ","́" },
+ ["ώ"]={ "ω","́" },
+ ["ϓ"]={ "ϒ","́" },
+ ["ϔ"]={ "ϒ","̈" },
+ ["Ѐ"]={ "Е","̀" },
+ ["Ё"]={ "Е","̈" },
+ ["Ѓ"]={ "Г","́" },
+ ["Ї"]={ "І","̈" },
+ ["Ќ"]={ "К","́" },
+ ["Ѝ"]={ "И","̀" },
+ ["Ў"]={ "У","̆" },
+ ["Й"]={ "И","̆" },
+ ["й"]={ "и","̆" },
+ ["ѐ"]={ "е","̀" },
+ ["ё"]={ "е","̈" },
+ ["ѓ"]={ "г","́" },
+ ["ї"]={ "і","̈" },
+ ["ќ"]={ "к","́" },
+ ["ѝ"]={ "и","̀" },
+ ["ў"]={ "у","̆" },
+ ["Ѷ"]={ "Ѵ","̏" },
+ ["ѷ"]={ "ѵ","̏" },
+ ["Ӂ"]={ "Ж","̆" },
+ ["ӂ"]={ "ж","̆" },
+ ["Ӑ"]={ "А","̆" },
+ ["ӑ"]={ "а","̆" },
+ ["Ӓ"]={ "А","̈" },
+ ["ӓ"]={ "а","̈" },
+ ["Ӗ"]={ "Е","̆" },
+ ["ӗ"]={ "е","̆" },
+ ["Ӛ"]={ "Ә","̈" },
+ ["ӛ"]={ "ә","̈" },
+ ["Ӝ"]={ "Ж","̈" },
+ ["ӝ"]={ "ж","̈" },
+ ["Ӟ"]={ "З","̈" },
+ ["ӟ"]={ "з","̈" },
+ ["Ӣ"]={ "И","̄" },
+ ["ӣ"]={ "и","̄" },
+ ["Ӥ"]={ "И","̈" },
+ ["ӥ"]={ "и","̈" },
+ ["Ӧ"]={ "О","̈" },
+ ["ӧ"]={ "о","̈" },
+ ["Ӫ"]={ "Ө","̈" },
+ ["ӫ"]={ "ө","̈" },
+ ["Ӭ"]={ "Э","̈" },
+ ["ӭ"]={ "э","̈" },
+ ["Ӯ"]={ "У","̄" },
+ ["ӯ"]={ "у","̄" },
+ ["Ӱ"]={ "У","̈" },
+ ["ӱ"]={ "у","̈" },
+ ["Ӳ"]={ "У","̋" },
+ ["ӳ"]={ "у","̋" },
+ ["Ӵ"]={ "Ч","̈" },
+ ["ӵ"]={ "ч","̈" },
+ ["Ӹ"]={ "Ы","̈" },
+ ["ӹ"]={ "ы","̈" },
+ ["آ"]={ "ا","ٓ" },
+ ["أ"]={ "ا","ٔ" },
+ ["ؤ"]={ "و","ٔ" },
+ ["إ"]={ "ا","ٕ" },
+ ["ئ"]={ "ي","ٔ" },
+ ["ۀ"]={ "ە","ٔ" },
+ ["ۂ"]={ "ہ","ٔ" },
+ ["ۓ"]={ "ے","ٔ" },
+ ["ऩ"]={ "न","़" },
+ ["ऱ"]={ "र","़" },
+ ["ऴ"]={ "ळ","़" },
+ ["क़"]={ "क","़" },
+ ["ख़"]={ "ख","़" },
+ ["ग़"]={ "ग","़" },
+ ["ज़"]={ "ज","़" },
+ ["ड़"]={ "ड","़" },
+ ["ढ़"]={ "ढ","़" },
+ ["फ़"]={ "फ","़" },
+ ["य़"]={ "य","़" },
+ ["ো"]={ "ে","া" },
+ ["ৌ"]={ "ে","ৗ" },
+ ["ড়"]={ "ড","়" },
+ ["ঢ়"]={ "ঢ","়" },
+ ["য়"]={ "য","়" },
+ ["ਲ਼"]={ "ਲ","਼" },
+ ["ਸ਼"]={ "ਸ","਼" },
+ ["ਖ਼"]={ "ਖ","਼" },
+ ["ਗ਼"]={ "ਗ","਼" },
+ ["ਜ਼"]={ "ਜ","਼" },
+ ["ਫ਼"]={ "ਫ","਼" },
+ ["ୈ"]={ "େ","ୖ" },
+ ["ୋ"]={ "େ","ା" },
+ ["ୌ"]={ "େ","ୗ" },
+ ["ଡ଼"]={ "ଡ","଼" },
+ ["ଢ଼"]={ "ଢ","଼" },
+ ["ஔ"]={ "ஒ","ௗ" },
+ ["ொ"]={ "ெ","ா" },
+ ["ோ"]={ "ே","ா" },
+ ["ௌ"]={ "ெ","ௗ" },
+ ["ై"]={ "ె","ౖ" },
+ ["ೀ"]={ "ಿ","ೕ" },
+ ["ೇ"]={ "ೆ","ೕ" },
+ ["ೈ"]={ "ೆ","ೖ" },
+ ["ೊ"]={ "ೆ","ೂ" },
+ ["ೋ"]={ "ೊ","ೕ" },
+ ["ൊ"]={ "െ","ാ" },
+ ["ോ"]={ "േ","ാ" },
+ ["ൌ"]={ "െ","ൗ" },
+ ["ේ"]={ "ෙ","්" },
+ ["ො"]={ "ෙ","ා" },
+ ["ෝ"]={ "ො","්" },
+ ["ෞ"]={ "ෙ","ෟ" },
+ ["གྷ"]={ "ག","ྷ" },
+ ["ཌྷ"]={ "ཌ","ྷ" },
+ ["དྷ"]={ "ད","ྷ" },
+ ["བྷ"]={ "བ","ྷ" },
+ ["ཛྷ"]={ "ཛ","ྷ" },
+ ["ཀྵ"]={ "ཀ","ྵ" },
+ ["ཱི"]={ "ཱ","ི" },
+ ["ཱུ"]={ "ཱ","ུ" },
+ ["ྲྀ"]={ "ྲ","ྀ" },
+ ["ླྀ"]={ "ླ","ྀ" },
+ ["ཱྀ"]={ "ཱ","ྀ" },
+ ["ྒྷ"]={ "ྒ","ྷ" },
+ ["ྜྷ"]={ "ྜ","ྷ" },
+ ["ྡྷ"]={ "ྡ","ྷ" },
+ ["ྦྷ"]={ "ྦ","ྷ" },
+ ["ྫྷ"]={ "ྫ","ྷ" },
+ ["ྐྵ"]={ "ྐ","ྵ" },
+ ["ဦ"]={ "ဥ","ီ" },
+ ["ᬆ"]={ "ᬅ","ᬵ" },
+ ["ᬈ"]={ "ᬇ","ᬵ" },
+ ["ᬊ"]={ "ᬉ","ᬵ" },
+ ["ᬌ"]={ "ᬋ","ᬵ" },
+ ["ᬎ"]={ "ᬍ","ᬵ" },
+ ["ᬒ"]={ "ᬑ","ᬵ" },
+ ["ᬻ"]={ "ᬺ","ᬵ" },
+ ["ᬽ"]={ "ᬼ","ᬵ" },
+ ["ᭀ"]={ "ᬾ","ᬵ" },
+ ["ᭁ"]={ "ᬿ","ᬵ" },
+ ["ᭃ"]={ "ᭂ","ᬵ" },
+ ["Ḁ"]={ "A","̥" },
+ ["ḁ"]={ "a","̥" },
+ ["Ḃ"]={ "B","̇" },
+ ["ḃ"]={ "b","̇" },
+ ["Ḅ"]={ "B","̣" },
+ ["ḅ"]={ "b","̣" },
+ ["Ḇ"]={ "B","̱" },
+ ["ḇ"]={ "b","̱" },
+ ["Ḉ"]={ "Ç","́" },
+ ["ḉ"]={ "ç","́" },
+ ["Ḋ"]={ "D","̇" },
+ ["ḋ"]={ "d","̇" },
+ ["Ḍ"]={ "D","̣" },
+ ["ḍ"]={ "d","̣" },
+ ["Ḏ"]={ "D","̱" },
+ ["ḏ"]={ "d","̱" },
+ ["Ḑ"]={ "D","̧" },
+ ["ḑ"]={ "d","̧" },
+ ["Ḓ"]={ "D","̭" },
+ ["ḓ"]={ "d","̭" },
+ ["Ḕ"]={ "Ē","̀" },
+ ["ḕ"]={ "ē","̀" },
+ ["Ḗ"]={ "Ē","́" },
+ ["ḗ"]={ "ē","́" },
+ ["Ḙ"]={ "E","̭" },
+ ["ḙ"]={ "e","̭" },
+ ["Ḛ"]={ "E","̰" },
+ ["ḛ"]={ "e","̰" },
+ ["Ḝ"]={ "Ȩ","̆" },
+ ["ḝ"]={ "ȩ","̆" },
+ ["Ḟ"]={ "F","̇" },
+ ["ḟ"]={ "f","̇" },
+ ["Ḡ"]={ "G","̄" },
+ ["ḡ"]={ "g","̄" },
+ ["Ḣ"]={ "H","̇" },
+ ["ḣ"]={ "h","̇" },
+ ["Ḥ"]={ "H","̣" },
+ ["ḥ"]={ "h","̣" },
+ ["Ḧ"]={ "H","̈" },
+ ["ḧ"]={ "h","̈" },
+ ["Ḩ"]={ "H","̧" },
+ ["ḩ"]={ "h","̧" },
+ ["Ḫ"]={ "H","̮" },
+ ["ḫ"]={ "h","̮" },
+ ["Ḭ"]={ "I","̰" },
+ ["ḭ"]={ "i","̰" },
+ ["Ḯ"]={ "Ï","́" },
+ ["ḯ"]={ "ï","́" },
+ ["Ḱ"]={ "K","́" },
+ ["ḱ"]={ "k","́" },
+ ["Ḳ"]={ "K","̣" },
+ ["ḳ"]={ "k","̣" },
+ ["Ḵ"]={ "K","̱" },
+ ["ḵ"]={ "k","̱" },
+ ["Ḷ"]={ "L","̣" },
+ ["ḷ"]={ "l","̣" },
+ ["Ḹ"]={ "Ḷ","̄" },
+ ["ḹ"]={ "ḷ","̄" },
+ ["Ḻ"]={ "L","̱" },
+ ["ḻ"]={ "l","̱" },
+ ["Ḽ"]={ "L","̭" },
+ ["ḽ"]={ "l","̭" },
+ ["Ḿ"]={ "M","́" },
+ ["ḿ"]={ "m","́" },
+ ["Ṁ"]={ "M","̇" },
+ ["ṁ"]={ "m","̇" },
+ ["Ṃ"]={ "M","̣" },
+ ["ṃ"]={ "m","̣" },
+ ["Ṅ"]={ "N","̇" },
+ ["ṅ"]={ "n","̇" },
+ ["Ṇ"]={ "N","̣" },
+ ["ṇ"]={ "n","̣" },
+ ["Ṉ"]={ "N","̱" },
+ ["ṉ"]={ "n","̱" },
+ ["Ṋ"]={ "N","̭" },
+ ["ṋ"]={ "n","̭" },
+ ["Ṍ"]={ "Õ","́" },
+ ["ṍ"]={ "õ","́" },
+ ["Ṏ"]={ "Õ","̈" },
+ ["ṏ"]={ "õ","̈" },
+ ["Ṑ"]={ "Ō","̀" },
+ ["ṑ"]={ "ō","̀" },
+ ["Ṓ"]={ "Ō","́" },
+ ["ṓ"]={ "ō","́" },
+ ["Ṕ"]={ "P","́" },
+ ["ṕ"]={ "p","́" },
+ ["Ṗ"]={ "P","̇" },
+ ["ṗ"]={ "p","̇" },
+ ["Ṙ"]={ "R","̇" },
+ ["ṙ"]={ "r","̇" },
+ ["Ṛ"]={ "R","̣" },
+ ["ṛ"]={ "r","̣" },
+ ["Ṝ"]={ "Ṛ","̄" },
+ ["ṝ"]={ "ṛ","̄" },
+ ["Ṟ"]={ "R","̱" },
+ ["ṟ"]={ "r","̱" },
+ ["Ṡ"]={ "S","̇" },
+ ["ṡ"]={ "s","̇" },
+ ["Ṣ"]={ "S","̣" },
+ ["ṣ"]={ "s","̣" },
+ ["Ṥ"]={ "Ś","̇" },
+ ["ṥ"]={ "ś","̇" },
+ ["Ṧ"]={ "Š","̇" },
+ ["ṧ"]={ "š","̇" },
+ ["Ṩ"]={ "Ṣ","̇" },
+ ["ṩ"]={ "ṣ","̇" },
+ ["Ṫ"]={ "T","̇" },
+ ["ṫ"]={ "t","̇" },
+ ["Ṭ"]={ "T","̣" },
+ ["ṭ"]={ "t","̣" },
+ ["Ṯ"]={ "T","̱" },
+ ["ṯ"]={ "t","̱" },
+ ["Ṱ"]={ "T","̭" },
+ ["ṱ"]={ "t","̭" },
+ ["Ṳ"]={ "U","̤" },
+ ["ṳ"]={ "u","̤" },
+ ["Ṵ"]={ "U","̰" },
+ ["ṵ"]={ "u","̰" },
+ ["Ṷ"]={ "U","̭" },
+ ["ṷ"]={ "u","̭" },
+ ["Ṹ"]={ "Ũ","́" },
+ ["ṹ"]={ "ũ","́" },
+ ["Ṻ"]={ "Ū","̈" },
+ ["ṻ"]={ "ū","̈" },
+ ["Ṽ"]={ "V","̃" },
+ ["ṽ"]={ "v","̃" },
+ ["Ṿ"]={ "V","̣" },
+ ["ṿ"]={ "v","̣" },
+ ["Ẁ"]={ "W","̀" },
+ ["ẁ"]={ "w","̀" },
+ ["Ẃ"]={ "W","́" },
+ ["ẃ"]={ "w","́" },
+ ["Ẅ"]={ "W","̈" },
+ ["ẅ"]={ "w","̈" },
+ ["Ẇ"]={ "W","̇" },
+ ["ẇ"]={ "w","̇" },
+ ["Ẉ"]={ "W","̣" },
+ ["ẉ"]={ "w","̣" },
+ ["Ẋ"]={ "X","̇" },
+ ["ẋ"]={ "x","̇" },
+ ["Ẍ"]={ "X","̈" },
+ ["ẍ"]={ "x","̈" },
+ ["Ẏ"]={ "Y","̇" },
+ ["ẏ"]={ "y","̇" },
+ ["Ẑ"]={ "Z","̂" },
+ ["ẑ"]={ "z","̂" },
+ ["Ẓ"]={ "Z","̣" },
+ ["ẓ"]={ "z","̣" },
+ ["Ẕ"]={ "Z","̱" },
+ ["ẕ"]={ "z","̱" },
+ ["ẖ"]={ "h","̱" },
+ ["ẗ"]={ "t","̈" },
+ ["ẘ"]={ "w","̊" },
+ ["ẙ"]={ "y","̊" },
+ ["ẛ"]={ "ſ","̇" },
+ ["Ạ"]={ "A","̣" },
+ ["ạ"]={ "a","̣" },
+ ["Ả"]={ "A","̉" },
+ ["ả"]={ "a","̉" },
+ ["Ấ"]={ "Â","́" },
+ ["ấ"]={ "â","́" },
+ ["Ầ"]={ "Â","̀" },
+ ["ầ"]={ "â","̀" },
+ ["Ẩ"]={ "Â","̉" },
+ ["ẩ"]={ "â","̉" },
+ ["Ẫ"]={ "Â","̃" },
+ ["ẫ"]={ "â","̃" },
+ ["Ậ"]={ "Ạ","̂" },
+ ["ậ"]={ "ạ","̂" },
+ ["Ắ"]={ "Ă","́" },
+ ["ắ"]={ "ă","́" },
+ ["Ằ"]={ "Ă","̀" },
+ ["ằ"]={ "ă","̀" },
+ ["Ẳ"]={ "Ă","̉" },
+ ["ẳ"]={ "ă","̉" },
+ ["Ẵ"]={ "Ă","̃" },
+ ["ẵ"]={ "ă","̃" },
+ ["Ặ"]={ "Ạ","̆" },
+ ["ặ"]={ "ạ","̆" },
+ ["Ẹ"]={ "E","̣" },
+ ["ẹ"]={ "e","̣" },
+ ["Ẻ"]={ "E","̉" },
+ ["ẻ"]={ "e","̉" },
+ ["Ẽ"]={ "E","̃" },
+ ["ẽ"]={ "e","̃" },
+ ["Ế"]={ "Ê","́" },
+ ["ế"]={ "ê","́" },
+ ["Ề"]={ "Ê","̀" },
+ ["ề"]={ "ê","̀" },
+ ["Ể"]={ "Ê","̉" },
+ ["ể"]={ "ê","̉" },
+ ["Ễ"]={ "Ê","̃" },
+ ["ễ"]={ "ê","̃" },
+ ["Ệ"]={ "Ẹ","̂" },
+ ["ệ"]={ "ẹ","̂" },
+ ["Ỉ"]={ "I","̉" },
+ ["ỉ"]={ "i","̉" },
+ ["Ị"]={ "I","̣" },
+ ["ị"]={ "i","̣" },
+ ["Ọ"]={ "O","̣" },
+ ["ọ"]={ "o","̣" },
+ ["Ỏ"]={ "O","̉" },
+ ["ỏ"]={ "o","̉" },
+ ["Ố"]={ "Ô","́" },
+ ["ố"]={ "ô","́" },
+ ["Ồ"]={ "Ô","̀" },
+ ["ồ"]={ "ô","̀" },
+ ["Ổ"]={ "Ô","̉" },
+ ["ổ"]={ "ô","̉" },
+ ["Ỗ"]={ "Ô","̃" },
+ ["ỗ"]={ "ô","̃" },
+ ["Ộ"]={ "Ọ","̂" },
+ ["ộ"]={ "ọ","̂" },
+ ["Ớ"]={ "Ơ","́" },
+ ["ớ"]={ "ơ","́" },
+ ["Ờ"]={ "Ơ","̀" },
+ ["ờ"]={ "ơ","̀" },
+ ["Ở"]={ "Ơ","̉" },
+ ["ở"]={ "ơ","̉" },
+ ["Ỡ"]={ "Ơ","̃" },
+ ["ỡ"]={ "ơ","̃" },
+ ["Ợ"]={ "Ơ","̣" },
+ ["ợ"]={ "ơ","̣" },
+ ["Ụ"]={ "U","̣" },
+ ["ụ"]={ "u","̣" },
+ ["Ủ"]={ "U","̉" },
+ ["ủ"]={ "u","̉" },
+ ["Ứ"]={ "Ư","́" },
+ ["ứ"]={ "ư","́" },
+ ["Ừ"]={ "Ư","̀" },
+ ["ừ"]={ "ư","̀" },
+ ["Ử"]={ "Ư","̉" },
+ ["ử"]={ "ư","̉" },
+ ["Ữ"]={ "Ư","̃" },
+ ["ữ"]={ "ư","̃" },
+ ["Ự"]={ "Ư","̣" },
+ ["ự"]={ "ư","̣" },
+ ["Ỳ"]={ "Y","̀" },
+ ["ỳ"]={ "y","̀" },
+ ["Ỵ"]={ "Y","̣" },
+ ["ỵ"]={ "y","̣" },
+ ["Ỷ"]={ "Y","̉" },
+ ["ỷ"]={ "y","̉" },
+ ["Ỹ"]={ "Y","̃" },
+ ["ỹ"]={ "y","̃" },
+ ["ἀ"]={ "α","̓" },
+ ["ἁ"]={ "α","̔" },
+ ["ἂ"]={ "ἀ","̀" },
+ ["ἃ"]={ "ἁ","̀" },
+ ["ἄ"]={ "ἀ","́" },
+ ["ἅ"]={ "ἁ","́" },
+ ["ἆ"]={ "ἀ","͂" },
+ ["ἇ"]={ "ἁ","͂" },
+ ["Ἀ"]={ "Α","̓" },
+ ["Ἁ"]={ "Α","̔" },
+ ["Ἂ"]={ "Ἀ","̀" },
+ ["Ἃ"]={ "Ἁ","̀" },
+ ["Ἄ"]={ "Ἀ","́" },
+ ["Ἅ"]={ "Ἁ","́" },
+ ["Ἆ"]={ "Ἀ","͂" },
+ ["Ἇ"]={ "Ἁ","͂" },
+ ["ἐ"]={ "ε","̓" },
+ ["ἑ"]={ "ε","̔" },
+ ["ἒ"]={ "ἐ","̀" },
+ ["ἓ"]={ "ἑ","̀" },
+ ["ἔ"]={ "ἐ","́" },
+ ["ἕ"]={ "ἑ","́" },
+ ["Ἐ"]={ "Ε","̓" },
+ ["Ἑ"]={ "Ε","̔" },
+ ["Ἒ"]={ "Ἐ","̀" },
+ ["Ἓ"]={ "Ἑ","̀" },
+ ["Ἔ"]={ "Ἐ","́" },
+ ["Ἕ"]={ "Ἑ","́" },
+ ["ἠ"]={ "η","̓" },
+ ["ἡ"]={ "η","̔" },
+ ["ἢ"]={ "ἠ","̀" },
+ ["ἣ"]={ "ἡ","̀" },
+ ["ἤ"]={ "ἠ","́" },
+ ["ἥ"]={ "ἡ","́" },
+ ["ἦ"]={ "ἠ","͂" },
+ ["ἧ"]={ "ἡ","͂" },
+ ["Ἠ"]={ "Η","̓" },
+ ["Ἡ"]={ "Η","̔" },
+ ["Ἢ"]={ "Ἠ","̀" },
+ ["Ἣ"]={ "Ἡ","̀" },
+ ["Ἤ"]={ "Ἠ","́" },
+ ["Ἥ"]={ "Ἡ","́" },
+ ["Ἦ"]={ "Ἠ","͂" },
+ ["Ἧ"]={ "Ἡ","͂" },
+ ["ἰ"]={ "ι","̓" },
+ ["ἱ"]={ "ι","̔" },
+ ["ἲ"]={ "ἰ","̀" },
+ ["ἳ"]={ "ἱ","̀" },
+ ["ἴ"]={ "ἰ","́" },
+ ["ἵ"]={ "ἱ","́" },
+ ["ἶ"]={ "ἰ","͂" },
+ ["ἷ"]={ "ἱ","͂" },
+ ["Ἰ"]={ "Ι","̓" },
+ ["Ἱ"]={ "Ι","̔" },
+ ["Ἲ"]={ "Ἰ","̀" },
+ ["Ἳ"]={ "Ἱ","̀" },
+ ["Ἴ"]={ "Ἰ","́" },
+ ["Ἵ"]={ "Ἱ","́" },
+ ["Ἶ"]={ "Ἰ","͂" },
+ ["Ἷ"]={ "Ἱ","͂" },
+ ["ὀ"]={ "ο","̓" },
+ ["ὁ"]={ "ο","̔" },
+ ["ὂ"]={ "ὀ","̀" },
+ ["ὃ"]={ "ὁ","̀" },
+ ["ὄ"]={ "ὀ","́" },
+ ["ὅ"]={ "ὁ","́" },
+ ["Ὀ"]={ "Ο","̓" },
+ ["Ὁ"]={ "Ο","̔" },
+ ["Ὂ"]={ "Ὀ","̀" },
+ ["Ὃ"]={ "Ὁ","̀" },
+ ["Ὄ"]={ "Ὀ","́" },
+ ["Ὅ"]={ "Ὁ","́" },
+ ["ὐ"]={ "υ","̓" },
+ ["ὑ"]={ "υ","̔" },
+ ["ὒ"]={ "ὐ","̀" },
+ ["ὓ"]={ "ὑ","̀" },
+ ["ὔ"]={ "ὐ","́" },
+ ["ὕ"]={ "ὑ","́" },
+ ["ὖ"]={ "ὐ","͂" },
+ ["ὗ"]={ "ὑ","͂" },
+ ["Ὑ"]={ "Υ","̔" },
+ ["Ὓ"]={ "Ὑ","̀" },
+ ["Ὕ"]={ "Ὑ","́" },
+ ["Ὗ"]={ "Ὑ","͂" },
+ ["ὠ"]={ "ω","̓" },
+ ["ὡ"]={ "ω","̔" },
+ ["ὢ"]={ "ὠ","̀" },
+ ["ὣ"]={ "ὡ","̀" },
+ ["ὤ"]={ "ὠ","́" },
+ ["ὥ"]={ "ὡ","́" },
+ ["ὦ"]={ "ὠ","͂" },
+ ["ὧ"]={ "ὡ","͂" },
+ ["Ὠ"]={ "Ω","̓" },
+ ["Ὡ"]={ "Ω","̔" },
+ ["Ὢ"]={ "Ὠ","̀" },
+ ["Ὣ"]={ "Ὡ","̀" },
+ ["Ὤ"]={ "Ὠ","́" },
+ ["Ὥ"]={ "Ὡ","́" },
+ ["Ὦ"]={ "Ὠ","͂" },
+ ["Ὧ"]={ "Ὡ","͂" },
+ ["ὰ"]={ "α","̀" },
+ ["ὲ"]={ "ε","̀" },
+ ["ὴ"]={ "η","̀" },
+ ["ὶ"]={ "ι","̀" },
+ ["ὸ"]={ "ο","̀" },
+ ["ὺ"]={ "υ","̀" },
+ ["ὼ"]={ "ω","̀" },
+ ["ᾀ"]={ "ἀ","ͅ" },
+ ["ᾁ"]={ "ἁ","ͅ" },
+ ["ᾂ"]={ "ἂ","ͅ" },
+ ["ᾃ"]={ "ἃ","ͅ" },
+ ["ᾄ"]={ "ἄ","ͅ" },
+ ["ᾅ"]={ "ἅ","ͅ" },
+ ["ᾆ"]={ "ἆ","ͅ" },
+ ["ᾇ"]={ "ἇ","ͅ" },
+ ["ᾈ"]={ "Ἀ","ͅ" },
+ ["ᾉ"]={ "Ἁ","ͅ" },
+ ["ᾊ"]={ "Ἂ","ͅ" },
+ ["ᾋ"]={ "Ἃ","ͅ" },
+ ["ᾌ"]={ "Ἄ","ͅ" },
+ ["ᾍ"]={ "Ἅ","ͅ" },
+ ["ᾎ"]={ "Ἆ","ͅ" },
+ ["ᾏ"]={ "Ἇ","ͅ" },
+ ["ᾐ"]={ "ἠ","ͅ" },
+ ["ᾑ"]={ "ἡ","ͅ" },
+ ["ᾒ"]={ "ἢ","ͅ" },
+ ["ᾓ"]={ "ἣ","ͅ" },
+ ["ᾔ"]={ "ἤ","ͅ" },
+ ["ᾕ"]={ "ἥ","ͅ" },
+ ["ᾖ"]={ "ἦ","ͅ" },
+ ["ᾗ"]={ "ἧ","ͅ" },
+ ["ᾘ"]={ "Ἠ","ͅ" },
+ ["ᾙ"]={ "Ἡ","ͅ" },
+ ["ᾚ"]={ "Ἢ","ͅ" },
+ ["ᾛ"]={ "Ἣ","ͅ" },
+ ["ᾜ"]={ "Ἤ","ͅ" },
+ ["ᾝ"]={ "Ἥ","ͅ" },
+ ["ᾞ"]={ "Ἦ","ͅ" },
+ ["ᾟ"]={ "Ἧ","ͅ" },
+ ["ᾠ"]={ "ὠ","ͅ" },
+ ["ᾡ"]={ "ὡ","ͅ" },
+ ["ᾢ"]={ "ὢ","ͅ" },
+ ["ᾣ"]={ "ὣ","ͅ" },
+ ["ᾤ"]={ "ὤ","ͅ" },
+ ["ᾥ"]={ "ὥ","ͅ" },
+ ["ᾦ"]={ "ὦ","ͅ" },
+ ["ᾧ"]={ "ὧ","ͅ" },
+ ["ᾨ"]={ "Ὠ","ͅ" },
+ ["ᾩ"]={ "Ὡ","ͅ" },
+ ["ᾪ"]={ "Ὢ","ͅ" },
+ ["ᾫ"]={ "Ὣ","ͅ" },
+ ["ᾬ"]={ "Ὤ","ͅ" },
+ ["ᾭ"]={ "Ὥ","ͅ" },
+ ["ᾮ"]={ "Ὦ","ͅ" },
+ ["ᾯ"]={ "Ὧ","ͅ" },
+ ["ᾰ"]={ "α","̆" },
+ ["ᾱ"]={ "α","̄" },
+ ["ᾲ"]={ "ὰ","ͅ" },
+ ["ᾳ"]={ "α","ͅ" },
+ ["ᾴ"]={ "ά","ͅ" },
+ ["ᾶ"]={ "α","͂" },
+ ["ᾷ"]={ "ᾶ","ͅ" },
+ ["Ᾰ"]={ "Α","̆" },
+ ["Ᾱ"]={ "Α","̄" },
+ ["Ὰ"]={ "Α","̀" },
+ ["ᾼ"]={ "Α","ͅ" },
+ ["῁"]={ "¨","͂" },
+ ["ῂ"]={ "ὴ","ͅ" },
+ ["ῃ"]={ "η","ͅ" },
+ ["ῄ"]={ "ή","ͅ" },
+ ["ῆ"]={ "η","͂" },
+ ["ῇ"]={ "ῆ","ͅ" },
+ ["Ὲ"]={ "Ε","̀" },
+ ["Ὴ"]={ "Η","̀" },
+ ["ῌ"]={ "Η","ͅ" },
+ ["῍"]={ "᾿","̀" },
+ ["῎"]={ "᾿","́" },
+ ["῏"]={ "᾿","͂" },
+ ["ῐ"]={ "ι","̆" },
+ ["ῑ"]={ "ι","̄" },
+ ["ῒ"]={ "ϊ","̀" },
+ ["ῖ"]={ "ι","͂" },
+ ["ῗ"]={ "ϊ","͂" },
+ ["Ῐ"]={ "Ι","̆" },
+ ["Ῑ"]={ "Ι","̄" },
+ ["Ὶ"]={ "Ι","̀" },
+ ["῝"]={ "῾","̀" },
+ ["῞"]={ "῾","́" },
+ ["῟"]={ "῾","͂" },
+ ["ῠ"]={ "υ","̆" },
+ ["ῡ"]={ "υ","̄" },
+ ["ῢ"]={ "ϋ","̀" },
+ ["ῤ"]={ "ρ","̓" },
+ ["ῥ"]={ "ρ","̔" },
+ ["ῦ"]={ "υ","͂" },
+ ["ῧ"]={ "ϋ","͂" },
+ ["Ῠ"]={ "Υ","̆" },
+ ["Ῡ"]={ "Υ","̄" },
+ ["Ὺ"]={ "Υ","̀" },
+ ["Ῥ"]={ "Ρ","̔" },
+ ["῭"]={ "¨","̀" },
+ ["ῲ"]={ "ὼ","ͅ" },
+ ["ῳ"]={ "ω","ͅ" },
+ ["ῴ"]={ "ώ","ͅ" },
+ ["ῶ"]={ "ω","͂" },
+ ["ῷ"]={ "ῶ","ͅ" },
+ ["Ὸ"]={ "Ο","̀" },
+ ["Ὼ"]={ "Ω","̀" },
+ ["ῼ"]={ "Ω","ͅ" },
+ ["↚"]={ "←","̸" },
+ ["↛"]={ "→","̸" },
+ ["↮"]={ "↔","̸" },
+ ["⇍"]={ "⇐","̸" },
+ ["⇎"]={ "⇔","̸" },
+ ["⇏"]={ "⇒","̸" },
+ ["∄"]={ "∃","̸" },
+ ["∉"]={ "∈","̸" },
+ ["∌"]={ "∋","̸" },
+ ["∤"]={ "∣","̸" },
+ ["∦"]={ "∥","̸" },
+ ["≁"]={ "∼","̸" },
+ ["≄"]={ "≃","̸" },
+ ["≇"]={ "≅","̸" },
+ ["≉"]={ "≈","̸" },
+ ["≠"]={ "=","̸" },
+ ["≢"]={ "≡","̸" },
+ ["≭"]={ "≍","̸" },
+ ["≮"]={ "<","̸" },
+ ["≯"]={ ">","̸" },
+ ["≰"]={ "≤","̸" },
+ ["≱"]={ "≥","̸" },
+ ["≴"]={ "≲","̸" },
+ ["≵"]={ "≳","̸" },
+ ["≸"]={ "≶","̸" },
+ ["≹"]={ "≷","̸" },
+ ["⊀"]={ "≺","̸" },
+ ["⊁"]={ "≻","̸" },
+ ["⊄"]={ "⊂","̸" },
+ ["⊅"]={ "⊃","̸" },
+ ["⊈"]={ "⊆","̸" },
+ ["⊉"]={ "⊇","̸" },
+ ["⊬"]={ "⊢","̸" },
+ ["⊭"]={ "⊨","̸" },
+ ["⊮"]={ "⊩","̸" },
+ ["⊯"]={ "⊫","̸" },
+ ["⋠"]={ "≼","̸" },
+ ["⋡"]={ "≽","̸" },
+ ["⋢"]={ "⊑","̸" },
+ ["⋣"]={ "⊒","̸" },
+ ["⋪"]={ "⊲","̸" },
+ ["⋫"]={ "⊳","̸" },
+ ["⋬"]={ "⊴","̸" },
+ ["⋭"]={ "⊵","̸" },
+ ["⫝̸"]={ "⫝","̸" },
+ ["が"]={ "か","゙" },
+ ["ぎ"]={ "き","゙" },
+ ["ぐ"]={ "く","゙" },
+ ["げ"]={ "け","゙" },
+ ["ご"]={ "こ","゙" },
+ ["ざ"]={ "さ","゙" },
+ ["じ"]={ "し","゙" },
+ ["ず"]={ "す","゙" },
+ ["ぜ"]={ "せ","゙" },
+ ["ぞ"]={ "そ","゙" },
+ ["だ"]={ "た","゙" },
+ ["ぢ"]={ "ち","゙" },
+ ["づ"]={ "つ","゙" },
+ ["で"]={ "て","゙" },
+ ["ど"]={ "と","゙" },
+ ["ば"]={ "は","゙" },
+ ["ぱ"]={ "は","゚" },
+ ["び"]={ "ひ","゙" },
+ ["ぴ"]={ "ひ","゚" },
+ ["ぶ"]={ "ふ","゙" },
+ ["ぷ"]={ "ふ","゚" },
+ ["べ"]={ "へ","゙" },
+ ["ぺ"]={ "へ","゚" },
+ ["ぼ"]={ "ほ","゙" },
+ ["ぽ"]={ "ほ","゚" },
+ ["ゔ"]={ "う","゙" },
+ ["ゞ"]={ "ゝ","゙" },
+ ["ガ"]={ "カ","゙" },
+ ["ギ"]={ "キ","゙" },
+ ["グ"]={ "ク","゙" },
+ ["ゲ"]={ "ケ","゙" },
+ ["ゴ"]={ "コ","゙" },
+ ["ザ"]={ "サ","゙" },
+ ["ジ"]={ "シ","゙" },
+ ["ズ"]={ "ス","゙" },
+ ["ゼ"]={ "セ","゙" },
+ ["ゾ"]={ "ソ","゙" },
+ ["ダ"]={ "タ","゙" },
+ ["ヂ"]={ "チ","゙" },
+ ["ヅ"]={ "ツ","゙" },
+ ["デ"]={ "テ","゙" },
+ ["ド"]={ "ト","゙" },
+ ["バ"]={ "ハ","゙" },
+ ["パ"]={ "ハ","゚" },
+ ["ビ"]={ "ヒ","゙" },
+ ["ピ"]={ "ヒ","゚" },
+ ["ブ"]={ "フ","゙" },
+ ["プ"]={ "フ","゚" },
+ ["ベ"]={ "ヘ","゙" },
+ ["ペ"]={ "ヘ","゚" },
+ ["ボ"]={ "ホ","゙" },
+ ["ポ"]={ "ホ","゚" },
+ ["ヴ"]={ "ウ","゙" },
+ ["ヷ"]={ "ワ","゙" },
+ ["ヸ"]={ "ヰ","゙" },
+ ["ヹ"]={ "ヱ","゙" },
+ ["ヺ"]={ "ヲ","゙" },
+ ["ヾ"]={ "ヽ","゙" },
+ ["יִ"]={ "י","ִ" },
+ ["ײַ"]={ "ײ","ַ" },
+ ["שׁ"]={ "ש","ׁ" },
+ ["שׂ"]={ "ש","ׂ" },
+ ["שּׁ"]={ "שּ","ׁ" },
+ ["שּׂ"]={ "שּ","ׂ" },
+ ["אַ"]={ "א","ַ" },
+ ["אָ"]={ "א","ָ" },
+ ["אּ"]={ "א","ּ" },
+ ["בּ"]={ "ב","ּ" },
+ ["גּ"]={ "ג","ּ" },
+ ["דּ"]={ "ד","ּ" },
+ ["הּ"]={ "ה","ּ" },
+ ["וּ"]={ "ו","ּ" },
+ ["זּ"]={ "ז","ּ" },
+ ["טּ"]={ "ט","ּ" },
+ ["יּ"]={ "י","ּ" },
+ ["ךּ"]={ "ך","ּ" },
+ ["כּ"]={ "כ","ּ" },
+ ["לּ"]={ "ל","ּ" },
+ ["מּ"]={ "מ","ּ" },
+ ["נּ"]={ "נ","ּ" },
+ ["סּ"]={ "ס","ּ" },
+ ["ףּ"]={ "ף","ּ" },
+ ["פּ"]={ "פ","ּ" },
+ ["צּ"]={ "צ","ּ" },
+ ["קּ"]={ "ק","ּ" },
+ ["רּ"]={ "ר","ּ" },
+ ["שּ"]={ "ש","ּ" },
+ ["תּ"]={ "ת","ּ" },
+ ["וֹ"]={ "ו","ֹ" },
+ ["בֿ"]={ "ב","ֿ" },
+ ["כֿ"]={ "כ","ֿ" },
+ ["פֿ"]={ "פ","ֿ" },
+ ["𑂚"]={ "𑂙","𑂺" },
+ ["𑂜"]={ "𑂛","𑂺" },
+ ["𑂫"]={ "𑂥","𑂺" },
+ ["𑄮"]={ "𑄱","𑄧" },
+ ["𑄯"]={ "𑄲","𑄧" },
+ ["𑍋"]={ "𑍇","𑌾" },
+ ["𑍌"]={ "𑍇","𑍗" },
+ ["𑒻"]={ "𑒹","𑒺" },
+ ["𑒼"]={ "𑒹","𑒰" },
+ ["𑒾"]={ "𑒹","𑒽" },
+ ["𑖺"]={ "𑖸","𑖯" },
+ ["𑖻"]={ "𑖹","𑖯" },
+ ["𝅗𝅥"]={ "𝅗","𝅥" },
+ ["𝅘𝅥"]={ "𝅘","𝅥" },
+ ["𝅘𝅥𝅮"]={ "𝅘𝅥","𝅮" },
+ ["𝅘𝅥𝅯"]={ "𝅘𝅥","𝅯" },
+ ["𝅘𝅥𝅰"]={ "𝅘𝅥","𝅰" },
+ ["𝅘𝅥𝅱"]={ "𝅘𝅥","𝅱" },
+ ["𝅘𝅥𝅲"]={ "𝅘𝅥","𝅲" },
+ ["𝆹𝅥"]={ "𝆹","𝅥" },
+ ["𝆺𝅥"]={ "𝆺","𝅥" },
+ ["𝆹𝅥𝅮"]={ "𝆹𝅥","𝅮" },
+ ["𝆺𝅥𝅮"]={ "𝆺𝅥","𝅮" },
+ ["𝆹𝅥𝅯"]={ "𝆹𝅥","𝅯" },
+ ["𝆺𝅥𝅯"]={ "𝆺𝅥","𝅯" },
+ },
+ },
+ },
+ ["name"]="collapse",
+ ["prepend"]=true,
+ ["type"]="ligature",
+}
+
+end -- closure
+
+do -- begin closure to overcome local limits and interference
+
+if not modules then modules={} end modules ['luatex-fonts-gbn']={
+ version=1.001,
+ comment="companion to luatex-*.tex",
+ author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright="PRAGMA ADE / ConTeXt Development Team",
+ license="see context related readme files"
+}
+if context then
+--removed
+
+end
+local next=next
+local fonts=fonts
+local nodes=nodes
+local nuts=nodes.nuts
+local traverse_id=nuts.traverse_id
+local flush_node=nuts.flush_node
+local glyph_code=nodes.nodecodes.glyph
+local disc_code=nodes.nodecodes.disc
+local tonode=nuts.tonode
+local tonut=nuts.tonut
+local getfont=nuts.getfont
+local getchar=nuts.getchar
+local getid=nuts.getid
+local getboth=nuts.getboth
+local getprev=nuts.getprev
+local getnext=nuts.getnext
+local getdisc=nuts.getdisc
+local setchar=nuts.setchar
+local setlink=nuts.setlink
+local setprev=nuts.setprev
+local n_ligaturing=node.ligaturing
+local n_kerning=node.kerning
+local d_ligaturing=nuts.ligaturing
+local d_kerning=nuts.kerning
+local basemodepass=true
+local function l_warning() logs.report("fonts","don't call 'node.ligaturing' directly") l_warning=nil end
+local function k_warning() logs.report("fonts","don't call 'node.kerning' directly") k_warning=nil end
+function node.ligaturing(...)
+ if basemodepass and l_warning then
+ l_warning()
+ end
+ return n_ligaturing(...)
+end
+function node.kerning(...)
+ if basemodepass and k_warning then
+ k_warning()
+ end
+ return n_kerning(...)
+end
+function nuts.ligaturing(...)
+ if basemodepass and l_warning then
+ l_warning()
+ end
+ return d_ligaturing(...)
+end
+function nuts.kerning(...)
+ if basemodepass and k_warning then
+ k_warning()
+ end
+ return d_kerning(...)
+end
+function nodes.handlers.setbasemodepass(v)
+ basemodepass=v
+end
+local function nodepass(head,groupcode,size,packtype,direction)
+ local fontdata=fonts.hashes.identifiers
+ if fontdata then
+ local usedfonts={}
+ local basefonts={}
+ local prevfont=nil
+ local basefont=nil
+ local variants=nil
+ local redundant=nil
+ local nofused=0
+ for n in traverse_id(glyph_code,head) do
+ local font=getfont(n)
+ if font~=prevfont then
+ if basefont then
+ basefont[2]=getprev(n)
+ end
+ prevfont=font
+ local used=usedfonts[font]
+ if not used then
+ local tfmdata=fontdata[font]
+ if tfmdata then
+ local shared=tfmdata.shared
+ if shared then
+ local processors=shared.processes
+ if processors and #processors>0 then
+ usedfonts[font]=processors
+ nofused=nofused+1
+ elseif basemodepass then
+ basefont={ n,nil }
+ basefonts[#basefonts+1]=basefont
+ end
+ end
+ local resources=tfmdata.resources
+ variants=resources and resources.variants
+ variants=variants and next(variants) and variants or false
+ end
+ else
+ local tfmdata=fontdata[prevfont]
+ if tfmdata then
+ local resources=tfmdata.resources
+ variants=resources and resources.variants
+ variants=variants and next(variants) and variants or false
+ end
+ end
+ end
+ if variants then
+ local char=getchar(n)
+ if (char>=0xFE00 and char<=0xFE0F) or (char>=0xE0100 and char<=0xE01EF) then
+ local hash=variants[char]
+ if hash then
+ local p=getprev(n)
+ if p and getid(p)==glyph_code then
+ local variant=hash[getchar(p)]
+ if variant then
+ setchar(p,variant)
+ end
+ end
+ end
+ if not redundant then
+ redundant={ n }
+ else
+ redundant[#redundant+1]=n
+ end
+ end
+ end
+ end
+ local nofbasefonts=#basefonts
+ if redundant then
+ for i=1,#redundant do
+ local r=redundant[i]
+ local p,n=getboth(r)
+ if r==head then
+ head=n
+ setprev(n)
+ else
+ setlink(p,n)
+ end
+ if nofbasefonts>0 then
+ for i=1,nofbasefonts do
+ local bi=basefonts[i]
+ if r==bi[1] then
+ bi[1]=n
+ end
+ if r==bi[2] then
+ bi[2]=n
+ end
+ end
+ end
+ flush_node(r)
+ end
+ end
+ for d in traverse_id(disc_code,head) do
+ local _,_,r=getdisc(d)
+ if r then
+ for n in traverse_id(glyph_code,r) do
+ local font=getfont(n)
+ if font~=prevfont then
+ prevfont=font
+ local used=usedfonts[font]
+ if not used then
+ local tfmdata=fontdata[font]
+ if tfmdata then
+ local shared=tfmdata.shared
+ if shared then
+ local processors=shared.processes
+ if processors and #processors>0 then
+ usedfonts[font]=processors
+ nofused=nofused+1
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+ if next(usedfonts) then
+ for font,processors in next,usedfonts do
+ for i=1,#processors do
+ head=processors[i](head,font,0,direction,nofused) or head
+ end
+ end
+ end
+ if basemodepass and nofbasefonts>0 then
+ for i=1,nofbasefonts do
+ local range=basefonts[i]
+ local start=range[1]
+ local stop=range[2]
+ if start then
+ local front=head==start
+ local prev,next
+ if stop then
+ next=getnext(stop)
+ start,stop=d_ligaturing(start,stop)
+ start,stop=d_kerning(start,stop)
+ else
+ prev=getprev(start)
+ start=d_ligaturing(start)
+ start=d_kerning(start)
+ end
+ if prev then
+ setlink(prev,start)
+ end
+ if next then
+ setlink(stop,next)
+ end
+ if front and head~=start then
+ head=start
+ end
+ end
+ end
+ end
+ end
+ return head
+end
+local function basepass(head)
+ if basemodepass then
+ head=d_ligaturing(head)
+ head=d_kerning(head)
+ end
+ return head
+end
+local protectpass=node.direct.protect_glyphs
+local injectpass=nodes.injections.handler
+function nodes.handlers.nodepass(head,...)
+ if head then
+ return tonode(nodepass(tonut(head),...))
+ end
+end
+function nodes.handlers.basepass(head)
+ if head then
+ return tonode(basepass(tonut(head)))
+ end
+end
+function nodes.handlers.injectpass(head)
+ if head then
+ return tonode(injectpass(tonut(head)))
+ end
+end
+function nodes.handlers.protectpass(head)
+ if head then
+ protectpass(tonut(head))
+ return head
+ end
+end
+function nodes.simple_font_handler(head,groupcode,size,packtype,direction)
+ if head then
+ head=tonut(head)
+ head=nodepass(head,groupcode,size,packtype,direction)
+ head=injectpass(head)
+ if not basemodepass then
+ head=basepass(head)
+ end
+ protectpass(head)
+ head=tonode(head)
+ end
+ return head
+end
+
+end -- closure
diff --git a/macros/luatex/generic/luaotfload/fontloader-util-fil.lua b/macros/luatex/generic/luaotfload/fontloader-util-fil.lua
new file mode 100644
index 0000000000..79af277437
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-util-fil.lua
@@ -0,0 +1,452 @@
+if not modules then modules = { } end modules ['util-fil'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+local tonumber = tonumber
+local byte = string.byte
+local char = string.char
+
+-- Here are a few helpers (the starting point were old ones I used for parsing
+-- flac files). In Lua 5.3 we can probably do this better. Some code will move
+-- here.
+
+-- We could comment those that are in fio and sio.
+
+utilities = utilities or { }
+local files = { }
+utilities.files = files
+
+-- we could have a gc method that closes but files auto close anyway
+
+local zerobased = { }
+
+function files.open(filename,zb)
+ local f = io.open(filename,"rb")
+ if f then
+ zerobased[f] = zb or false
+ end
+ return f
+end
+
+function files.close(f)
+ zerobased[f] = nil
+ f:close()
+end
+
+function files.size(f)
+ local current = f:seek()
+ local size = f:seek("end")
+ f:seek("set",current)
+ return size
+end
+
+files.getsize = files.size
+
+function files.setposition(f,n)
+ if zerobased[f] then
+ f:seek("set",n)
+ else
+ f:seek("set",n - 1)
+ end
+end
+
+function files.getposition(f)
+ if zerobased[f] then
+ return f:seek()
+ else
+ return f:seek() + 1
+ end
+end
+
+function files.look(f,n,chars)
+ local p = f:seek()
+ local s = f:read(n)
+ f:seek("set",p)
+ if chars then
+ return s
+ else
+ return byte(s,1,#s)
+ end
+end
+
+function files.skip(f,n)
+ if n == 1 then
+ f:read(n)
+ else
+ f:seek("set",f:seek()+n)
+ end
+end
+
+function files.readbyte(f)
+ return byte(f:read(1))
+end
+
+function files.readbytes(f,n)
+ return byte(f:read(n),1,n)
+end
+
+function files.readbytetable(f,n)
+ -- return { byte(f:read(n),1,n) }
+ local s = f:read(n or 1)
+ return { byte(s,1,#s) } -- best use the real length
+end
+
+function files.readchar(f)
+ return f:read(1)
+end
+
+function files.readstring(f,n)
+ return f:read(n or 1)
+end
+
+function files.readinteger1(f) -- one byte
+ local n = byte(f:read(1))
+ if n >= 0x80 then
+ return n - 0x100
+ else
+ return n
+ end
+end
+
+files.readcardinal1 = files.readbyte -- one byte
+files.readcardinal = files.readcardinal1
+files.readinteger = files.readinteger1
+files.readsignedbyte = files.readinteger1
+
+function files.readcardinal2(f)
+ local a, b = byte(f:read(2),1,2)
+ return 0x100 * a + b
+end
+
+function files.readcardinal2le(f)
+ local b, a = byte(f:read(2),1,2)
+ return 0x100 * a + b
+end
+
+function files.readinteger2(f)
+ local a, b = byte(f:read(2),1,2)
+ if a >= 0x80 then
+ return 0x100 * a + b - 0x10000
+ else
+ return 0x100 * a + b
+ end
+end
+
+function files.readinteger2le(f)
+ local b, a = byte(f:read(2),1,2)
+ if a >= 0x80 then
+ return 0x100 * a + b - 0x10000
+ else
+ return 0x100 * a + b
+ end
+end
+
+function files.readcardinal3(f)
+ local a, b, c = byte(f:read(3),1,3)
+ return 0x10000 * a + 0x100 * b + c
+end
+
+function files.readcardinal3le(f)
+ local c, b, a = byte(f:read(3),1,3)
+ return 0x10000 * a + 0x100 * b + c
+end
+
+function files.readinteger3(f)
+ local a, b, c = byte(f:read(3),1,3)
+ if a >= 0x80 then
+ return 0x10000 * a + 0x100 * b + c - 0x1000000
+ else
+ return 0x10000 * a + 0x100 * b + c
+ end
+end
+
+function files.readinteger3le(f)
+ local c, b, a = byte(f:read(3),1,3)
+ if a >= 0x80 then
+ return 0x10000 * a + 0x100 * b + c - 0x1000000
+ else
+ return 0x10000 * a + 0x100 * b + c
+ end
+end
+
+function files.readcardinal4(f)
+ local a, b, c, d = byte(f:read(4),1,4)
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d
+end
+
+function files.readcardinal4le(f)
+ local d, c, b, a = byte(f:read(4),1,4)
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d
+end
+
+function files.readinteger4(f)
+ local a, b, c, d = byte(f:read(4),1,4)
+ if a >= 0x80 then
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d - 0x100000000
+ else
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d
+ end
+end
+
+function files.readinteger4le(f)
+ local d, c, b, a = byte(f:read(4),1,4)
+ if a >= 0x80 then
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d - 0x100000000
+ else
+ return 0x1000000 * a + 0x10000 * b + 0x100 * c + d
+ end
+end
+
+function files.readfixed2(f)
+ local a, b = byte(f:read(2),1,2)
+ if a >= 0x80 then
+ tonumber((a - 0x100) .. "." .. b)
+ else
+ tonumber(( a ) .. "." .. b)
+ end
+end
+
+-- (real) (n>>16) + ((n&0xffff)/65536.0)) but no cast in lua (we could use unpack)
+
+function files.readfixed4(f)
+ local a, b, c, d = byte(f:read(4),1,4)
+ if a >= 0x80 then
+ tonumber((0x100 * a + b - 0x10000) .. "." .. (0x100 * c + d))
+ else
+ tonumber((0x100 * a + b ) .. "." .. (0x100 * c + d))
+ end
+end
+
+-- (real) ((n<<16)>>(16+14)) + ((n&0x3fff)/16384.0))
+
+if bit32 then
+
+ local extract = bit32.extract
+ local band = bit32.band
+
+ function files.read2dot14(f)
+ local a, b = byte(f:read(2),1,2)
+ if a >= 0x80 then
+ local n = -(0x100 * a + b)
+ return - (extract(n,14,2) + (band(n,0x3FFF) / 16384.0))
+ else
+ local n = 0x100 * a + b
+ return (extract(n,14,2) + (band(n,0x3FFF) / 16384.0))
+ end
+ end
+
+end
+
+function files.skipshort(f,n)
+ f:read(2*(n or 1))
+end
+
+function files.skiplong(f,n)
+ f:read(4*(n or 1))
+end
+
+-- writers (kind of slow)
+
+if bit32 then
+
+ local rshift = bit32.rshift
+
+ function files.writecardinal2(f,n)
+ local a = char(n % 256)
+ n = rshift(n,8)
+ local b = char(n % 256)
+ f:write(b,a)
+ end
+
+ function files.writecardinal4(f,n)
+ local a = char(n % 256)
+ n = rshift(n,8)
+ local b = char(n % 256)
+ n = rshift(n,8)
+ local c = char(n % 256)
+ n = rshift(n,8)
+ local d = char(n % 256)
+ f:write(d,c,b,a)
+ end
+
+ function files.writecardinal2le(f,n)
+ local a = char(n % 256)
+ n = rshift(n,8)
+ local b = char(n % 256)
+ f:write(a,b)
+ end
+
+ function files.writecardinal4le(f,n)
+ local a = char(n % 256)
+ n = rshift(n,8)
+ local b = char(n % 256)
+ n = rshift(n,8)
+ local c = char(n % 256)
+ n = rshift(n,8)
+ local d = char(n % 256)
+ f:write(a,b,c,d)
+ end
+
+else
+
+ local floor = math.floor
+
+ function files.writecardinal2(f,n)
+ local a = char(n % 256)
+ n = floor(n/256)
+ local b = char(n % 256)
+ f:write(b,a)
+ end
+
+ function files.writecardinal4(f,n)
+ local a = char(n % 256)
+ n = floor(n/256)
+ local b = char(n % 256)
+ n = floor(n/256)
+ local c = char(n % 256)
+ n = floor(n/256)
+ local d = char(n % 256)
+ f:write(d,c,b,a)
+ end
+
+ function files.writecardinal2le(f,n)
+ local a = char(n % 256)
+ n = floor(n/256)
+ local b = char(n % 256)
+ f:write(a,b)
+ end
+
+ function files.writecardinal4le(f,n)
+ local a = char(n % 256)
+ n = floor(n/256)
+ local b = char(n % 256)
+ n = floor(n/256)
+ local c = char(n % 256)
+ n = floor(n/256)
+ local d = char(n % 256)
+ f:write(a,b,c,d)
+ end
+
+end
+
+function files.writestring(f,s)
+ f:write(char(byte(s,1,#s)))
+end
+
+function files.writebyte(f,b)
+ f:write(char(b))
+end
+
+if fio and fio.readcardinal1 then
+
+ files.readcardinal1 = fio.readcardinal1
+ files.readcardinal2 = fio.readcardinal2
+ files.readcardinal3 = fio.readcardinal3
+ files.readcardinal4 = fio.readcardinal4
+
+ files.readcardinal1le = fio.readcardinal1le or files.readcardinal1le
+ files.readcardinal2le = fio.readcardinal2le or files.readcardinal2le
+ files.readcardinal3le = fio.readcardinal3le or files.readcardinal3le
+ files.readcardinal4le = fio.readcardinal4le or files.readcardinal4le
+
+ files.readinteger1 = fio.readinteger1
+ files.readinteger2 = fio.readinteger2
+ files.readinteger3 = fio.readinteger3
+ files.readinteger4 = fio.readinteger4
+
+ files.readinteger1le = fio.readinteger1le or files.readinteger1le
+ files.readinteger2le = fio.readinteger2le or files.readinteger2le
+ files.readinteger3le = fio.readinteger3le or files.readinteger3le
+ files.readinteger4le = fio.readinteger4le or files.readinteger4le
+
+ files.readfixed2 = fio.readfixed2
+ files.readfixed4 = fio.readfixed4
+ files.read2dot14 = fio.read2dot14
+ files.setposition = fio.setposition
+ files.getposition = fio.getposition
+
+ files.readbyte = files.readcardinal1
+ files.readsignedbyte = files.readinteger1
+ files.readcardinal = files.readcardinal1
+ files.readinteger = files.readinteger1
+
+ local skipposition = fio.skipposition
+ files.skipposition = skipposition
+
+ files.readbytes = fio.readbytes
+ files.readbytetable = fio.readbytetable
+
+ function files.skipshort(f,n)
+ skipposition(f,2*(n or 1))
+ end
+
+ function files.skiplong(f,n)
+ skipposition(f,4*(n or 1))
+ end
+
+end
+
+if fio and fio.writecardinal1 then
+
+ files.writecardinal1 = fio.writecardinal1
+ files.writecardinal2 = fio.writecardinal2
+ files.writecardinal3 = fio.writecardinal3
+ files.writecardinal4 = fio.writecardinal4
+
+ files.writecardinal1le = fio.writecardinal1le
+ files.writecardinal2le = fio.writecardinal2le
+ files.writecardinal3le = fio.writecardinal3le
+ files.writecardinal4le = fio.writecardinal4le
+
+ files.writeinteger1 = fio.writeinteger1 or fio.writecardinal1
+ files.writeinteger2 = fio.writeinteger2 or fio.writecardinal2
+ files.writeinteger3 = fio.writeinteger3 or fio.writecardinal3
+ files.writeinteger4 = fio.writeinteger4 or fio.writecardinal4
+
+ files.writeinteger1le = files.writeinteger1le or fio.writecardinal1le
+ files.writeinteger2le = files.writeinteger2le or fio.writecardinal2le
+ files.writeinteger3le = files.writeinteger3le or fio.writecardinal3le
+ files.writeinteger4le = files.writeinteger4le or fio.writecardinal4le
+
+end
+
+if fio and fio.readcardinaltable then
+
+ files.readcardinaltable = fio.readcardinaltable
+ files.readintegertable = fio.readintegertable
+
+else
+
+ local readcardinal1 = files.readcardinal1
+ local readcardinal2 = files.readcardinal2
+ local readcardinal3 = files.readcardinal3
+ local readcardinal4 = files.readcardinal4
+
+ function files.readcardinaltable(f,n,b)
+ local t = { }
+ if b == 1 then for i=1,n do t[i] = readcardinal1(f) end
+ elseif b == 2 then for i=1,n do t[i] = readcardinal2(f) end
+ elseif b == 3 then for i=1,n do t[i] = readcardinal3(f) end
+ elseif b == 4 then for i=1,n do t[i] = readcardinal4(f) end end
+ return t
+ end
+
+ local readinteger1 = files.readinteger1
+ local readinteger2 = files.readinteger2
+ local readinteger3 = files.readinteger3
+ local readinteger4 = files.readinteger4
+
+ function files.readintegertable(f,n,b)
+ local t = { }
+ if b == 1 then for i=1,n do t[i] = readinteger1(f) end
+ elseif b == 2 then for i=1,n do t[i] = readinteger2(f) end
+ elseif b == 3 then for i=1,n do t[i] = readinteger3(f) end
+ elseif b == 4 then for i=1,n do t[i] = readinteger4(f) end end
+ return t
+ end
+
+end
diff --git a/macros/luatex/generic/luaotfload/fontloader-util-str.lua b/macros/luatex/generic/luaotfload/fontloader-util-str.lua
new file mode 100644
index 0000000000..ad22302df0
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/fontloader-util-str.lua
@@ -0,0 +1,1461 @@
+if not modules then modules = { } end modules ['util-str'] = {
+ version = 1.001,
+ comment = "companion to luat-lib.mkiv",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ license = "see context related readme files"
+}
+
+utilities = utilities or { }
+utilities.strings = utilities.strings or { }
+local strings = utilities.strings
+
+local format, gsub, rep, sub, find = string.format, string.gsub, string.rep, string.sub, string.find
+local load, dump = load, string.dump
+local tonumber, type, tostring, next, setmetatable = tonumber, type, tostring, next, setmetatable
+local unpack, concat = table.unpack, table.concat
+local P, V, C, S, R, Ct, Cs, Cp, Carg, Cc = lpeg.P, lpeg.V, lpeg.C, lpeg.S, lpeg.R, lpeg.Ct, lpeg.Cs, lpeg.Cp, lpeg.Carg, lpeg.Cc
+local patterns, lpegmatch = lpeg.patterns, lpeg.match
+local utfchar, utfbyte, utflen = utf.char, utf.byte, utf.len
+
+----- loadstripped = utilities.lua.loadstripped
+----- setmetatableindex = table.setmetatableindex
+
+local loadstripped = function(str,shortcuts)
+ if shortcuts then
+ return load(dump(load(str),true),nil,nil,shortcuts)
+ else
+ return load(dump(load(str),true))
+ end
+end
+
+-- todo: make a special namespace for the formatter
+
+if not number then number = { } end -- temp hack for luatex-fonts
+
+local stripzero = patterns.stripzero
+local stripzeros = patterns.stripzeros
+local newline = patterns.newline
+local endofstring = patterns.endofstring
+local anything = patterns.anything
+local whitespace = patterns.whitespace
+local space = patterns.space
+local spacer = patterns.spacer
+local spaceortab = patterns.spaceortab
+local digit = patterns.digit
+local sign = patterns.sign
+local period = patterns.period
+
+-- local function points(n)
+-- n = tonumber(n)
+-- return (not n or n == 0) and "0pt" or lpegmatch(stripzeros,format("%.5fpt",n/65536))
+-- end
+
+-- local function basepoints(n)
+-- n = tonumber(n)
+-- return (not n or n == 0) and "0bp" or lpegmatch(stripzeros,format("%.5fbp", n*(7200/7227)/65536))
+-- end
+
+local ptf = 1 / 65536
+local bpf = (7200/7227) / 65536
+
+local function points(n)
+ if n == 0 then
+ return "0pt"
+ end
+ n = tonumber(n)
+ if not n or n == 0 then
+ return "0pt"
+ end
+ n = n * ptf
+ if n % 1 == 0 then
+ return format("%ipt",n)
+ end
+ return lpegmatch(stripzeros,format("%.5fpt",n)) -- plural as we need to keep the pt
+end
+
+local function basepoints(n)
+ if n == 0 then
+ return "0pt"
+ end
+ n = tonumber(n)
+ if not n or n == 0 then
+ return "0pt"
+ end
+ n = n * bpf
+ if n % 1 == 0 then
+ return format("%ibp",n)
+ end
+ return lpegmatch(stripzeros,format("%.5fbp",n)) -- plural as we need to keep the pt
+end
+
+number.points = points
+number.basepoints = basepoints
+
+-- str = " \n \ntest \n test\ntest "
+-- print("["..string.gsub(string.collapsecrlf(str),"\n","+").."]")
+
+local rubish = spaceortab^0 * newline
+local anyrubish = spaceortab + newline
+local stripped = (spaceortab^1 / "") * newline
+local leading = rubish^0 / ""
+local trailing = (anyrubish^1 * endofstring) / ""
+local redundant = rubish^3 / "\n"
+
+local pattern = Cs(leading * (trailing + redundant + stripped + anything)^0)
+
+function strings.collapsecrlf(str)
+ return lpegmatch(pattern,str)
+end
+
+-- The following functions might end up in another namespace.
+
+local repeaters = { } -- watch how we also moved the -1 in depth-1 to the creator
+
+function strings.newrepeater(str,offset)
+ offset = offset or 0
+ local s = repeaters[str]
+ if not s then
+ s = { }
+ repeaters[str] = s
+ end
+ local t = s[offset]
+ if t then
+ return t
+ end
+ t = { }
+ setmetatable(t, { __index = function(t,k)
+ if not k then
+ return ""
+ end
+ local n = k + offset
+ local s = n > 0 and rep(str,n) or ""
+ t[k] = s
+ return s
+ end })
+ s[offset] = t
+ return t
+end
+
+-- local dashes = strings.newrepeater("--",-1)
+-- print(dashes[2],dashes[3],dashes[1])
+
+local extra, tab, start = 0, 0, 4, 0
+
+local nspaces = strings.newrepeater(" ")
+
+string.nspaces = nspaces
+
+local pattern =
+ Carg(1) / function(t)
+ extra, tab, start = 0, t or 7, 1
+ end
+ * Cs((
+ Cp() * patterns.tab / function(position)
+ local current = (position - start + 1) + extra
+ local spaces = tab-(current-1) % tab
+ if spaces > 0 then
+ extra = extra + spaces - 1
+ return nspaces[spaces] -- rep(" ",spaces)
+ else
+ return ""
+ end
+ end
+ + newline * Cp() / function(position)
+ extra, start = 0, position
+ end
+ + anything
+ )^1)
+
+function strings.tabtospace(str,tab)
+ -- no real gain in first checking if a \t is there
+ return lpegmatch(pattern,str,1,tab or 7)
+end
+
+function string.utfpadding(s,n)
+ if not n or n == 0 then
+ return ""
+ end
+ local l = utflen(s)
+ if n > 0 then
+ return nspaces[n-l]
+ else
+ return nspaces[-n-l]
+ end
+end
+
+-- local t = {
+-- "1234567123456712345671234567",
+-- "\tb\tc",
+-- "a\tb\tc",
+-- "aa\tbb\tcc",
+-- "aaa\tbbb\tccc",
+-- "aaaa\tbbbb\tcccc",
+-- "aaaaa\tbbbbb\tccccc",
+-- "aaaaaa\tbbbbbb\tcccccc\n aaaaaa\tbbbbbb\tcccccc",
+-- "one\n two\nxxx three\nxx four\nx five\nsix",
+-- }
+-- for k=1,#t do
+-- print(strings.tabtospace(t[k]))
+-- end
+
+-- todo: lpeg
+
+-- function strings.striplong(str) -- strips all leading spaces
+-- str = gsub(str,"^%s*","")
+-- str = gsub(str,"[\n\r]+ *","\n")
+-- return str
+-- end
+
+local optionalspace = spacer^0
+local nospace = optionalspace/""
+local endofline = nospace * newline
+
+local stripend = (whitespace^1 * endofstring)/""
+
+local normalline = (nospace * ((1-optionalspace*(newline+endofstring))^1) * nospace)
+
+local stripempty = endofline^1/""
+local normalempty = endofline^1
+local singleempty = endofline * (endofline^0/"")
+local doubleempty = endofline * endofline^-1 * (endofline^0/"")
+local stripstart = stripempty^0
+
+local intospace = whitespace^1/" "
+local noleading = whitespace^1/""
+local notrailing = noleading * endofstring
+
+local p_prune_normal = Cs ( stripstart * ( stripend + normalline + normalempty )^0 )
+local p_prune_collapse = Cs ( stripstart * ( stripend + normalline + doubleempty )^0 )
+local p_prune_noempty = Cs ( stripstart * ( stripend + normalline + singleempty )^0 )
+local p_prune_intospace = Cs ( noleading * ( notrailing + intospace + 1 )^0 )
+local p_retain_normal = Cs ( ( normalline + normalempty )^0 )
+local p_retain_collapse = Cs ( ( normalline + doubleempty )^0 )
+local p_retain_noempty = Cs ( ( normalline + singleempty )^0 )
+
+-- function striplines(str,prune,collapse,noempty)
+-- if prune then
+-- if noempty then
+-- return lpegmatch(p_prune_noempty,str) or str
+-- elseif collapse then
+-- return lpegmatch(p_prune_collapse,str) or str
+-- else
+-- return lpegmatch(p_prune_normal,str) or str
+-- end
+-- else
+-- if noempty then
+-- return lpegmatch(p_retain_noempty,str) or str
+-- elseif collapse then
+-- return lpegmatch(p_retain_collapse,str) or str
+-- else
+-- return lpegmatch(p_retain_normal,str) or str
+-- end
+-- end
+-- end
+
+local striplinepatterns = {
+ ["prune"] = p_prune_normal,
+ ["prune and collapse"] = p_prune_collapse, -- default
+ ["prune and no empty"] = p_prune_noempty,
+ ["prune and to space"] = p_prune_intospace,
+ ["retain"] = p_retain_normal,
+ ["retain and collapse"] = p_retain_collapse,
+ ["retain and no empty"] = p_retain_noempty,
+ ["collapse"] = patterns.collapser,
+}
+
+setmetatable(striplinepatterns,{ __index = function(t,k) return p_prune_collapse end })
+
+strings.striplinepatterns = striplinepatterns
+
+function strings.striplines(str,how)
+ return str and lpegmatch(striplinepatterns[how],str) or str
+end
+
+function strings.collapse(str) -- maybe also in strings
+ return str and lpegmatch(p_prune_intospace,str) or str
+end
+
+-- also see: string.collapsespaces
+
+strings.striplong = strings.striplines -- for old times sake
+
+-- local str = table.concat( {
+-- " ",
+-- " aap",
+-- " noot mies",
+-- " ",
+-- " ",
+-- " zus wim jet",
+-- "zus wim jet",
+-- " zus wim jet",
+-- " ",
+-- }, "\n")
+--
+-- local str = table.concat( {
+-- " aaaa",
+-- " bb",
+-- " cccccc",
+-- " ",
+-- }, "\n")
+--
+-- for k, v in table.sortedhash(utilities.strings.striplinepatterns) do
+-- logs.report("stripper","method: %s, result: [[%s]]",k,utilities.strings.striplines(str,k))
+-- end
+
+-- inspect(strings.striplong([[
+-- aaaa
+-- bb
+-- cccccc
+-- ]]))
+
+function strings.nice(str)
+ str = gsub(str,"[:%-+_]+"," ") -- maybe more
+ return str
+end
+
+-- Work in progress. Interesting is that compared to the built-in this is faster in
+-- luatex than in luajittex where we have a comparable speed. It only makes sense
+-- to use the formatter when a (somewhat) complex format is used a lot. Each formatter
+-- is a function so there is some overhead and not all formatted output is worth that
+-- overhead. Keep in mind that there is an extra function call involved. In principle
+-- we end up with a string concatination so one could inline such a sequence but often
+-- at the cost of less readabinity. So, it's a sort of (visual) compromise. Of course
+-- there is the benefit of more variants. (Concerning the speed: a simple format like
+-- %05fpt is better off with format than with a formatter, but as soon as you put
+-- something in front formatters become faster. Passing the pt as extra argument makes
+-- formatters behave better. Of course this is rather implementation dependent. Also,
+-- when a specific format is only used a few times the overhead in creating it is not
+-- compensated by speed.)
+--
+-- More info can be found in cld-mkiv.pdf so here I stick to a simple list.
+--
+-- integer %...i number
+-- integer %...d number
+-- unsigned %...u number -- not used
+-- character %...c number
+-- hexadecimal %...x number
+-- HEXADECIMAL %...X number
+-- octal %...o number
+-- string %...s string number
+-- float %...f number
+-- checked float %...F number
+-- exponential %...e number
+-- exponential %...E number
+-- stripped e %...j number
+-- stripped E %...J number
+-- autofloat %...g number
+-- autofloat %...G number
+-- utf character %...c number
+-- force tostring %...S any
+-- force tostring %Q any
+-- force tonumber %N number (strip leading zeros)
+-- signed number %I number
+-- rounded number %r number
+-- 0xhexadecimal %...h character number
+-- 0xHEXADECIMAL %...H character number
+-- U+hexadecimal %...u character number
+-- U+HEXADECIMAL %...U character number
+-- points %p number (scaled points)
+-- basepoints %b number (scaled points)
+-- table concat %...t table
+-- table concat %{.}t table
+-- serialize %...T sequenced (no nested tables)
+-- serialize %{.}T sequenced (no nested tables)
+-- boolean (logic) %l boolean
+-- BOOLEAN %L boolean
+-- whitespace %...w number
+-- whitespace %...W (fixed)
+-- automatic %...a 'whatever' (string, table, ...)
+-- automatic %...A "whatever" (string, table, ...)
+-- zap %...z skip
+-- stripped %...N %...N
+-- comma/period real %...m
+-- period/comma real %...M
+-- formatted float %...k n.m
+
+local n = 0
+
+-- we are somewhat sloppy in parsing prefixes as it's not that critical
+
+-- hard to avoid but we can collect them in a private namespace if needed
+
+-- inline the next two makes no sense as we only use this in logging
+
+local sequenced = table.sequenced
+
+function string.autodouble(s,sep)
+ if s == nil then
+ return '""'
+ end
+ local t = type(s)
+ if t == "number" then
+ return tostring(s) -- tostring not really needed
+ end
+ if t == "table" then
+ return ('"' .. sequenced(s,sep or ",") .. '"')
+ end
+ return ('"' .. tostring(s) .. '"')
+end
+
+function string.autosingle(s,sep)
+ if s == nil then
+ return "''"
+ end
+ local t = type(s)
+ if t == "number" then
+ return tostring(s) -- tostring not really needed
+ end
+ if t == "table" then
+ return ("'" .. sequenced(s,sep or ",") .. "'")
+ end
+ return ("'" .. tostring(s) .. "'")
+end
+
+local tracedchars = { [0] =
+ -- the regular bunch
+ "[null]", "[soh]", "[stx]", "[etx]", "[eot]", "[enq]", "[ack]", "[bel]",
+ "[bs]", "[ht]", "[lf]", "[vt]", "[ff]", "[cr]", "[so]", "[si]",
+ "[dle]", "[dc1]", "[dc2]", "[dc3]", "[dc4]", "[nak]", "[syn]", "[etb]",
+ "[can]", "[em]", "[sub]", "[esc]", "[fs]", "[gs]", "[rs]", "[us]",
+ -- plus space
+ "[space]", -- 0x20
+}
+
+string.tracedchars = tracedchars
+strings.tracers = tracedchars
+
+function string.tracedchar(b)
+ -- todo: table
+ if type(b) == "number" then
+ return tracedchars[b] or (utfchar(b) .. " (U+" .. format("%05X",b) .. ")")
+ else
+ local c = utfbyte(b)
+ return tracedchars[c] or (b .. " (U+" .. (c and format("%05X",c) or "?????") .. ")")
+ end
+end
+
+function number.signed(i)
+ if i > 0 then
+ return "+", i
+ else
+ return "-", -i
+ end
+end
+
+-- maybe to util-num
+
+local two = digit * digit
+local three = two * digit
+local prefix = (Carg(1) * three)^1
+
+local splitter = Cs (
+ (((1 - (three^1 * period))^1 + C(three)) * prefix + C((1-period)^1))
+ * (anything/"" * Carg(2)) * C(2)
+)
+
+local splitter3 = Cs (
+ three * prefix * endofstring +
+ two * prefix * endofstring +
+ digit * prefix * endofstring +
+ three +
+ two +
+ digit
+)
+
+patterns.formattednumber = splitter
+
+function number.formatted(n,sep1,sep2)
+ if sep1 == false then
+ if type(n) == "number" then
+ n = tostring(n)
+ end
+ return lpegmatch(splitter3,n,1,sep2 or ".")
+ else
+ if type(n) == "number" then
+ n = format("%0.2f",n)
+ end
+ if sep1 == true then
+ return lpegmatch(splitter,n,1,".",",")
+ elseif sep1 == "." then
+ return lpegmatch(splitter,n,1,sep1,sep2 or ",")
+ elseif sep1 == "," then
+ return lpegmatch(splitter,n,1,sep1,sep2 or ".")
+ else
+ return lpegmatch(splitter,n,1,sep1 or ",",sep2 or ".")
+ end
+ end
+end
+
+-- print(number.formatted(1))
+-- print(number.formatted(12))
+-- print(number.formatted(123))
+-- print(number.formatted(1234))
+-- print(number.formatted(12345))
+-- print(number.formatted(123456))
+-- print(number.formatted(1234567))
+-- print(number.formatted(12345678))
+-- print(number.formatted(12345678,true))
+-- print(number.formatted(1,false))
+-- print(number.formatted(12,false))
+-- print(number.formatted(123,false))
+-- print(number.formatted(1234,false))
+-- print(number.formatted(12345,false))
+-- print(number.formatted(123456,false))
+-- print(number.formatted(1234567,false))
+-- print(number.formatted(12345678,false))
+-- print(number.formatted(1234.56,"!","?"))
+
+local p = Cs(
+ P("-")^0
+ * (P("0")^1/"")^0
+ * (1-period)^0
+ * (period * P("0")^1 * endofstring/"" + period^0)
+ * P(1-P("0")^1*endofstring)^0
+ )
+
+function number.compactfloat(n,fmt)
+ if n == 0 then
+ return "0"
+ elseif n == 1 then
+ return "1"
+ end
+ n = lpegmatch(p,format(fmt or "%0.3f",n))
+ if n == "." or n == "" or n == "-" then
+ return "0"
+ end
+ return n
+end
+
+local zero = P("0")^1 / ""
+local plus = P("+") / ""
+local minus = P("-")
+local separator = period
+local trailing = zero^1 * #S("eE")
+local exponent = (S("eE") * (plus + Cs((minus * zero^0 * endofstring)/"") + minus) * zero^0 * (endofstring * Cc("0") + anything^1))
+local pattern_a = Cs(minus^0 * digit^1 * (separator/"" * trailing + separator * (trailing + digit)^0) * exponent)
+local pattern_b = Cs((exponent + anything)^0)
+
+function number.sparseexponent(f,n)
+ if not n then
+ n = f
+ f = "%e"
+ end
+ local tn = type(n)
+ if tn == "string" then -- cast to number
+ local m = tonumber(n)
+ if m then
+ return lpegmatch((f == "%e" or f == "%E") and pattern_a or pattern_b,format(f,m))
+ end
+ elseif tn == "number" then
+ return lpegmatch((f == "%e" or f == "%E") and pattern_a or pattern_b,format(f,n))
+ end
+ return tostring(n)
+end
+
+local hf = { }
+local hs = { }
+
+setmetatable(hf, { __index = function(t,k)
+ local v = "%." .. k .. "f"
+ t[k] = v
+ return v
+end } )
+
+setmetatable(hs, { __index = function(t,k)
+ local v = "%" .. k .. "s"
+ t[k] = v
+ return v
+end } )
+
+function number.formattedfloat(n,b,a)
+ local s = format(hf[a],n)
+ local l = (b or 0) + (a or 0) + 1
+ if #s < l then
+ return format(hs[l],s)
+ else
+ return s
+ end
+end
+
+local template = [[
+%s
+%s
+return function(%s) return %s end
+]]
+
+-- this might move
+
+local pattern = Cs(Cc('"') * (
+ (1-S('"\\\n\r'))^1
+ + P('"') / '\\"'
+ + P('\\') / '\\\\'
+ + P('\n') / '\\n'
+ + P('\r') / '\\r'
+)^0 * Cc('"'))
+
+patterns.escapedquotes = pattern
+
+function string.escapedquotes(s)
+ return lpegmatch(pattern,s)
+end
+
+-- print(string.escapedquotes('1\\23\n"'))
+
+-- but for now here
+
+local preamble = ""
+
+local environment = {
+ global = global or _G,
+ lpeg = lpeg,
+ type = type,
+ tostring = tostring,
+ tonumber = tonumber,
+ format = string.format,
+ concat = table.concat,
+ signed = number.signed,
+ points = number.points,
+ basepoints = number.basepoints,
+ utfchar = utf.char,
+ utfbyte = utf.byte,
+ lpegmatch = lpeg.match,
+ nspaces = string.nspaces,
+ utfpadding = string.utfpadding,
+ tracedchar = string.tracedchar,
+ autosingle = string.autosingle,
+ autodouble = string.autodouble,
+ sequenced = table.sequenced,
+ formattednumber = number.formatted,
+ sparseexponent = number.sparseexponent,
+ formattedfloat = number.formattedfloat,
+ stripzero = patterns.stripzero,
+ stripzeros = patterns.stripzeros,
+ escapedquotes = string.escapedquotes,
+
+ FORMAT = string.f9,
+}
+
+-- -- --
+
+local arguments = { "a1" } -- faster than previously used (select(n,...))
+
+setmetatable(arguments, { __index =
+ function(t,k)
+ local v = t[k-1] .. ",a" .. k
+ t[k] = v
+ return v
+ end
+})
+
+local prefix_any = C((sign + space + period + digit)^0)
+local prefix_sub = (C((sign + digit)^0) + Cc(0))
+ * period
+ * (C((sign + digit)^0) + Cc(0))
+local prefix_tab = P("{") * C((1-P("}"))^0) * P("}") + C((1-R("az","AZ","09","%%"))^0)
+
+-- we've split all cases as then we can optimize them (let's omit the fuzzy u)
+
+-- todo: replace outer formats in next by ..
+
+local format_s = function(f)
+ n = n + 1
+ if f and f ~= "" then
+ return format("format('%%%ss',a%s)",f,n)
+ else -- best no tostring in order to stay compatible (.. does a selective tostring too)
+ return format("(a%s or '')",n) -- goodie: nil check
+ end
+end
+
+local format_S = function(f) -- can be optimized
+ n = n + 1
+ if f and f ~= "" then
+ return format("format('%%%ss',tostring(a%s))",f,n)
+ else
+ return format("tostring(a%s)",n)
+ end
+end
+
+local format_right = function(f)
+ n = n + 1
+ f = tonumber(f)
+ if not f or f == 0 then
+ return format("(a%s or '')",n)
+ elseif f > 0 then
+ return format("utfpadding(a%s,%i)..a%s",n,f,n)
+ else
+ return format("a%s..utfpadding(a%s,%i)",n,n,f)
+ end
+end
+
+local format_left = function(f)
+ n = n + 1
+ f = tonumber(f)
+ if not f or f == 0 then
+ return format("(a%s or '')",n)
+ end
+ if f < 0 then
+ return format("utfpadding(a%s,%i)..a%s",n,-f,n)
+ else
+ return format("a%s..utfpadding(a%s,%i)",n,n,-f)
+ end
+end
+
+local format_q = function()
+ n = n + 1
+ -- lua 5.3 has a different q than lua 5.2 (which does a tostring on numbers)
+ -- return format("(a%s ~= nil and format('%%q',a%s) or '')",n,n)
+ return format("(a%s ~= nil and format('%%q',tostring(a%s)) or '')",n,n)
+ -- return format("(a%s ~= nil and escapedquotes(tostring(a%s)) or '')",n,n)
+end
+
+local format_Q = function() -- fast escaping
+ n = n + 1
+-- return format("format('%%q',tostring(a%s))",n)
+ return format("escapedquotes(tostring(a%s))",n)
+end
+
+local format_i = function(f)
+ n = n + 1
+ if f and f ~= "" then
+ return format("format('%%%si',a%s)",f,n)
+ else
+ return format("format('%%i',a%s)",n) -- why not just tostring()
+ end
+end
+
+local format_d = format_i
+
+local format_I = function(f)
+ n = n + 1
+ return format("format('%%s%%%si',signed(a%s))",f,n)
+end
+
+local format_f = function(f)
+ n = n + 1
+ return format("format('%%%sf',a%s)",f,n)
+end
+
+-- The next one formats an integer as integer and very small values as zero. This is needed
+-- for pdf backend code.
+--
+-- 1.23 % 1 : 0.23
+-- - 1.23 % 1 : 0.77
+--
+-- We could probably use just %s with integers but who knows what Lua 5.3 will do? So let's
+-- for the moment use %i.
+
+local format_F = function(f) -- beware, no cast to number
+ n = n + 1
+ if not f or f == "" then
+ return format("(((a%s > -0.0000000005 and a%s < 0.0000000005) and '0') or format((a%s %% 1 == 0) and '%%i' or '%%.9f',a%s))",n,n,n,n)
+ else
+ return format("format((a%s %% 1 == 0) and '%%i' or '%%%sf',a%s)",n,f,n)
+ end
+end
+
+-- if string.f9 then
+-- format_F = function(f) -- beware, no cast to number
+-- n = n + 1
+-- if not f or f == "" then
+-- return format("(((a%s > -0.0000000005 and a%s < 0.0000000005) and '0') or FORMAT(a%s))",n,n,n,n,n)
+-- else
+-- return format("((a%s %% 1 == 0) and format('%%i',a%s) or FORMAT(a%s,'%%%sf'))",n,n,n,f)
+-- end
+-- end
+-- end
+
+local format_k = function(b,a) -- slow
+ n = n + 1
+ return format("formattedfloat(a%s,%s,%s)",n,b or 0,a or 0)
+end
+
+local format_g = function(f)
+ n = n + 1
+ return format("format('%%%sg',a%s)",f,n)
+end
+
+local format_G = function(f)
+ n = n + 1
+ return format("format('%%%sG',a%s)",f,n)
+end
+
+local format_e = function(f)
+ n = n + 1
+ return format("format('%%%se',a%s)",f,n)
+end
+
+local format_E = function(f)
+ n = n + 1
+ return format("format('%%%sE',a%s)",f,n)
+end
+
+local format_j = function(f)
+ n = n + 1
+ return format("sparseexponent('%%%se',a%s)",f,n)
+end
+
+local format_J = function(f)
+ n = n + 1
+ return format("sparseexponent('%%%sE',a%s)",f,n)
+end
+
+local format_x = function(f)
+ n = n + 1
+ return format("format('%%%sx',a%s)",f,n)
+end
+
+local format_X = function(f)
+ n = n + 1
+ return format("format('%%%sX',a%s)",f,n)
+end
+
+local format_o = function(f)
+ n = n + 1
+ return format("format('%%%so',a%s)",f,n)
+end
+
+local format_c = function()
+ n = n + 1
+ return format("utfchar(a%s)",n)
+end
+
+local format_C = function()
+ n = n + 1
+ return format("tracedchar(a%s)",n)
+end
+
+local format_r = function(f)
+ n = n + 1
+ return format("format('%%%s.0f',a%s)",f,n)
+end
+
+local format_h = function(f)
+ n = n + 1
+ if f == "-" then
+ f = sub(f,2)
+ return format("format('%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ else
+ return format("format('0x%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ end
+end
+
+local format_H = function(f)
+ n = n + 1
+ if f == "-" then
+ f = sub(f,2)
+ return format("format('%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ else
+ return format("format('0x%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ end
+end
+
+local format_u = function(f)
+ n = n + 1
+ if f == "-" then
+ f = sub(f,2)
+ return format("format('%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ else
+ return format("format('u+%%%sx',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ end
+end
+
+local format_U = function(f)
+ n = n + 1
+ if f == "-" then
+ f = sub(f,2)
+ return format("format('%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ else
+ return format("format('U+%%%sX',type(a%s) == 'number' and a%s or utfbyte(a%s))",f == "" and "05" or f,n,n,n)
+ end
+end
+
+local format_p = function()
+ n = n + 1
+ return format("points(a%s)",n)
+end
+
+local format_b = function()
+ n = n + 1
+ return format("basepoints(a%s)",n)
+end
+
+local format_t = function(f)
+ n = n + 1
+ if f and f ~= "" then
+ return format("concat(a%s,%q)",n,f)
+ else
+ return format("concat(a%s)",n)
+ end
+end
+
+local format_T = function(f)
+ n = n + 1
+ if f and f ~= "" then
+ return format("sequenced(a%s,%q)",n,f)
+ else
+ return format("sequenced(a%s)",n)
+ end
+end
+
+local format_l = function()
+ n = n + 1
+ return format("(a%s and 'true' or 'false')",n)
+end
+
+local format_L = function()
+ n = n + 1
+ return format("(a%s and 'TRUE' or 'FALSE')",n)
+end
+
+local format_n = function() -- strips leading and trailing zeros and removes .0
+ n = n + 1
+ return format("((a%s %% 1 == 0) and format('%%i',a%s) or tostring(a%s))",n,n,n)
+end
+
+-- local format_N = function() -- strips leading and trailing zeros (also accepts string)
+-- n = n + 1
+-- return format("tostring(tonumber(a%s) or a%s)",n,n)
+-- end
+
+-- local format_N = function(f) -- strips leading and trailing zeros
+-- n = n + 1
+-- -- stripzero (singular) as we only have a number
+-- if not f or f == "" then
+-- return format("(((a%s > -0.0000000005 and a%s < 0.0000000005) and '0') or ((a%s %% 1 == 0) and format('%%i',a%s)) or lpegmatch(stripzero,format('%%.9f',a%s)))",n,n,n,n,n)
+-- else
+-- return format("(((a%s %% 1 == 0) and format('%%i',a%s)) or lpegmatch(stripzero,format('%%%sf',a%s)))",n,n,f,n)
+-- end
+-- end
+
+-- local format_N = function(f) -- strips leading and trailing zeros
+-- n = n + 1
+-- -- stripzero (singular) as we only have a number
+-- if not f or f == "" then
+-- return format("(((a%s %% 1 == 0) and format('%%i',a%s)) or ((a%s > -0.0000000005 and a%s < 0.0000000005) and '0') or lpegmatch(stripzero,format('%%.9f',a%s)))",n,n,n,n,n)
+-- else
+-- return format("(((a%s %% 1 == 0) and format('%%i',a%s)) or lpegmatch(stripzero,format('%%%sf',a%s)))",n,n,f,n)
+-- end
+-- end
+
+local format_N = function(f) -- strips leading and trailing zeros
+ n = n + 1
+ -- stripzero (singular) as we only have a number
+ if not f or f == "" then
+ f = ".9"
+ end -- always a leading number !
+ return format("(((a%s %% 1 == 0) and format('%%i',a%s)) or lpegmatch(stripzero,format('%%%sf',a%s)))",n,n,f,n)
+end
+
+local format_a = function(f)
+ n = n + 1
+ if f and f ~= "" then
+ return format("autosingle(a%s,%q)",n,f)
+ else
+ return format("autosingle(a%s)",n)
+ end
+end
+
+local format_A = function(f)
+ n = n + 1
+ if f and f ~= "" then
+ return format("autodouble(a%s,%q)",n,f)
+ else
+ return format("autodouble(a%s)",n)
+ end
+end
+
+local format_w = function(f) -- handy when doing depth related indent
+ n = n + 1
+ f = tonumber(f)
+ if f then -- not that useful
+ return format("nspaces[%s+a%s]",f,n) -- no real need for tonumber
+ else
+ return format("nspaces[a%s]",n) -- no real need for tonumber
+ end
+end
+
+local format_W = function(f) -- handy when doing depth related indent
+ return format("nspaces[%s]",tonumber(f) or 0)
+end
+
+local format_m = function(f)
+ n = n + 1
+ if not f or f == "" then
+ f = ","
+ end
+ if f == "0" then
+ return format([[formattednumber(a%s,false)]],n)
+ else
+ return format([[formattednumber(a%s,%q,".")]],n,f)
+ end
+end
+
+local format_M = function(f)
+ n = n + 1
+ if not f or f == "" then
+ f = "."
+ end
+ if f == "0" then
+ return format([[formattednumber(a%s,false)]],n)
+ else
+ return format([[formattednumber(a%s,%q,",")]],n,f)
+ end
+end
+
+--
+
+local format_z = function(f)
+ n = n + (tonumber(f) or 1)
+ return "''" -- okay, not that efficient to append '' but a special case anyway
+end
+
+--
+
+-- local strip
+--
+-- local format_Z = function(f)
+-- n = n + 1
+-- if not f or f == "" then
+-- f = ".9"
+-- end
+-- return format("(((a%s %% 1 == 0) and format('%%i',a%s)) or (strip and lpegmatch(stripzero,format('%%%sf',a%s))) or format('%%%sf',a%s))",n,n,f,n,f,n)
+-- end
+--
+-- function strings.stripformatterzeros()
+-- strip = true
+-- end
+
+-- add(formatters,"texexp", [[texexp(...)]], "local texexp = metapost.texexp")
+--
+-- add(formatters,"foo:bar",[[foo(...)]], { foo = function(...) print(...) return "!" end })
+-- print(string.formatters["foo %3!foo:bar! bar"](1,2,3))
+
+
+local format_rest = function(s)
+ return format("%q",s) -- catches " and \n and such
+end
+
+-- local format_extension = function(extensions,f,name)
+-- local extension = extensions[name] or "tostring(%s)"
+-- local f = tonumber(f) or 1
+-- local w = find(extension,"%.%.%.")
+-- if f == 0 then
+-- if w then
+-- extension = gsub(extension,"%.%.%.","")
+-- end
+-- return extension
+-- elseif f == 1 then
+-- if w then
+-- extension = gsub(extension,"%.%.%.","%%s")
+-- end
+-- n = n + 1
+-- local a = "a" .. n
+-- return format(extension,a,a) -- maybe more times?
+-- elseif f < 0 then
+-- local a = "a" .. (n + f + 1)
+-- return format(extension,a,a)
+-- else
+-- if w then
+-- extension = gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
+-- end
+-- -- we could fill an array and then n = n + 1 unpack(t,n,n+f) but as we
+-- -- cache we don't save much and there are hardly any extensions anyway
+-- local t = { }
+-- for i=1,f do
+-- n = n + 1
+-- -- t[#t+1] = "a" .. n
+-- t[i] = "a" .. n
+-- end
+-- return format(extension,unpack(t))
+-- end
+-- end
+
+local format_extension = function(extensions,f,name)
+ local extension = extensions[name] or "tostring(%s)"
+ local f = tonumber(f) or 1
+ local w = find(extension,"%.%.%.")
+ if w then
+ -- we have a wildcard
+ if f == 0 then
+ extension = gsub(extension,"%.%.%.","")
+ return extension
+ elseif f == 1 then
+ extension = gsub(extension,"%.%.%.","%%s")
+ n = n + 1
+ local a = "a" .. n
+ return format(extension,a,a) -- maybe more times?
+ elseif f < 0 then
+ local a = "a" .. (n + f + 1)
+ return format(extension,a,a)
+ else
+ extension = gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
+ -- we could fill an array and then n = n + 1 unpack(t,n,n+f) but as we
+ -- cache we don't save much and there are hardly any extensions anyway
+ local t = { }
+ for i=1,f do
+ n = n + 1
+ -- t[#t+1] = "a" .. n
+ t[i] = "a" .. n
+ end
+ return format(extension,unpack(t))
+ end
+ else
+ extension = gsub(extension,"%%s",function()
+ n = n + 1
+ return "a" .. n
+ end)
+ return extension
+ end
+end
+
+-- aA b cC d eE f gG hH iI jJ lL mM N o p qQ r sS tT uU wW xX z
+
+-- extensions : %!tag!
+
+-- can be made faster but not called that often
+
+local builder = Cs { "start",
+ start = (
+ (
+ P("%") / ""
+ * (
+ V("!") -- new
+ + V("s") + V("q")
+ + V("i") + V("d")
+ + V("f") + V("F") + V("g") + V("G") + V("e") + V("E")
+ + V("x") + V("X") + V("o")
+ --
+ + V("c")
+ + V("C")
+ + V("S") -- new
+ + V("Q") -- new
+ + V("n") -- new
+ + V("N") -- new
+ + V("k") -- new
+ --
+ + V("r")
+ + V("h") + V("H") + V("u") + V("U")
+ + V("p") + V("b")
+ + V("t") + V("T")
+ + V("l") + V("L")
+ + V("I")
+ + V("w") -- new
+ + V("W") -- new
+ + V("a") -- new
+ + V("A") -- new
+ + V("j") + V("J") -- stripped e E
+ + V("m") + V("M") -- new (formatted number)
+ + V("z") -- new
+ --
+ + V(">") -- left padding
+ + V("<") -- right padding
+ --
+ -- + V("?") -- ignored, probably messed up %
+ )
+ + V("*")
+ )
+ * (endofstring + Carg(1))
+ )^0,
+ --
+ ["s"] = (prefix_any * P("s")) / format_s, -- %s => regular %s (string)
+ ["q"] = (prefix_any * P("q")) / format_q, -- %q => regular %q (quoted string)
+ ["i"] = (prefix_any * P("i")) / format_i, -- %i => regular %i (integer)
+ ["d"] = (prefix_any * P("d")) / format_d, -- %d => regular %d (integer)
+ ["f"] = (prefix_any * P("f")) / format_f, -- %f => regular %f (float)
+ ["F"] = (prefix_any * P("F")) / format_F, -- %F => regular %f (float) but 0/1 check
+ ["g"] = (prefix_any * P("g")) / format_g, -- %g => regular %g (float)
+ ["G"] = (prefix_any * P("G")) / format_G, -- %G => regular %G (float)
+ ["e"] = (prefix_any * P("e")) / format_e, -- %e => regular %e (float)
+ ["E"] = (prefix_any * P("E")) / format_E, -- %E => regular %E (float)
+ ["x"] = (prefix_any * P("x")) / format_x, -- %x => regular %x (hexadecimal)
+ ["X"] = (prefix_any * P("X")) / format_X, -- %X => regular %X (HEXADECIMAL)
+ ["o"] = (prefix_any * P("o")) / format_o, -- %o => regular %o (octal)
+ --
+ ["S"] = (prefix_any * P("S")) / format_S, -- %S => %s (tostring)
+ ["Q"] = (prefix_any * P("Q")) / format_Q, -- %Q => %q (tostring)
+ ["n"] = (prefix_any * P("n")) / format_n, -- %n => tonumber (strips leading and trailing zeros, as well as .0, expects number)
+ ["N"] = (prefix_any * P("N")) / format_N, -- %N => tonumber (strips leading and trailing zeros, also takes string)
+ ["k"] = (prefix_sub * P("k")) / format_k, -- %k => like f but with n.m
+ ["c"] = (prefix_any * P("c")) / format_c, -- %c => utf character (extension to regular)
+ ["C"] = (prefix_any * P("C")) / format_C, -- %c => U+.... utf character
+ --
+ ["r"] = (prefix_any * P("r")) / format_r, -- %r => round
+ ["h"] = (prefix_any * P("h")) / format_h, -- %h => 0x0a1b2 (when - no 0x) was v
+ ["H"] = (prefix_any * P("H")) / format_H, -- %H => 0x0A1B2 (when - no 0x) was V
+ ["u"] = (prefix_any * P("u")) / format_u, -- %u => u+0a1b2 (when - no u+)
+ ["U"] = (prefix_any * P("U")) / format_U, -- %U => U+0A1B2 (when - no U+)
+ ["p"] = (prefix_any * P("p")) / format_p, -- %p => 12.345pt / maybe: P (and more units)
+ ["b"] = (prefix_any * P("b")) / format_b, -- %b => 12.342bp / maybe: B (and more units)
+ ["t"] = (prefix_tab * P("t")) / format_t, -- %t => concat
+ ["T"] = (prefix_tab * P("T")) / format_T, -- %t => sequenced
+ ["l"] = (prefix_any * P("l")) / format_l, -- %l => boolean
+ ["L"] = (prefix_any * P("L")) / format_L, -- %L => BOOLEAN
+ ["I"] = (prefix_any * P("I")) / format_I, -- %I => signed integer
+ --
+ ["w"] = (prefix_any * P("w")) / format_w, -- %w => n spaces (optional prefix is added)
+ ["W"] = (prefix_any * P("W")) / format_W, -- %W => mandate prefix, no specifier
+ --
+ ["j"] = (prefix_any * P("j")) / format_j, -- %j => %e (float) stripped exponent (irrational)
+ ["J"] = (prefix_any * P("J")) / format_J, -- %J => %E (float) stripped exponent (irrational)
+ --
+ ["m"] = (prefix_any * P("m")) / format_m, -- %m => xxx.xxx.xxx,xx (optional prefix instead of .)
+ ["M"] = (prefix_any * P("M")) / format_M, -- %M => xxx,xxx,xxx.xx (optional prefix instead of ,)
+ --
+ ["z"] = (prefix_any * P("z")) / format_z, -- %z => skip n arguments
+ -- ["Z"] = (prefix_any * P("Z")) / format_Z, -- %Z => optionally strip zeros
+ --
+ ["a"] = (prefix_any * P("a")) / format_a, -- %a => '...' (forces tostring)
+ ["A"] = (prefix_any * P("A")) / format_A, -- %A => "..." (forces tostring)
+ --
+ ["<"] = (prefix_any * P("<")) / format_left,
+ [">"] = (prefix_any * P(">")) / format_right,
+ --
+ ["*"] = Cs(((1-P("%"))^1 + P("%%")/"%%")^1) / format_rest, -- rest (including %%)
+ ["?"] = Cs(((1-P("%"))^1 )^1) / format_rest, -- rest (including %%)
+ --
+ ["!"] = Carg(2) * prefix_any * P("!") * C((1-P("!"))^1) * P("!") / format_extension,
+}
+
+-- We can be clever and only alias what is needed:
+
+local xx = setmetatable({ }, { __index = function(t,k) local v = format("%02x",k) t[k] = v return v end })
+local XX = setmetatable({ }, { __index = function(t,k) local v = format("%02X",k) t[k] = v return v end })
+
+local preset = {
+ ["%02x"] = function(n) return xx[n] end,
+ ["%02X"] = function(n) return XX[n] end,
+}
+
+local direct =
+ P("%") * (sign + space + period + digit)^0 * S("sqidfgGeExXo") * endofstring
+ / [[local format = string.format return function(str) return format("%0",str) end]]
+
+local function make(t,str)
+ local f = preset[str]
+ if f then
+ return f
+ end
+ local p = lpegmatch(direct,str)
+ if p then
+ -- print("builder 1 >",p)
+ f = loadstripped(p)()
+ else
+ n = 0 -- used in patterns
+ -- p = lpegmatch(builder,str,1,"..",t._extensions_) -- after this we know n
+ p = lpegmatch(builder,str,1,t._connector_,t._extensions_) -- after this we know n
+ if n > 0 then
+ p = format(template,preamble,t._preamble_,arguments[n],p)
+ -- print("builder 2 >",p)
+ f = loadstripped(p,t._environment_)() -- t._environment is not populated (was experiment)
+ else
+ f = function() return str end
+ end
+ end
+ -- if jit then jit.on(f,true) end
+ t[str] = f
+ return f
+end
+
+-- -- collect periodically
+--
+-- local threshold = 1000 -- max nof cached formats
+--
+-- local function make(t,str)
+-- local f = rawget(t,str)
+-- if f then
+-- return f
+-- end
+-- local parent = t._t_
+-- if parent._n_ > threshold then
+-- local m = { _t_ = parent }
+-- getmetatable(parent).__index = m
+-- setmetatable(m, { __index = make })
+-- else
+-- parent._n_ = parent._n_ + 1
+-- end
+-- local f
+-- local p = lpegmatch(direct,str)
+-- if p then
+-- f = loadstripped(p)()
+-- else
+-- n = 0
+-- p = lpegmatch(builder,str,1,"..",parent._extensions_) -- after this we know n
+-- if n > 0 then
+-- p = format(template,preamble,parent._preamble_,arguments[n],p)
+-- -- print("builder>",p)
+-- f = loadstripped(p)()
+-- else
+-- f = function() return str end
+-- end
+-- end
+-- t[str] = f
+-- return f
+-- end
+
+local function use(t,fmt,...)
+ return t[fmt](...)
+end
+
+strings.formatters = { }
+
+-- we cannot make these tables weak, unless we start using an indirect
+-- table (metatable) in which case we could better keep a count and
+-- clear that table when a threshold is reached
+
+-- _connector_ is an experiment
+
+function strings.formatters.new(noconcat)
+ local e = { } -- better make a copy as we can overload
+ for k, v in next, environment do
+ e[k] = v
+ end
+ local t = {
+ _type_ = "formatter",
+ _connector_ = noconcat and "," or "..",
+ _extensions_ = { },
+ _preamble_ = "",
+ _environment_ = e,
+ }
+ setmetatable(t, { __index = make, __call = use })
+ return t
+end
+
+local formatters = strings.formatters.new() -- the default instance
+
+string.formatters = formatters -- in the main string namespace
+string.formatter = function(str,...) return formatters[str](...) end -- sometimes nicer name
+
+local function add(t,name,template,preamble)
+ if type(t) == "table" and t._type_ == "formatter" then
+ t._extensions_[name] = template or "%s"
+ if type(preamble) == "string" then
+ t._preamble_ = preamble .. "\n" .. t._preamble_ -- so no overload !
+ elseif type(preamble) == "table" then
+ for k, v in next, preamble do
+ t._environment_[k] = v
+ end
+ end
+ end
+end
+
+strings.formatters.add = add
+
+-- registered in the default instance (should we fall back on this one?)
+
+patterns.xmlescape = Cs((P("<")/"&lt;" + P(">")/"&gt;" + P("&")/"&amp;" + P('"')/"&quot;" + anything)^0)
+patterns.texescape = Cs((C(S("#$%\\{}"))/"\\%1" + anything)^0)
+patterns.luaescape = Cs(((1-S('"\n'))^1 + P('"')/'\\"' + P('\n')/'\\n"')^0) -- maybe also \0
+patterns.luaquoted = Cs(Cc('"') * ((1-S('"\n'))^1 + P('"')/'\\"' + P('\n')/'\\n"')^0 * Cc('"'))
+
+-- escaping by lpeg is faster for strings without quotes, slower on a string with quotes, but
+-- faster again when other q-escapables are found (the ones we don't need to escape)
+
+add(formatters,"xml",[[lpegmatch(xmlescape,%s)]],{ xmlescape = patterns.xmlescape })
+add(formatters,"tex",[[lpegmatch(texescape,%s)]],{ texescape = patterns.texescape })
+add(formatters,"lua",[[lpegmatch(luaescape,%s)]],{ luaescape = patterns.luaescape })
+
+-- -- yes or no:
+--
+-- local function make(t,str)
+-- local f
+-- local p = lpegmatch(direct,str)
+-- if p then
+-- f = loadstripped(p)()
+-- else
+-- n = 0
+-- p = lpegmatch(builder,str,1,",") -- after this we know n
+-- if n > 0 then
+-- p = format(template,template_shortcuts,arguments[n],p)
+-- f = loadstripped(p)()
+-- else
+-- f = function() return str end
+-- end
+-- end
+-- t[str] = f
+-- return f
+-- end
+--
+-- local formatteds = string.formatteds or { }
+-- string.formatteds = formatteds
+--
+-- setmetatable(formatteds, { __index = make, __call = use })
+
+-- This is a somewhat silly one used in commandline reconstruction but the older
+-- method, using a combination of fine, gsub, quoted and unquoted was not that
+-- reliable.
+--
+-- '"foo"bar \"and " whatever"' => "foo\"bar \"and \" whatever"
+-- 'foo"bar \"and " whatever' => "foo\"bar \"and \" whatever"
+
+local dquote = patterns.dquote -- P('"')
+local equote = patterns.escaped + dquote / '\\"' + 1
+local cquote = Cc('"')
+
+local pattern =
+ Cs(dquote * (equote - P(-2))^0 * dquote) -- we keep the outer but escape unescaped ones
+ + Cs(cquote * (equote - space)^0 * space * equote^0 * cquote) -- we escape unescaped ones
+
+function string.optionalquoted(str)
+ return lpegmatch(pattern,str) or str
+end
+
+local pattern = Cs((newline / (os.newline or "\r") + 1)^0)
+
+function string.replacenewlines(str)
+ return lpegmatch(pattern,str)
+end
+
+--
+
+function strings.newcollector()
+ local result, r = { }, 0
+ return
+ function(fmt,str,...) -- write
+ r = r + 1
+ result[r] = str == nil and fmt or formatters[fmt](str,...)
+ end,
+ function(connector) -- flush
+ if result then
+ local str = concat(result,connector)
+ result, r = { }, 0
+ return str
+ end
+ end
+end
+
+--
+
+local f_16_16 = formatters["%0.5N"]
+
+function number.to16dot16(n)
+ return f_16_16(n/65536.0)
+end
+
+--
+
+if not string.explode then
+
+ local tsplitat = lpeg.tsplitat
+
+ local p_utf = patterns.utf8character
+ local p_check = C(p_utf) * (P("+") * Cc(true))^0
+ local p_split = Ct(C(p_utf)^0)
+ local p_space = Ct((C(1-P(" ")^1) + P(" ")^1)^0)
+
+ function string.explode(str,symbol)
+ if symbol == "" then
+ return lpegmatch(p_split,str)
+ elseif symbol then
+ local a, b = lpegmatch(p_check,symbol)
+ if b then
+ return lpegmatch(tsplitat(P(a)^1),str)
+ else
+ return lpegmatch(tsplitat(a),str)
+ end
+ else
+ return lpegmatch(p_space,str)
+ end
+ end
+
+end
diff --git a/macros/luatex/generic/luaotfload/luaotfload-auxiliary.lua b/macros/luatex/generic/luaotfload/luaotfload-auxiliary.lua
new file mode 100644
index 0000000000..3e3283b5ff
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-auxiliary.lua
@@ -0,0 +1,851 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-auxiliary.lua
+-- DESCRIPTION: part of luaotfload
+-- AUTHOR: Khaled Hosny, Élie Roux, Philipp Gesang
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-auxiliary",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / auxiliary functions",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+luaotfload = luaotfload or { }
+local log = luaotfload.log
+local logreport = log.report
+local fonthashes = fonts.hashes
+local encodings = fonts.encodings
+local identifiers = fonthashes.identifiers
+local fontnames = fonts.names
+
+local fontid = font.id
+local texsprint = tex.sprint
+
+local dofile = dofile
+local getmetatable = getmetatable
+local setmetatable = setmetatable
+local utfcodepoint = utf8.codepoint
+local stringlower = string.lower
+local stringformat = string.format
+local stringgsub = string.gsub
+local stringbyte = string.byte
+local stringfind = string.find
+local tablecopy = table.copy
+
+local aux = { }
+local luaotfload_callbacks = { }
+
+-----------------------------------------------------------------------
+--- font patches
+-----------------------------------------------------------------------
+
+--- https://github.com/khaledhosny/luaotfload/issues/54
+
+local function rewrite_fontname(tfmdata, specification)
+ local format = tfmdata.format or tfmdata.properties.format
+ if stringfind (specification, " ") then
+ tfmdata.name = stringformat ("%q", specification)
+ else
+ --- other specs should parse just fine
+ tfmdata.name = specification
+ end
+end
+
+local rewriting = false
+
+function aux.start_rewrite_fontname()
+ if rewriting == false then
+ luatexbase.add_to_callback (
+ "luaotfload.patch_font",
+ rewrite_fontname,
+ "luaotfload.rewrite_fontname")
+ rewriting = true
+ logreport ("log", 1, "aux",
+ "start rewriting tfmdata.name field")
+ end
+end
+
+function aux.stop_rewrite_fontname()
+ if rewriting == true then
+ luatexbase.remove_from_callback
+ ("luaotfload.patch_font", "luaotfload.rewrite_fontname")
+ rewriting = false
+ logreport ("log", 1, "aux",
+ "stop rewriting tfmdata.name field")
+ end
+end
+
+
+--[[doc--
+This sets two dimensions apparently relied upon by the unicode-math
+package.
+--doc]]--
+
+local function set_sscale_dimens(fontdata)
+ local resources = fontdata.resources if not resources then return end
+ local mathconstants = resources.MathConstants if not mathconstants then return end
+ local parameters = fontdata.parameters if not parameters then return end
+ --- the default values below are complete crap
+ parameters [10] = mathconstants.ScriptPercentScaleDown or 70
+ parameters [11] = mathconstants.ScriptScriptPercentScaleDown or 50
+end
+
+luaotfload_callbacks [#luaotfload_callbacks + 1] = {
+ "patch_font", set_sscale_dimens, "set_sscale_dimens",
+}
+
+local default_units = 1000
+
+--- fontobj -> int
+local function lookup_units(fontdata)
+ local units = fontdata.units
+ if units and units > 0 then return units end
+ local shared = fontdata.shared if not shared then return default_units end
+ local rawdata = shared.rawdata if not rawdata then return default_units end
+ local metadata = rawdata.metadata if not metadata then return default_units end
+ local capheight = metadata.capheight if not capheight then return default_units end
+ local units = metadata.units or fontdata.units
+ if not units or units == 0 then
+ return default_units
+ end
+ return units
+end
+
+--[[doc--
+This callback corrects some values of the Cambria font.
+--doc]]--
+--- fontobj -> unit
+local function patch_cambria_domh(fontdata)
+ local mathconstants = fontdata.MathConstants
+ if mathconstants and fontdata.psname == "CambriaMath" then
+ --- my test Cambria has 2048
+ local units = fontdata.units or lookup_units(fontdata)
+ local sz = fontdata.parameters.size or fontdata.size
+ local mh = 2800 / units * sz
+ if mathconstants.DisplayOperatorMinHeight < mh then
+ mathconstants.DisplayOperatorMinHeight = mh
+ end
+ end
+end
+
+luaotfload_callbacks [#luaotfload_callbacks + 1] = {
+ "patch_font", patch_cambria_domh, "patch_cambria_domh",
+}
+
+
+--[[doc--
+
+ Add missing field to fonts that lack it. Addresses issue
+ https://github.com/lualatex/luaotfload/issues/253
+
+ This is considered a hack, especially since importing the
+ unicode-math package fixes the problem quite nicely.
+
+--doc]]--
+
+--- fontobj -> unit
+local function fixup_fontdata(data)
+ local t = type (data)
+ --- Some OT fonts like Libertine R lack the resources table, causing
+ --- the fontloader to nil-index.
+ if t == "table" then
+ if data and not data.resources then data.resources = { } end
+ end
+end
+
+luaotfload_callbacks [#luaotfload_callbacks + 1] = {
+ "patch_font_unsafe", fixup_fontdata, "fixup_fontdata",
+}
+
+
+--[[doc--
+
+Comment from fontspec:
+
+ “Here we patch fonts tfm table to emulate \XeTeX's \cs{fontdimen8},
+ which stores the caps-height of the font. (Cf.\ \cs{fontdimen5} which
+ stores the x-height.)
+
+ Falls back to measuring the glyph if the font doesn't contain the
+ necessary information.
+ This needs to be extended for fonts that don't contain an `X'.”
+
+--doc]]--
+
+local capheight_reference_chars = { "X", "M", "Ж", "ξ", }
+local capheight_reference_codepoints do
+ capheight_reference_codepoints = { }
+ for i = 1, #capheight_reference_chars do
+ local chr = capheight_reference_chars [i]
+ capheight_reference_codepoints [i] = utfcodepoint (chr)
+ end
+end
+
+local function determine_capheight(fontdata)
+ local parameters = fontdata.parameters if not parameters then return false end
+ local characters = fontdata.characters if not characters then return false end
+ --- Pretty simplistic but it does return *some* value for most fonts;
+ --- we could also refine the approach to return some kind of average
+ --- of all capital letters or a user-provided subset.
+ for i = 1, #capheight_reference_codepoints do
+ local refcp = capheight_reference_codepoints [i]
+ local refchar = characters [refcp]
+ if refchar then
+ logreport ("both", 4, "aux",
+ "picked height of character ‘%s’ (U+%d) as \\fontdimen8 \z
+ candidate",
+ capheight_reference_chars [i], refcp)
+ return refchar.height
+ end
+ end
+ return false
+end
+
+local function query_ascender(fontdata)
+ local parameters = fontdata.parameters if not parameters then return false end
+ local ascender = parameters.ascender
+ if ascender then
+ return ascender --- pre-scaled
+ end
+
+ local shared = fontdata.shared if not shared then return false end
+ local rawdata = shared.rawdata if not rawdata then return false end
+ local metadata = rawdata.metadata if not metadata then return false end
+ ascender = metadata.ascender if not ascender then return false end
+ local size = parameters.size if not size then return false end
+ local units = lookup_units (fontdata)
+ if not units or units == 0 then return false end
+ return ascender * size / units --- scaled
+end
+
+local function query_capheight(fontdata)
+ local parameters = fontdata.parameters if not parameters then return false end
+ local shared = fontdata.shared if not shared then return false end
+ local rawdata = shared.rawdata if not rawdata then return false end
+ local metadata = rawdata.metadata if not metadata then return false end
+ local capheight = metadata.capheight if not capheight then return false end
+ local size = parameters.size if not size then return false end
+ local units = lookup_units (fontdata)
+ if not units or units == 0 then return false end
+ return capheight * size / units
+end
+
+local function query_fontdimen8(fontdata)
+ local parameters = fontdata.parameters if not parameters then return false end
+ local fontdimen8 = parameters [8]
+ if fontdimen8 then return fontdimen8 end
+ return false
+end
+
+local function caphtfmt(ref, ht)
+ if not ht then return "<none>" end
+ if not ref then return tostring (ht) end
+ return stringformat ("%s(δ=%s)", ht, ht - ref)
+end
+
+local function set_capheight(fontdata)
+ if not fontdata then
+ logreport ("both", 0, "aux",
+ "error: set_capheight() received garbage")
+ return
+ end
+ local capheight_dimen8 = query_fontdimen8 (fontdata)
+ local capheight_alleged = query_capheight (fontdata)
+ local capheight_ascender = query_ascender (fontdata)
+ local capheight_measured = determine_capheight (fontdata)
+ logreport ("term", 4, "aux",
+ "capht: param[8]=%s advertised=%s ascender=%s measured=%s",
+ tostring (capheight_dimen8),
+ caphtfmt (capheight_dimen8, capheight_alleged),
+ caphtfmt (capheight_dimen8, capheight_ascender),
+ caphtfmt (capheight_dimen8, capheight_measured))
+ if capheight_dimen8 then --- nothing to do
+ return
+ end
+
+ local capheight = capheight_alleged or capheight_ascender or capheight_measured
+ if capheight then
+ fontdata.parameters [8] = capheight
+ end
+end
+
+luaotfload_callbacks [#luaotfload_callbacks + 1] = {
+ "patch_font", set_capheight, "set_capheight",
+}
+
+-- Of course there are also fonts with no sensible x-height, so let's add a
+-- fallback there:
+local function set_xheight(tfmdata)
+ local parameters = tfmdata.parameters
+ if not parameters then return end
+ if not (parameters.x_height or parameters[5] or 0) == 0 then return end
+ if tfmdata.characters and tfmdata.characters[120] then
+ parameters.x_height = tfmdata.characters[120].height
+ else
+ parameters.x_height = (parameters.ascender or 0)/2
+ end
+end
+luaotfload_callbacks [#luaotfload_callbacks + 1] = {
+ "patch_font", set_xheight, "set_xheight",
+}
+-----------------------------------------------------------------------
+--- glyphs and characters
+-----------------------------------------------------------------------
+
+--- int -> int -> bool
+function aux.font_has_glyph(font_id, codepoint)
+ local fontdata = fonts.hashes.identifiers[font_id]
+ if fontdata then
+ if fontdata.characters[codepoint] ~= nil then return true end
+ end
+ return false
+end
+
+--- undocumented
+
+local function raw_slot_of_name(font_id, glyphname)
+ local fontdata = font.fonts[font_id]
+ if fontdata.type == "virtual" then --- get base font for glyph idx
+ local codepoint = encodings.agl.unicodes[glyphname]
+ local glyph = fontdata.characters[codepoint]
+ if fontdata.characters[codepoint] then
+ return codepoint
+ end
+ end
+ return false
+end
+
+--[[doc--
+
+ This one is approximately “name_to_slot” from the microtype package;
+ note that it is all about Adobe Glyph names and glyph slots in the
+ font. The names and values may diverge from actual Unicode.
+
+ http://www.adobe.com/devnet/opentype/archives/glyph.html
+
+ The “unsafe” switch triggers a fallback lookup in the raw fonts
+ table. As some of the information is stored as references, this may
+ have unpredictable side-effects.
+
+--doc]]--
+
+--- int -> string -> bool -> (int | false)
+function aux.slot_of_name(font_id, glyphname, unsafe)
+ if not font_id or type (font_id) ~= "number"
+ or not glyphname or type (glyphname) ~= "string"
+ then
+ logreport ("both", 0, "aux",
+ "invalid parameters to slot_of_name (%s, %s)",
+ tostring (font_id), tostring (glyphname))
+ return false
+ end
+
+ local tfmdata = identifiers [font_id]
+ if not tfmdata then return raw_slot_of_name (font_id, glyphname) end
+ local resources = tfmdata.resources if not resources then return false end
+ local unicodes = resources.unicodes if not unicodes then return false end
+
+ local unicode = unicodes [glyphname]
+ if unicode then
+ if type (unicode) == "number" then
+ return unicode
+ else
+ return unicode [1] --- for multiple components
+ end
+ end
+ return false
+end
+
+--[[doc--
+
+ Inverse of above; not authoritative as to my knowledge the official
+ inverse of the AGL is the AGLFN. Maybe this whole issue should be
+ dealt with in a separate package that loads char-def.lua and thereby
+ solves the problem for the next couple decades.
+
+ http://partners.adobe.com/public/developer/en/opentype/aglfn13.txt
+
+--doc]]--
+
+local indices
+
+--- int -> (string | false)
+function aux.name_of_slot(codepoint)
+ if not codepoint or type (codepoint) ~= "number" then
+ logreport ("both", 0, "aux",
+ "invalid parameters to name_of_slot (%s)",
+ tostring (codepoint))
+ return false
+ end
+
+ if not indices then --- this will load the glyph list
+ local unicodes = encodings.agl.unicodes
+ if not unicodes or not next (unicodes)then
+ logreport ("both", 0, "aux",
+ "name_of_slot: failed to load the AGL.")
+ end
+ indices = table.swapped (unicodes)
+ end
+
+ local glyphname = indices [codepoint]
+ if glyphname then
+ return glyphname
+ end
+ return false
+end
+
+-----------------------------------------------------------------------
+--- features / scripts / languages
+-----------------------------------------------------------------------
+--- lots of arrowcode ahead
+
+local function get_features(tfmdata)
+ local resources = tfmdata.resources if not resources then return false end
+ local features = resources.features if not features then return false end
+ return features
+end
+
+--[[doc--
+This function, modeled after “check_script()” from fontspec, returns
+true if in the given font, the script “asked_script” is accounted for in at
+least one feature.
+--doc]]--
+
+--- int -> string -> bool
+function aux.provides_script(font_id, asked_script)
+ if not font_id or type (font_id) ~= "number"
+ or not asked_script or type (asked_script) ~= "string"
+ then
+ logreport ("both", 0, "aux",
+ "invalid parameters to provides_script(%s, %s)",
+ tostring (font_id), tostring (asked_script))
+ return false
+ end
+ asked_script = stringlower(asked_script)
+ if font_id and font_id > 0 then
+ local tfmdata = identifiers[font_id]
+ if not tfmdata then return false end
+ local features = get_features (tfmdata)
+ if features == false then
+ logreport ("log", 1, "aux", "font no %d lacks a features table", font_id)
+ return false
+ end
+ for method, featuredata in next, features do
+ --- where method: "gpos" | "gsub"
+ for feature, data in next, featuredata do
+ if data[asked_script] then
+ logreport ("log", 1, "aux",
+ "font no %d (%s) defines feature %s for script %s",
+ font_id, fontname, feature, asked_script)
+ return true
+ end
+ end
+ end
+ logreport ("log", 0, "aux",
+ "font no %d (%s) defines no feature for script %s",
+ font_id, fontname, asked_script)
+ end
+ logreport ("log", 0, "aux", "no font with id %d", font_id)
+ return false
+end
+
+--[[doc--
+This function, modeled after “check_language()” from fontspec, returns
+true if in the given font, the language with tage “asked_language” is
+accounted for in the script with tag “asked_script” in at least one
+feature.
+--doc]]--
+
+--- int -> string -> string -> bool
+function aux.provides_language(font_id, asked_script, asked_language)
+ if not font_id or type (font_id) ~= "number"
+ or not asked_script or type (asked_script) ~= "string"
+ or not asked_language or type (asked_language) ~= "string"
+ then
+ logreport ("both", 0, "aux",
+ "invalid parameters to provides_language(%s, %s, %s)",
+ tostring (font_id),
+ tostring (asked_script),
+ tostring (asked_language))
+ return false
+ end
+ asked_script = stringlower(asked_script)
+ asked_language = stringlower(asked_language)
+ if font_id and font_id > 0 then
+ local tfmdata = identifiers[font_id]
+ if not tfmdata then return false end
+ local features = get_features (tfmdata)
+ if features == false then
+ logreport ("log", 1, "aux", "font no %d lacks a features table", font_id)
+ return false
+ end
+ for method, featuredata in next, features do
+ --- where method: "gpos" | "gsub"
+ for feature, data in next, featuredata do
+ local scriptdata = data[asked_script]
+ if scriptdata and scriptdata[asked_language] then
+ logreport ("log", 1, "aux",
+ "font no %d (%s) defines feature %s "
+ .. "for script %s with language %s",
+ font_id, fontname, feature,
+ asked_script, asked_language)
+ return true
+ end
+ end
+ end
+ logreport ("log", 0, "aux",
+ "font no %d (%s) defines no feature "
+ .. "for script %s with language %s",
+ font_id, fontname, asked_script, asked_language)
+ end
+ logreport ("log", 0, "aux", "no font with id %d", font_id)
+ return false
+end
+
+--[[doc--
+We strip the syntax elements from feature definitions (shouldn’t
+actually be there in the first place, but who cares ...)
+--doc]]--
+
+local lpeg = require"lpeg"
+local C, P, S = lpeg.C, lpeg.P, lpeg.S
+local lpegmatch = lpeg.match
+
+local sign = S"+-"
+local rhs = P"=" * P(1)^0 * P(-1)
+local strip_garbage = sign^-1 * C((1 - rhs)^1)
+
+--s = "+foo" --> foo
+--ss = "-bar" --> bar
+--sss = "baz" --> baz
+--t = "foo=bar" --> foo
+--tt = "+bar=baz" --> bar
+--ttt = "-baz=true" --> baz
+--
+--print(lpeg.match(strip_garbage, s))
+--print(lpeg.match(strip_garbage, ss))
+--print(lpeg.match(strip_garbage, sss))
+--print(lpeg.match(strip_garbage, t))
+--print(lpeg.match(strip_garbage, tt))
+--print(lpeg.match(strip_garbage, ttt))
+
+--[[doc--
+This function, modeled after “check_feature()” from fontspec, returns
+true if in the given font, the language with tag “asked_language” is
+accounted for in the script with tag “asked_script” in feature
+“asked_feature”.
+--doc]]--
+
+--- int -> string -> string -> string -> bool
+function aux.provides_feature(font_id, asked_script,
+ asked_language, asked_feature)
+ if not font_id or type (font_id) ~= "number"
+ or not asked_script or type (asked_script) ~= "string"
+ or not asked_language or type (asked_language) ~= "string"
+ or not asked_feature or type (asked_feature) ~= "string"
+ then
+ logreport ("both", 0, "aux",
+ "invalid parameters to provides_feature(%s, %s, %s, %s)",
+ tostring (font_id), tostring (asked_script),
+ tostring (asked_language), tostring (asked_feature))
+ return false
+ end
+ asked_script = stringlower(asked_script)
+ asked_language = stringlower(asked_language)
+ asked_feature = lpegmatch(strip_garbage, asked_feature)
+
+ if font_id > 0 then
+ local tfmdata = identifiers[font_id]
+ if not tfmdata then return false end
+ local features = get_features (tfmdata)
+ if features == false then
+ logreport ("log", 1, "aux", "font no %d lacks a features table", font_id)
+ return false
+ end
+ for method, featuredata in next, features do
+ --- where method: "gpos" | "gsub"
+ local feature = featuredata[asked_feature]
+ if feature then
+ local scriptdata = feature[asked_script]
+ if scriptdata and scriptdata[asked_language] then
+ logreport ("log", 1, "aux",
+ "font no %d (%s) defines feature %s "
+ .. "for script %s with language %s",
+ font_id, fontname, asked_feature,
+ asked_script, asked_language)
+ return true
+ end
+ end
+ end
+ logreport ("log", 0, "aux",
+ "font no %d (%s) does not define feature %s for script %s with language %s",
+ font_id, fontname, asked_feature, asked_script, asked_language)
+ end
+ logreport ("log", 0, "aux", "no font with id %d", font_id)
+ return false
+end
+
+-----------------------------------------------------------------------
+--- font dimensions
+-----------------------------------------------------------------------
+
+--- int -> string -> int
+local function get_math_dimension(font_id, dimenname)
+ if type(font_id) == "string" then
+ font_id = fontid(font_id) --- safeguard
+ end
+ local fontdata = identifiers[font_id]
+ local mathdata = fontdata.mathparameters
+ if mathdata then
+ return mathdata[dimenname] or 0
+ end
+ return 0
+end
+
+aux.get_math_dimension = get_math_dimension
+
+--- int -> string -> unit
+function aux.sprint_math_dimension(font_id, dimenname)
+ if type(font_id) == "string" then
+ font_id = fontid(font_id)
+ end
+ local dim = get_math_dimension(font_id, dimenname)
+ texsprint(luatexbase.catcodetables["latex-package"], dim, "sp")
+end
+
+-----------------------------------------------------------------------
+--- extra database functions
+-----------------------------------------------------------------------
+
+--[====[-- TODO -> port this to new db model
+
+--- local directories -------------------------------------------------
+
+--- migrated from luaotfload-database.lua
+--- https://github.com/lualatex/luaotfload/pull/61#issuecomment-17776975
+
+--- string -> (int * int)
+local scan_external_dir = function (dir)
+ local old_names, new_names = names.data()
+ if not old_names then
+ old_names = load_names()
+ end
+ new_names = tablecopy(old_names)
+ local n_scanned, n_new = scan_dir(dir, old_names, new_names)
+ --- FIXME
+ --- This doesn’t seem right. If a db update is triggered after this
+ --- point, then the added fonts will be saved along with it --
+ --- which is not as “temporarily” as it should be. (This should be
+ --- addressed during a refactoring of names_resolve().)
+ names.data = new_names
+ return n_scanned, n_new
+end
+
+aux.scan_external_dir = scan_external_dir
+
+--]====]--
+
+function aux.scan_external_dir()
+ print "ERROR: scan_external_dir() is not implemented"
+end
+
+--- db queries --------------------------------------------------------
+
+--- https://github.com/lualatex/luaotfload/issues/74
+--- string -> (string * int)
+local function resolve_fontname(name)
+ local foundname, subfont = luaotfload.resolvers.name {
+ name = name,
+ specification = "name:" .. name,
+ }
+ if foundname then
+ return foundname, subfont
+ end
+ return false, false
+end
+
+aux.resolve_fontname = resolve_fontname
+
+--- string list -> (string * int)
+function aux.resolve_fontlist(names)
+ for n = 1, #names do
+ local foundname, subfont = resolve_fontname(this)
+ if foundname then
+ return foundname, subfont
+ end
+ end
+ return false, false
+end
+
+--- index access ------------------------------------------------------
+
+--- Based on a discussion on the Luatex mailing list:
+--- http://tug.org/pipermail/luatex/2014-June/004881.html
+
+--[[doc--
+
+ aux.read_font_index -- Read the names index from the canonical
+ location and return its contents. This does not affect the behavior
+ of Luaotfload: The returned table is independent of what the font
+ resolvers use internally. Access is raw: each call to the function
+ will result in the entire table being re-read from disk.
+
+--doc]]--
+
+local load_names = fontnames.load
+local access_font_index = fontnames.access_font_index
+
+function aux.read_font_index()
+ return load_names (true) or { }
+end
+
+--[[doc--
+
+ aux.font_index -- Access Luaotfload’s internal database. If the
+ database hasn’t been loaded yet this will cause it to be loaded, with
+ all the possible side-effects like for instance creating the index
+ file if it doesn’t exist, reading all font files, &c.
+
+--doc]]--
+
+function aux.font_index() return access_font_index () end
+
+
+--- loaded fonts ------------------------------------------------------
+
+--- just a proof of concept
+
+--- fontobj -> string list -> (string list) list
+local function get_font_data (tfmdata, keys)
+ local acc = {}
+ for n = 1, #keys do
+ acc[n] = tfmdata[keys[n]] or false
+ end
+ return acc
+end
+
+--[[doc--
+
+ The next one operates on the fonts.hashes.identifiers table.
+ It returns a list containing tuples of font ids and the
+ contents of the fields specified in the first argument.
+ Font table entries that were created indirectly -- e.g. by
+ \letterspacefont or during font expansion -- will not be
+ listed.
+
+--doc]]--
+
+local default_keys = { "fullname" }
+
+--- string list -> (int * string list) list
+function aux.get_loaded_fonts (keys)
+ keys = keys or default_keys
+ local acc = {}
+ for id, tfmdata in pairs(identifiers) do
+ local data = get_font_data(tfmdata, keys)
+ acc[#acc+1] = { id, data }
+ end
+ return acc
+end
+
+--- Raw access to the font.* namespace is unsafe so no documentation on
+--- this one.
+function aux.get_raw_fonts ()
+ local res = { }
+ for i, v in font.each() do
+ if v.filename then
+ res[#res+1] = { i, v }
+ end
+ end
+ return res
+end
+
+-----------------------------------------------------------------------
+--- font parameters
+-----------------------------------------------------------------------
+--- analogy of font-hsh
+
+fonthashes.parameters = fonthashes.parameters or { }
+fonthashes.quads = fonthashes.quads or { }
+
+local parameters = fonthashes.parameters or { }
+local quads = fonthashes.quads or { }
+
+setmetatable(parameters, { __index = function (t, font_id)
+ local tfmdata = identifiers[font_id]
+ if not tfmdata then --- unsafe; avoid
+ tfmdata = font.fonts[font_id]
+ end
+ if tfmdata and type(tfmdata) == "table" then
+ local fontparameters = tfmdata.parameters
+ t[font_id] = fontparameters
+ return fontparameters
+ end
+ return nil
+end})
+
+--[[doc--
+
+ Note that the reason as to why we prefer functions over table indices
+ is that functions are much safer against unintended manipulation.
+ This justifies the overhead they cost.
+
+--doc]]--
+
+--- int -> (number | false)
+function aux.get_quad(font_id)
+ local quad = quads[font_id]
+ if quad then
+ return quad
+ end
+ local fontparameters = parameters[font_id]
+ if fontparameters then
+ local quad = fontparameters.quad or 0
+ quads[font_id] = quad
+ return quad
+ end
+ return false
+end
+
+-----------------------------------------------------------------------
+--- initialization
+-----------------------------------------------------------------------
+
+local function inject_callbacks (lst)
+ if not lst and next (lst) then return false end
+
+ local inject = function (def)
+ local cb, fn, id = unpack (def)
+ cb = tostring (cb)
+ id = tostring (id)
+ if not cb or not fn or not id or not type (fn) == "function" then
+ logreport ("both", 0, "aux", "Invalid callback requested (%q, %s, %q).",
+ cb, tostring (fn), id)
+ return false
+ end
+ cb = stringformat ("luaotfload.%s", cb)
+ id = stringformat ("luaotfload.aux.%s", id)
+ logreport ("log", 5, "aux", "Installing callback %q->%q.", cb, id)
+ luatexbase.add_to_callback (cb, fn, id)
+ return true
+ end
+
+ local ret = true
+ for i = 1, #lst do ret = inject (lst [i]) end
+ return ret
+end
+
+return function ()
+ luaotfload.aux = aux
+ return inject_callbacks (luaotfload_callbacks)
+end
+
+-- vim:tw=79:sw=2:ts=8:et
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload-blacklist.cnf b/macros/luatex/generic/luaotfload/luaotfload-blacklist.cnf
new file mode 100644
index 0000000000..e82669b9f8
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-blacklist.cnf
@@ -0,0 +1,4 @@
+spltfgbd.ttf
+spltfgbi.ttf
+spltfgit.ttf
+spltfgrg.ttf
diff --git a/macros/luatex/generic/luaotfload/luaotfload-characters.lua b/macros/luatex/generic/luaotfload/luaotfload-characters.lua
new file mode 100644
index 0000000000..ded3b3eaf0
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-characters.lua
@@ -0,0 +1,203947 @@
+return {
+ [0x0]={
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x0,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x2,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x3,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x4,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x5,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x6,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x7,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8,
+ },
+ {
+ category="cc",
+ direction="s",
+ linebreak="ba",
+ unicodeslot=0x9,
+ },
+ {
+ category="cc",
+ direction="b",
+ linebreak="lf",
+ unicodeslot=0xA,
+ },
+ {
+ category="cc",
+ direction="s",
+ linebreak="bk",
+ unicodeslot=0xB,
+ },
+ {
+ category="cc",
+ direction="ws",
+ linebreak="bk",
+ unicodeslot=0xC,
+ },
+ {
+ category="cc",
+ direction="b",
+ linebreak="cr",
+ unicodeslot=0xD,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xF,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x10,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x11,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x12,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x13,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x14,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x15,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x16,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x17,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x18,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x19,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1A,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1B,
+ },
+ {
+ category="cc",
+ direction="b",
+ linebreak="cm",
+ unicodeslot=0x1C,
+ },
+ {
+ category="cc",
+ direction="b",
+ linebreak="cm",
+ unicodeslot=0x1D,
+ },
+ {
+ category="cc",
+ direction="b",
+ linebreak="cm",
+ unicodeslot=0x1E,
+ },
+ {
+ category="cc",
+ direction="s",
+ linebreak="cm",
+ unicodeslot=0x1F,
+ },
+ {
+ category="zs",
+ direction="ws",
+ linebreak="sp",
+ unicodeslot=0x20,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x21,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x22,
+ },
+ {
+ category="po",
+ direction="et",
+ linebreak="al",
+ unicodeslot=0x23,
+ },
+ {
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x24,
+ },
+ {
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x25,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x27,
+ },
+ {
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x29,
+ textclass="open",
+ unicodeslot=0x28,
+ },
+ {
+ category="pe",
+ direction="on",
+ linebreak="cp",
+ mirror=0x28,
+ textclass="close",
+ unicodeslot=0x29,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A,
+ },
+ {
+ category="sm",
+ direction="es",
+ linebreak="pr",
+ unicodeslot=0x2B,
+ },
+ {
+ category="po",
+ direction="cs",
+ linebreak="is",
+ unicodeslot=0x2C,
+ },
+ {
+ category="pd",
+ direction="es",
+ linebreak="hy",
+ unicodeslot=0x2D,
+ },
+ {
+ category="po",
+ direction="cs",
+ linebreak="is",
+ unicodeslot=0x2E,
+ },
+ {
+ category="po",
+ direction="cs",
+ linebreak="sy",
+ unicodeslot=0x2F,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x30,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x31,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x32,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x33,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x34,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x35,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x36,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x37,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x38,
+ },
+ {
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x39,
+ },
+ {
+ category="po",
+ direction="cs",
+ linebreak="is",
+ unicodeslot=0x3A,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="is",
+ unicodeslot=0x3B,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x3E,
+ textclass="open",
+ unicodeslot=0x3C,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x3D,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x3C,
+ textclass="close",
+ unicodeslot=0x3E,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x3F,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x40,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x45,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4E,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x58,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x59,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x5A,
+ },
+ {
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x5D,
+ textclass="open",
+ unicodeslot=0x5B,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="pr",
+ unicodeslot=0x5C,
+ },
+ {
+ category="pe",
+ direction="on",
+ linebreak="cp",
+ mirror=0x5B,
+ textclass="close",
+ unicodeslot=0x5D,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x5E,
+ },
+ {
+ category="pc",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x5F,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x60,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x61,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x62,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x63,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x64,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x65,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x66,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x67,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x68,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x69,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x6A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x6B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x6C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x6D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x6E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x6F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x70,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x71,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x72,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x73,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x74,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x75,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x76,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x77,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x78,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x79,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x7A,
+ },
+ {
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x7D,
+ textclass="open",
+ unicodeslot=0x7B,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x7C,
+ },
+ {
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x7B,
+ textclass="close",
+ unicodeslot=0x7D,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x7E,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x7F,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x80,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x81,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x82,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x83,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x84,
+ },
+ {
+ category="cc",
+ direction="b",
+ linebreak="nl",
+ unicodeslot=0x85,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x86,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x87,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x88,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x89,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8A,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8B,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8C,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8D,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8E,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x8F,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x90,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x91,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x92,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x93,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x94,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x95,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x96,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x97,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x98,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x99,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x9A,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x9B,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x9C,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x9D,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x9E,
+ },
+ {
+ category="cc",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x9F,
+ },
+ {
+ category="zs",
+ direction="cs",
+ linebreak="gl",
+ specials={ "nobreak", 0x20 },
+ unicodeslot=0xA0,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0xA1,
+ },
+ {
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0xA2,
+ },
+ {
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0xA3,
+ },
+ {
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0xA4,
+ },
+ {
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0xA5,
+ },
+ {
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA6,
+ },
+ {
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0xA7,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x308 },
+ unicodeslot=0xA8,
+ },
+ {
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="ai",
+ specials={ "super", 0x61 },
+ unicodeslot=0xAA,
+ },
+ {
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0xBB,
+ textclass="open",
+ unicodeslot=0xAB,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xAC,
+ },
+ {
+ category="cf",
+ direction="bn",
+ linebreak="ba",
+ unicodeslot=0xAD,
+ },
+ {
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xAE,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x304 },
+ unicodeslot=0xAF,
+ },
+ {
+ category="so",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0xB0,
+ },
+ {
+ category="sm",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0xB1,
+ },
+ {
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "super", 0x32 },
+ unicodeslot=0xB2,
+ },
+ {
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "super", 0x33 },
+ unicodeslot=0xB3,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="bb",
+ specials={ "compat", 0x20, 0x301 },
+ unicodeslot=0xB4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3BC },
+ unicodeslot=0xB5,
+ },
+ {
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0xB6,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0xB7,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x327 },
+ unicodeslot=0xB8,
+ },
+ {
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "super", 0x31 },
+ unicodeslot=0xB9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="ai",
+ specials={ "super", 0x6F },
+ unicodeslot=0xBA,
+ },
+ {
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0xAB,
+ textclass="close",
+ unicodeslot=0xBB,
+ },
+ {
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x31, 0x2044, 0x34 },
+ unicodeslot=0xBC,
+ },
+ {
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x31, 0x2044, 0x32 },
+ unicodeslot=0xBD,
+ },
+ {
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x33, 0x2044, 0x34 },
+ unicodeslot=0xBE,
+ },
+ {
+ category="po",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0xBF,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x300 },
+ unicodeslot=0xC0,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x301 },
+ unicodeslot=0xC1,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x302 },
+ unicodeslot=0xC2,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x303 },
+ unicodeslot=0xC3,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x308 },
+ unicodeslot=0xC4,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x30A },
+ unicodeslot=0xC5,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xC6,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43, 0x327 },
+ unicodeslot=0xC7,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x300 },
+ unicodeslot=0xC8,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x301 },
+ unicodeslot=0xC9,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x302 },
+ unicodeslot=0xCA,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x308 },
+ unicodeslot=0xCB,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x300 },
+ unicodeslot=0xCC,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x301 },
+ unicodeslot=0xCD,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x302 },
+ unicodeslot=0xCE,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x308 },
+ unicodeslot=0xCF,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD0,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x303 },
+ unicodeslot=0xD1,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x300 },
+ unicodeslot=0xD2,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x301 },
+ unicodeslot=0xD3,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x302 },
+ unicodeslot=0xD4,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x303 },
+ unicodeslot=0xD5,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x308 },
+ unicodeslot=0xD6,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0xD7,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x300 },
+ unicodeslot=0xD9,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x301 },
+ unicodeslot=0xDA,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x302 },
+ unicodeslot=0xDB,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x308 },
+ unicodeslot=0xDC,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x301 },
+ unicodeslot=0xDD,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDF,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x300 },
+ unicodeslot=0xE0,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x301 },
+ unicodeslot=0xE1,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x302 },
+ unicodeslot=0xE2,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x303 },
+ unicodeslot=0xE3,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x308 },
+ unicodeslot=0xE4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x30A },
+ unicodeslot=0xE5,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xE6,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x63, 0x327 },
+ unicodeslot=0xE7,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x300 },
+ unicodeslot=0xE8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x301 },
+ unicodeslot=0xE9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x302 },
+ unicodeslot=0xEA,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x308 },
+ unicodeslot=0xEB,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x300 },
+ unicodeslot=0xEC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x301 },
+ unicodeslot=0xED,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x302 },
+ unicodeslot=0xEE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x308 },
+ unicodeslot=0xEF,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF0,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x303 },
+ unicodeslot=0xF1,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x300 },
+ unicodeslot=0xF2,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x301 },
+ unicodeslot=0xF3,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x302 },
+ unicodeslot=0xF4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x303 },
+ unicodeslot=0xF5,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x308 },
+ unicodeslot=0xF6,
+ },
+ {
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0xF7,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x300 },
+ unicodeslot=0xF9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x301 },
+ unicodeslot=0xFA,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x302 },
+ unicodeslot=0xFB,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x308 },
+ unicodeslot=0xFC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x301 },
+ unicodeslot=0xFD,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x308 },
+ unicodeslot=0xFF,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x304 },
+ unicodeslot=0x100,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x304 },
+ unicodeslot=0x101,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x306 },
+ unicodeslot=0x102,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x306 },
+ unicodeslot=0x103,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x328 },
+ unicodeslot=0x104,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x328 },
+ unicodeslot=0x105,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43, 0x301 },
+ unicodeslot=0x106,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x63, 0x301 },
+ unicodeslot=0x107,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43, 0x302 },
+ unicodeslot=0x108,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x63, 0x302 },
+ unicodeslot=0x109,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43, 0x307 },
+ unicodeslot=0x10A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x63, 0x307 },
+ unicodeslot=0x10B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43, 0x30C },
+ unicodeslot=0x10C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x63, 0x30C },
+ unicodeslot=0x10D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44, 0x30C },
+ unicodeslot=0x10E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x64, 0x30C },
+ unicodeslot=0x10F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x304 },
+ unicodeslot=0x112,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x304 },
+ unicodeslot=0x113,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x306 },
+ unicodeslot=0x114,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x306 },
+ unicodeslot=0x115,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x307 },
+ unicodeslot=0x116,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x307 },
+ unicodeslot=0x117,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x328 },
+ unicodeslot=0x118,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x328 },
+ unicodeslot=0x119,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x30C },
+ unicodeslot=0x11A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x30C },
+ unicodeslot=0x11B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x302 },
+ unicodeslot=0x11C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x302 },
+ unicodeslot=0x11D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x306 },
+ unicodeslot=0x11E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x306 },
+ unicodeslot=0x11F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x307 },
+ unicodeslot=0x120,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x307 },
+ unicodeslot=0x121,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x327 },
+ unicodeslot=0x122,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x327 },
+ unicodeslot=0x123,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x302 },
+ unicodeslot=0x124,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x302 },
+ unicodeslot=0x125,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x303 },
+ unicodeslot=0x128,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x303 },
+ unicodeslot=0x129,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x304 },
+ unicodeslot=0x12A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x304 },
+ unicodeslot=0x12B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x306 },
+ unicodeslot=0x12C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x306 },
+ unicodeslot=0x12D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x328 },
+ unicodeslot=0x12E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x328 },
+ unicodeslot=0x12F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x307 },
+ unicodeslot=0x130,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x49, 0x4A },
+ unicodeslot=0x132,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x69, 0x6A },
+ unicodeslot=0x133,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4A, 0x302 },
+ unicodeslot=0x134,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6A, 0x302 },
+ unicodeslot=0x135,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4B, 0x327 },
+ unicodeslot=0x136,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6B, 0x327 },
+ unicodeslot=0x137,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4C, 0x301 },
+ unicodeslot=0x139,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6C, 0x301 },
+ unicodeslot=0x13A,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4C, 0x327 },
+ unicodeslot=0x13B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6C, 0x327 },
+ unicodeslot=0x13C,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4C, 0x30C },
+ unicodeslot=0x13D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6C, 0x30C },
+ unicodeslot=0x13E,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4C, 0xB7 },
+ unicodeslot=0x13F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x6C, 0xB7 },
+ unicodeslot=0x140,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x301 },
+ unicodeslot=0x143,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x301 },
+ unicodeslot=0x144,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x327 },
+ unicodeslot=0x145,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x327 },
+ unicodeslot=0x146,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x30C },
+ unicodeslot=0x147,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x30C },
+ unicodeslot=0x148,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x2BC, 0x6E },
+ unicodeslot=0x149,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x304 },
+ unicodeslot=0x14C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x304 },
+ unicodeslot=0x14D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x306 },
+ unicodeslot=0x14E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x306 },
+ unicodeslot=0x14F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x30B },
+ unicodeslot=0x150,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x30B },
+ unicodeslot=0x151,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x301 },
+ unicodeslot=0x154,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x301 },
+ unicodeslot=0x155,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x327 },
+ unicodeslot=0x156,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x327 },
+ unicodeslot=0x157,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x30C },
+ unicodeslot=0x158,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x30C },
+ unicodeslot=0x159,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x301 },
+ unicodeslot=0x15A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x301 },
+ unicodeslot=0x15B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x302 },
+ unicodeslot=0x15C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x302 },
+ unicodeslot=0x15D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x327 },
+ unicodeslot=0x15E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x327 },
+ unicodeslot=0x15F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x30C },
+ unicodeslot=0x160,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x30C },
+ unicodeslot=0x161,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x327 },
+ unicodeslot=0x162,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x327 },
+ unicodeslot=0x163,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x30C },
+ unicodeslot=0x164,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x30C },
+ unicodeslot=0x165,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x303 },
+ unicodeslot=0x168,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x303 },
+ unicodeslot=0x169,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x304 },
+ unicodeslot=0x16A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x304 },
+ unicodeslot=0x16B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x306 },
+ unicodeslot=0x16C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x306 },
+ unicodeslot=0x16D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x30A },
+ unicodeslot=0x16E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x30A },
+ unicodeslot=0x16F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x30B },
+ unicodeslot=0x170,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x30B },
+ unicodeslot=0x171,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x328 },
+ unicodeslot=0x172,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x328 },
+ unicodeslot=0x173,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x57, 0x302 },
+ unicodeslot=0x174,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x302 },
+ unicodeslot=0x175,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x302 },
+ unicodeslot=0x176,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x302 },
+ unicodeslot=0x177,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x308 },
+ unicodeslot=0x178,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x5A, 0x301 },
+ unicodeslot=0x179,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x7A, 0x301 },
+ unicodeslot=0x17A,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x5A, 0x307 },
+ unicodeslot=0x17B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x7A, 0x307 },
+ unicodeslot=0x17C,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x5A, 0x30C },
+ unicodeslot=0x17D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x7A, 0x30C },
+ unicodeslot=0x17E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x73 },
+ unicodeslot=0x17F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x180,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x181,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x187,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x191,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x192,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x193,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x194,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x195,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x196,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x197,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x198,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x199,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x19A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x19B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x19C,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x19D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x19E,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x19F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x31B },
+ unicodeslot=0x1A0,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x31B },
+ unicodeslot=0x1A1,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A2,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A3,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A5,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A6,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A7,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A8,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1AA,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1AB,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1AC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1AD,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1AE,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x31B },
+ unicodeslot=0x1AF,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x31B },
+ unicodeslot=0x1B0,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B3,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B4,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B5,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B6,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B7,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BA,
+ },
+ {
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BB,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BF,
+ },
+ {
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0,
+ },
+ {
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1,
+ },
+ {
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C2,
+ },
+ {
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C3,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x44, 0x17D },
+ unicodeslot=0x1C4,
+ },
+ {
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x44, 0x17E },
+ unicodeslot=0x1C5,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x64, 0x17E },
+ unicodeslot=0x1C6,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4C, 0x4A },
+ unicodeslot=0x1C7,
+ },
+ {
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4C, 0x6A },
+ unicodeslot=0x1C8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x6C, 0x6A },
+ unicodeslot=0x1C9,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4E, 0x4A },
+ unicodeslot=0x1CA,
+ },
+ {
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4E, 0x6A },
+ unicodeslot=0x1CB,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x6E, 0x6A },
+ unicodeslot=0x1CC,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x30C },
+ unicodeslot=0x1CD,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x30C },
+ unicodeslot=0x1CE,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x30C },
+ unicodeslot=0x1CF,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x30C },
+ unicodeslot=0x1D0,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x30C },
+ unicodeslot=0x1D1,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x30C },
+ unicodeslot=0x1D2,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x30C },
+ unicodeslot=0x1D3,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x30C },
+ unicodeslot=0x1D4,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xDC, 0x304 },
+ unicodeslot=0x1D5,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xFC, 0x304 },
+ unicodeslot=0x1D6,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xDC, 0x301 },
+ unicodeslot=0x1D7,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xFC, 0x301 },
+ unicodeslot=0x1D8,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xDC, 0x30C },
+ unicodeslot=0x1D9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xFC, 0x30C },
+ unicodeslot=0x1DA,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xDC, 0x300 },
+ unicodeslot=0x1DB,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xFC, 0x300 },
+ unicodeslot=0x1DC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DD,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC4, 0x304 },
+ unicodeslot=0x1DE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE4, 0x304 },
+ unicodeslot=0x1DF,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x226, 0x304 },
+ unicodeslot=0x1E0,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x227, 0x304 },
+ unicodeslot=0x1E1,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC6, 0x304 },
+ unicodeslot=0x1E2,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE6, 0x304 },
+ unicodeslot=0x1E3,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E5,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x30C },
+ unicodeslot=0x1E6,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x30C },
+ unicodeslot=0x1E7,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4B, 0x30C },
+ unicodeslot=0x1E8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6B, 0x30C },
+ unicodeslot=0x1E9,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x328 },
+ unicodeslot=0x1EA,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x328 },
+ unicodeslot=0x1EB,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EA, 0x304 },
+ unicodeslot=0x1EC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EB, 0x304 },
+ unicodeslot=0x1ED,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B7, 0x30C },
+ unicodeslot=0x1EE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x292, 0x30C },
+ unicodeslot=0x1EF,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6A, 0x30C },
+ unicodeslot=0x1F0,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x44, 0x5A },
+ unicodeslot=0x1F1,
+ },
+ {
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x44, 0x7A },
+ unicodeslot=0x1F2,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x64, 0x7A },
+ unicodeslot=0x1F3,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x301 },
+ unicodeslot=0x1F4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x301 },
+ unicodeslot=0x1F5,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1F6,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1F7,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x300 },
+ unicodeslot=0x1F8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x300 },
+ unicodeslot=0x1F9,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC5, 0x301 },
+ unicodeslot=0x1FA,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE5, 0x301 },
+ unicodeslot=0x1FB,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC6, 0x301 },
+ unicodeslot=0x1FC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE6, 0x301 },
+ unicodeslot=0x1FD,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD8, 0x301 },
+ unicodeslot=0x1FE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF8, 0x301 },
+ unicodeslot=0x1FF,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x30F },
+ unicodeslot=0x200,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x30F },
+ unicodeslot=0x201,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x311 },
+ unicodeslot=0x202,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x311 },
+ unicodeslot=0x203,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x30F },
+ unicodeslot=0x204,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x30F },
+ unicodeslot=0x205,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x311 },
+ unicodeslot=0x206,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x311 },
+ unicodeslot=0x207,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x30F },
+ unicodeslot=0x208,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x30F },
+ unicodeslot=0x209,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x311 },
+ unicodeslot=0x20A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x311 },
+ unicodeslot=0x20B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x30F },
+ unicodeslot=0x20C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x30F },
+ unicodeslot=0x20D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x311 },
+ unicodeslot=0x20E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x311 },
+ unicodeslot=0x20F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x30F },
+ unicodeslot=0x210,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x30F },
+ unicodeslot=0x211,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x311 },
+ unicodeslot=0x212,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x311 },
+ unicodeslot=0x213,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x30F },
+ unicodeslot=0x214,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x30F },
+ unicodeslot=0x215,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x311 },
+ unicodeslot=0x216,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x311 },
+ unicodeslot=0x217,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x326 },
+ unicodeslot=0x218,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x326 },
+ unicodeslot=0x219,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x326 },
+ unicodeslot=0x21A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x326 },
+ unicodeslot=0x21B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x21C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x21D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x30C },
+ unicodeslot=0x21E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x30C },
+ unicodeslot=0x21F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x220,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x221,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x222,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x223,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x224,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x225,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x307 },
+ unicodeslot=0x226,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x307 },
+ unicodeslot=0x227,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x327 },
+ unicodeslot=0x228,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x327 },
+ unicodeslot=0x229,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD6, 0x304 },
+ unicodeslot=0x22A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF6, 0x304 },
+ unicodeslot=0x22B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD5, 0x304 },
+ unicodeslot=0x22C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF5, 0x304 },
+ unicodeslot=0x22D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x307 },
+ unicodeslot=0x22E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x307 },
+ unicodeslot=0x22F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x22E, 0x304 },
+ unicodeslot=0x230,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x22F, 0x304 },
+ unicodeslot=0x231,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x304 },
+ unicodeslot=0x232,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x304 },
+ unicodeslot=0x233,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x237,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x238,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x239,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x23A,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x23B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x23C,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x23D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x23E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x23F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x240,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x241,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x242,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x243,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x244,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x245,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x246,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x247,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x248,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x249,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x24A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x24B,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x24C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x24D,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x24E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x24F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x250,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x251,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x252,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x253,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x254,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x255,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x256,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x257,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x258,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x259,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x25A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x25B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x25C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x25D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x25E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x25F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x260,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x261,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x262,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x263,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x264,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x265,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x266,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x267,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x268,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x269,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x270,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x271,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x272,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x273,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x274,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x275,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x276,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x277,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x278,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x279,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x27A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x27B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x27C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x27D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x27E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x27F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x290,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x291,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x292,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x293,
+ },
+ {
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x294,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x295,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x296,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x297,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x298,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x299,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x29A,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x29B,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x29C,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x29D,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x29E,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x29F,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A0,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A1,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A2,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A3,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A4,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A5,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A6,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A7,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A8,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2A9,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2AA,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2AB,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2AC,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2AD,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2AE,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2AF,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x68 },
+ unicodeslot=0x2B0,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x266 },
+ unicodeslot=0x2B1,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x6A },
+ unicodeslot=0x2B2,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x72 },
+ unicodeslot=0x2B3,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x279 },
+ unicodeslot=0x2B4,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x27B },
+ unicodeslot=0x2B5,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x281 },
+ unicodeslot=0x2B6,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x77 },
+ unicodeslot=0x2B7,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x79 },
+ unicodeslot=0x2B8,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2BB,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2BC,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2BD,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2BE,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2BF,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2C2,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2C3,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2C4,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2C5,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x302 },
+ unicodeslot=0x2C6,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x30C },
+ unicodeslot=0x2C7,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x2C8,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2C9,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2CA,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2CB,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x2CC,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2CD,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CE,
+ },
+ {
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CF,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x2D0,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2D2,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2D3,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2D4,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2D5,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2D6,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2D7,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x306 },
+ unicodeslot=0x2D8,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x307 },
+ unicodeslot=0x2D9,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x30A },
+ unicodeslot=0x2DA,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x328 },
+ unicodeslot=0x2DB,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x303 },
+ unicodeslot=0x2DC,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x20, 0x30B },
+ unicodeslot=0x2DD,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2DE,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x2DF,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x263 },
+ unicodeslot=0x2E0,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x6C },
+ unicodeslot=0x2E1,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x73 },
+ unicodeslot=0x2E2,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x78 },
+ unicodeslot=0x2E3,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x295 },
+ unicodeslot=0x2E4,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E5,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E6,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E7,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E8,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E9,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2EA,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2EB,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2EC,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2ED,
+ },
+ {
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2EE,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2EF,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F0,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F1,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F2,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F3,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F4,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F5,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F6,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F7,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F8,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2F9,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2FA,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2FB,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2FC,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2FD,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2FE,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2FF,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x300,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x301,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x302,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x303,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x304,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x305,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x306,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x307,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x308,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x309,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x30A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x30B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x30C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x30D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x30E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x30F,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x310,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x311,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x312,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x313,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x314,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x315,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x316,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x317,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x318,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x319,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x31A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x31B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x31C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x31D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x31E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x31F,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x320,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x321,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x322,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x323,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x324,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x325,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x326,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x327,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x328,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x329,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x32A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x32B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x32C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x32D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x32E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x32F,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x330,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x331,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x332,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x333,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x334,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x335,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x336,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x337,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x338,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x339,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x33A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x33B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x33C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x33D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x33E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x33F,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0x300 },
+ unicodeslot=0x340,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0x301 },
+ unicodeslot=0x341,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x342,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0x313 },
+ unicodeslot=0x343,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0x308, 0x301 },
+ unicodeslot=0x344,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x345,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x346,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x347,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x348,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x349,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x34A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x34B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x34C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x34D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x34E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x34F,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x350,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x351,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x352,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x353,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x354,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x355,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x356,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x357,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x358,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x359,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x35A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x35B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x35C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x35D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x35E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x35F,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x360,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x361,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="gl",
+ unicodeslot=0x362,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x363,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x364,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x365,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x366,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x367,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x368,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x369,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x36A,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x36B,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x36C,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x36D,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x36E,
+ },
+ {
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x36F,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x370,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x371,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x372,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x373,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2B9 },
+ unicodeslot=0x374,
+ },
+ {
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x375,
+ },
+ {
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x376,
+ },
+ {
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x377,
+ },
+ [0x37A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x345 },
+ unicodeslot=0x37A,
+ },
+ [0x37B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x37B,
+ },
+ [0x37C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x37C,
+ },
+ [0x37D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x37D,
+ },
+ [0x37E]={
+ category="po",
+ direction="on",
+ linebreak="is",
+ specials={ "char", 0x3B },
+ unicodeslot=0x37E,
+ },
+ [0x37F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x37F,
+ },
+ [0x384]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x301 },
+ unicodeslot=0x384,
+ },
+ [0x385]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0xA8, 0x301 },
+ unicodeslot=0x385,
+ },
+ [0x386]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x301 },
+ unicodeslot=0x386,
+ },
+ [0x387]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0xB7 },
+ unicodeslot=0x387,
+ },
+ [0x388]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x395, 0x301 },
+ unicodeslot=0x388,
+ },
+ [0x389]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x397, 0x301 },
+ unicodeslot=0x389,
+ },
+ [0x38A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x301 },
+ unicodeslot=0x38A,
+ },
+ [0x38C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x39F, 0x301 },
+ unicodeslot=0x38C,
+ },
+ [0x38E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A5, 0x301 },
+ unicodeslot=0x38E,
+ },
+ [0x38F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A9, 0x301 },
+ unicodeslot=0x38F,
+ },
+ [0x390]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CA, 0x301 },
+ unicodeslot=0x390,
+ },
+ [0x391]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x391,
+ },
+ [0x392]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x392,
+ },
+ [0x393]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x393,
+ },
+ [0x394]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x394,
+ },
+ [0x395]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x395,
+ },
+ [0x396]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x396,
+ },
+ [0x397]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x397,
+ },
+ [0x398]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x398,
+ },
+ [0x399]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x399,
+ },
+ [0x39A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x39A,
+ },
+ [0x39B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x39B,
+ },
+ [0x39C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x39C,
+ },
+ [0x39D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x39D,
+ },
+ [0x39E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x39E,
+ },
+ [0x39F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x39F,
+ },
+ [0x3A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A0,
+ },
+ [0x3A1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A1,
+ },
+ [0x3A3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A3,
+ },
+ [0x3A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A4,
+ },
+ [0x3A5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A5,
+ },
+ [0x3A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A6,
+ },
+ [0x3A7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A7,
+ },
+ [0x3A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A8,
+ },
+ [0x3A9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3A9,
+ },
+ [0x3AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x308 },
+ unicodeslot=0x3AA,
+ },
+ [0x3AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A5, 0x308 },
+ unicodeslot=0x3AB,
+ },
+ [0x3AC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x301 },
+ unicodeslot=0x3AC,
+ },
+ [0x3AD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B5, 0x301 },
+ unicodeslot=0x3AD,
+ },
+ [0x3AE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B7, 0x301 },
+ unicodeslot=0x3AE,
+ },
+ [0x3AF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x301 },
+ unicodeslot=0x3AF,
+ },
+ [0x3B0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CB, 0x301 },
+ unicodeslot=0x3B0,
+ },
+ [0x3B1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B1,
+ },
+ [0x3B2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B2,
+ },
+ [0x3B3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B3,
+ },
+ [0x3B4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B4,
+ },
+ [0x3B5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B5,
+ },
+ [0x3B6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B6,
+ },
+ [0x3B7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B7,
+ },
+ [0x3B8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B8,
+ },
+ [0x3B9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3B9,
+ },
+ [0x3BA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3BA,
+ },
+ [0x3BB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3BB,
+ },
+ [0x3BC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3BC,
+ },
+ [0x3BD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3BD,
+ },
+ [0x3BE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3BE,
+ },
+ [0x3BF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3BF,
+ },
+ [0x3C0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C0,
+ },
+ [0x3C1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C1,
+ },
+ [0x3C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C2,
+ },
+ [0x3C3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C3,
+ },
+ [0x3C4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C4,
+ },
+ [0x3C5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C5,
+ },
+ [0x3C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C6,
+ },
+ [0x3C7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C7,
+ },
+ [0x3C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C8,
+ },
+ [0x3C9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3C9,
+ },
+ [0x3CA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x308 },
+ unicodeslot=0x3CA,
+ },
+ [0x3CB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x308 },
+ unicodeslot=0x3CB,
+ },
+ [0x3CC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3BF, 0x301 },
+ unicodeslot=0x3CC,
+ },
+ [0x3CD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x301 },
+ unicodeslot=0x3CD,
+ },
+ [0x3CE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C9, 0x301 },
+ unicodeslot=0x3CE,
+ },
+ [0x3CF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3CF,
+ },
+ [0x3D0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3B2 },
+ unicodeslot=0x3D0,
+ },
+ [0x3D1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3B8 },
+ unicodeslot=0x3D1,
+ },
+ [0x3D2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3A5 },
+ unicodeslot=0x3D2,
+ },
+ [0x3D3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3D2, 0x301 },
+ unicodeslot=0x3D3,
+ },
+ [0x3D4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3D2, 0x308 },
+ unicodeslot=0x3D4,
+ },
+ [0x3D5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3C6 },
+ unicodeslot=0x3D5,
+ },
+ [0x3D6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3C0 },
+ unicodeslot=0x3D6,
+ },
+ [0x3D7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3D7,
+ },
+ [0x3D8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3D8,
+ },
+ [0x3D9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3D9,
+ },
+ [0x3DA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3DA,
+ },
+ [0x3DB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3DB,
+ },
+ [0x3DC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3DC,
+ },
+ [0x3DD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3DD,
+ },
+ [0x3DE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3DE,
+ },
+ [0x3DF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3DF,
+ },
+ [0x3E0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E0,
+ },
+ [0x3E1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E1,
+ },
+ [0x3E2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E2,
+ },
+ [0x3E3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E3,
+ },
+ [0x3E4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E4,
+ },
+ [0x3E5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E5,
+ },
+ [0x3E6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E6,
+ },
+ [0x3E7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E7,
+ },
+ [0x3E8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E8,
+ },
+ [0x3E9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3E9,
+ },
+ [0x3EA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3EA,
+ },
+ [0x3EB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3EB,
+ },
+ [0x3EC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3EC,
+ },
+ [0x3ED]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3ED,
+ },
+ [0x3EE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3EE,
+ },
+ [0x3EF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3EF,
+ },
+ [0x3F0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3BA },
+ unicodeslot=0x3F0,
+ },
+ [0x3F1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3C1 },
+ unicodeslot=0x3F1,
+ },
+ [0x3F2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3C2 },
+ unicodeslot=0x3F2,
+ },
+ [0x3F3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3F3,
+ },
+ [0x3F4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x398 },
+ unicodeslot=0x3F4,
+ },
+ [0x3F5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3B5 },
+ unicodeslot=0x3F5,
+ },
+ [0x3F6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x3F6,
+ },
+ [0x3F7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3F7,
+ },
+ [0x3F8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3F8,
+ },
+ [0x3F9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x3A3 },
+ unicodeslot=0x3F9,
+ },
+ [0x3FA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3FA,
+ },
+ [0x3FB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3FB,
+ },
+ [0x3FC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3FC,
+ },
+ [0x3FD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3FD,
+ },
+ [0x3FE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3FE,
+ },
+ [0x3FF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x3FF,
+ },
+ [0x400]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x415, 0x300 },
+ unicodeslot=0x400,
+ },
+ [0x401]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x415, 0x308 },
+ unicodeslot=0x401,
+ },
+ [0x402]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x402,
+ },
+ [0x403]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x413, 0x301 },
+ unicodeslot=0x403,
+ },
+ [0x404]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x404,
+ },
+ [0x405]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x405,
+ },
+ [0x406]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x406,
+ },
+ [0x407]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x406, 0x308 },
+ unicodeslot=0x407,
+ },
+ [0x408]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x408,
+ },
+ [0x409]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x409,
+ },
+ [0x40A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x40A,
+ },
+ [0x40B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x40B,
+ },
+ [0x40C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41A, 0x301 },
+ unicodeslot=0x40C,
+ },
+ [0x40D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x418, 0x300 },
+ unicodeslot=0x40D,
+ },
+ [0x40E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x423, 0x306 },
+ unicodeslot=0x40E,
+ },
+ [0x40F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x40F,
+ },
+ [0x410]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x410,
+ },
+ [0x411]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x411,
+ },
+ [0x412]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x412,
+ },
+ [0x413]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x413,
+ },
+ [0x414]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x414,
+ },
+ [0x415]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x415,
+ },
+ [0x416]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x416,
+ },
+ [0x417]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x417,
+ },
+ [0x418]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x418,
+ },
+ [0x419]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x418, 0x306 },
+ unicodeslot=0x419,
+ },
+ [0x41A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41A,
+ },
+ [0x41B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41B,
+ },
+ [0x41C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41C,
+ },
+ [0x41D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41D,
+ },
+ [0x41E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41E,
+ },
+ [0x41F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x41F,
+ },
+ [0x420]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x420,
+ },
+ [0x421]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x421,
+ },
+ [0x422]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x422,
+ },
+ [0x423]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x423,
+ },
+ [0x424]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x424,
+ },
+ [0x425]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x425,
+ },
+ [0x426]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x426,
+ },
+ [0x427]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x427,
+ },
+ [0x428]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x428,
+ },
+ [0x429]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x429,
+ },
+ [0x42A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42A,
+ },
+ [0x42B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42B,
+ },
+ [0x42C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42C,
+ },
+ [0x42D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42D,
+ },
+ [0x42E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42E,
+ },
+ [0x42F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x42F,
+ },
+ [0x430]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x430,
+ },
+ [0x431]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x431,
+ },
+ [0x432]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x432,
+ },
+ [0x433]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x433,
+ },
+ [0x434]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x434,
+ },
+ [0x435]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x435,
+ },
+ [0x436]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x436,
+ },
+ [0x437]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x437,
+ },
+ [0x438]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x438,
+ },
+ [0x439]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x438, 0x306 },
+ unicodeslot=0x439,
+ },
+ [0x43A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43A,
+ },
+ [0x43B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43B,
+ },
+ [0x43C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43C,
+ },
+ [0x43D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43D,
+ },
+ [0x43E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43E,
+ },
+ [0x43F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x43F,
+ },
+ [0x440]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x440,
+ },
+ [0x441]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x441,
+ },
+ [0x442]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x442,
+ },
+ [0x443]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x443,
+ },
+ [0x444]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x444,
+ },
+ [0x445]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x445,
+ },
+ [0x446]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x446,
+ },
+ [0x447]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x447,
+ },
+ [0x448]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x448,
+ },
+ [0x449]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x449,
+ },
+ [0x44A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44A,
+ },
+ [0x44B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44B,
+ },
+ [0x44C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44C,
+ },
+ [0x44D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44D,
+ },
+ [0x44E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44E,
+ },
+ [0x44F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x44F,
+ },
+ [0x450]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x435, 0x300 },
+ unicodeslot=0x450,
+ },
+ [0x451]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x435, 0x308 },
+ unicodeslot=0x451,
+ },
+ [0x452]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x452,
+ },
+ [0x453]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x433, 0x301 },
+ unicodeslot=0x453,
+ },
+ [0x454]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x454,
+ },
+ [0x455]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x455,
+ },
+ [0x456]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x456,
+ },
+ [0x457]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x456, 0x308 },
+ unicodeslot=0x457,
+ },
+ [0x458]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x458,
+ },
+ [0x459]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x459,
+ },
+ [0x45A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x45A,
+ },
+ [0x45B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x45B,
+ },
+ [0x45C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43A, 0x301 },
+ unicodeslot=0x45C,
+ },
+ [0x45D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x438, 0x300 },
+ unicodeslot=0x45D,
+ },
+ [0x45E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x443, 0x306 },
+ unicodeslot=0x45E,
+ },
+ [0x45F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x45F,
+ },
+ [0x460]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x460,
+ },
+ [0x461]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x461,
+ },
+ [0x462]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x462,
+ },
+ [0x463]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x463,
+ },
+ [0x464]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x464,
+ },
+ [0x465]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x465,
+ },
+ [0x466]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x466,
+ },
+ [0x467]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x467,
+ },
+ [0x468]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x468,
+ },
+ [0x469]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x469,
+ },
+ [0x46A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46A,
+ },
+ [0x46B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46B,
+ },
+ [0x46C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46C,
+ },
+ [0x46D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46D,
+ },
+ [0x46E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46E,
+ },
+ [0x46F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x46F,
+ },
+ [0x470]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x470,
+ },
+ [0x471]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x471,
+ },
+ [0x472]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x472,
+ },
+ [0x473]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x473,
+ },
+ [0x474]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x474,
+ },
+ [0x475]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x475,
+ },
+ [0x476]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x474, 0x30F },
+ unicodeslot=0x476,
+ },
+ [0x477]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x475, 0x30F },
+ unicodeslot=0x477,
+ },
+ [0x478]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x478,
+ },
+ [0x479]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x479,
+ },
+ [0x47A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47A,
+ },
+ [0x47B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47B,
+ },
+ [0x47C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47C,
+ },
+ [0x47D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47D,
+ },
+ [0x47E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47E,
+ },
+ [0x47F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x47F,
+ },
+ [0x480]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x480,
+ },
+ [0x481]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x481,
+ },
+ [0x482]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x482,
+ },
+ [0x483]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x483,
+ },
+ [0x484]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x484,
+ },
+ [0x485]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x485,
+ },
+ [0x486]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x486,
+ },
+ [0x487]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x487,
+ },
+ [0x488]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x488,
+ },
+ [0x489]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x489,
+ },
+ [0x48A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48A,
+ },
+ [0x48B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48B,
+ },
+ [0x48C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48C,
+ },
+ [0x48D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48D,
+ },
+ [0x48E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48E,
+ },
+ [0x48F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x48F,
+ },
+ [0x490]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x490,
+ },
+ [0x491]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x491,
+ },
+ [0x492]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x492,
+ },
+ [0x493]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x493,
+ },
+ [0x494]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x494,
+ },
+ [0x495]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x495,
+ },
+ [0x496]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x496,
+ },
+ [0x497]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x497,
+ },
+ [0x498]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x498,
+ },
+ [0x499]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x499,
+ },
+ [0x49A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49A,
+ },
+ [0x49B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49B,
+ },
+ [0x49C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49C,
+ },
+ [0x49D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49D,
+ },
+ [0x49E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49E,
+ },
+ [0x49F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x49F,
+ },
+ [0x4A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A0,
+ },
+ [0x4A1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A1,
+ },
+ [0x4A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A2,
+ },
+ [0x4A3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A3,
+ },
+ [0x4A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A4,
+ },
+ [0x4A5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A5,
+ },
+ [0x4A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A6,
+ },
+ [0x4A7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A7,
+ },
+ [0x4A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A8,
+ },
+ [0x4A9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4A9,
+ },
+ [0x4AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4AA,
+ },
+ [0x4AB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4AB,
+ },
+ [0x4AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4AC,
+ },
+ [0x4AD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4AD,
+ },
+ [0x4AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4AE,
+ },
+ [0x4AF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4AF,
+ },
+ [0x4B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B0,
+ },
+ [0x4B1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B1,
+ },
+ [0x4B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B2,
+ },
+ [0x4B3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B3,
+ },
+ [0x4B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B4,
+ },
+ [0x4B5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B5,
+ },
+ [0x4B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B6,
+ },
+ [0x4B7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B7,
+ },
+ [0x4B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B8,
+ },
+ [0x4B9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4B9,
+ },
+ [0x4BA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4BA,
+ },
+ [0x4BB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4BB,
+ },
+ [0x4BC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4BC,
+ },
+ [0x4BD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4BD,
+ },
+ [0x4BE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4BE,
+ },
+ [0x4BF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4BF,
+ },
+ [0x4C0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C0,
+ },
+ [0x4C1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x416, 0x306 },
+ unicodeslot=0x4C1,
+ },
+ [0x4C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x436, 0x306 },
+ unicodeslot=0x4C2,
+ },
+ [0x4C3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C3,
+ },
+ [0x4C4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C4,
+ },
+ [0x4C5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C5,
+ },
+ [0x4C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C6,
+ },
+ [0x4C7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C7,
+ },
+ [0x4C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C8,
+ },
+ [0x4C9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4C9,
+ },
+ [0x4CA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4CA,
+ },
+ [0x4CB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4CB,
+ },
+ [0x4CC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4CC,
+ },
+ [0x4CD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4CD,
+ },
+ [0x4CE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4CE,
+ },
+ [0x4CF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4CF,
+ },
+ [0x4D0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x410, 0x306 },
+ unicodeslot=0x4D0,
+ },
+ [0x4D1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x430, 0x306 },
+ unicodeslot=0x4D1,
+ },
+ [0x4D2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x410, 0x308 },
+ unicodeslot=0x4D2,
+ },
+ [0x4D3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x430, 0x308 },
+ unicodeslot=0x4D3,
+ },
+ [0x4D4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4D4,
+ },
+ [0x4D5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4D5,
+ },
+ [0x4D6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x415, 0x306 },
+ unicodeslot=0x4D6,
+ },
+ [0x4D7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x435, 0x306 },
+ unicodeslot=0x4D7,
+ },
+ [0x4D8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4D8,
+ },
+ [0x4D9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4D9,
+ },
+ [0x4DA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4D8, 0x308 },
+ unicodeslot=0x4DA,
+ },
+ [0x4DB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4D9, 0x308 },
+ unicodeslot=0x4DB,
+ },
+ [0x4DC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x416, 0x308 },
+ unicodeslot=0x4DC,
+ },
+ [0x4DD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x436, 0x308 },
+ unicodeslot=0x4DD,
+ },
+ [0x4DE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x417, 0x308 },
+ unicodeslot=0x4DE,
+ },
+ [0x4DF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x437, 0x308 },
+ unicodeslot=0x4DF,
+ },
+ [0x4E0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4E0,
+ },
+ [0x4E1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4E1,
+ },
+ [0x4E2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x418, 0x304 },
+ unicodeslot=0x4E2,
+ },
+ [0x4E3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x438, 0x304 },
+ unicodeslot=0x4E3,
+ },
+ [0x4E4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x418, 0x308 },
+ unicodeslot=0x4E4,
+ },
+ [0x4E5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x438, 0x308 },
+ unicodeslot=0x4E5,
+ },
+ [0x4E6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41E, 0x308 },
+ unicodeslot=0x4E6,
+ },
+ [0x4E7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x43E, 0x308 },
+ unicodeslot=0x4E7,
+ },
+ [0x4E8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4E8,
+ },
+ [0x4E9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4E9,
+ },
+ [0x4EA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E8, 0x308 },
+ unicodeslot=0x4EA,
+ },
+ [0x4EB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E9, 0x308 },
+ unicodeslot=0x4EB,
+ },
+ [0x4EC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x42D, 0x308 },
+ unicodeslot=0x4EC,
+ },
+ [0x4ED]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44D, 0x308 },
+ unicodeslot=0x4ED,
+ },
+ [0x4EE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x423, 0x304 },
+ unicodeslot=0x4EE,
+ },
+ [0x4EF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x443, 0x304 },
+ unicodeslot=0x4EF,
+ },
+ [0x4F0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x423, 0x308 },
+ unicodeslot=0x4F0,
+ },
+ [0x4F1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x443, 0x308 },
+ unicodeslot=0x4F1,
+ },
+ [0x4F2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x423, 0x30B },
+ unicodeslot=0x4F2,
+ },
+ [0x4F3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x443, 0x30B },
+ unicodeslot=0x4F3,
+ },
+ [0x4F4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x427, 0x308 },
+ unicodeslot=0x4F4,
+ },
+ [0x4F5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x447, 0x308 },
+ unicodeslot=0x4F5,
+ },
+ [0x4F6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4F6,
+ },
+ [0x4F7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4F7,
+ },
+ [0x4F8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x42B, 0x308 },
+ unicodeslot=0x4F8,
+ },
+ [0x4F9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44B, 0x308 },
+ unicodeslot=0x4F9,
+ },
+ [0x4FA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4FA,
+ },
+ [0x4FB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4FB,
+ },
+ [0x4FC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4FC,
+ },
+ [0x4FD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4FD,
+ },
+ [0x4FE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4FE,
+ },
+ [0x4FF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x4FF,
+ },
+ [0x500]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x500,
+ },
+ [0x501]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x501,
+ },
+ [0x502]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x502,
+ },
+ [0x503]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x503,
+ },
+ [0x504]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x504,
+ },
+ [0x505]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x505,
+ },
+ [0x506]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x506,
+ },
+ [0x507]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x507,
+ },
+ [0x508]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x508,
+ },
+ [0x509]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x509,
+ },
+ [0x50A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50A,
+ },
+ [0x50B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50B,
+ },
+ [0x50C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50C,
+ },
+ [0x50D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50D,
+ },
+ [0x50E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50E,
+ },
+ [0x50F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x50F,
+ },
+ [0x510]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x510,
+ },
+ [0x511]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x511,
+ },
+ [0x512]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x512,
+ },
+ [0x513]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x513,
+ },
+ [0x514]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x514,
+ },
+ [0x515]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x515,
+ },
+ [0x516]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x516,
+ },
+ [0x517]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x517,
+ },
+ [0x518]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x518,
+ },
+ [0x519]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x519,
+ },
+ [0x51A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51A,
+ },
+ [0x51B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51B,
+ },
+ [0x51C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51C,
+ },
+ [0x51D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51D,
+ },
+ [0x51E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51E,
+ },
+ [0x51F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x51F,
+ },
+ [0x520]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x520,
+ },
+ [0x521]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x521,
+ },
+ [0x522]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x522,
+ },
+ [0x523]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x523,
+ },
+ [0x524]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x524,
+ },
+ [0x525]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x525,
+ },
+ [0x526]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x526,
+ },
+ [0x527]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x527,
+ },
+ [0x528]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x528,
+ },
+ [0x529]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x529,
+ },
+ [0x52A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52A,
+ },
+ [0x52B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52B,
+ },
+ [0x52C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52C,
+ },
+ [0x52D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52D,
+ },
+ [0x52E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52E,
+ },
+ [0x52F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x52F,
+ },
+ [0x531]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x531,
+ },
+ [0x532]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x532,
+ },
+ [0x533]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x533,
+ },
+ [0x534]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x534,
+ },
+ [0x535]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x535,
+ },
+ [0x536]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x536,
+ },
+ [0x537]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x537,
+ },
+ [0x538]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x538,
+ },
+ [0x539]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x539,
+ },
+ [0x53A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53A,
+ },
+ [0x53B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53B,
+ },
+ [0x53C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53C,
+ },
+ [0x53D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53D,
+ },
+ [0x53E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53E,
+ },
+ [0x53F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x53F,
+ },
+ [0x540]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x540,
+ },
+ [0x541]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x541,
+ },
+ [0x542]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x542,
+ },
+ [0x543]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x543,
+ },
+ [0x544]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x544,
+ },
+ [0x545]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x545,
+ },
+ [0x546]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x546,
+ },
+ [0x547]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x547,
+ },
+ [0x548]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x548,
+ },
+ [0x549]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x549,
+ },
+ [0x54A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54A,
+ },
+ [0x54B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54B,
+ },
+ [0x54C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54C,
+ },
+ [0x54D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54D,
+ },
+ [0x54E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54E,
+ },
+ [0x54F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x54F,
+ },
+ [0x550]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x550,
+ },
+ [0x551]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x551,
+ },
+ [0x552]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x552,
+ },
+ [0x553]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x553,
+ },
+ [0x554]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x554,
+ },
+ [0x555]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x555,
+ },
+ [0x556]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x556,
+ },
+ [0x559]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x559,
+ },
+ [0x55A]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55A,
+ },
+ [0x55B]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55B,
+ },
+ [0x55C]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55C,
+ },
+ [0x55D]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55D,
+ },
+ [0x55E]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55E,
+ },
+ [0x55F]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x55F,
+ },
+ [0x560]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x560,
+ },
+ [0x561]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x561,
+ },
+ [0x562]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x562,
+ },
+ [0x563]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x563,
+ },
+ [0x564]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x564,
+ },
+ [0x565]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x565,
+ },
+ [0x566]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x566,
+ },
+ [0x567]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x567,
+ },
+ [0x568]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x568,
+ },
+ [0x569]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x569,
+ },
+ [0x56A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56A,
+ },
+ [0x56B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56B,
+ },
+ [0x56C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56C,
+ },
+ [0x56D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56D,
+ },
+ [0x56E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56E,
+ },
+ [0x56F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x56F,
+ },
+ [0x570]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x570,
+ },
+ [0x571]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x571,
+ },
+ [0x572]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x572,
+ },
+ [0x573]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x573,
+ },
+ [0x574]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x574,
+ },
+ [0x575]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x575,
+ },
+ [0x576]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x576,
+ },
+ [0x577]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x577,
+ },
+ [0x578]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x578,
+ },
+ [0x579]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x579,
+ },
+ [0x57A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57A,
+ },
+ [0x57B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57B,
+ },
+ [0x57C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57C,
+ },
+ [0x57D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57D,
+ },
+ [0x57E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57E,
+ },
+ [0x57F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x57F,
+ },
+ [0x580]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x580,
+ },
+ [0x581]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x581,
+ },
+ [0x582]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x582,
+ },
+ [0x583]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x583,
+ },
+ [0x584]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x584,
+ },
+ [0x585]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x585,
+ },
+ [0x586]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x586,
+ },
+ [0x587]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x565, 0x582 },
+ unicodeslot=0x587,
+ },
+ [0x588]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x588,
+ },
+ [0x589]={
+ category="po",
+ direction="l",
+ linebreak="is",
+ unicodeslot=0x589,
+ },
+ [0x58A]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x58A,
+ },
+ [0x58D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x58D,
+ },
+ [0x58E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x58E,
+ },
+ [0x58F]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x58F,
+ },
+ [0x591]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x591,
+ },
+ [0x592]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x592,
+ },
+ [0x593]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x593,
+ },
+ [0x594]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x594,
+ },
+ [0x595]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x595,
+ },
+ [0x596]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x596,
+ },
+ [0x597]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x597,
+ },
+ [0x598]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x598,
+ },
+ [0x599]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x599,
+ },
+ [0x59A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x59A,
+ },
+ [0x59B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x59B,
+ },
+ [0x59C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x59C,
+ },
+ [0x59D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x59D,
+ },
+ [0x59E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x59E,
+ },
+ [0x59F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x59F,
+ },
+ [0x5A0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A0,
+ },
+ [0x5A1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A1,
+ },
+ [0x5A2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A2,
+ },
+ [0x5A3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A3,
+ },
+ [0x5A4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A4,
+ },
+ [0x5A5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A5,
+ },
+ [0x5A6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A6,
+ },
+ [0x5A7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A7,
+ },
+ [0x5A8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A8,
+ },
+ [0x5A9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5A9,
+ },
+ [0x5AA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5AA,
+ },
+ [0x5AB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5AB,
+ },
+ [0x5AC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5AC,
+ },
+ [0x5AD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5AD,
+ },
+ [0x5AE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5AE,
+ },
+ [0x5AF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5AF,
+ },
+ [0x5B0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B0,
+ },
+ [0x5B1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B1,
+ },
+ [0x5B2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B2,
+ },
+ [0x5B3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B3,
+ },
+ [0x5B4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B4,
+ },
+ [0x5B5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B5,
+ },
+ [0x5B6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B6,
+ },
+ [0x5B7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B7,
+ },
+ [0x5B8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B8,
+ },
+ [0x5B9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5B9,
+ },
+ [0x5BA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5BA,
+ },
+ [0x5BB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5BB,
+ },
+ [0x5BC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5BC,
+ },
+ [0x5BD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5BD,
+ },
+ [0x5BE]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x5BE,
+ },
+ [0x5BF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5BF,
+ },
+ [0x5C0]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x5C0,
+ },
+ [0x5C1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5C1,
+ },
+ [0x5C2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5C2,
+ },
+ [0x5C3]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x5C3,
+ },
+ [0x5C4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5C4,
+ },
+ [0x5C5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5C5,
+ },
+ [0x5C6]={
+ category="po",
+ direction="r",
+ linebreak="ex",
+ unicodeslot=0x5C6,
+ },
+ [0x5C7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x5C7,
+ },
+ [0x5D0]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D0,
+ },
+ [0x5D1]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D1,
+ },
+ [0x5D2]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D2,
+ },
+ [0x5D3]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D3,
+ },
+ [0x5D4]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D4,
+ },
+ [0x5D5]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D5,
+ },
+ [0x5D6]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D6,
+ },
+ [0x5D7]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D7,
+ },
+ [0x5D8]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D8,
+ },
+ [0x5D9]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5D9,
+ },
+ [0x5DA]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5DA,
+ },
+ [0x5DB]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5DB,
+ },
+ [0x5DC]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5DC,
+ },
+ [0x5DD]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5DD,
+ },
+ [0x5DE]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5DE,
+ },
+ [0x5DF]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5DF,
+ },
+ [0x5E0]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E0,
+ },
+ [0x5E1]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E1,
+ },
+ [0x5E2]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E2,
+ },
+ [0x5E3]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E3,
+ },
+ [0x5E4]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E4,
+ },
+ [0x5E5]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E5,
+ },
+ [0x5E6]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E6,
+ },
+ [0x5E7]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E7,
+ },
+ [0x5E8]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E8,
+ },
+ [0x5E9]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5E9,
+ },
+ [0x5EA]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5EA,
+ },
+ [0x5EF]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5EF,
+ },
+ [0x5F0]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5F0,
+ },
+ [0x5F1]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5F1,
+ },
+ [0x5F2]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ unicodeslot=0x5F2,
+ },
+ [0x5F3]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x5F3,
+ },
+ [0x5F4]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x5F4,
+ },
+ [0x600]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x600,
+ },
+ [0x601]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x601,
+ },
+ [0x602]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x602,
+ },
+ [0x603]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x603,
+ },
+ [0x604]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x604,
+ },
+ [0x605]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x605,
+ },
+ [0x606]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x606,
+ },
+ [0x607]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x607,
+ },
+ [0x608]={
+ category="sm",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x608,
+ },
+ [0x609]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x609,
+ },
+ [0x60A]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x60A,
+ },
+ [0x60B]={
+ category="sc",
+ direction="al",
+ linebreak="po",
+ unicodeslot=0x60B,
+ },
+ [0x60C]={
+ category="po",
+ direction="cs",
+ linebreak="is",
+ unicodeslot=0x60C,
+ },
+ [0x60D]={
+ category="po",
+ direction="al",
+ linebreak="is",
+ unicodeslot=0x60D,
+ },
+ [0x60E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x60E,
+ },
+ [0x60F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x60F,
+ },
+ [0x610]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x610,
+ },
+ [0x611]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x611,
+ },
+ [0x612]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x612,
+ },
+ [0x613]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x613,
+ },
+ [0x614]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x614,
+ },
+ [0x615]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x615,
+ },
+ [0x616]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x616,
+ },
+ [0x617]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x617,
+ },
+ [0x618]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x618,
+ },
+ [0x619]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x619,
+ },
+ [0x61A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x61A,
+ },
+ [0x61B]={
+ category="po",
+ direction="al",
+ linebreak="ex",
+ unicodeslot=0x61B,
+ },
+ [0x61C]={
+ category="cf",
+ direction="al",
+ linebreak="cm",
+ unicodeslot=0x61C,
+ },
+ [0x61E]={
+ category="po",
+ direction="al",
+ linebreak="ex",
+ unicodeslot=0x61E,
+ },
+ [0x61F]={
+ category="po",
+ direction="al",
+ linebreak="ex",
+ unicodeslot=0x61F,
+ },
+ [0x620]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x620,
+ },
+ [0x621]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x621,
+ },
+ [0x622]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x627, 0x653 },
+ unicodeslot=0x622,
+ },
+ [0x623]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x627, 0x654 },
+ unicodeslot=0x623,
+ },
+ [0x624]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x648, 0x654 },
+ unicodeslot=0x624,
+ },
+ [0x625]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x627, 0x655 },
+ unicodeslot=0x625,
+ },
+ [0x626]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x64A, 0x654 },
+ unicodeslot=0x626,
+ },
+ [0x627]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x627,
+ },
+ [0x628]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x628,
+ },
+ [0x629]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x629,
+ },
+ [0x62A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x62A,
+ },
+ [0x62B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x62B,
+ },
+ [0x62C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x62C,
+ },
+ [0x62D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x62D,
+ },
+ [0x62E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x62E,
+ },
+ [0x62F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x62F,
+ },
+ [0x630]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x630,
+ },
+ [0x631]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x631,
+ },
+ [0x632]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x632,
+ },
+ [0x633]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x633,
+ },
+ [0x634]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x634,
+ },
+ [0x635]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x635,
+ },
+ [0x636]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x636,
+ },
+ [0x637]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x637,
+ },
+ [0x638]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x638,
+ },
+ [0x639]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x639,
+ },
+ [0x63A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x63A,
+ },
+ [0x63B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x63B,
+ },
+ [0x63C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x63C,
+ },
+ [0x63D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x63D,
+ },
+ [0x63E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x63E,
+ },
+ [0x63F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x63F,
+ },
+ [0x640]={
+ category="lm",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x640,
+ },
+ [0x641]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x641,
+ },
+ [0x642]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x642,
+ },
+ [0x643]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x643,
+ },
+ [0x644]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x644,
+ },
+ [0x645]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x645,
+ },
+ [0x646]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x646,
+ },
+ [0x647]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x647,
+ },
+ [0x648]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x648,
+ },
+ [0x649]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x649,
+ },
+ [0x64A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x64A,
+ },
+ [0x64B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x64B,
+ },
+ [0x64C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x64C,
+ },
+ [0x64D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x64D,
+ },
+ [0x64E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x64E,
+ },
+ [0x64F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x64F,
+ },
+ [0x650]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x650,
+ },
+ [0x651]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x651,
+ },
+ [0x652]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x652,
+ },
+ [0x653]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x653,
+ },
+ [0x654]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x654,
+ },
+ [0x655]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x655,
+ },
+ [0x656]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x656,
+ },
+ [0x657]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x657,
+ },
+ [0x658]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x658,
+ },
+ [0x659]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x659,
+ },
+ [0x65A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x65A,
+ },
+ [0x65B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x65B,
+ },
+ [0x65C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x65C,
+ },
+ [0x65D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x65D,
+ },
+ [0x65E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x65E,
+ },
+ [0x65F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x65F,
+ },
+ [0x660]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x660,
+ },
+ [0x661]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x661,
+ },
+ [0x662]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x662,
+ },
+ [0x663]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x663,
+ },
+ [0x664]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x664,
+ },
+ [0x665]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x665,
+ },
+ [0x666]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x666,
+ },
+ [0x667]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x667,
+ },
+ [0x668]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x668,
+ },
+ [0x669]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x669,
+ },
+ [0x66A]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x66A,
+ },
+ [0x66B]={
+ category="po",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x66B,
+ },
+ [0x66C]={
+ category="po",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x66C,
+ },
+ [0x66D]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x66D,
+ },
+ [0x66E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x66E,
+ },
+ [0x66F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x66F,
+ },
+ [0x670]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x670,
+ },
+ [0x671]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x671,
+ },
+ [0x672]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x672,
+ },
+ [0x673]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x673,
+ },
+ [0x674]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x674,
+ },
+ [0x675]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "compat", 0x627, 0x674 },
+ unicodeslot=0x675,
+ },
+ [0x676]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "compat", 0x648, 0x674 },
+ unicodeslot=0x676,
+ },
+ [0x677]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "compat", 0x6C7, 0x674 },
+ unicodeslot=0x677,
+ },
+ [0x678]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "compat", 0x64A, 0x674 },
+ unicodeslot=0x678,
+ },
+ [0x679]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x679,
+ },
+ [0x67A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x67A,
+ },
+ [0x67B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x67B,
+ },
+ [0x67C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x67C,
+ },
+ [0x67D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x67D,
+ },
+ [0x67E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x67E,
+ },
+ [0x67F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x67F,
+ },
+ [0x680]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x680,
+ },
+ [0x681]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x681,
+ },
+ [0x682]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x682,
+ },
+ [0x683]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x683,
+ },
+ [0x684]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x684,
+ },
+ [0x685]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x685,
+ },
+ [0x686]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x686,
+ },
+ [0x687]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x687,
+ },
+ [0x688]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x688,
+ },
+ [0x689]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x689,
+ },
+ [0x68A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x68A,
+ },
+ [0x68B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x68B,
+ },
+ [0x68C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x68C,
+ },
+ [0x68D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x68D,
+ },
+ [0x68E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x68E,
+ },
+ [0x68F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x68F,
+ },
+ [0x690]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x690,
+ },
+ [0x691]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x691,
+ },
+ [0x692]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x692,
+ },
+ [0x693]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x693,
+ },
+ [0x694]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x694,
+ },
+ [0x695]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x695,
+ },
+ [0x696]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x696,
+ },
+ [0x697]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x697,
+ },
+ [0x698]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x698,
+ },
+ [0x699]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x699,
+ },
+ [0x69A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x69A,
+ },
+ [0x69B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x69B,
+ },
+ [0x69C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x69C,
+ },
+ [0x69D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x69D,
+ },
+ [0x69E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x69E,
+ },
+ [0x69F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x69F,
+ },
+ [0x6A0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A0,
+ },
+ [0x6A1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A1,
+ },
+ [0x6A2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A2,
+ },
+ [0x6A3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A3,
+ },
+ [0x6A4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A4,
+ },
+ [0x6A5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A5,
+ },
+ [0x6A6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A6,
+ },
+ [0x6A7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A7,
+ },
+ [0x6A8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A8,
+ },
+ [0x6A9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6A9,
+ },
+ [0x6AA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6AA,
+ },
+ [0x6AB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6AB,
+ },
+ [0x6AC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6AC,
+ },
+ [0x6AD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6AD,
+ },
+ [0x6AE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6AE,
+ },
+ [0x6AF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6AF,
+ },
+ [0x6B0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B0,
+ },
+ [0x6B1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B1,
+ },
+ [0x6B2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B2,
+ },
+ [0x6B3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B3,
+ },
+ [0x6B4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B4,
+ },
+ [0x6B5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B5,
+ },
+ [0x6B6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B6,
+ },
+ [0x6B7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B7,
+ },
+ [0x6B8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B8,
+ },
+ [0x6B9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6B9,
+ },
+ [0x6BA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6BA,
+ },
+ [0x6BB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6BB,
+ },
+ [0x6BC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6BC,
+ },
+ [0x6BD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6BD,
+ },
+ [0x6BE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6BE,
+ },
+ [0x6BF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6BF,
+ },
+ [0x6C0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x6D5, 0x654 },
+ unicodeslot=0x6C0,
+ },
+ [0x6C1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C1,
+ },
+ [0x6C2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x6C1, 0x654 },
+ unicodeslot=0x6C2,
+ },
+ [0x6C3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C3,
+ },
+ [0x6C4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C4,
+ },
+ [0x6C5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C5,
+ },
+ [0x6C6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C6,
+ },
+ [0x6C7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C7,
+ },
+ [0x6C8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C8,
+ },
+ [0x6C9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6C9,
+ },
+ [0x6CA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6CA,
+ },
+ [0x6CB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6CB,
+ },
+ [0x6CC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6CC,
+ },
+ [0x6CD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6CD,
+ },
+ [0x6CE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6CE,
+ },
+ [0x6CF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6CF,
+ },
+ [0x6D0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6D0,
+ },
+ [0x6D1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6D1,
+ },
+ [0x6D2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6D2,
+ },
+ [0x6D3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "char", 0x6D2, 0x654 },
+ unicodeslot=0x6D3,
+ },
+ [0x6D4]={
+ category="po",
+ direction="al",
+ linebreak="ex",
+ unicodeslot=0x6D4,
+ },
+ [0x6D5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6D5,
+ },
+ [0x6D6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6D6,
+ },
+ [0x6D7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6D7,
+ },
+ [0x6D8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6D8,
+ },
+ [0x6D9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6D9,
+ },
+ [0x6DA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6DA,
+ },
+ [0x6DB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6DB,
+ },
+ [0x6DC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6DC,
+ },
+ [0x6DD]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x6DD,
+ },
+ [0x6DE]={
+ category="me",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x6DE,
+ },
+ [0x6DF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6DF,
+ },
+ [0x6E0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E0,
+ },
+ [0x6E1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E1,
+ },
+ [0x6E2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E2,
+ },
+ [0x6E3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E3,
+ },
+ [0x6E4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E4,
+ },
+ [0x6E5]={
+ category="lm",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6E5,
+ },
+ [0x6E6]={
+ category="lm",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6E6,
+ },
+ [0x6E7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E7,
+ },
+ [0x6E8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6E8,
+ },
+ [0x6E9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x6E9,
+ },
+ [0x6EA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6EA,
+ },
+ [0x6EB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6EB,
+ },
+ [0x6EC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6EC,
+ },
+ [0x6ED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x6ED,
+ },
+ [0x6EE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6EE,
+ },
+ [0x6EF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6EF,
+ },
+ [0x6F0]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F0,
+ },
+ [0x6F1]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F1,
+ },
+ [0x6F2]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F2,
+ },
+ [0x6F3]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F3,
+ },
+ [0x6F4]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F4,
+ },
+ [0x6F5]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F5,
+ },
+ [0x6F6]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F6,
+ },
+ [0x6F7]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F7,
+ },
+ [0x6F8]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F8,
+ },
+ [0x6F9]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ unicodeslot=0x6F9,
+ },
+ [0x6FA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6FA,
+ },
+ [0x6FB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6FB,
+ },
+ [0x6FC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6FC,
+ },
+ [0x6FD]={
+ category="so",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6FD,
+ },
+ [0x6FE]={
+ category="so",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6FE,
+ },
+ [0x6FF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x6FF,
+ },
+ [0x700]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x700,
+ },
+ [0x701]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x701,
+ },
+ [0x702]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x702,
+ },
+ [0x703]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x703,
+ },
+ [0x704]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x704,
+ },
+ [0x705]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x705,
+ },
+ [0x706]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x706,
+ },
+ [0x707]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x707,
+ },
+ [0x708]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x708,
+ },
+ [0x709]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x709,
+ },
+ [0x70A]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x70A,
+ },
+ [0x70B]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x70B,
+ },
+ [0x70C]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x70C,
+ },
+ [0x70D]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x70D,
+ },
+ [0x70F]={
+ category="cf",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x70F,
+ },
+ [0x710]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x710,
+ },
+ [0x711]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x711,
+ },
+ [0x712]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x712,
+ },
+ [0x713]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x713,
+ },
+ [0x714]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x714,
+ },
+ [0x715]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x715,
+ },
+ [0x716]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x716,
+ },
+ [0x717]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x717,
+ },
+ [0x718]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x718,
+ },
+ [0x719]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x719,
+ },
+ [0x71A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x71A,
+ },
+ [0x71B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x71B,
+ },
+ [0x71C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x71C,
+ },
+ [0x71D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x71D,
+ },
+ [0x71E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x71E,
+ },
+ [0x71F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x71F,
+ },
+ [0x720]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x720,
+ },
+ [0x721]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x721,
+ },
+ [0x722]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x722,
+ },
+ [0x723]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x723,
+ },
+ [0x724]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x724,
+ },
+ [0x725]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x725,
+ },
+ [0x726]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x726,
+ },
+ [0x727]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x727,
+ },
+ [0x728]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x728,
+ },
+ [0x729]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x729,
+ },
+ [0x72A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x72A,
+ },
+ [0x72B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x72B,
+ },
+ [0x72C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x72C,
+ },
+ [0x72D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x72D,
+ },
+ [0x72E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x72E,
+ },
+ [0x72F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x72F,
+ },
+ [0x730]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x730,
+ },
+ [0x731]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x731,
+ },
+ [0x732]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x732,
+ },
+ [0x733]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x733,
+ },
+ [0x734]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x734,
+ },
+ [0x735]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x735,
+ },
+ [0x736]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x736,
+ },
+ [0x737]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x737,
+ },
+ [0x738]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x738,
+ },
+ [0x739]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x739,
+ },
+ [0x73A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x73A,
+ },
+ [0x73B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x73B,
+ },
+ [0x73C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x73C,
+ },
+ [0x73D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x73D,
+ },
+ [0x73E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x73E,
+ },
+ [0x73F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x73F,
+ },
+ [0x740]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x740,
+ },
+ [0x741]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x741,
+ },
+ [0x742]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x742,
+ },
+ [0x743]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x743,
+ },
+ [0x744]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x744,
+ },
+ [0x745]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x745,
+ },
+ [0x746]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x746,
+ },
+ [0x747]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x747,
+ },
+ [0x748]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x748,
+ },
+ [0x749]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x749,
+ },
+ [0x74A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x74A,
+ },
+ [0x74D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x74D,
+ },
+ [0x74E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x74E,
+ },
+ [0x74F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x74F,
+ },
+ [0x750]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x750,
+ },
+ [0x751]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x751,
+ },
+ [0x752]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x752,
+ },
+ [0x753]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x753,
+ },
+ [0x754]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x754,
+ },
+ [0x755]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x755,
+ },
+ [0x756]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x756,
+ },
+ [0x757]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x757,
+ },
+ [0x758]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x758,
+ },
+ [0x759]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x759,
+ },
+ [0x75A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x75A,
+ },
+ [0x75B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x75B,
+ },
+ [0x75C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x75C,
+ },
+ [0x75D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x75D,
+ },
+ [0x75E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x75E,
+ },
+ [0x75F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x75F,
+ },
+ [0x760]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x760,
+ },
+ [0x761]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x761,
+ },
+ [0x762]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x762,
+ },
+ [0x763]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x763,
+ },
+ [0x764]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x764,
+ },
+ [0x765]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x765,
+ },
+ [0x766]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x766,
+ },
+ [0x767]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x767,
+ },
+ [0x768]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x768,
+ },
+ [0x769]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x769,
+ },
+ [0x76A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x76A,
+ },
+ [0x76B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x76B,
+ },
+ [0x76C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x76C,
+ },
+ [0x76D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x76D,
+ },
+ [0x76E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x76E,
+ },
+ [0x76F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x76F,
+ },
+ [0x770]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x770,
+ },
+ [0x771]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x771,
+ },
+ [0x772]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x772,
+ },
+ [0x773]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x773,
+ },
+ [0x774]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x774,
+ },
+ [0x775]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x775,
+ },
+ [0x776]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x776,
+ },
+ [0x777]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x777,
+ },
+ [0x778]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x778,
+ },
+ [0x779]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x779,
+ },
+ [0x77A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x77A,
+ },
+ [0x77B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x77B,
+ },
+ [0x77C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x77C,
+ },
+ [0x77D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x77D,
+ },
+ [0x77E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x77E,
+ },
+ [0x77F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x77F,
+ },
+ [0x780]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x780,
+ },
+ [0x781]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x781,
+ },
+ [0x782]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x782,
+ },
+ [0x783]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x783,
+ },
+ [0x784]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x784,
+ },
+ [0x785]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x785,
+ },
+ [0x786]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x786,
+ },
+ [0x787]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x787,
+ },
+ [0x788]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x788,
+ },
+ [0x789]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x789,
+ },
+ [0x78A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x78A,
+ },
+ [0x78B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x78B,
+ },
+ [0x78C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x78C,
+ },
+ [0x78D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x78D,
+ },
+ [0x78E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x78E,
+ },
+ [0x78F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x78F,
+ },
+ [0x790]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x790,
+ },
+ [0x791]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x791,
+ },
+ [0x792]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x792,
+ },
+ [0x793]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x793,
+ },
+ [0x794]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x794,
+ },
+ [0x795]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x795,
+ },
+ [0x796]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x796,
+ },
+ [0x797]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x797,
+ },
+ [0x798]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x798,
+ },
+ [0x799]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x799,
+ },
+ [0x79A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x79A,
+ },
+ [0x79B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x79B,
+ },
+ [0x79C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x79C,
+ },
+ [0x79D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x79D,
+ },
+ [0x79E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x79E,
+ },
+ [0x79F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x79F,
+ },
+ [0x7A0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7A0,
+ },
+ [0x7A1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7A1,
+ },
+ [0x7A2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7A2,
+ },
+ [0x7A3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7A3,
+ },
+ [0x7A4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7A4,
+ },
+ [0x7A5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7A5,
+ },
+ [0x7A6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7A6,
+ },
+ [0x7A7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7A7,
+ },
+ [0x7A8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7A8,
+ },
+ [0x7A9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7A9,
+ },
+ [0x7AA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7AA,
+ },
+ [0x7AB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7AB,
+ },
+ [0x7AC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7AC,
+ },
+ [0x7AD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7AD,
+ },
+ [0x7AE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7AE,
+ },
+ [0x7AF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7AF,
+ },
+ [0x7B0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7B0,
+ },
+ [0x7B1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x7B1,
+ },
+ [0x7C0]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C0,
+ },
+ [0x7C1]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C1,
+ },
+ [0x7C2]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C2,
+ },
+ [0x7C3]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C3,
+ },
+ [0x7C4]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C4,
+ },
+ [0x7C5]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C5,
+ },
+ [0x7C6]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C6,
+ },
+ [0x7C7]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C7,
+ },
+ [0x7C8]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C8,
+ },
+ [0x7C9]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x7C9,
+ },
+ [0x7CA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7CA,
+ },
+ [0x7CB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7CB,
+ },
+ [0x7CC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7CC,
+ },
+ [0x7CD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7CD,
+ },
+ [0x7CE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7CE,
+ },
+ [0x7CF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7CF,
+ },
+ [0x7D0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D0,
+ },
+ [0x7D1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D1,
+ },
+ [0x7D2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D2,
+ },
+ [0x7D3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D3,
+ },
+ [0x7D4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D4,
+ },
+ [0x7D5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D5,
+ },
+ [0x7D6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D6,
+ },
+ [0x7D7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D7,
+ },
+ [0x7D8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D8,
+ },
+ [0x7D9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7D9,
+ },
+ [0x7DA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7DA,
+ },
+ [0x7DB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7DB,
+ },
+ [0x7DC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7DC,
+ },
+ [0x7DD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7DD,
+ },
+ [0x7DE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7DE,
+ },
+ [0x7DF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7DF,
+ },
+ [0x7E0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E0,
+ },
+ [0x7E1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E1,
+ },
+ [0x7E2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E2,
+ },
+ [0x7E3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E3,
+ },
+ [0x7E4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E4,
+ },
+ [0x7E5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E5,
+ },
+ [0x7E6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E6,
+ },
+ [0x7E7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E7,
+ },
+ [0x7E8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E8,
+ },
+ [0x7E9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7E9,
+ },
+ [0x7EA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7EA,
+ },
+ [0x7EB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7EB,
+ },
+ [0x7EC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7EC,
+ },
+ [0x7ED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7ED,
+ },
+ [0x7EE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7EE,
+ },
+ [0x7EF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7EF,
+ },
+ [0x7F0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7F0,
+ },
+ [0x7F1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7F1,
+ },
+ [0x7F2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7F2,
+ },
+ [0x7F3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7F3,
+ },
+ [0x7F4]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7F4,
+ },
+ [0x7F5]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7F5,
+ },
+ [0x7F6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x7F6,
+ },
+ [0x7F7]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x7F7,
+ },
+ [0x7F8]={
+ category="po",
+ direction="on",
+ linebreak="is",
+ unicodeslot=0x7F8,
+ },
+ [0x7F9]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x7F9,
+ },
+ [0x7FA]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x7FA,
+ },
+ [0x7FD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x7FD,
+ },
+ [0x7FE]={
+ category="sc",
+ direction="r",
+ linebreak="pr",
+ unicodeslot=0x7FE,
+ },
+ [0x7FF]={
+ category="sc",
+ direction="r",
+ linebreak="pr",
+ unicodeslot=0x7FF,
+ },
+ [0x800]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x800,
+ },
+ [0x801]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x801,
+ },
+ [0x802]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x802,
+ },
+ [0x803]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x803,
+ },
+ [0x804]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x804,
+ },
+ [0x805]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x805,
+ },
+ [0x806]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x806,
+ },
+ [0x807]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x807,
+ },
+ [0x808]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x808,
+ },
+ [0x809]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x809,
+ },
+ [0x80A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x80A,
+ },
+ [0x80B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x80B,
+ },
+ [0x80C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x80C,
+ },
+ [0x80D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x80D,
+ },
+ [0x80E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x80E,
+ },
+ [0x80F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x80F,
+ },
+ [0x810]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x810,
+ },
+ [0x811]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x811,
+ },
+ [0x812]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x812,
+ },
+ [0x813]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x813,
+ },
+ [0x814]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x814,
+ },
+ [0x815]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x815,
+ },
+ [0x816]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x816,
+ },
+ [0x817]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x817,
+ },
+ [0x818]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x818,
+ },
+ [0x819]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x819,
+ },
+ [0x81A]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x81A,
+ },
+ [0x81B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x81B,
+ },
+ [0x81C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x81C,
+ },
+ [0x81D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x81D,
+ },
+ [0x81E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x81E,
+ },
+ [0x81F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x81F,
+ },
+ [0x820]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x820,
+ },
+ [0x821]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x821,
+ },
+ [0x822]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x822,
+ },
+ [0x823]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x823,
+ },
+ [0x824]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x824,
+ },
+ [0x825]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x825,
+ },
+ [0x826]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x826,
+ },
+ [0x827]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x827,
+ },
+ [0x828]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x828,
+ },
+ [0x829]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x829,
+ },
+ [0x82A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x82A,
+ },
+ [0x82B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x82B,
+ },
+ [0x82C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x82C,
+ },
+ [0x82D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x82D,
+ },
+ [0x830]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x830,
+ },
+ [0x831]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x831,
+ },
+ [0x832]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x832,
+ },
+ [0x833]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x833,
+ },
+ [0x834]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x834,
+ },
+ [0x835]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x835,
+ },
+ [0x836]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x836,
+ },
+ [0x837]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x837,
+ },
+ [0x838]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x838,
+ },
+ [0x839]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x839,
+ },
+ [0x83A]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x83A,
+ },
+ [0x83B]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x83B,
+ },
+ [0x83C]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x83C,
+ },
+ [0x83D]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x83D,
+ },
+ [0x83E]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x83E,
+ },
+ [0x840]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x840,
+ },
+ [0x841]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x841,
+ },
+ [0x842]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x842,
+ },
+ [0x843]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x843,
+ },
+ [0x844]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x844,
+ },
+ [0x845]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x845,
+ },
+ [0x846]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x846,
+ },
+ [0x847]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x847,
+ },
+ [0x848]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x848,
+ },
+ [0x849]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x849,
+ },
+ [0x84A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x84A,
+ },
+ [0x84B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x84B,
+ },
+ [0x84C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x84C,
+ },
+ [0x84D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x84D,
+ },
+ [0x84E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x84E,
+ },
+ [0x84F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x84F,
+ },
+ [0x850]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x850,
+ },
+ [0x851]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x851,
+ },
+ [0x852]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x852,
+ },
+ [0x853]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x853,
+ },
+ [0x854]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x854,
+ },
+ [0x855]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x855,
+ },
+ [0x856]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x856,
+ },
+ [0x857]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x857,
+ },
+ [0x858]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x858,
+ },
+ [0x859]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x859,
+ },
+ [0x85A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x85A,
+ },
+ [0x85B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x85B,
+ },
+ [0x85E]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x85E,
+ },
+ [0x860]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x860,
+ },
+ [0x861]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x861,
+ },
+ [0x862]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x862,
+ },
+ [0x863]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x863,
+ },
+ [0x864]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x864,
+ },
+ [0x865]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x865,
+ },
+ [0x866]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x866,
+ },
+ [0x867]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x867,
+ },
+ [0x868]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x868,
+ },
+ [0x869]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x869,
+ },
+ [0x86A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x86A,
+ },
+ [0x8A0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A0,
+ },
+ [0x8A1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A1,
+ },
+ [0x8A2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A2,
+ },
+ [0x8A3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A3,
+ },
+ [0x8A4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A4,
+ },
+ [0x8A5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A5,
+ },
+ [0x8A6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A6,
+ },
+ [0x8A7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A7,
+ },
+ [0x8A8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A8,
+ },
+ [0x8A9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8A9,
+ },
+ [0x8AA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8AA,
+ },
+ [0x8AB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8AB,
+ },
+ [0x8AC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8AC,
+ },
+ [0x8AD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8AD,
+ },
+ [0x8AE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8AE,
+ },
+ [0x8AF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8AF,
+ },
+ [0x8B0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B0,
+ },
+ [0x8B1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B1,
+ },
+ [0x8B2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B2,
+ },
+ [0x8B3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B3,
+ },
+ [0x8B4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B4,
+ },
+ [0x8B6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B6,
+ },
+ [0x8B7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B7,
+ },
+ [0x8B8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B8,
+ },
+ [0x8B9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8B9,
+ },
+ [0x8BA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8BA,
+ },
+ [0x8BB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8BB,
+ },
+ [0x8BC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8BC,
+ },
+ [0x8BD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x8BD,
+ },
+ [0x8D3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D3,
+ },
+ [0x8D4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D4,
+ },
+ [0x8D5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D5,
+ },
+ [0x8D6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D6,
+ },
+ [0x8D7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D7,
+ },
+ [0x8D8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D8,
+ },
+ [0x8D9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8D9,
+ },
+ [0x8DA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8DA,
+ },
+ [0x8DB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8DB,
+ },
+ [0x8DC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8DC,
+ },
+ [0x8DD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8DD,
+ },
+ [0x8DE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8DE,
+ },
+ [0x8DF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8DF,
+ },
+ [0x8E0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E0,
+ },
+ [0x8E1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E1,
+ },
+ [0x8E2]={
+ category="cf",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x8E2,
+ },
+ [0x8E3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E3,
+ },
+ [0x8E4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E4,
+ },
+ [0x8E5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E5,
+ },
+ [0x8E6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E6,
+ },
+ [0x8E7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E7,
+ },
+ [0x8E8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E8,
+ },
+ [0x8E9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8E9,
+ },
+ [0x8EA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8EA,
+ },
+ [0x8EB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8EB,
+ },
+ [0x8EC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8EC,
+ },
+ [0x8ED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8ED,
+ },
+ [0x8EE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8EE,
+ },
+ [0x8EF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8EF,
+ },
+ [0x8F0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F0,
+ },
+ [0x8F1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F1,
+ },
+ [0x8F2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F2,
+ },
+ [0x8F3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F3,
+ },
+ [0x8F4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F4,
+ },
+ [0x8F5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F5,
+ },
+ [0x8F6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F6,
+ },
+ [0x8F7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F7,
+ },
+ [0x8F8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F8,
+ },
+ [0x8F9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8F9,
+ },
+ [0x8FA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8FA,
+ },
+ [0x8FB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8FB,
+ },
+ [0x8FC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8FC,
+ },
+ [0x8FD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8FD,
+ },
+ [0x8FE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8FE,
+ },
+ [0x8FF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x8FF,
+ },
+ [0x900]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x900,
+ },
+ [0x901]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x901,
+ },
+ [0x902]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x902,
+ },
+ [0x903]={
+ category="mc",
+ direction="l",
+ indic="m",
+ indicmark="r",
+ linebreak="cm",
+ unicodeslot=0x903,
+ },
+ [0x904]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x904,
+ },
+ [0x905]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x905,
+ },
+ [0x906]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x906,
+ },
+ [0x907]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x907,
+ },
+ [0x908]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x908,
+ },
+ [0x909]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x909,
+ },
+ [0x90A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x90A,
+ },
+ [0x90B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x90B,
+ },
+ [0x90C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x90C,
+ },
+ [0x90D]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x90D,
+ },
+ [0x90E]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x90E,
+ },
+ [0x90F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x90F,
+ },
+ [0x910]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x910,
+ },
+ [0x911]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x911,
+ },
+ [0x912]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x912,
+ },
+ [0x913]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x913,
+ },
+ [0x914]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x914,
+ },
+ [0x915]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x915,
+ },
+ [0x916]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x916,
+ },
+ [0x917]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x917,
+ },
+ [0x918]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x918,
+ },
+ [0x919]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x919,
+ },
+ [0x91A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x91A,
+ },
+ [0x91B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x91B,
+ },
+ [0x91C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x91C,
+ },
+ [0x91D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x91D,
+ },
+ [0x91E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x91E,
+ },
+ [0x91F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x91F,
+ },
+ [0x920]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x920,
+ },
+ [0x921]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x921,
+ },
+ [0x922]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x922,
+ },
+ [0x923]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x923,
+ },
+ [0x924]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x924,
+ },
+ [0x925]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x925,
+ },
+ [0x926]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x926,
+ },
+ [0x927]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x927,
+ },
+ [0x928]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x928,
+ },
+ [0x929]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x928, 0x93C },
+ unicodeslot=0x929,
+ },
+ [0x92A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x92A,
+ },
+ [0x92B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x92B,
+ },
+ [0x92C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x92C,
+ },
+ [0x92D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x92D,
+ },
+ [0x92E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x92E,
+ },
+ [0x92F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x92F,
+ },
+ [0x930]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="bp",
+ linebreak="al",
+ unicodeslot=0x930,
+ },
+ [0x931]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x930, 0x93C },
+ unicodeslot=0x931,
+ },
+ [0x932]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x932,
+ },
+ [0x933]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x933,
+ },
+ [0x934]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x933, 0x93C },
+ unicodeslot=0x934,
+ },
+ [0x935]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x935,
+ },
+ [0x936]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x936,
+ },
+ [0x937]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x937,
+ },
+ [0x938]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x938,
+ },
+ [0x939]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x939,
+ },
+ [0x93A]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x93A,
+ },
+ [0x93B]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="cm",
+ unicodeslot=0x93B,
+ },
+ [0x93C]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="nukta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x93C,
+ },
+ [0x93D]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x93D,
+ },
+ [0x93E]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x93E,
+ },
+ [0x93F]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0x93F,
+ },
+ [0x940]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x940,
+ },
+ [0x941]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x941,
+ },
+ [0x942]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x942,
+ },
+ [0x943]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x943,
+ },
+ [0x944]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x944,
+ },
+ [0x945]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x945,
+ },
+ [0x946]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x946,
+ },
+ [0x947]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x947,
+ },
+ [0x948]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x948,
+ },
+ [0x949]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x949,
+ },
+ [0x94A]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x94A,
+ },
+ [0x94B]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x94B,
+ },
+ [0x94C]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x94C,
+ },
+ [0x94D]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x94D,
+ },
+ [0x94E]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0x94E,
+ },
+ [0x94F]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="cm",
+ unicodeslot=0x94F,
+ },
+ [0x950]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x950,
+ },
+ [0x951]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x951,
+ },
+ [0x952]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicclass="anudatta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x952,
+ },
+ [0x953]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x953,
+ },
+ [0x954]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x954,
+ },
+ [0x955]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0x955,
+ },
+ [0x956]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x956,
+ },
+ [0x957]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x957,
+ },
+ [0x958]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x915, 0x93C },
+ unicodeslot=0x958,
+ },
+ [0x959]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x916, 0x93C },
+ unicodeslot=0x959,
+ },
+ [0x95A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x917, 0x93C },
+ unicodeslot=0x95A,
+ },
+ [0x95B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x91C, 0x93C },
+ unicodeslot=0x95B,
+ },
+ [0x95C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x921, 0x93C },
+ unicodeslot=0x95C,
+ },
+ [0x95D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x922, 0x93C },
+ unicodeslot=0x95D,
+ },
+ [0x95E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x92B, 0x93C },
+ unicodeslot=0x95E,
+ },
+ [0x95F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x92F, 0x93C },
+ unicodeslot=0x95F,
+ },
+ [0x960]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x960,
+ },
+ [0x961]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x961,
+ },
+ [0x962]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x962,
+ },
+ [0x963]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x963,
+ },
+ [0x964]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="ba",
+ unicodeslot=0x964,
+ },
+ [0x965]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="ba",
+ unicodeslot=0x965,
+ },
+ [0x966]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x966,
+ },
+ [0x967]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x967,
+ },
+ [0x968]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x968,
+ },
+ [0x969]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x969,
+ },
+ [0x96A]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x96A,
+ },
+ [0x96B]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x96B,
+ },
+ [0x96C]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x96C,
+ },
+ [0x96D]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x96D,
+ },
+ [0x96E]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x96E,
+ },
+ [0x96F]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x96F,
+ },
+ [0x970]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x970,
+ },
+ [0x971]={
+ category="lm",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x971,
+ },
+ [0x972]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x972,
+ },
+ [0x973]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x973,
+ },
+ [0x974]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x974,
+ },
+ [0x975]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x975,
+ },
+ [0x976]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x976,
+ },
+ [0x977]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x977,
+ },
+ [0x978]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x978,
+ },
+ [0x979]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x979,
+ },
+ [0x97A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x97A,
+ },
+ [0x97B]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x97B,
+ },
+ [0x97C]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x97C,
+ },
+ [0x97D]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x97D,
+ },
+ [0x97E]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x97E,
+ },
+ [0x97F]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x97F,
+ },
+ [0x980]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x980,
+ },
+ [0x981]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0x981,
+ },
+ [0x982]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0x982,
+ },
+ [0x983]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0x983,
+ },
+ [0x985]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x985,
+ },
+ [0x986]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x986,
+ },
+ [0x987]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x987,
+ },
+ [0x988]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x988,
+ },
+ [0x989]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x989,
+ },
+ [0x98A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x98A,
+ },
+ [0x98B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x98B,
+ },
+ [0x98C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x98C,
+ },
+ [0x98F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x98F,
+ },
+ [0x990]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x990,
+ },
+ [0x993]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x993,
+ },
+ [0x994]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x994,
+ },
+ [0x995]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x995,
+ },
+ [0x996]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x996,
+ },
+ [0x997]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x997,
+ },
+ [0x998]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x998,
+ },
+ [0x999]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x999,
+ },
+ [0x99A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x99A,
+ },
+ [0x99B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x99B,
+ },
+ [0x99C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x99C,
+ },
+ [0x99D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x99D,
+ },
+ [0x99E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x99E,
+ },
+ [0x99F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x99F,
+ },
+ [0x9A0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A0,
+ },
+ [0x9A1]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A1,
+ },
+ [0x9A2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A2,
+ },
+ [0x9A3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A3,
+ },
+ [0x9A4]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A4,
+ },
+ [0x9A5]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A5,
+ },
+ [0x9A6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A6,
+ },
+ [0x9A7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A7,
+ },
+ [0x9A8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9A8,
+ },
+ [0x9AA]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9AA,
+ },
+ [0x9AB]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9AB,
+ },
+ [0x9AC]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9AC,
+ },
+ [0x9AD]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9AD,
+ },
+ [0x9AE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9AE,
+ },
+ [0x9AF]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9AF,
+ },
+ [0x9B0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="as",
+ linebreak="al",
+ unicodeslot=0x9B0,
+ },
+ [0x9B2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9B2,
+ },
+ [0x9B6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9B6,
+ },
+ [0x9B7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9B7,
+ },
+ [0x9B8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9B8,
+ },
+ [0x9B9]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9B9,
+ },
+ [0x9BC]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="nukta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x9BC,
+ },
+ [0x9BD]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9BD,
+ },
+ [0x9BE]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0x9BE,
+ },
+ [0x9BF]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0x9BF,
+ },
+ [0x9C0]={
+ category="mc",
+ direction="l",
+ indic="o",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0x9C0,
+ },
+ [0x9C1]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x9C1,
+ },
+ [0x9C2]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x9C2,
+ },
+ [0x9C3]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x9C3,
+ },
+ [0x9C4]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x9C4,
+ },
+ [0x9C7]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0x9C7,
+ },
+ [0x9C8]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0x9C8,
+ },
+ [0x9CB]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0x9C7, 0x9BE },
+ unicodeslot=0x9CB,
+ },
+ [0x9CC]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0x9C7, 0x9D7 },
+ unicodeslot=0x9CC,
+ },
+ [0x9CD]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0x9CD,
+ },
+ [0x9CE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0x9CE,
+ },
+ [0x9D7]={
+ category="mc",
+ direction="l",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0x9D7,
+ },
+ [0x9DC]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x9A1, 0x9BC },
+ unicodeslot=0x9DC,
+ },
+ [0x9DD]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x9A2, 0x9BC },
+ unicodeslot=0x9DD,
+ },
+ [0x9DF]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0x9AF, 0x9BC },
+ unicodeslot=0x9DF,
+ },
+ [0x9E0]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x9E0,
+ },
+ [0x9E1]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0x9E1,
+ },
+ [0x9E2]={
+ category="mn",
+ direction="nsm",
+ indic="i",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x9E2,
+ },
+ [0x9E3]={
+ category="mn",
+ direction="nsm",
+ indic="i",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0x9E3,
+ },
+ [0x9E6]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9E6,
+ },
+ [0x9E7]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9E7,
+ },
+ [0x9E8]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9E8,
+ },
+ [0x9E9]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9E9,
+ },
+ [0x9EA]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9EA,
+ },
+ [0x9EB]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9EB,
+ },
+ [0x9EC]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9EC,
+ },
+ [0x9ED]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9ED,
+ },
+ [0x9EE]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9EE,
+ },
+ [0x9EF]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x9EF,
+ },
+ [0x9F0]={
+ category="lo",
+ direction="l",
+ indic="o",
+ indicclass="ra",
+ indicorder="as",
+ linebreak="al",
+ unicodeslot=0x9F0,
+ },
+ [0x9F1]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9F1,
+ },
+ [0x9F2]={
+ category="sc",
+ direction="et",
+ indic="o",
+ linebreak="po",
+ unicodeslot=0x9F2,
+ },
+ [0x9F3]={
+ category="sc",
+ direction="et",
+ indic="o",
+ linebreak="po",
+ unicodeslot=0x9F3,
+ },
+ [0x9F4]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9F4,
+ },
+ [0x9F5]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9F5,
+ },
+ [0x9F6]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9F6,
+ },
+ [0x9F7]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9F7,
+ },
+ [0x9F8]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9F8,
+ },
+ [0x9F9]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="po",
+ unicodeslot=0x9F9,
+ },
+ [0x9FA]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9FA,
+ },
+ [0x9FB]={
+ category="sc",
+ direction="et",
+ indic="o",
+ linebreak="pr",
+ unicodeslot=0x9FB,
+ },
+ [0x9FC]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9FC,
+ },
+ [0x9FD]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x9FD,
+ },
+ [0x9FE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x9FE,
+ },
+ [0xA01]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA01,
+ },
+ [0xA02]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA02,
+ },
+ [0xA03]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xA03,
+ },
+ [0xA05]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA05,
+ },
+ [0xA06]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA06,
+ },
+ [0xA07]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA07,
+ },
+ [0xA08]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA08,
+ },
+ [0xA09]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA09,
+ },
+ [0xA0A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA0A,
+ },
+ [0xA0F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA0F,
+ },
+ [0xA10]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA10,
+ },
+ [0xA13]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA13,
+ },
+ [0xA14]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA14,
+ },
+ [0xA15]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA15,
+ },
+ [0xA16]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA16,
+ },
+ [0xA17]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA17,
+ },
+ [0xA18]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA18,
+ },
+ [0xA19]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA19,
+ },
+ [0xA1A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA1A,
+ },
+ [0xA1B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA1B,
+ },
+ [0xA1C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA1C,
+ },
+ [0xA1D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA1D,
+ },
+ [0xA1E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA1E,
+ },
+ [0xA1F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA1F,
+ },
+ [0xA20]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA20,
+ },
+ [0xA21]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA21,
+ },
+ [0xA22]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA22,
+ },
+ [0xA23]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA23,
+ },
+ [0xA24]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA24,
+ },
+ [0xA25]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA25,
+ },
+ [0xA26]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA26,
+ },
+ [0xA27]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA27,
+ },
+ [0xA28]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA28,
+ },
+ [0xA2A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA2A,
+ },
+ [0xA2B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA2B,
+ },
+ [0xA2C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA2C,
+ },
+ [0xA2D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA2D,
+ },
+ [0xA2E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA2E,
+ },
+ [0xA2F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA2F,
+ },
+ [0xA30]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="bs",
+ linebreak="al",
+ unicodeslot=0xA30,
+ },
+ [0xA32]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA32,
+ },
+ [0xA33]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xA32, 0xA3C },
+ unicodeslot=0xA33,
+ },
+ [0xA35]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA35,
+ },
+ [0xA36]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xA38, 0xA3C },
+ unicodeslot=0xA36,
+ },
+ [0xA38]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA38,
+ },
+ [0xA39]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA39,
+ },
+ [0xA3C]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="nukta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xA3C,
+ },
+ [0xA3E]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA3E,
+ },
+ [0xA3F]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0xA3F,
+ },
+ [0xA40]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA40,
+ },
+ [0xA41]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA41,
+ },
+ [0xA42]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA42,
+ },
+ [0xA47]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xA47,
+ },
+ [0xA48]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xA48,
+ },
+ [0xA4B]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xA4B,
+ },
+ [0xA4C]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xA4C,
+ },
+ [0xA4D]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xA4D,
+ },
+ [0xA51]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xA51,
+ },
+ [0xA59]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xA16, 0xA3C },
+ unicodeslot=0xA59,
+ },
+ [0xA5A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xA17, 0xA3C },
+ unicodeslot=0xA5A,
+ },
+ [0xA5B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xA1C, 0xA3C },
+ unicodeslot=0xA5B,
+ },
+ [0xA5C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA5C,
+ },
+ [0xA5E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xA2B, 0xA3C },
+ unicodeslot=0xA5E,
+ },
+ [0xA66]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA66,
+ },
+ [0xA67]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA67,
+ },
+ [0xA68]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA68,
+ },
+ [0xA69]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA69,
+ },
+ [0xA6A]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA6A,
+ },
+ [0xA6B]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA6B,
+ },
+ [0xA6C]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA6C,
+ },
+ [0xA6D]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA6D,
+ },
+ [0xA6E]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA6E,
+ },
+ [0xA6F]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA6F,
+ },
+ [0xA70]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA70,
+ },
+ [0xA71]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xA71,
+ },
+ [0xA72]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xA72,
+ },
+ [0xA73]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xA73,
+ },
+ [0xA74]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xA74,
+ },
+ [0xA75]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xA75,
+ },
+ [0xA76]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76,
+ },
+ [0xA81]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xA81,
+ },
+ [0xA82]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA82,
+ },
+ [0xA83]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xA83,
+ },
+ [0xA85]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA85,
+ },
+ [0xA86]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA86,
+ },
+ [0xA87]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA87,
+ },
+ [0xA88]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA88,
+ },
+ [0xA89]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA89,
+ },
+ [0xA8A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA8A,
+ },
+ [0xA8B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA8B,
+ },
+ [0xA8C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA8C,
+ },
+ [0xA8D]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA8D,
+ },
+ [0xA8F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA8F,
+ },
+ [0xA90]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA90,
+ },
+ [0xA91]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA91,
+ },
+ [0xA93]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA93,
+ },
+ [0xA94]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xA94,
+ },
+ [0xA95]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA95,
+ },
+ [0xA96]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA96,
+ },
+ [0xA97]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA97,
+ },
+ [0xA98]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA98,
+ },
+ [0xA99]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA99,
+ },
+ [0xA9A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA9A,
+ },
+ [0xA9B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA9B,
+ },
+ [0xA9C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA9C,
+ },
+ [0xA9D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA9D,
+ },
+ [0xA9E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA9E,
+ },
+ [0xA9F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xA9F,
+ },
+ [0xAA0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA0,
+ },
+ [0xAA1]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA1,
+ },
+ [0xAA2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA2,
+ },
+ [0xAA3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA3,
+ },
+ [0xAA4]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA4,
+ },
+ [0xAA5]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA5,
+ },
+ [0xAA6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA6,
+ },
+ [0xAA7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA7,
+ },
+ [0xAA8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAA8,
+ },
+ [0xAAA]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAAA,
+ },
+ [0xAAB]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAAB,
+ },
+ [0xAAC]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAAC,
+ },
+ [0xAAD]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAAD,
+ },
+ [0xAAE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAAE,
+ },
+ [0xAAF]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicorder="ap",
+ linebreak="al",
+ unicodeslot=0xAAF,
+ },
+ [0xAB0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="bp",
+ linebreak="al",
+ unicodeslot=0xAB0,
+ },
+ [0xAB2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB2,
+ },
+ [0xAB3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB3,
+ },
+ [0xAB5]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB5,
+ },
+ [0xAB6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB6,
+ },
+ [0xAB7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB7,
+ },
+ [0xAB8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB8,
+ },
+ [0xAB9]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xAB9,
+ },
+ [0xABC]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="nukta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xABC,
+ },
+ [0xABD]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xABD,
+ },
+ [0xABE]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xABE,
+ },
+ [0xABF]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0xABF,
+ },
+ [0xAC0]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAC0,
+ },
+ [0xAC1]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAC1,
+ },
+ [0xAC2]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAC2,
+ },
+ [0xAC3]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAC3,
+ },
+ [0xAC4]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAC4,
+ },
+ [0xAC5]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xAC5,
+ },
+ [0xAC7]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xAC7,
+ },
+ [0xAC8]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xAC8,
+ },
+ [0xAC9]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAC9,
+ },
+ [0xACB]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xACB,
+ },
+ [0xACC]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xACC,
+ },
+ [0xACD]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xACD,
+ },
+ [0xAD0]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xAD0,
+ },
+ [0xAE0]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xAE0,
+ },
+ [0xAE1]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xAE1,
+ },
+ [0xAE2]={
+ category="mn",
+ direction="nsm",
+ indic="i",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAE2,
+ },
+ [0xAE3]={
+ category="mn",
+ direction="nsm",
+ indic="i",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xAE3,
+ },
+ [0xAE6]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAE6,
+ },
+ [0xAE7]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAE7,
+ },
+ [0xAE8]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAE8,
+ },
+ [0xAE9]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAE9,
+ },
+ [0xAEA]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAEA,
+ },
+ [0xAEB]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAEB,
+ },
+ [0xAEC]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAEC,
+ },
+ [0xAED]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAED,
+ },
+ [0xAEE]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAEE,
+ },
+ [0xAEF]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xAEF,
+ },
+ [0xAF0]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xAF0,
+ },
+ [0xAF1]={
+ category="sc",
+ direction="et",
+ indic="o",
+ linebreak="pr",
+ unicodeslot=0xAF1,
+ },
+ [0xAF9]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xAF9,
+ },
+ [0xAFA]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xAFA,
+ },
+ [0xAFB]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xAFB,
+ },
+ [0xAFC]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xAFC,
+ },
+ [0xAFD]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xAFD,
+ },
+ [0xAFE]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xAFE,
+ },
+ [0xAFF]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xAFF,
+ },
+ [0xB01]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xB01,
+ },
+ [0xB02]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xB02,
+ },
+ [0xB03]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xB03,
+ },
+ [0xB05]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB05,
+ },
+ [0xB06]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB06,
+ },
+ [0xB07]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB07,
+ },
+ [0xB08]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB08,
+ },
+ [0xB09]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB09,
+ },
+ [0xB0A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB0A,
+ },
+ [0xB0B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB0B,
+ },
+ [0xB0C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB0C,
+ },
+ [0xB0F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB0F,
+ },
+ [0xB10]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB10,
+ },
+ [0xB13]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB13,
+ },
+ [0xB14]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB14,
+ },
+ [0xB15]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB15,
+ },
+ [0xB16]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB16,
+ },
+ [0xB17]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB17,
+ },
+ [0xB18]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB18,
+ },
+ [0xB19]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB19,
+ },
+ [0xB1A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB1A,
+ },
+ [0xB1B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB1B,
+ },
+ [0xB1C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB1C,
+ },
+ [0xB1D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB1D,
+ },
+ [0xB1E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB1E,
+ },
+ [0xB1F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB1F,
+ },
+ [0xB20]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB20,
+ },
+ [0xB21]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB21,
+ },
+ [0xB22]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB22,
+ },
+ [0xB23]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB23,
+ },
+ [0xB24]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB24,
+ },
+ [0xB25]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB25,
+ },
+ [0xB26]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB26,
+ },
+ [0xB27]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB27,
+ },
+ [0xB28]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB28,
+ },
+ [0xB2A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB2A,
+ },
+ [0xB2B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB2B,
+ },
+ [0xB2C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB2C,
+ },
+ [0xB2D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB2D,
+ },
+ [0xB2E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB2E,
+ },
+ [0xB2F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB2F,
+ },
+ [0xB30]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="am",
+ linebreak="al",
+ unicodeslot=0xB30,
+ },
+ [0xB32]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB32,
+ },
+ [0xB33]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB33,
+ },
+ [0xB35]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB35,
+ },
+ [0xB36]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB36,
+ },
+ [0xB37]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB37,
+ },
+ [0xB38]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB38,
+ },
+ [0xB39]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB39,
+ },
+ [0xB3C]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="nukta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xB3C,
+ },
+ [0xB3D]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB3D,
+ },
+ [0xB3E]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xB3E,
+ },
+ [0xB3F]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="am",
+ linebreak="cm",
+ unicodeslot=0xB3F,
+ },
+ [0xB40]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xB40,
+ },
+ [0xB41]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xB41,
+ },
+ [0xB42]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xB42,
+ },
+ [0xB43]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xB43,
+ },
+ [0xB44]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xB44,
+ },
+ [0xB47]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bh",
+ linebreak="cm",
+ unicodeslot=0xB47,
+ },
+ [0xB48]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xB47, 0xB56 },
+ unicodeslot=0xB48,
+ },
+ [0xB4B]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xB47, 0xB3E },
+ unicodeslot=0xB4B,
+ },
+ [0xB4C]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xB47, 0xB57 },
+ unicodeslot=0xB4C,
+ },
+ [0xB4D]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xB4D,
+ },
+ [0xB56]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="am",
+ linebreak="cm",
+ unicodeslot=0xB56,
+ },
+ [0xB57]={
+ category="mc",
+ direction="l",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xB57,
+ },
+ [0xB5C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xB21, 0xB3C },
+ unicodeslot=0xB5C,
+ },
+ [0xB5D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ specials={ "char", 0xB22, 0xB3C },
+ unicodeslot=0xB5D,
+ },
+ [0xB5F]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB5F,
+ },
+ [0xB60]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB60,
+ },
+ [0xB61]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB61,
+ },
+ [0xB62]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xB62,
+ },
+ [0xB63]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xB63,
+ },
+ [0xB66]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB66,
+ },
+ [0xB67]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB67,
+ },
+ [0xB68]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB68,
+ },
+ [0xB69]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB69,
+ },
+ [0xB6A]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB6A,
+ },
+ [0xB6B]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB6B,
+ },
+ [0xB6C]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB6C,
+ },
+ [0xB6D]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB6D,
+ },
+ [0xB6E]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB6E,
+ },
+ [0xB6F]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xB6F,
+ },
+ [0xB70]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB70,
+ },
+ [0xB71]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB71,
+ },
+ [0xB72]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB72,
+ },
+ [0xB73]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB73,
+ },
+ [0xB74]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB74,
+ },
+ [0xB75]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB75,
+ },
+ [0xB76]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB76,
+ },
+ [0xB77]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB77,
+ },
+ [0xB82]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xB82,
+ },
+ [0xB83]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xB83,
+ },
+ [0xB85]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB85,
+ },
+ [0xB86]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB86,
+ },
+ [0xB87]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB87,
+ },
+ [0xB88]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB88,
+ },
+ [0xB89]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB89,
+ },
+ [0xB8A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB8A,
+ },
+ [0xB8E]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB8E,
+ },
+ [0xB8F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB8F,
+ },
+ [0xB90]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB90,
+ },
+ [0xB92]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB92,
+ },
+ [0xB93]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xB93,
+ },
+ [0xB94]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ specials={ "char", 0xB92, 0xBD7 },
+ unicodeslot=0xB94,
+ },
+ [0xB95]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB95,
+ },
+ [0xB99]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB99,
+ },
+ [0xB9A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB9A,
+ },
+ [0xB9C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB9C,
+ },
+ [0xB9E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB9E,
+ },
+ [0xB9F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xB9F,
+ },
+ [0xBA3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBA3,
+ },
+ [0xBA4]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBA4,
+ },
+ [0xBA8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBA8,
+ },
+ [0xBA9]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBA9,
+ },
+ [0xBAA]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBAA,
+ },
+ [0xBAE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBAE,
+ },
+ [0xBAF]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBAF,
+ },
+ [0xBB0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="ap",
+ linebreak="al",
+ unicodeslot=0xBB0,
+ },
+ [0xBB1]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB1,
+ },
+ [0xBB2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB2,
+ },
+ [0xBB3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB3,
+ },
+ [0xBB4]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB4,
+ },
+ [0xBB5]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB5,
+ },
+ [0xBB6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB6,
+ },
+ [0xBB7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB7,
+ },
+ [0xBB8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB8,
+ },
+ [0xBB9]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xBB9,
+ },
+ [0xBBE]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xBBE,
+ },
+ [0xBBF]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xBBF,
+ },
+ [0xBC0]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xBC0,
+ },
+ [0xBC1]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xBC1,
+ },
+ [0xBC2]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="b",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xBC2,
+ },
+ [0xBC6]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bm",
+ linebreak="cm",
+ unicodeslot=0xBC6,
+ },
+ [0xBC7]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bm",
+ linebreak="cm",
+ unicodeslot=0xBC7,
+ },
+ [0xBC8]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bm",
+ linebreak="cm",
+ unicodeslot=0xBC8,
+ },
+ [0xBCA]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xBC6, 0xBBE },
+ unicodeslot=0xBCA,
+ },
+ [0xBCB]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xBC7, 0xBBE },
+ unicodeslot=0xBCB,
+ },
+ [0xBCC]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xBC6, 0xBD7 },
+ unicodeslot=0xBCC,
+ },
+ [0xBCD]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xBCD,
+ },
+ [0xBD0]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBD0,
+ },
+ [0xBD7]={
+ category="mc",
+ direction="l",
+ indic="o",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xBD7,
+ },
+ [0xBE6]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBE6,
+ },
+ [0xBE7]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBE7,
+ },
+ [0xBE8]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBE8,
+ },
+ [0xBE9]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBE9,
+ },
+ [0xBEA]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBEA,
+ },
+ [0xBEB]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBEB,
+ },
+ [0xBEC]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBEC,
+ },
+ [0xBED]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBED,
+ },
+ [0xBEE]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBEE,
+ },
+ [0xBEF]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xBEF,
+ },
+ [0xBF0]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF0,
+ },
+ [0xBF1]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF1,
+ },
+ [0xBF2]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF2,
+ },
+ [0xBF3]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF3,
+ },
+ [0xBF4]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF4,
+ },
+ [0xBF5]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF5,
+ },
+ [0xBF6]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF6,
+ },
+ [0xBF7]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF7,
+ },
+ [0xBF8]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBF8,
+ },
+ [0xBF9]={
+ category="sc",
+ direction="et",
+ indic="o",
+ linebreak="pr",
+ unicodeslot=0xBF9,
+ },
+ [0xBFA]={
+ category="so",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xBFA,
+ },
+ [0xC00]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC00,
+ },
+ [0xC01]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC01,
+ },
+ [0xC02]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC02,
+ },
+ [0xC03]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC03,
+ },
+ [0xC04]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xC04,
+ },
+ [0xC05]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC05,
+ },
+ [0xC06]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC06,
+ },
+ [0xC07]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC07,
+ },
+ [0xC08]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC08,
+ },
+ [0xC09]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC09,
+ },
+ [0xC0A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC0A,
+ },
+ [0xC0B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC0B,
+ },
+ [0xC0C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC0C,
+ },
+ [0xC0E]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC0E,
+ },
+ [0xC0F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC0F,
+ },
+ [0xC10]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC10,
+ },
+ [0xC12]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC12,
+ },
+ [0xC13]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC13,
+ },
+ [0xC14]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC14,
+ },
+ [0xC15]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC15,
+ },
+ [0xC16]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC16,
+ },
+ [0xC17]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC17,
+ },
+ [0xC18]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC18,
+ },
+ [0xC19]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC19,
+ },
+ [0xC1A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC1A,
+ },
+ [0xC1B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC1B,
+ },
+ [0xC1C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC1C,
+ },
+ [0xC1D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC1D,
+ },
+ [0xC1E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC1E,
+ },
+ [0xC1F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC1F,
+ },
+ [0xC20]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC20,
+ },
+ [0xC21]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC21,
+ },
+ [0xC22]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC22,
+ },
+ [0xC23]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC23,
+ },
+ [0xC24]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC24,
+ },
+ [0xC25]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC25,
+ },
+ [0xC26]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC26,
+ },
+ [0xC27]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC27,
+ },
+ [0xC28]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC28,
+ },
+ [0xC2A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC2A,
+ },
+ [0xC2B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC2B,
+ },
+ [0xC2C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC2C,
+ },
+ [0xC2D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC2D,
+ },
+ [0xC2E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC2E,
+ },
+ [0xC2F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC2F,
+ },
+ [0xC30]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="ap",
+ linebreak="al",
+ unicodeslot=0xC30,
+ },
+ [0xC31]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC31,
+ },
+ [0xC32]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC32,
+ },
+ [0xC33]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC33,
+ },
+ [0xC34]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC34,
+ },
+ [0xC35]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC35,
+ },
+ [0xC36]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC36,
+ },
+ [0xC37]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC37,
+ },
+ [0xC38]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC38,
+ },
+ [0xC39]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC39,
+ },
+ [0xC3D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC3D,
+ },
+ [0xC3E]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC3E,
+ },
+ [0xC3F]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC3F,
+ },
+ [0xC40]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC40,
+ },
+ [0xC41]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC41,
+ },
+ [0xC42]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC42,
+ },
+ [0xC43]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xC43,
+ },
+ [0xC44]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xC44,
+ },
+ [0xC46]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC46,
+ },
+ [0xC47]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC47,
+ },
+ [0xC48]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xC46, 0xC56 },
+ unicodeslot=0xC48,
+ },
+ [0xC4A]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC4A,
+ },
+ [0xC4B]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC4B,
+ },
+ [0xC4C]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC4C,
+ },
+ [0xC4D]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xC4D,
+ },
+ [0xC55]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC55,
+ },
+ [0xC56]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xC56,
+ },
+ [0xC58]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC58,
+ },
+ [0xC59]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC59,
+ },
+ [0xC5A]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC5A,
+ },
+ [0xC60]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC60,
+ },
+ [0xC61]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC61,
+ },
+ [0xC62]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xC62,
+ },
+ [0xC63]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xC63,
+ },
+ [0xC66]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC66,
+ },
+ [0xC67]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC67,
+ },
+ [0xC68]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC68,
+ },
+ [0xC69]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC69,
+ },
+ [0xC6A]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC6A,
+ },
+ [0xC6B]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC6B,
+ },
+ [0xC6C]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC6C,
+ },
+ [0xC6D]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC6D,
+ },
+ [0xC6E]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC6E,
+ },
+ [0xC6F]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xC6F,
+ },
+ [0xC77]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xC77,
+ },
+ [0xC78]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC78,
+ },
+ [0xC79]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC79,
+ },
+ [0xC7A]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC7A,
+ },
+ [0xC7B]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC7B,
+ },
+ [0xC7C]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC7C,
+ },
+ [0xC7D]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC7D,
+ },
+ [0xC7E]={
+ category="no",
+ direction="on",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC7E,
+ },
+ [0xC7F]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC7F,
+ },
+ [0xC80]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xC80,
+ },
+ [0xC81]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC81,
+ },
+ [0xC82]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC82,
+ },
+ [0xC83]={
+ category="mc",
+ direction="l",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xC83,
+ },
+ [0xC84]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xC84,
+ },
+ [0xC85]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC85,
+ },
+ [0xC86]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC86,
+ },
+ [0xC87]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC87,
+ },
+ [0xC88]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC88,
+ },
+ [0xC89]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC89,
+ },
+ [0xC8A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC8A,
+ },
+ [0xC8B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC8B,
+ },
+ [0xC8C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC8C,
+ },
+ [0xC8E]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC8E,
+ },
+ [0xC8F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC8F,
+ },
+ [0xC90]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC90,
+ },
+ [0xC92]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC92,
+ },
+ [0xC93]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC93,
+ },
+ [0xC94]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xC94,
+ },
+ [0xC95]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC95,
+ },
+ [0xC96]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC96,
+ },
+ [0xC97]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC97,
+ },
+ [0xC98]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC98,
+ },
+ [0xC99]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC99,
+ },
+ [0xC9A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC9A,
+ },
+ [0xC9B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC9B,
+ },
+ [0xC9C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC9C,
+ },
+ [0xC9D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC9D,
+ },
+ [0xC9E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC9E,
+ },
+ [0xC9F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xC9F,
+ },
+ [0xCA0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA0,
+ },
+ [0xCA1]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA1,
+ },
+ [0xCA2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA2,
+ },
+ [0xCA3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA3,
+ },
+ [0xCA4]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA4,
+ },
+ [0xCA5]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA5,
+ },
+ [0xCA6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA6,
+ },
+ [0xCA7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA7,
+ },
+ [0xCA8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCA8,
+ },
+ [0xCAA]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCAA,
+ },
+ [0xCAB]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCAB,
+ },
+ [0xCAC]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCAC,
+ },
+ [0xCAD]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCAD,
+ },
+ [0xCAE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCAE,
+ },
+ [0xCAF]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCAF,
+ },
+ [0xCB0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="ap",
+ linebreak="al",
+ unicodeslot=0xCB0,
+ },
+ [0xCB1]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB1,
+ },
+ [0xCB2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB2,
+ },
+ [0xCB3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB3,
+ },
+ [0xCB5]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB5,
+ },
+ [0xCB6]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB6,
+ },
+ [0xCB7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB7,
+ },
+ [0xCB8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB8,
+ },
+ [0xCB9]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCB9,
+ },
+ [0xCBC]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="nukta",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xCBC,
+ },
+ [0xCBD]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xCBD,
+ },
+ [0xCBE]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCBE,
+ },
+ [0xCBF]={
+ category="mn",
+ direction="l",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCBF,
+ },
+ [0xCC0]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xCBF, 0xCD5 },
+ unicodeslot=0xCC0,
+ },
+ [0xCC1]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCC1,
+ },
+ [0xCC2]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCC2,
+ },
+ [0xCC3]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xCC3,
+ },
+ [0xCC4]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xCC4,
+ },
+ [0xCC6]={
+ category="mn",
+ direction="l",
+ indic="d",
+ indicmark="t",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCC6,
+ },
+ [0xCC7]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xCC6, 0xCD5 },
+ unicodeslot=0xCC7,
+ },
+ [0xCC8]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xCC6, 0xCD6 },
+ unicodeslot=0xCC8,
+ },
+ [0xCCA]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xCC6, 0xCC2 },
+ unicodeslot=0xCCA,
+ },
+ [0xCCB]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xCCA, 0xCD5 },
+ unicodeslot=0xCCB,
+ },
+ [0xCCC]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="r",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCCC,
+ },
+ [0xCCD]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ linebreak="cm",
+ unicodeslot=0xCCD,
+ },
+ [0xCD5]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xCD5,
+ },
+ [0xCD6]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="b",
+ indicorder="as",
+ linebreak="cm",
+ unicodeslot=0xCD6,
+ },
+ [0xCDE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xCDE,
+ },
+ [0xCE0]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xCE0,
+ },
+ [0xCE1]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xCE1,
+ },
+ [0xCE2]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCE2,
+ },
+ [0xCE3]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ indicorder="bs",
+ linebreak="cm",
+ unicodeslot=0xCE3,
+ },
+ [0xCE6]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCE6,
+ },
+ [0xCE7]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCE7,
+ },
+ [0xCE8]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCE8,
+ },
+ [0xCE9]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCE9,
+ },
+ [0xCEA]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCEA,
+ },
+ [0xCEB]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCEB,
+ },
+ [0xCEC]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCEC,
+ },
+ [0xCED]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCED,
+ },
+ [0xCEE]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCEE,
+ },
+ [0xCEF]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xCEF,
+ },
+ [0xCF1]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xCF1,
+ },
+ [0xCF2]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xCF2,
+ },
+ [0xD00]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xD00,
+ },
+ [0xD01]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xD01,
+ },
+ [0xD02]={
+ category="mc",
+ direction="l",
+ indic="m",
+ linebreak="cm",
+ unicodeslot=0xD02,
+ },
+ [0xD03]={
+ category="mc",
+ direction="l",
+ indic="m",
+ linebreak="cm",
+ unicodeslot=0xD03,
+ },
+ [0xD05]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD05,
+ },
+ [0xD06]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD06,
+ },
+ [0xD07]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD07,
+ },
+ [0xD08]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD08,
+ },
+ [0xD09]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD09,
+ },
+ [0xD0A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD0A,
+ },
+ [0xD0B]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD0B,
+ },
+ [0xD0C]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD0C,
+ },
+ [0xD0E]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD0E,
+ },
+ [0xD0F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD0F,
+ },
+ [0xD10]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD10,
+ },
+ [0xD12]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD12,
+ },
+ [0xD13]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD13,
+ },
+ [0xD14]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD14,
+ },
+ [0xD15]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD15,
+ },
+ [0xD16]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD16,
+ },
+ [0xD17]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD17,
+ },
+ [0xD18]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD18,
+ },
+ [0xD19]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD19,
+ },
+ [0xD1A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD1A,
+ },
+ [0xD1B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD1B,
+ },
+ [0xD1C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD1C,
+ },
+ [0xD1D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD1D,
+ },
+ [0xD1E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD1E,
+ },
+ [0xD1F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD1F,
+ },
+ [0xD20]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD20,
+ },
+ [0xD21]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD21,
+ },
+ [0xD22]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD22,
+ },
+ [0xD23]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD23,
+ },
+ [0xD24]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD24,
+ },
+ [0xD25]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD25,
+ },
+ [0xD26]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD26,
+ },
+ [0xD27]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD27,
+ },
+ [0xD28]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD28,
+ },
+ [0xD29]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD29,
+ },
+ [0xD2A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD2A,
+ },
+ [0xD2B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD2B,
+ },
+ [0xD2C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD2C,
+ },
+ [0xD2D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD2D,
+ },
+ [0xD2E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD2E,
+ },
+ [0xD2F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD2F,
+ },
+ [0xD30]={
+ category="lo",
+ direction="l",
+ indic="c",
+ indicclass="ra",
+ indicorder="am",
+ linebreak="al",
+ unicodeslot=0xD30,
+ },
+ [0xD31]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD31,
+ },
+ [0xD32]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD32,
+ },
+ [0xD33]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD33,
+ },
+ [0xD34]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD34,
+ },
+ [0xD35]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD35,
+ },
+ [0xD36]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD36,
+ },
+ [0xD37]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD37,
+ },
+ [0xD38]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD38,
+ },
+ [0xD39]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD39,
+ },
+ [0xD3A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="al",
+ unicodeslot=0xD3A,
+ },
+ [0xD3B]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xD3B,
+ },
+ [0xD3C]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ linebreak="cm",
+ unicodeslot=0xD3C,
+ },
+ [0xD3D]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD3D,
+ },
+ [0xD3E]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD3E,
+ },
+ [0xD3F]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD3F,
+ },
+ [0xD40]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD40,
+ },
+ [0xD41]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD41,
+ },
+ [0xD42]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD42,
+ },
+ [0xD43]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD43,
+ },
+ [0xD44]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="r",
+ linebreak="cm",
+ unicodeslot=0xD44,
+ },
+ [0xD46]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bm",
+ linebreak="cm",
+ unicodeslot=0xD46,
+ },
+ [0xD47]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bm",
+ linebreak="cm",
+ unicodeslot=0xD47,
+ },
+ [0xD48]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ indicorder="bm",
+ linebreak="cm",
+ unicodeslot=0xD48,
+ },
+ [0xD4A]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xD46, 0xD3E },
+ unicodeslot=0xD4A,
+ },
+ [0xD4B]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xD47, 0xD3E },
+ unicodeslot=0xD4B,
+ },
+ [0xD4C]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="s",
+ linebreak="cm",
+ specials={ "char", 0xD46, 0xD57 },
+ unicodeslot=0xD4C,
+ },
+ [0xD4D]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicclass="halant",
+ linebreak="cm",
+ unicodeslot=0xD4D,
+ },
+ [0xD4E]={
+ category="lo",
+ direction="l",
+ indic="o",
+ indicmark="t",
+ linebreak="al",
+ unicodeslot=0xD4E,
+ },
+ [0xD4F]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD4F,
+ },
+ [0xD54]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD54,
+ },
+ [0xD55]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD55,
+ },
+ [0xD56]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD56,
+ },
+ [0xD57]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ indicorder="ap",
+ linebreak="cm",
+ unicodeslot=0xD57,
+ },
+ [0xD58]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD58,
+ },
+ [0xD59]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD59,
+ },
+ [0xD5A]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD5A,
+ },
+ [0xD5B]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD5B,
+ },
+ [0xD5C]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD5C,
+ },
+ [0xD5D]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD5D,
+ },
+ [0xD5E]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD5E,
+ },
+ [0xD5F]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD5F,
+ },
+ [0xD60]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD60,
+ },
+ [0xD61]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="al",
+ unicodeslot=0xD61,
+ },
+ [0xD62]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xD62,
+ },
+ [0xD63]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="cm",
+ unicodeslot=0xD63,
+ },
+ [0xD66]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD66,
+ },
+ [0xD67]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD67,
+ },
+ [0xD68]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD68,
+ },
+ [0xD69]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD69,
+ },
+ [0xD6A]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD6A,
+ },
+ [0xD6B]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD6B,
+ },
+ [0xD6C]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD6C,
+ },
+ [0xD6D]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD6D,
+ },
+ [0xD6E]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD6E,
+ },
+ [0xD6F]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xD6F,
+ },
+ [0xD70]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD70,
+ },
+ [0xD71]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD71,
+ },
+ [0xD72]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD72,
+ },
+ [0xD73]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD73,
+ },
+ [0xD74]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD74,
+ },
+ [0xD75]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD75,
+ },
+ [0xD76]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD76,
+ },
+ [0xD77]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD77,
+ },
+ [0xD78]={
+ category="no",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD78,
+ },
+ [0xD79]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="po",
+ unicodeslot=0xD79,
+ },
+ [0xD7A]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD7A,
+ },
+ [0xD7B]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD7B,
+ },
+ [0xD7C]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD7C,
+ },
+ [0xD7D]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD7D,
+ },
+ [0xD7E]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD7E,
+ },
+ [0xD7F]={
+ category="lo",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0xD7F,
+ },
+ [0xD82]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xD82,
+ },
+ [0xD83]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xD83,
+ },
+ [0xD85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD85,
+ },
+ [0xD86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD86,
+ },
+ [0xD87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD87,
+ },
+ [0xD88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD88,
+ },
+ [0xD89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD89,
+ },
+ [0xD8A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8A,
+ },
+ [0xD8B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8B,
+ },
+ [0xD8C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8C,
+ },
+ [0xD8D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8D,
+ },
+ [0xD8E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8E,
+ },
+ [0xD8F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD8F,
+ },
+ [0xD90]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD90,
+ },
+ [0xD91]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD91,
+ },
+ [0xD92]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD92,
+ },
+ [0xD93]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD93,
+ },
+ [0xD94]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD94,
+ },
+ [0xD95]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD95,
+ },
+ [0xD96]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD96,
+ },
+ [0xD9A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD9A,
+ },
+ [0xD9B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD9B,
+ },
+ [0xD9C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD9C,
+ },
+ [0xD9D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD9D,
+ },
+ [0xD9E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD9E,
+ },
+ [0xD9F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xD9F,
+ },
+ [0xDA0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA0,
+ },
+ [0xDA1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA1,
+ },
+ [0xDA2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA2,
+ },
+ [0xDA3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA3,
+ },
+ [0xDA4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA4,
+ },
+ [0xDA5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA5,
+ },
+ [0xDA6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA6,
+ },
+ [0xDA7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA7,
+ },
+ [0xDA8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA8,
+ },
+ [0xDA9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDA9,
+ },
+ [0xDAA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDAA,
+ },
+ [0xDAB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDAB,
+ },
+ [0xDAC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDAC,
+ },
+ [0xDAD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDAD,
+ },
+ [0xDAE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDAE,
+ },
+ [0xDAF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDAF,
+ },
+ [0xDB0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB0,
+ },
+ [0xDB1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB1,
+ },
+ [0xDB3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB3,
+ },
+ [0xDB4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB4,
+ },
+ [0xDB5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB5,
+ },
+ [0xDB6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB6,
+ },
+ [0xDB7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB7,
+ },
+ [0xDB8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB8,
+ },
+ [0xDB9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDB9,
+ },
+ [0xDBA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDBA,
+ },
+ [0xDBB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDBB,
+ },
+ [0xDBD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDBD,
+ },
+ [0xDC0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC0,
+ },
+ [0xDC1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC1,
+ },
+ [0xDC2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC2,
+ },
+ [0xDC3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC3,
+ },
+ [0xDC4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC4,
+ },
+ [0xDC5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC5,
+ },
+ [0xDC6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDC6,
+ },
+ [0xDCA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xDCA,
+ },
+ [0xDCF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDCF,
+ },
+ [0xDD0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDD0,
+ },
+ [0xDD1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDD1,
+ },
+ [0xDD2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xDD2,
+ },
+ [0xDD3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xDD3,
+ },
+ [0xDD4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xDD4,
+ },
+ [0xDD6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xDD6,
+ },
+ [0xDD8]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDD8,
+ },
+ [0xDD9]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDD9,
+ },
+ [0xDDA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0xDD9, 0xDCA },
+ unicodeslot=0xDDA,
+ },
+ [0xDDB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDDB,
+ },
+ [0xDDC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0xDD9, 0xDCF },
+ unicodeslot=0xDDC,
+ },
+ [0xDDD]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0xDDC, 0xDCA },
+ unicodeslot=0xDDD,
+ },
+ [0xDDE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0xDD9, 0xDDF },
+ unicodeslot=0xDDE,
+ },
+ [0xDDF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDDF,
+ },
+ [0xDE6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDE6,
+ },
+ [0xDE7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDE7,
+ },
+ [0xDE8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDE8,
+ },
+ [0xDE9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDE9,
+ },
+ [0xDEA]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDEA,
+ },
+ [0xDEB]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDEB,
+ },
+ [0xDEC]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDEC,
+ },
+ [0xDED]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDED,
+ },
+ [0xDEE]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDEE,
+ },
+ [0xDEF]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xDEF,
+ },
+ [0xDF2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDF2,
+ },
+ [0xDF3]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xDF3,
+ },
+ [0xDF4]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xDF4,
+ },
+ [0xE01]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE01,
+ },
+ [0xE02]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE02,
+ },
+ [0xE03]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE03,
+ },
+ [0xE04]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE04,
+ },
+ [0xE05]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE05,
+ },
+ [0xE06]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE06,
+ },
+ [0xE07]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE07,
+ },
+ [0xE08]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE08,
+ },
+ [0xE09]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE09,
+ },
+ [0xE0A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE0A,
+ },
+ [0xE0B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE0B,
+ },
+ [0xE0C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE0C,
+ },
+ [0xE0D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE0D,
+ },
+ [0xE0E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE0E,
+ },
+ [0xE0F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE0F,
+ },
+ [0xE10]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE10,
+ },
+ [0xE11]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE11,
+ },
+ [0xE12]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE12,
+ },
+ [0xE13]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE13,
+ },
+ [0xE14]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE14,
+ },
+ [0xE15]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE15,
+ },
+ [0xE16]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE16,
+ },
+ [0xE17]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE17,
+ },
+ [0xE18]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE18,
+ },
+ [0xE19]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE19,
+ },
+ [0xE1A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE1A,
+ },
+ [0xE1B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE1B,
+ },
+ [0xE1C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE1C,
+ },
+ [0xE1D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE1D,
+ },
+ [0xE1E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE1E,
+ },
+ [0xE1F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE1F,
+ },
+ [0xE20]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE20,
+ },
+ [0xE21]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE21,
+ },
+ [0xE22]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE22,
+ },
+ [0xE23]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE23,
+ },
+ [0xE24]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE24,
+ },
+ [0xE25]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE25,
+ },
+ [0xE26]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE26,
+ },
+ [0xE27]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE27,
+ },
+ [0xE28]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE28,
+ },
+ [0xE29]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE29,
+ },
+ [0xE2A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE2A,
+ },
+ [0xE2B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE2B,
+ },
+ [0xE2C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE2C,
+ },
+ [0xE2D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE2D,
+ },
+ [0xE2E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE2E,
+ },
+ [0xE2F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE2F,
+ },
+ [0xE30]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE30,
+ },
+ [0xE31]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE31,
+ },
+ [0xE32]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE32,
+ },
+ [0xE33]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ specials={ "compat", 0xE4D, 0xE32 },
+ unicodeslot=0xE33,
+ },
+ [0xE34]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE34,
+ },
+ [0xE35]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE35,
+ },
+ [0xE36]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE36,
+ },
+ [0xE37]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE37,
+ },
+ [0xE38]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE38,
+ },
+ [0xE39]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE39,
+ },
+ [0xE3A]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE3A,
+ },
+ [0xE3F]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0xE3F,
+ },
+ [0xE40]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE40,
+ },
+ [0xE41]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE41,
+ },
+ [0xE42]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE42,
+ },
+ [0xE43]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE43,
+ },
+ [0xE44]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE44,
+ },
+ [0xE45]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE45,
+ },
+ [0xE46]={
+ category="lm",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE46,
+ },
+ [0xE47]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE47,
+ },
+ [0xE48]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE48,
+ },
+ [0xE49]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE49,
+ },
+ [0xE4A]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE4A,
+ },
+ [0xE4B]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE4B,
+ },
+ [0xE4C]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE4C,
+ },
+ [0xE4D]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE4D,
+ },
+ [0xE4E]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xE4E,
+ },
+ [0xE4F]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xE4F,
+ },
+ [0xE50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE50,
+ },
+ [0xE51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE51,
+ },
+ [0xE52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE52,
+ },
+ [0xE53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE53,
+ },
+ [0xE54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE54,
+ },
+ [0xE55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE55,
+ },
+ [0xE56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE56,
+ },
+ [0xE57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE57,
+ },
+ [0xE58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE58,
+ },
+ [0xE59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xE59,
+ },
+ [0xE5A]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xE5A,
+ },
+ [0xE5B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xE5B,
+ },
+ [0xE81]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE81,
+ },
+ [0xE82]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE82,
+ },
+ [0xE84]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE84,
+ },
+ [0xE86]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE86,
+ },
+ [0xE87]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE87,
+ },
+ [0xE88]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE88,
+ },
+ [0xE89]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE89,
+ },
+ [0xE8A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE8A,
+ },
+ [0xE8C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE8C,
+ },
+ [0xE8D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE8D,
+ },
+ [0xE8E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE8E,
+ },
+ [0xE8F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE8F,
+ },
+ [0xE90]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE90,
+ },
+ [0xE91]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE91,
+ },
+ [0xE92]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE92,
+ },
+ [0xE93]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE93,
+ },
+ [0xE94]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE94,
+ },
+ [0xE95]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE95,
+ },
+ [0xE96]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE96,
+ },
+ [0xE97]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE97,
+ },
+ [0xE98]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE98,
+ },
+ [0xE99]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE99,
+ },
+ [0xE9A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE9A,
+ },
+ [0xE9B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE9B,
+ },
+ [0xE9C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE9C,
+ },
+ [0xE9D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE9D,
+ },
+ [0xE9E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE9E,
+ },
+ [0xE9F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xE9F,
+ },
+ [0xEA0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA0,
+ },
+ [0xEA1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA1,
+ },
+ [0xEA2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA2,
+ },
+ [0xEA3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA3,
+ },
+ [0xEA5]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA5,
+ },
+ [0xEA7]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA7,
+ },
+ [0xEA8]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA8,
+ },
+ [0xEA9]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEA9,
+ },
+ [0xEAA]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEAA,
+ },
+ [0xEAB]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEAB,
+ },
+ [0xEAC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEAC,
+ },
+ [0xEAD]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEAD,
+ },
+ [0xEAE]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEAE,
+ },
+ [0xEAF]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEAF,
+ },
+ [0xEB0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEB0,
+ },
+ [0xEB1]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB1,
+ },
+ [0xEB2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEB2,
+ },
+ [0xEB3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ specials={ "compat", 0xECD, 0xEB2 },
+ unicodeslot=0xEB3,
+ },
+ [0xEB4]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB4,
+ },
+ [0xEB5]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB5,
+ },
+ [0xEB6]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB6,
+ },
+ [0xEB7]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB7,
+ },
+ [0xEB8]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB8,
+ },
+ [0xEB9]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEB9,
+ },
+ [0xEBA]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEBA,
+ },
+ [0xEBB]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEBB,
+ },
+ [0xEBC]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEBC,
+ },
+ [0xEBD]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEBD,
+ },
+ [0xEC0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEC0,
+ },
+ [0xEC1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEC1,
+ },
+ [0xEC2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEC2,
+ },
+ [0xEC3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEC3,
+ },
+ [0xEC4]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEC4,
+ },
+ [0xEC6]={
+ category="lm",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEC6,
+ },
+ [0xEC8]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEC8,
+ },
+ [0xEC9]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xEC9,
+ },
+ [0xECA]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xECA,
+ },
+ [0xECB]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xECB,
+ },
+ [0xECC]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xECC,
+ },
+ [0xECD]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xECD,
+ },
+ [0xED0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED0,
+ },
+ [0xED1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED1,
+ },
+ [0xED2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED2,
+ },
+ [0xED3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED3,
+ },
+ [0xED4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED4,
+ },
+ [0xED5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED5,
+ },
+ [0xED6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED6,
+ },
+ [0xED7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED7,
+ },
+ [0xED8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED8,
+ },
+ [0xED9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xED9,
+ },
+ [0xEDC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ specials={ "compat", 0xEAB, 0xE99 },
+ unicodeslot=0xEDC,
+ },
+ [0xEDD]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ specials={ "compat", 0xEAB, 0xEA1 },
+ unicodeslot=0xEDD,
+ },
+ [0xEDE]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEDE,
+ },
+ [0xEDF]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xEDF,
+ },
+ [0xF00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF00,
+ },
+ [0xF01]={
+ category="so",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF01,
+ },
+ [0xF02]={
+ category="so",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF02,
+ },
+ [0xF03]={
+ category="so",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF03,
+ },
+ [0xF04]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF04,
+ },
+ [0xF05]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF05,
+ },
+ [0xF06]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF06,
+ },
+ [0xF07]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF07,
+ },
+ [0xF08]={
+ category="po",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0xF08,
+ },
+ [0xF09]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF09,
+ },
+ [0xF0A]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xF0A,
+ },
+ [0xF0B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xF0B,
+ },
+ [0xF0C]={
+ category="po",
+ direction="l",
+ linebreak="gl",
+ specials={ "nobreak", 0xF0B },
+ unicodeslot=0xF0C,
+ },
+ [0xF0D]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0xF0D,
+ },
+ [0xF0E]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0xF0E,
+ },
+ [0xF0F]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0xF0F,
+ },
+ [0xF10]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0xF10,
+ },
+ [0xF11]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0xF11,
+ },
+ [0xF12]={
+ category="po",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0xF12,
+ },
+ [0xF13]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF13,
+ },
+ [0xF14]={
+ category="so",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0xF14,
+ },
+ [0xF15]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF15,
+ },
+ [0xF16]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF16,
+ },
+ [0xF17]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF17,
+ },
+ [0xF18]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF18,
+ },
+ [0xF19]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF19,
+ },
+ [0xF1A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF1A,
+ },
+ [0xF1B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF1B,
+ },
+ [0xF1C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF1C,
+ },
+ [0xF1D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF1D,
+ },
+ [0xF1E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF1E,
+ },
+ [0xF1F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF1F,
+ },
+ [0xF20]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF20,
+ },
+ [0xF21]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF21,
+ },
+ [0xF22]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF22,
+ },
+ [0xF23]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF23,
+ },
+ [0xF24]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF24,
+ },
+ [0xF25]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF25,
+ },
+ [0xF26]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF26,
+ },
+ [0xF27]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF27,
+ },
+ [0xF28]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF28,
+ },
+ [0xF29]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xF29,
+ },
+ [0xF2A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF2A,
+ },
+ [0xF2B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF2B,
+ },
+ [0xF2C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF2C,
+ },
+ [0xF2D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF2D,
+ },
+ [0xF2E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF2E,
+ },
+ [0xF2F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF2F,
+ },
+ [0xF30]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF30,
+ },
+ [0xF31]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF31,
+ },
+ [0xF32]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF32,
+ },
+ [0xF33]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF33,
+ },
+ [0xF34]={
+ category="so",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xF34,
+ },
+ [0xF35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF35,
+ },
+ [0xF36]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF36,
+ },
+ [0xF37]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF37,
+ },
+ [0xF38]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF38,
+ },
+ [0xF39]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF39,
+ },
+ [0xF3A]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xF3B,
+ unicodeslot=0xF3A,
+ },
+ [0xF3B]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xF3A,
+ unicodeslot=0xF3B,
+ },
+ [0xF3C]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xF3D,
+ unicodeslot=0xF3C,
+ },
+ [0xF3D]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xF3C,
+ unicodeslot=0xF3D,
+ },
+ [0xF3E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xF3E,
+ },
+ [0xF3F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xF3F,
+ },
+ [0xF40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF40,
+ },
+ [0xF41]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF41,
+ },
+ [0xF42]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF42,
+ },
+ [0xF43]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF42, 0xFB7 },
+ unicodeslot=0xF43,
+ },
+ [0xF44]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF44,
+ },
+ [0xF45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF45,
+ },
+ [0xF46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF46,
+ },
+ [0xF47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF47,
+ },
+ [0xF49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF49,
+ },
+ [0xF4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF4A,
+ },
+ [0xF4B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF4B,
+ },
+ [0xF4C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF4C,
+ },
+ [0xF4D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF4C, 0xFB7 },
+ unicodeslot=0xF4D,
+ },
+ [0xF4E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF4E,
+ },
+ [0xF4F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF4F,
+ },
+ [0xF50]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF50,
+ },
+ [0xF51]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF51,
+ },
+ [0xF52]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF51, 0xFB7 },
+ unicodeslot=0xF52,
+ },
+ [0xF53]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF53,
+ },
+ [0xF54]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF54,
+ },
+ [0xF55]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF55,
+ },
+ [0xF56]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF56,
+ },
+ [0xF57]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF56, 0xFB7 },
+ unicodeslot=0xF57,
+ },
+ [0xF58]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF58,
+ },
+ [0xF59]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF59,
+ },
+ [0xF5A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF5A,
+ },
+ [0xF5B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF5B,
+ },
+ [0xF5C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF5B, 0xFB7 },
+ unicodeslot=0xF5C,
+ },
+ [0xF5D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF5D,
+ },
+ [0xF5E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF5E,
+ },
+ [0xF5F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF5F,
+ },
+ [0xF60]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF60,
+ },
+ [0xF61]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF61,
+ },
+ [0xF62]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF62,
+ },
+ [0xF63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF63,
+ },
+ [0xF64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF64,
+ },
+ [0xF65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF65,
+ },
+ [0xF66]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF66,
+ },
+ [0xF67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF67,
+ },
+ [0xF68]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF68,
+ },
+ [0xF69]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF40, 0xFB5 },
+ unicodeslot=0xF69,
+ },
+ [0xF6A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF6A,
+ },
+ [0xF6B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF6B,
+ },
+ [0xF6C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF6C,
+ },
+ [0xF71]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF71,
+ },
+ [0xF72]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF72,
+ },
+ [0xF73]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xF71, 0xF72 },
+ unicodeslot=0xF73,
+ },
+ [0xF74]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF74,
+ },
+ [0xF75]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xF71, 0xF74 },
+ unicodeslot=0xF75,
+ },
+ [0xF76]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xFB2, 0xF80 },
+ unicodeslot=0xF76,
+ },
+ [0xF77]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "compat", 0xFB2, 0xF81 },
+ unicodeslot=0xF77,
+ },
+ [0xF78]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xFB3, 0xF80 },
+ unicodeslot=0xF78,
+ },
+ [0xF79]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "compat", 0xFB3, 0xF81 },
+ unicodeslot=0xF79,
+ },
+ [0xF7A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF7A,
+ },
+ [0xF7B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF7B,
+ },
+ [0xF7C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF7C,
+ },
+ [0xF7D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF7D,
+ },
+ [0xF7E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF7E,
+ },
+ [0xF7F]={
+ category="mc",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xF7F,
+ },
+ [0xF80]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF80,
+ },
+ [0xF81]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xF71, 0xF80 },
+ unicodeslot=0xF81,
+ },
+ [0xF82]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF82,
+ },
+ [0xF83]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF83,
+ },
+ [0xF84]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF84,
+ },
+ [0xF85]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xF85,
+ },
+ [0xF86]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF86,
+ },
+ [0xF87]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF87,
+ },
+ [0xF88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF88,
+ },
+ [0xF89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF89,
+ },
+ [0xF8A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF8A,
+ },
+ [0xF8B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF8B,
+ },
+ [0xF8C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xF8C,
+ },
+ [0xF8D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF8D,
+ },
+ [0xF8E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF8E,
+ },
+ [0xF8F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF8F,
+ },
+ [0xF90]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF90,
+ },
+ [0xF91]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF91,
+ },
+ [0xF92]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF92,
+ },
+ [0xF93]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xF92, 0xFB7 },
+ unicodeslot=0xF93,
+ },
+ [0xF94]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF94,
+ },
+ [0xF95]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF95,
+ },
+ [0xF96]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF96,
+ },
+ [0xF97]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF97,
+ },
+ [0xF99]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF99,
+ },
+ [0xF9A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF9A,
+ },
+ [0xF9B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF9B,
+ },
+ [0xF9C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF9C,
+ },
+ [0xF9D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xF9C, 0xFB7 },
+ unicodeslot=0xF9D,
+ },
+ [0xF9E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF9E,
+ },
+ [0xF9F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xF9F,
+ },
+ [0xFA0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA0,
+ },
+ [0xFA1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA1,
+ },
+ [0xFA2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xFA1, 0xFB7 },
+ unicodeslot=0xFA2,
+ },
+ [0xFA3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA3,
+ },
+ [0xFA4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA4,
+ },
+ [0xFA5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA5,
+ },
+ [0xFA6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA6,
+ },
+ [0xFA7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xFA6, 0xFB7 },
+ unicodeslot=0xFA7,
+ },
+ [0xFA8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA8,
+ },
+ [0xFA9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFA9,
+ },
+ [0xFAA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFAA,
+ },
+ [0xFAB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFAB,
+ },
+ [0xFAC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xFAB, 0xFB7 },
+ unicodeslot=0xFAC,
+ },
+ [0xFAD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFAD,
+ },
+ [0xFAE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFAE,
+ },
+ [0xFAF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFAF,
+ },
+ [0xFB0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB0,
+ },
+ [0xFB1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB1,
+ },
+ [0xFB2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB2,
+ },
+ [0xFB3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB3,
+ },
+ [0xFB4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB4,
+ },
+ [0xFB5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB5,
+ },
+ [0xFB6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB6,
+ },
+ [0xFB7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB7,
+ },
+ [0xFB8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB8,
+ },
+ [0xFB9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0xF90, 0xFB5 },
+ unicodeslot=0xFB9,
+ },
+ [0xFBA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFBA,
+ },
+ [0xFBB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFBB,
+ },
+ [0xFBC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFBC,
+ },
+ [0xFBE]={
+ category="so",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xFBE,
+ },
+ [0xFBF]={
+ category="so",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xFBF,
+ },
+ [0xFC0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC0,
+ },
+ [0xFC1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC1,
+ },
+ [0xFC2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC2,
+ },
+ [0xFC3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC3,
+ },
+ [0xFC4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC4,
+ },
+ [0xFC5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC5,
+ },
+ [0xFC6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFC6,
+ },
+ [0xFC7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC7,
+ },
+ [0xFC8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC8,
+ },
+ [0xFC9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFC9,
+ },
+ [0xFCA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFCA,
+ },
+ [0xFCB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFCB,
+ },
+ [0xFCC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFCC,
+ },
+ [0xFCE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFCE,
+ },
+ [0xFCF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFCF,
+ },
+ [0xFD0]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xFD0,
+ },
+ [0xFD1]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xFD1,
+ },
+ [0xFD2]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xFD2,
+ },
+ [0xFD3]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xFD3,
+ },
+ [0xFD4]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFD4,
+ },
+ [0xFD5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFD5,
+ },
+ [0xFD6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFD6,
+ },
+ [0xFD7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFD7,
+ },
+ [0xFD8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xFD8,
+ },
+ [0xFD9]={
+ category="po",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0xFD9,
+ },
+ [0xFDA]={
+ category="po",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0xFDA,
+ },
+ [0x1000]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1000,
+ },
+ [0x1001]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1001,
+ },
+ [0x1002]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1002,
+ },
+ [0x1003]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1003,
+ },
+ [0x1004]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1004,
+ },
+ [0x1005]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1005,
+ },
+ [0x1006]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1006,
+ },
+ [0x1007]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1007,
+ },
+ [0x1008]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1008,
+ },
+ [0x1009]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1009,
+ },
+ [0x100A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x100A,
+ },
+ [0x100B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x100B,
+ },
+ [0x100C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x100C,
+ },
+ [0x100D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x100D,
+ },
+ [0x100E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x100E,
+ },
+ [0x100F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x100F,
+ },
+ [0x1010]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1010,
+ },
+ [0x1011]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1011,
+ },
+ [0x1012]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1012,
+ },
+ [0x1013]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1013,
+ },
+ [0x1014]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1014,
+ },
+ [0x1015]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1015,
+ },
+ [0x1016]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1016,
+ },
+ [0x1017]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1017,
+ },
+ [0x1018]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1018,
+ },
+ [0x1019]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1019,
+ },
+ [0x101A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x101A,
+ },
+ [0x101B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x101B,
+ },
+ [0x101C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x101C,
+ },
+ [0x101D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x101D,
+ },
+ [0x101E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x101E,
+ },
+ [0x101F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x101F,
+ },
+ [0x1020]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1020,
+ },
+ [0x1021]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1021,
+ },
+ [0x1022]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1022,
+ },
+ [0x1023]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1023,
+ },
+ [0x1024]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1024,
+ },
+ [0x1025]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1025,
+ },
+ [0x1026]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ specials={ "char", 0x1025, 0x102E },
+ unicodeslot=0x1026,
+ },
+ [0x1027]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1027,
+ },
+ [0x1028]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1028,
+ },
+ [0x1029]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1029,
+ },
+ [0x102A]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x102A,
+ },
+ [0x102B]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x102B,
+ },
+ [0x102C]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x102C,
+ },
+ [0x102D]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x102D,
+ },
+ [0x102E]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x102E,
+ },
+ [0x102F]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x102F,
+ },
+ [0x1030]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1030,
+ },
+ [0x1031]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ linebreak="sa",
+ unicodeslot=0x1031,
+ },
+ [0x1032]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1032,
+ },
+ [0x1033]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1033,
+ },
+ [0x1034]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1034,
+ },
+ [0x1035]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1035,
+ },
+ [0x1036]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1036,
+ },
+ [0x1037]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1037,
+ },
+ [0x1038]={
+ category="mc",
+ direction="l",
+ indic="m",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1038,
+ },
+ [0x1039]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1039,
+ },
+ [0x103A]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x103A,
+ },
+ [0x103B]={
+ category="mc",
+ direction="l",
+ indic="c",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x103B,
+ },
+ [0x103C]={
+ category="mc",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x103C,
+ },
+ [0x103D]={
+ category="mn",
+ direction="nsm",
+ indic="c",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x103D,
+ },
+ [0x103E]={
+ category="mn",
+ direction="nsm",
+ indic="c",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x103E,
+ },
+ [0x103F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x103F,
+ },
+ [0x1040]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1040,
+ },
+ [0x1041]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1041,
+ },
+ [0x1042]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1042,
+ },
+ [0x1043]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1043,
+ },
+ [0x1044]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1044,
+ },
+ [0x1045]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1045,
+ },
+ [0x1046]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1046,
+ },
+ [0x1047]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1047,
+ },
+ [0x1048]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1048,
+ },
+ [0x1049]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1049,
+ },
+ [0x104A]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="ba",
+ unicodeslot=0x104A,
+ },
+ [0x104B]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="ba",
+ unicodeslot=0x104B,
+ },
+ [0x104C]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x104C,
+ },
+ [0x104D]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x104D,
+ },
+ [0x104E]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x104E,
+ },
+ [0x104F]={
+ category="po",
+ direction="l",
+ indic="o",
+ linebreak="al",
+ unicodeslot=0x104F,
+ },
+ [0x1050]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1050,
+ },
+ [0x1051]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1051,
+ },
+ [0x1052]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1052,
+ },
+ [0x1053]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1053,
+ },
+ [0x1054]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1054,
+ },
+ [0x1055]={
+ category="lo",
+ direction="l",
+ indic="i",
+ linebreak="sa",
+ unicodeslot=0x1055,
+ },
+ [0x1056]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1056,
+ },
+ [0x1057]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1057,
+ },
+ [0x1058]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1058,
+ },
+ [0x1059]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1059,
+ },
+ [0x105A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x105A,
+ },
+ [0x105B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x105B,
+ },
+ [0x105C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x105C,
+ },
+ [0x105D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x105D,
+ },
+ [0x105E]={
+ category="mn",
+ direction="nsm",
+ indic="c",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x105E,
+ },
+ [0x105F]={
+ category="mn",
+ direction="nsm",
+ indic="c",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x105F,
+ },
+ [0x1060]={
+ category="mn",
+ direction="nsm",
+ indic="c",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1060,
+ },
+ [0x1061]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1061,
+ },
+ [0x1062]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1062,
+ },
+ [0x1063]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1063,
+ },
+ [0x1064]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1064,
+ },
+ [0x1065]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1065,
+ },
+ [0x1066]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1066,
+ },
+ [0x1067]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1067,
+ },
+ [0x1068]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1068,
+ },
+ [0x1069]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1069,
+ },
+ [0x106A]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x106A,
+ },
+ [0x106B]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x106B,
+ },
+ [0x106C]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x106C,
+ },
+ [0x106D]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x106D,
+ },
+ [0x106E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x106E,
+ },
+ [0x106F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x106F,
+ },
+ [0x1070]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1070,
+ },
+ [0x1071]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1071,
+ },
+ [0x1072]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1072,
+ },
+ [0x1073]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1073,
+ },
+ [0x1074]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1074,
+ },
+ [0x1075]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1075,
+ },
+ [0x1076]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1076,
+ },
+ [0x1077]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1077,
+ },
+ [0x1078]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1078,
+ },
+ [0x1079]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1079,
+ },
+ [0x107A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x107A,
+ },
+ [0x107B]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x107B,
+ },
+ [0x107C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x107C,
+ },
+ [0x107D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x107D,
+ },
+ [0x107E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x107E,
+ },
+ [0x107F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x107F,
+ },
+ [0x1080]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1080,
+ },
+ [0x1081]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x1081,
+ },
+ [0x1082]={
+ category="mn",
+ direction="nsm",
+ indic="c",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x1082,
+ },
+ [0x1083]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1083,
+ },
+ [0x1084]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="l",
+ linebreak="sa",
+ unicodeslot=0x1084,
+ },
+ [0x1085]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1085,
+ },
+ [0x1086]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x1086,
+ },
+ [0x1087]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1087,
+ },
+ [0x1088]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1088,
+ },
+ [0x1089]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x1089,
+ },
+ [0x108A]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x108A,
+ },
+ [0x108B]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x108B,
+ },
+ [0x108C]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x108C,
+ },
+ [0x108D]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicmark="b",
+ linebreak="sa",
+ unicodeslot=0x108D,
+ },
+ [0x108E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0x108E,
+ },
+ [0x108F]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x108F,
+ },
+ [0x1090]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1090,
+ },
+ [0x1091]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1091,
+ },
+ [0x1092]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1092,
+ },
+ [0x1093]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1093,
+ },
+ [0x1094]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1094,
+ },
+ [0x1095]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1095,
+ },
+ [0x1096]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1096,
+ },
+ [0x1097]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1097,
+ },
+ [0x1098]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1098,
+ },
+ [0x1099]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0x1099,
+ },
+ [0x109A]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x109A,
+ },
+ [0x109B]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x109B,
+ },
+ [0x109C]={
+ category="mc",
+ direction="l",
+ indic="d",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0x109C,
+ },
+ [0x109D]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0x109D,
+ },
+ [0x109E]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0x109E,
+ },
+ [0x109F]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0x109F,
+ },
+ [0x10A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A0,
+ },
+ [0x10A1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A1,
+ },
+ [0x10A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A2,
+ },
+ [0x10A3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A3,
+ },
+ [0x10A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A4,
+ },
+ [0x10A5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A5,
+ },
+ [0x10A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A6,
+ },
+ [0x10A7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A7,
+ },
+ [0x10A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A8,
+ },
+ [0x10A9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10A9,
+ },
+ [0x10AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10AA,
+ },
+ [0x10AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10AB,
+ },
+ [0x10AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10AC,
+ },
+ [0x10AD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10AD,
+ },
+ [0x10AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10AE,
+ },
+ [0x10AF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10AF,
+ },
+ [0x10B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B0,
+ },
+ [0x10B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B1,
+ },
+ [0x10B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B2,
+ },
+ [0x10B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B3,
+ },
+ [0x10B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B4,
+ },
+ [0x10B5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B5,
+ },
+ [0x10B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B6,
+ },
+ [0x10B7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B7,
+ },
+ [0x10B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B8,
+ },
+ [0x10B9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10B9,
+ },
+ [0x10BA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10BA,
+ },
+ [0x10BB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10BB,
+ },
+ [0x10BC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10BC,
+ },
+ [0x10BD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10BD,
+ },
+ [0x10BE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10BE,
+ },
+ [0x10BF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10BF,
+ },
+ [0x10C0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C0,
+ },
+ [0x10C1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C1,
+ },
+ [0x10C2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C2,
+ },
+ [0x10C3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C3,
+ },
+ [0x10C4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C4,
+ },
+ [0x10C5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C5,
+ },
+ [0x10C7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10C7,
+ },
+ [0x10CD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10CD,
+ },
+ [0x10D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D0,
+ },
+ [0x10D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D1,
+ },
+ [0x10D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D2,
+ },
+ [0x10D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D3,
+ },
+ [0x10D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D4,
+ },
+ [0x10D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D5,
+ },
+ [0x10D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D6,
+ },
+ [0x10D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D7,
+ },
+ [0x10D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D8,
+ },
+ [0x10D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10D9,
+ },
+ [0x10DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10DA,
+ },
+ [0x10DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10DB,
+ },
+ [0x10DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10DC,
+ },
+ [0x10DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10DD,
+ },
+ [0x10DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10DE,
+ },
+ [0x10DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10DF,
+ },
+ [0x10E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E0,
+ },
+ [0x10E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E1,
+ },
+ [0x10E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E2,
+ },
+ [0x10E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E3,
+ },
+ [0x10E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E4,
+ },
+ [0x10E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E5,
+ },
+ [0x10E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E6,
+ },
+ [0x10E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E7,
+ },
+ [0x10E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E8,
+ },
+ [0x10E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10E9,
+ },
+ [0x10EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10EA,
+ },
+ [0x10EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10EB,
+ },
+ [0x10EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10EC,
+ },
+ [0x10ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10ED,
+ },
+ [0x10EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10EE,
+ },
+ [0x10EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10EF,
+ },
+ [0x10F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F0,
+ },
+ [0x10F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F1,
+ },
+ [0x10F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F2,
+ },
+ [0x10F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F3,
+ },
+ [0x10F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F4,
+ },
+ [0x10F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F5,
+ },
+ [0x10F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F6,
+ },
+ [0x10F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F7,
+ },
+ [0x10F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F8,
+ },
+ [0x10F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10F9,
+ },
+ [0x10FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10FA,
+ },
+ [0x10FB]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10FB,
+ },
+ [0x10FC]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x10DC },
+ unicodeslot=0x10FC,
+ },
+ [0x10FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10FD,
+ },
+ [0x10FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10FE,
+ },
+ [0x10FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10FF,
+ },
+ [0x1100]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1100,
+ },
+ [0x1101]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1101,
+ },
+ [0x1102]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1102,
+ },
+ [0x1103]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1103,
+ },
+ [0x1104]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1104,
+ },
+ [0x1105]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1105,
+ },
+ [0x1106]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1106,
+ },
+ [0x1107]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1107,
+ },
+ [0x1108]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1108,
+ },
+ [0x1109]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1109,
+ },
+ [0x110A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x110A,
+ },
+ [0x110B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x110B,
+ },
+ [0x110C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x110C,
+ },
+ [0x110D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x110D,
+ },
+ [0x110E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x110E,
+ },
+ [0x110F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x110F,
+ },
+ [0x1110]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1110,
+ },
+ [0x1111]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1111,
+ },
+ [0x1112]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1112,
+ },
+ [0x1113]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1113,
+ },
+ [0x1114]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1114,
+ },
+ [0x1115]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1115,
+ },
+ [0x1116]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1116,
+ },
+ [0x1117]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1117,
+ },
+ [0x1118]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1118,
+ },
+ [0x1119]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1119,
+ },
+ [0x111A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x111A,
+ },
+ [0x111B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x111B,
+ },
+ [0x111C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x111C,
+ },
+ [0x111D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x111D,
+ },
+ [0x111E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x111E,
+ },
+ [0x111F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x111F,
+ },
+ [0x1120]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1120,
+ },
+ [0x1121]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1121,
+ },
+ [0x1122]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1122,
+ },
+ [0x1123]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1123,
+ },
+ [0x1124]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1124,
+ },
+ [0x1125]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1125,
+ },
+ [0x1126]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1126,
+ },
+ [0x1127]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1127,
+ },
+ [0x1128]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1128,
+ },
+ [0x1129]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1129,
+ },
+ [0x112A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x112A,
+ },
+ [0x112B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x112B,
+ },
+ [0x112C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x112C,
+ },
+ [0x112D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x112D,
+ },
+ [0x112E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x112E,
+ },
+ [0x112F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x112F,
+ },
+ [0x1130]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1130,
+ },
+ [0x1131]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1131,
+ },
+ [0x1132]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1132,
+ },
+ [0x1133]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1133,
+ },
+ [0x1134]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1134,
+ },
+ [0x1135]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1135,
+ },
+ [0x1136]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1136,
+ },
+ [0x1137]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1137,
+ },
+ [0x1138]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1138,
+ },
+ [0x1139]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1139,
+ },
+ [0x113A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x113A,
+ },
+ [0x113B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x113B,
+ },
+ [0x113C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x113C,
+ },
+ [0x113D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x113D,
+ },
+ [0x113E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x113E,
+ },
+ [0x113F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x113F,
+ },
+ [0x1140]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1140,
+ },
+ [0x1141]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1141,
+ },
+ [0x1142]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1142,
+ },
+ [0x1143]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1143,
+ },
+ [0x1144]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1144,
+ },
+ [0x1145]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1145,
+ },
+ [0x1146]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1146,
+ },
+ [0x1147]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1147,
+ },
+ [0x1148]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1148,
+ },
+ [0x1149]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1149,
+ },
+ [0x114A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x114A,
+ },
+ [0x114B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x114B,
+ },
+ [0x114C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x114C,
+ },
+ [0x114D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x114D,
+ },
+ [0x114E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x114E,
+ },
+ [0x114F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x114F,
+ },
+ [0x1150]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1150,
+ },
+ [0x1151]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1151,
+ },
+ [0x1152]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1152,
+ },
+ [0x1153]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1153,
+ },
+ [0x1154]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1154,
+ },
+ [0x1155]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1155,
+ },
+ [0x1156]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1156,
+ },
+ [0x1157]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1157,
+ },
+ [0x1158]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1158,
+ },
+ [0x1159]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x1159,
+ },
+ [0x115A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x115A,
+ },
+ [0x115B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x115B,
+ },
+ [0x115C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x115C,
+ },
+ [0x115D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x115D,
+ },
+ [0x115E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x115E,
+ },
+ [0x115F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0x115F,
+ },
+ [0x1160]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1160,
+ },
+ [0x1161]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1161,
+ },
+ [0x1162]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1162,
+ },
+ [0x1163]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1163,
+ },
+ [0x1164]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1164,
+ },
+ [0x1165]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1165,
+ },
+ [0x1166]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1166,
+ },
+ [0x1167]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1167,
+ },
+ [0x1168]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1168,
+ },
+ [0x1169]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1169,
+ },
+ [0x116A]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x116A,
+ },
+ [0x116B]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x116B,
+ },
+ [0x116C]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x116C,
+ },
+ [0x116D]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x116D,
+ },
+ [0x116E]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x116E,
+ },
+ [0x116F]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x116F,
+ },
+ [0x1170]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1170,
+ },
+ [0x1171]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1171,
+ },
+ [0x1172]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1172,
+ },
+ [0x1173]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1173,
+ },
+ [0x1174]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1174,
+ },
+ [0x1175]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1175,
+ },
+ [0x1176]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1176,
+ },
+ [0x1177]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1177,
+ },
+ [0x1178]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1178,
+ },
+ [0x1179]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1179,
+ },
+ [0x117A]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x117A,
+ },
+ [0x117B]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x117B,
+ },
+ [0x117C]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x117C,
+ },
+ [0x117D]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x117D,
+ },
+ [0x117E]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x117E,
+ },
+ [0x117F]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x117F,
+ },
+ [0x1180]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1180,
+ },
+ [0x1181]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1181,
+ },
+ [0x1182]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1182,
+ },
+ [0x1183]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1183,
+ },
+ [0x1184]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1184,
+ },
+ [0x1185]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1185,
+ },
+ [0x1186]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1186,
+ },
+ [0x1187]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1187,
+ },
+ [0x1188]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1188,
+ },
+ [0x1189]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1189,
+ },
+ [0x118A]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x118A,
+ },
+ [0x118B]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x118B,
+ },
+ [0x118C]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x118C,
+ },
+ [0x118D]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x118D,
+ },
+ [0x118E]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x118E,
+ },
+ [0x118F]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x118F,
+ },
+ [0x1190]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1190,
+ },
+ [0x1191]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1191,
+ },
+ [0x1192]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1192,
+ },
+ [0x1193]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1193,
+ },
+ [0x1194]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1194,
+ },
+ [0x1195]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1195,
+ },
+ [0x1196]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1196,
+ },
+ [0x1197]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1197,
+ },
+ [0x1198]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1198,
+ },
+ [0x1199]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x1199,
+ },
+ [0x119A]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x119A,
+ },
+ [0x119B]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x119B,
+ },
+ [0x119C]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x119C,
+ },
+ [0x119D]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x119D,
+ },
+ [0x119E]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x119E,
+ },
+ [0x119F]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x119F,
+ },
+ [0x11A0]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A0,
+ },
+ [0x11A1]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A1,
+ },
+ [0x11A2]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A2,
+ },
+ [0x11A3]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A3,
+ },
+ [0x11A4]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A4,
+ },
+ [0x11A5]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A5,
+ },
+ [0x11A6]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A6,
+ },
+ [0x11A7]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0x11A7,
+ },
+ [0x11A8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11A8,
+ },
+ [0x11A9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11A9,
+ },
+ [0x11AA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11AA,
+ },
+ [0x11AB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11AB,
+ },
+ [0x11AC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11AC,
+ },
+ [0x11AD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11AD,
+ },
+ [0x11AE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11AE,
+ },
+ [0x11AF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11AF,
+ },
+ [0x11B0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B0,
+ },
+ [0x11B1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B1,
+ },
+ [0x11B2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B2,
+ },
+ [0x11B3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B3,
+ },
+ [0x11B4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B4,
+ },
+ [0x11B5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B5,
+ },
+ [0x11B6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B6,
+ },
+ [0x11B7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B7,
+ },
+ [0x11B8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B8,
+ },
+ [0x11B9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11B9,
+ },
+ [0x11BA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11BA,
+ },
+ [0x11BB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11BB,
+ },
+ [0x11BC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11BC,
+ },
+ [0x11BD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11BD,
+ },
+ [0x11BE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11BE,
+ },
+ [0x11BF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11BF,
+ },
+ [0x11C0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C0,
+ },
+ [0x11C1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C1,
+ },
+ [0x11C2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C2,
+ },
+ [0x11C3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C3,
+ },
+ [0x11C4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C4,
+ },
+ [0x11C5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C5,
+ },
+ [0x11C6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C6,
+ },
+ [0x11C7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C7,
+ },
+ [0x11C8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C8,
+ },
+ [0x11C9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11C9,
+ },
+ [0x11CA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11CA,
+ },
+ [0x11CB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11CB,
+ },
+ [0x11CC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11CC,
+ },
+ [0x11CD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11CD,
+ },
+ [0x11CE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11CE,
+ },
+ [0x11CF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11CF,
+ },
+ [0x11D0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D0,
+ },
+ [0x11D1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D1,
+ },
+ [0x11D2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D2,
+ },
+ [0x11D3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D3,
+ },
+ [0x11D4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D4,
+ },
+ [0x11D5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D5,
+ },
+ [0x11D6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D6,
+ },
+ [0x11D7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D7,
+ },
+ [0x11D8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D8,
+ },
+ [0x11D9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11D9,
+ },
+ [0x11DA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11DA,
+ },
+ [0x11DB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11DB,
+ },
+ [0x11DC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11DC,
+ },
+ [0x11DD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11DD,
+ },
+ [0x11DE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11DE,
+ },
+ [0x11DF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11DF,
+ },
+ [0x11E0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E0,
+ },
+ [0x11E1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E1,
+ },
+ [0x11E2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E2,
+ },
+ [0x11E3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E3,
+ },
+ [0x11E4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E4,
+ },
+ [0x11E5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E5,
+ },
+ [0x11E6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E6,
+ },
+ [0x11E7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E7,
+ },
+ [0x11E8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E8,
+ },
+ [0x11E9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11E9,
+ },
+ [0x11EA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11EA,
+ },
+ [0x11EB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11EB,
+ },
+ [0x11EC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11EC,
+ },
+ [0x11ED]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11ED,
+ },
+ [0x11EE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11EE,
+ },
+ [0x11EF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11EF,
+ },
+ [0x11F0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F0,
+ },
+ [0x11F1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F1,
+ },
+ [0x11F2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F2,
+ },
+ [0x11F3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F3,
+ },
+ [0x11F4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F4,
+ },
+ [0x11F5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F5,
+ },
+ [0x11F6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F6,
+ },
+ [0x11F7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F7,
+ },
+ [0x11F8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F8,
+ },
+ [0x11F9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11F9,
+ },
+ [0x11FA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11FA,
+ },
+ [0x11FB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11FB,
+ },
+ [0x11FC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11FC,
+ },
+ [0x11FD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11FD,
+ },
+ [0x11FE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11FE,
+ },
+ [0x11FF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0x11FF,
+ },
+ [0x1200]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200,
+ },
+ [0x1201]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201,
+ },
+ [0x1202]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202,
+ },
+ [0x1203]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203,
+ },
+ [0x1204]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204,
+ },
+ [0x1205]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205,
+ },
+ [0x1206]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206,
+ },
+ [0x1207]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207,
+ },
+ [0x1208]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208,
+ },
+ [0x1209]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209,
+ },
+ [0x120A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A,
+ },
+ [0x120B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B,
+ },
+ [0x120C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C,
+ },
+ [0x120D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D,
+ },
+ [0x120E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E,
+ },
+ [0x120F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F,
+ },
+ [0x1210]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210,
+ },
+ [0x1211]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211,
+ },
+ [0x1212]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212,
+ },
+ [0x1213]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213,
+ },
+ [0x1214]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214,
+ },
+ [0x1215]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215,
+ },
+ [0x1216]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216,
+ },
+ [0x1217]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217,
+ },
+ [0x1218]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218,
+ },
+ [0x1219]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219,
+ },
+ [0x121A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A,
+ },
+ [0x121B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B,
+ },
+ [0x121C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C,
+ },
+ [0x121D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D,
+ },
+ [0x121E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E,
+ },
+ [0x121F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F,
+ },
+ [0x1220]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220,
+ },
+ [0x1221]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221,
+ },
+ [0x1222]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222,
+ },
+ [0x1223]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223,
+ },
+ [0x1224]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224,
+ },
+ [0x1225]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225,
+ },
+ [0x1226]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226,
+ },
+ [0x1227]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227,
+ },
+ [0x1228]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228,
+ },
+ [0x1229]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229,
+ },
+ [0x122A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A,
+ },
+ [0x122B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B,
+ },
+ [0x122C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C,
+ },
+ [0x122D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D,
+ },
+ [0x122E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E,
+ },
+ [0x122F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F,
+ },
+ [0x1230]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230,
+ },
+ [0x1231]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231,
+ },
+ [0x1232]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232,
+ },
+ [0x1233]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233,
+ },
+ [0x1234]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234,
+ },
+ [0x1235]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235,
+ },
+ [0x1236]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236,
+ },
+ [0x1237]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237,
+ },
+ [0x1238]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238,
+ },
+ [0x1239]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1239,
+ },
+ [0x123A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x123A,
+ },
+ [0x123B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x123B,
+ },
+ [0x123C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x123C,
+ },
+ [0x123D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x123D,
+ },
+ [0x123E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x123E,
+ },
+ [0x123F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x123F,
+ },
+ [0x1240]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240,
+ },
+ [0x1241]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241,
+ },
+ [0x1242]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242,
+ },
+ [0x1243]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243,
+ },
+ [0x1244]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244,
+ },
+ [0x1245]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245,
+ },
+ [0x1246]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1246,
+ },
+ [0x1247]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1247,
+ },
+ [0x1248]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248,
+ },
+ [0x124A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A,
+ },
+ [0x124B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B,
+ },
+ [0x124C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C,
+ },
+ [0x124D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D,
+ },
+ [0x1250]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250,
+ },
+ [0x1251]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251,
+ },
+ [0x1252]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252,
+ },
+ [0x1253]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253,
+ },
+ [0x1254]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1254,
+ },
+ [0x1255]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1255,
+ },
+ [0x1256]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1256,
+ },
+ [0x1258]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1258,
+ },
+ [0x125A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x125A,
+ },
+ [0x125B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x125B,
+ },
+ [0x125C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x125C,
+ },
+ [0x125D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x125D,
+ },
+ [0x1260]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1260,
+ },
+ [0x1261]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1261,
+ },
+ [0x1262]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1262,
+ },
+ [0x1263]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1263,
+ },
+ [0x1264]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1264,
+ },
+ [0x1265]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1265,
+ },
+ [0x1266]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1266,
+ },
+ [0x1267]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1267,
+ },
+ [0x1268]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1268,
+ },
+ [0x1269]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1269,
+ },
+ [0x126A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126A,
+ },
+ [0x126B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126B,
+ },
+ [0x126C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126C,
+ },
+ [0x126D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126D,
+ },
+ [0x126E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126E,
+ },
+ [0x126F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x126F,
+ },
+ [0x1270]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1270,
+ },
+ [0x1271]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1271,
+ },
+ [0x1272]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1272,
+ },
+ [0x1273]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1273,
+ },
+ [0x1274]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1274,
+ },
+ [0x1275]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1275,
+ },
+ [0x1276]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1276,
+ },
+ [0x1277]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1277,
+ },
+ [0x1278]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1278,
+ },
+ [0x1279]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1279,
+ },
+ [0x127A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127A,
+ },
+ [0x127B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127B,
+ },
+ [0x127C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127C,
+ },
+ [0x127D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127D,
+ },
+ [0x127E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127E,
+ },
+ [0x127F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x127F,
+ },
+ [0x1280]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1280,
+ },
+ [0x1281]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1281,
+ },
+ [0x1282]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1282,
+ },
+ [0x1283]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1283,
+ },
+ [0x1284]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1284,
+ },
+ [0x1285]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1285,
+ },
+ [0x1286]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1286,
+ },
+ [0x1287]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1287,
+ },
+ [0x1288]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1288,
+ },
+ [0x128A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x128A,
+ },
+ [0x128B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x128B,
+ },
+ [0x128C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x128C,
+ },
+ [0x128D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x128D,
+ },
+ [0x1290]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1290,
+ },
+ [0x1291]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1291,
+ },
+ [0x1292]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1292,
+ },
+ [0x1293]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1293,
+ },
+ [0x1294]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1294,
+ },
+ [0x1295]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1295,
+ },
+ [0x1296]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1296,
+ },
+ [0x1297]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1297,
+ },
+ [0x1298]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1298,
+ },
+ [0x1299]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1299,
+ },
+ [0x129A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x129A,
+ },
+ [0x129B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x129B,
+ },
+ [0x129C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x129C,
+ },
+ [0x129D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x129D,
+ },
+ [0x129E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x129E,
+ },
+ [0x129F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x129F,
+ },
+ [0x12A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A0,
+ },
+ [0x12A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A1,
+ },
+ [0x12A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A2,
+ },
+ [0x12A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A3,
+ },
+ [0x12A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A4,
+ },
+ [0x12A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A5,
+ },
+ [0x12A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A6,
+ },
+ [0x12A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A7,
+ },
+ [0x12A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A8,
+ },
+ [0x12A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12A9,
+ },
+ [0x12AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12AA,
+ },
+ [0x12AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12AB,
+ },
+ [0x12AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12AC,
+ },
+ [0x12AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12AD,
+ },
+ [0x12AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12AE,
+ },
+ [0x12AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12AF,
+ },
+ [0x12B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B0,
+ },
+ [0x12B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B2,
+ },
+ [0x12B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B3,
+ },
+ [0x12B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B4,
+ },
+ [0x12B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B5,
+ },
+ [0x12B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B8,
+ },
+ [0x12B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12B9,
+ },
+ [0x12BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12BA,
+ },
+ [0x12BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12BB,
+ },
+ [0x12BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12BC,
+ },
+ [0x12BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12BD,
+ },
+ [0x12BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12BE,
+ },
+ [0x12C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C0,
+ },
+ [0x12C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C2,
+ },
+ [0x12C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C3,
+ },
+ [0x12C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C4,
+ },
+ [0x12C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C5,
+ },
+ [0x12C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C8,
+ },
+ [0x12C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12C9,
+ },
+ [0x12CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12CA,
+ },
+ [0x12CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12CB,
+ },
+ [0x12CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12CC,
+ },
+ [0x12CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12CD,
+ },
+ [0x12CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12CE,
+ },
+ [0x12CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12CF,
+ },
+ [0x12D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D0,
+ },
+ [0x12D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D1,
+ },
+ [0x12D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D2,
+ },
+ [0x12D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D3,
+ },
+ [0x12D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D4,
+ },
+ [0x12D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D5,
+ },
+ [0x12D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D6,
+ },
+ [0x12D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D8,
+ },
+ [0x12D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12D9,
+ },
+ [0x12DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12DA,
+ },
+ [0x12DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12DB,
+ },
+ [0x12DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12DC,
+ },
+ [0x12DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12DD,
+ },
+ [0x12DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12DE,
+ },
+ [0x12DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12DF,
+ },
+ [0x12E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E0,
+ },
+ [0x12E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E1,
+ },
+ [0x12E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E2,
+ },
+ [0x12E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E3,
+ },
+ [0x12E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E4,
+ },
+ [0x12E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E5,
+ },
+ [0x12E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E6,
+ },
+ [0x12E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E7,
+ },
+ [0x12E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E8,
+ },
+ [0x12E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12E9,
+ },
+ [0x12EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12EA,
+ },
+ [0x12EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12EB,
+ },
+ [0x12EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12EC,
+ },
+ [0x12ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12ED,
+ },
+ [0x12EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12EE,
+ },
+ [0x12EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12EF,
+ },
+ [0x12F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F0,
+ },
+ [0x12F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F1,
+ },
+ [0x12F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F2,
+ },
+ [0x12F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F3,
+ },
+ [0x12F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F4,
+ },
+ [0x12F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F5,
+ },
+ [0x12F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F6,
+ },
+ [0x12F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F7,
+ },
+ [0x12F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F8,
+ },
+ [0x12F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12F9,
+ },
+ [0x12FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12FA,
+ },
+ [0x12FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12FB,
+ },
+ [0x12FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12FC,
+ },
+ [0x12FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12FD,
+ },
+ [0x12FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12FE,
+ },
+ [0x12FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12FF,
+ },
+ [0x1300]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300,
+ },
+ [0x1301]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301,
+ },
+ [0x1302]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302,
+ },
+ [0x1303]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303,
+ },
+ [0x1304]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304,
+ },
+ [0x1305]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305,
+ },
+ [0x1306]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306,
+ },
+ [0x1307]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307,
+ },
+ [0x1308]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308,
+ },
+ [0x1309]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309,
+ },
+ [0x130A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A,
+ },
+ [0x130B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B,
+ },
+ [0x130C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C,
+ },
+ [0x130D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D,
+ },
+ [0x130E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E,
+ },
+ [0x130F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F,
+ },
+ [0x1310]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310,
+ },
+ [0x1312]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312,
+ },
+ [0x1313]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313,
+ },
+ [0x1314]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314,
+ },
+ [0x1315]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315,
+ },
+ [0x1318]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318,
+ },
+ [0x1319]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319,
+ },
+ [0x131A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A,
+ },
+ [0x131B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B,
+ },
+ [0x131C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C,
+ },
+ [0x131D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D,
+ },
+ [0x131E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E,
+ },
+ [0x131F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F,
+ },
+ [0x1320]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320,
+ },
+ [0x1321]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321,
+ },
+ [0x1322]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322,
+ },
+ [0x1323]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323,
+ },
+ [0x1324]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324,
+ },
+ [0x1325]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1325,
+ },
+ [0x1326]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326,
+ },
+ [0x1327]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327,
+ },
+ [0x1328]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328,
+ },
+ [0x1329]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329,
+ },
+ [0x132A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A,
+ },
+ [0x132B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B,
+ },
+ [0x132C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C,
+ },
+ [0x132D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D,
+ },
+ [0x132E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E,
+ },
+ [0x132F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F,
+ },
+ [0x1330]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330,
+ },
+ [0x1331]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331,
+ },
+ [0x1332]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332,
+ },
+ [0x1333]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333,
+ },
+ [0x1334]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334,
+ },
+ [0x1335]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335,
+ },
+ [0x1336]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336,
+ },
+ [0x1337]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1337,
+ },
+ [0x1338]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338,
+ },
+ [0x1339]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339,
+ },
+ [0x133A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A,
+ },
+ [0x133B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B,
+ },
+ [0x133C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C,
+ },
+ [0x133D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D,
+ },
+ [0x133E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E,
+ },
+ [0x133F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F,
+ },
+ [0x1340]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340,
+ },
+ [0x1341]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341,
+ },
+ [0x1342]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1342,
+ },
+ [0x1343]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1343,
+ },
+ [0x1344]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1344,
+ },
+ [0x1345]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1345,
+ },
+ [0x1346]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1346,
+ },
+ [0x1347]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1347,
+ },
+ [0x1348]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1348,
+ },
+ [0x1349]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1349,
+ },
+ [0x134A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x134A,
+ },
+ [0x134B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x134B,
+ },
+ [0x134C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x134C,
+ },
+ [0x134D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x134D,
+ },
+ [0x134E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x134E,
+ },
+ [0x134F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x134F,
+ },
+ [0x1350]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1350,
+ },
+ [0x1351]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1351,
+ },
+ [0x1352]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1352,
+ },
+ [0x1353]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1353,
+ },
+ [0x1354]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1354,
+ },
+ [0x1355]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1355,
+ },
+ [0x1356]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1356,
+ },
+ [0x1357]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1357,
+ },
+ [0x1358]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1358,
+ },
+ [0x1359]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1359,
+ },
+ [0x135A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x135A,
+ },
+ [0x135D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x135D,
+ },
+ [0x135E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x135E,
+ },
+ [0x135F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x135F,
+ },
+ [0x1360]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1360,
+ },
+ [0x1361]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1361,
+ },
+ [0x1362]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1362,
+ },
+ [0x1363]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1363,
+ },
+ [0x1364]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1364,
+ },
+ [0x1365]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1365,
+ },
+ [0x1366]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1366,
+ },
+ [0x1367]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1367,
+ },
+ [0x1368]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1368,
+ },
+ [0x1369]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1369,
+ },
+ [0x136A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x136A,
+ },
+ [0x136B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x136B,
+ },
+ [0x136C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x136C,
+ },
+ [0x136D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x136D,
+ },
+ [0x136E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x136E,
+ },
+ [0x136F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x136F,
+ },
+ [0x1370]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1370,
+ },
+ [0x1371]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1371,
+ },
+ [0x1372]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1372,
+ },
+ [0x1373]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1373,
+ },
+ [0x1374]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1374,
+ },
+ [0x1375]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1375,
+ },
+ [0x1376]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1376,
+ },
+ [0x1377]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1377,
+ },
+ [0x1378]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1378,
+ },
+ [0x1379]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1379,
+ },
+ [0x137A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x137A,
+ },
+ [0x137B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x137B,
+ },
+ [0x137C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x137C,
+ },
+ [0x1380]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1380,
+ },
+ [0x1381]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1381,
+ },
+ [0x1382]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1382,
+ },
+ [0x1383]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1383,
+ },
+ [0x1384]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1384,
+ },
+ [0x1385]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1385,
+ },
+ [0x1386]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1386,
+ },
+ [0x1387]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1387,
+ },
+ [0x1388]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1388,
+ },
+ [0x1389]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1389,
+ },
+ [0x138A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138A,
+ },
+ [0x138B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138B,
+ },
+ [0x138C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138C,
+ },
+ [0x138D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138D,
+ },
+ [0x138E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138E,
+ },
+ [0x138F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x138F,
+ },
+ [0x1390]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1390,
+ },
+ [0x1391]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1391,
+ },
+ [0x1392]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1392,
+ },
+ [0x1393]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1393,
+ },
+ [0x1394]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1394,
+ },
+ [0x1395]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1395,
+ },
+ [0x1396]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1396,
+ },
+ [0x1397]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1397,
+ },
+ [0x1398]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1398,
+ },
+ [0x1399]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1399,
+ },
+ [0x13A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A0,
+ },
+ [0x13A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A1,
+ },
+ [0x13A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A2,
+ },
+ [0x13A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A3,
+ },
+ [0x13A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A4,
+ },
+ [0x13A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A5,
+ },
+ [0x13A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A6,
+ },
+ [0x13A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A7,
+ },
+ [0x13A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A8,
+ },
+ [0x13A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13A9,
+ },
+ [0x13AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13AA,
+ },
+ [0x13AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13AB,
+ },
+ [0x13AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13AC,
+ },
+ [0x13AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13AD,
+ },
+ [0x13AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13AE,
+ },
+ [0x13AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13AF,
+ },
+ [0x13B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B0,
+ },
+ [0x13B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B1,
+ },
+ [0x13B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B2,
+ },
+ [0x13B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B3,
+ },
+ [0x13B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B4,
+ },
+ [0x13B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B5,
+ },
+ [0x13B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B6,
+ },
+ [0x13B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B7,
+ },
+ [0x13B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B8,
+ },
+ [0x13B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13B9,
+ },
+ [0x13BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13BA,
+ },
+ [0x13BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13BB,
+ },
+ [0x13BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13BC,
+ },
+ [0x13BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13BD,
+ },
+ [0x13BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13BE,
+ },
+ [0x13BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13BF,
+ },
+ [0x13C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C0,
+ },
+ [0x13C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C1,
+ },
+ [0x13C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C2,
+ },
+ [0x13C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C3,
+ },
+ [0x13C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C4,
+ },
+ [0x13C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C5,
+ },
+ [0x13C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C6,
+ },
+ [0x13C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C7,
+ },
+ [0x13C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C8,
+ },
+ [0x13C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13C9,
+ },
+ [0x13CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13CA,
+ },
+ [0x13CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13CB,
+ },
+ [0x13CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13CC,
+ },
+ [0x13CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13CD,
+ },
+ [0x13CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13CE,
+ },
+ [0x13CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13CF,
+ },
+ [0x13D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D0,
+ },
+ [0x13D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D1,
+ },
+ [0x13D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D2,
+ },
+ [0x13D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D3,
+ },
+ [0x13D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D4,
+ },
+ [0x13D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D5,
+ },
+ [0x13D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D6,
+ },
+ [0x13D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D7,
+ },
+ [0x13D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D8,
+ },
+ [0x13D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13D9,
+ },
+ [0x13DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13DA,
+ },
+ [0x13DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13DB,
+ },
+ [0x13DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13DC,
+ },
+ [0x13DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13DD,
+ },
+ [0x13DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13DE,
+ },
+ [0x13DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13DF,
+ },
+ [0x13E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E0,
+ },
+ [0x13E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E1,
+ },
+ [0x13E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E2,
+ },
+ [0x13E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E3,
+ },
+ [0x13E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E4,
+ },
+ [0x13E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E5,
+ },
+ [0x13E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E6,
+ },
+ [0x13E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E7,
+ },
+ [0x13E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E8,
+ },
+ [0x13E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13E9,
+ },
+ [0x13EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13EA,
+ },
+ [0x13EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13EB,
+ },
+ [0x13EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13EC,
+ },
+ [0x13ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13ED,
+ },
+ [0x13EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13EE,
+ },
+ [0x13EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13EF,
+ },
+ [0x13F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F0,
+ },
+ [0x13F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F1,
+ },
+ [0x13F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F2,
+ },
+ [0x13F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F3,
+ },
+ [0x13F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F4,
+ },
+ [0x13F5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F5,
+ },
+ [0x13F8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F8,
+ },
+ [0x13F9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13F9,
+ },
+ [0x13FA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13FA,
+ },
+ [0x13FB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13FB,
+ },
+ [0x13FC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13FC,
+ },
+ [0x13FD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13FD,
+ },
+ [0x1400]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x1400,
+ },
+ [0x1401]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1401,
+ },
+ [0x1402]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1402,
+ },
+ [0x1403]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1403,
+ },
+ [0x1404]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1404,
+ },
+ [0x1405]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1405,
+ },
+ [0x1406]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1406,
+ },
+ [0x1407]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1407,
+ },
+ [0x1408]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1408,
+ },
+ [0x1409]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1409,
+ },
+ [0x140A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x140A,
+ },
+ [0x140B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x140B,
+ },
+ [0x140C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x140C,
+ },
+ [0x140D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x140D,
+ },
+ [0x140E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x140E,
+ },
+ [0x140F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x140F,
+ },
+ [0x1410]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1410,
+ },
+ [0x1411]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1411,
+ },
+ [0x1412]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1412,
+ },
+ [0x1413]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1413,
+ },
+ [0x1414]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1414,
+ },
+ [0x1415]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1415,
+ },
+ [0x1416]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1416,
+ },
+ [0x1417]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1417,
+ },
+ [0x1418]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1418,
+ },
+ [0x1419]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1419,
+ },
+ [0x141A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141A,
+ },
+ [0x141B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141B,
+ },
+ [0x141C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141C,
+ },
+ [0x141D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141D,
+ },
+ [0x141E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141E,
+ },
+ [0x141F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x141F,
+ },
+ [0x1420]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1420,
+ },
+ [0x1421]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1421,
+ },
+ [0x1422]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1422,
+ },
+ [0x1423]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1423,
+ },
+ [0x1424]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1424,
+ },
+ [0x1425]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1425,
+ },
+ [0x1426]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1426,
+ },
+ [0x1427]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1427,
+ },
+ [0x1428]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1428,
+ },
+ [0x1429]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1429,
+ },
+ [0x142A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142A,
+ },
+ [0x142B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142B,
+ },
+ [0x142C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142C,
+ },
+ [0x142D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142D,
+ },
+ [0x142E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142E,
+ },
+ [0x142F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x142F,
+ },
+ [0x1430]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1430,
+ },
+ [0x1431]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1431,
+ },
+ [0x1432]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1432,
+ },
+ [0x1433]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1433,
+ },
+ [0x1434]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1434,
+ },
+ [0x1435]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1435,
+ },
+ [0x1436]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1436,
+ },
+ [0x1437]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1437,
+ },
+ [0x1438]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1438,
+ },
+ [0x1439]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1439,
+ },
+ [0x143A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x143A,
+ },
+ [0x143B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x143B,
+ },
+ [0x143C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x143C,
+ },
+ [0x143D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x143D,
+ },
+ [0x143E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x143E,
+ },
+ [0x143F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x143F,
+ },
+ [0x1440]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440,
+ },
+ [0x1441]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441,
+ },
+ [0x1442]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442,
+ },
+ [0x1443]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443,
+ },
+ [0x1444]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444,
+ },
+ [0x1445]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445,
+ },
+ [0x1446]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446,
+ },
+ [0x1447]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447,
+ },
+ [0x1448]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448,
+ },
+ [0x1449]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449,
+ },
+ [0x144A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A,
+ },
+ [0x144B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B,
+ },
+ [0x144C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C,
+ },
+ [0x144D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D,
+ },
+ [0x144E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E,
+ },
+ [0x144F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F,
+ },
+ [0x1450]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450,
+ },
+ [0x1451]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451,
+ },
+ [0x1452]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452,
+ },
+ [0x1453]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453,
+ },
+ [0x1454]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454,
+ },
+ [0x1455]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455,
+ },
+ [0x1456]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456,
+ },
+ [0x1457]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457,
+ },
+ [0x1458]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458,
+ },
+ [0x1459]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459,
+ },
+ [0x145A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A,
+ },
+ [0x145B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B,
+ },
+ [0x145C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C,
+ },
+ [0x145D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D,
+ },
+ [0x145E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E,
+ },
+ [0x145F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F,
+ },
+ [0x1460]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460,
+ },
+ [0x1461]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461,
+ },
+ [0x1462]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462,
+ },
+ [0x1463]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463,
+ },
+ [0x1464]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1464,
+ },
+ [0x1465]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1465,
+ },
+ [0x1466]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1466,
+ },
+ [0x1467]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1467,
+ },
+ [0x1468]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1468,
+ },
+ [0x1469]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1469,
+ },
+ [0x146A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x146A,
+ },
+ [0x146B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x146B,
+ },
+ [0x146C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x146C,
+ },
+ [0x146D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x146D,
+ },
+ [0x146E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x146E,
+ },
+ [0x146F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x146F,
+ },
+ [0x1470]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1470,
+ },
+ [0x1471]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1471,
+ },
+ [0x1472]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1472,
+ },
+ [0x1473]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1473,
+ },
+ [0x1474]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1474,
+ },
+ [0x1475]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1475,
+ },
+ [0x1476]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1476,
+ },
+ [0x1477]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1477,
+ },
+ [0x1478]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1478,
+ },
+ [0x1479]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1479,
+ },
+ [0x147A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x147A,
+ },
+ [0x147B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x147B,
+ },
+ [0x147C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x147C,
+ },
+ [0x147D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x147D,
+ },
+ [0x147E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x147E,
+ },
+ [0x147F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x147F,
+ },
+ [0x1480]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1480,
+ },
+ [0x1481]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1481,
+ },
+ [0x1482]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1482,
+ },
+ [0x1483]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1483,
+ },
+ [0x1484]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1484,
+ },
+ [0x1485]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1485,
+ },
+ [0x1486]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1486,
+ },
+ [0x1487]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1487,
+ },
+ [0x1488]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1488,
+ },
+ [0x1489]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1489,
+ },
+ [0x148A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x148A,
+ },
+ [0x148B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x148B,
+ },
+ [0x148C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x148C,
+ },
+ [0x148D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x148D,
+ },
+ [0x148E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x148E,
+ },
+ [0x148F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x148F,
+ },
+ [0x1490]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1490,
+ },
+ [0x1491]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1491,
+ },
+ [0x1492]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1492,
+ },
+ [0x1493]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1493,
+ },
+ [0x1494]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1494,
+ },
+ [0x1495]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1495,
+ },
+ [0x1496]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1496,
+ },
+ [0x1497]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1497,
+ },
+ [0x1498]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1498,
+ },
+ [0x1499]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1499,
+ },
+ [0x149A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x149A,
+ },
+ [0x149B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x149B,
+ },
+ [0x149C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x149C,
+ },
+ [0x149D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x149D,
+ },
+ [0x149E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x149E,
+ },
+ [0x149F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x149F,
+ },
+ [0x14A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A0,
+ },
+ [0x14A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A1,
+ },
+ [0x14A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A2,
+ },
+ [0x14A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A3,
+ },
+ [0x14A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A4,
+ },
+ [0x14A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A5,
+ },
+ [0x14A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A6,
+ },
+ [0x14A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A7,
+ },
+ [0x14A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A8,
+ },
+ [0x14A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14A9,
+ },
+ [0x14AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14AA,
+ },
+ [0x14AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14AB,
+ },
+ [0x14AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14AC,
+ },
+ [0x14AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14AD,
+ },
+ [0x14AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14AE,
+ },
+ [0x14AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14AF,
+ },
+ [0x14B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B0,
+ },
+ [0x14B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B1,
+ },
+ [0x14B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B2,
+ },
+ [0x14B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B3,
+ },
+ [0x14B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B4,
+ },
+ [0x14B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B5,
+ },
+ [0x14B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B6,
+ },
+ [0x14B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B7,
+ },
+ [0x14B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B8,
+ },
+ [0x14B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14B9,
+ },
+ [0x14BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14BA,
+ },
+ [0x14BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14BB,
+ },
+ [0x14BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14BC,
+ },
+ [0x14BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14BD,
+ },
+ [0x14BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14BE,
+ },
+ [0x14BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14BF,
+ },
+ [0x14C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C0,
+ },
+ [0x14C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C1,
+ },
+ [0x14C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C2,
+ },
+ [0x14C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C3,
+ },
+ [0x14C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C4,
+ },
+ [0x14C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C5,
+ },
+ [0x14C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C6,
+ },
+ [0x14C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C7,
+ },
+ [0x14C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C8,
+ },
+ [0x14C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14C9,
+ },
+ [0x14CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14CA,
+ },
+ [0x14CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14CB,
+ },
+ [0x14CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14CC,
+ },
+ [0x14CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14CD,
+ },
+ [0x14CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14CE,
+ },
+ [0x14CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14CF,
+ },
+ [0x14D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D0,
+ },
+ [0x14D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D1,
+ },
+ [0x14D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D2,
+ },
+ [0x14D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D3,
+ },
+ [0x14D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D4,
+ },
+ [0x14D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D5,
+ },
+ [0x14D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D6,
+ },
+ [0x14D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D7,
+ },
+ [0x14D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D8,
+ },
+ [0x14D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14D9,
+ },
+ [0x14DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14DA,
+ },
+ [0x14DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14DB,
+ },
+ [0x14DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14DC,
+ },
+ [0x14DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14DD,
+ },
+ [0x14DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14DE,
+ },
+ [0x14DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14DF,
+ },
+ [0x14E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E0,
+ },
+ [0x14E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E1,
+ },
+ [0x14E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E2,
+ },
+ [0x14E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E3,
+ },
+ [0x14E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E4,
+ },
+ [0x14E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E5,
+ },
+ [0x14E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E6,
+ },
+ [0x14E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E7,
+ },
+ [0x14E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E8,
+ },
+ [0x14E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14E9,
+ },
+ [0x14EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14EA,
+ },
+ [0x14EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14EB,
+ },
+ [0x14EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14EC,
+ },
+ [0x14ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14ED,
+ },
+ [0x14EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14EE,
+ },
+ [0x14EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14EF,
+ },
+ [0x14F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F0,
+ },
+ [0x14F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F1,
+ },
+ [0x14F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F2,
+ },
+ [0x14F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F3,
+ },
+ [0x14F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F4,
+ },
+ [0x14F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F5,
+ },
+ [0x14F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F6,
+ },
+ [0x14F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F7,
+ },
+ [0x14F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F8,
+ },
+ [0x14F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14F9,
+ },
+ [0x14FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14FA,
+ },
+ [0x14FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14FB,
+ },
+ [0x14FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14FC,
+ },
+ [0x14FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14FD,
+ },
+ [0x14FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14FE,
+ },
+ [0x14FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14FF,
+ },
+ [0x1500]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1500,
+ },
+ [0x1501]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1501,
+ },
+ [0x1502]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1502,
+ },
+ [0x1503]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1503,
+ },
+ [0x1504]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1504,
+ },
+ [0x1505]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1505,
+ },
+ [0x1506]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1506,
+ },
+ [0x1507]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1507,
+ },
+ [0x1508]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1508,
+ },
+ [0x1509]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1509,
+ },
+ [0x150A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x150A,
+ },
+ [0x150B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x150B,
+ },
+ [0x150C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x150C,
+ },
+ [0x150D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x150D,
+ },
+ [0x150E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x150E,
+ },
+ [0x150F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x150F,
+ },
+ [0x1510]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1510,
+ },
+ [0x1511]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1511,
+ },
+ [0x1512]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1512,
+ },
+ [0x1513]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1513,
+ },
+ [0x1514]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1514,
+ },
+ [0x1515]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1515,
+ },
+ [0x1516]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1516,
+ },
+ [0x1517]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1517,
+ },
+ [0x1518]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1518,
+ },
+ [0x1519]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1519,
+ },
+ [0x151A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x151A,
+ },
+ [0x151B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x151B,
+ },
+ [0x151C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x151C,
+ },
+ [0x151D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x151D,
+ },
+ [0x151E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x151E,
+ },
+ [0x151F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x151F,
+ },
+ [0x1520]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1520,
+ },
+ [0x1521]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1521,
+ },
+ [0x1522]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1522,
+ },
+ [0x1523]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1523,
+ },
+ [0x1524]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1524,
+ },
+ [0x1525]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1525,
+ },
+ [0x1526]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1526,
+ },
+ [0x1527]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1527,
+ },
+ [0x1528]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1528,
+ },
+ [0x1529]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1529,
+ },
+ [0x152A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152A,
+ },
+ [0x152B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152B,
+ },
+ [0x152C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152C,
+ },
+ [0x152D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152D,
+ },
+ [0x152E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152E,
+ },
+ [0x152F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x152F,
+ },
+ [0x1530]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1530,
+ },
+ [0x1531]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1531,
+ },
+ [0x1532]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1532,
+ },
+ [0x1533]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1533,
+ },
+ [0x1534]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1534,
+ },
+ [0x1535]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1535,
+ },
+ [0x1536]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1536,
+ },
+ [0x1537]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1537,
+ },
+ [0x1538]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1538,
+ },
+ [0x1539]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1539,
+ },
+ [0x153A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153A,
+ },
+ [0x153B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153B,
+ },
+ [0x153C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153C,
+ },
+ [0x153D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153D,
+ },
+ [0x153E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153E,
+ },
+ [0x153F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x153F,
+ },
+ [0x1540]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1540,
+ },
+ [0x1541]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1541,
+ },
+ [0x1542]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1542,
+ },
+ [0x1543]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1543,
+ },
+ [0x1544]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1544,
+ },
+ [0x1545]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1545,
+ },
+ [0x1546]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1546,
+ },
+ [0x1547]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1547,
+ },
+ [0x1548]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1548,
+ },
+ [0x1549]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1549,
+ },
+ [0x154A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x154A,
+ },
+ [0x154B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x154B,
+ },
+ [0x154C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x154C,
+ },
+ [0x154D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x154D,
+ },
+ [0x154E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x154E,
+ },
+ [0x154F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x154F,
+ },
+ [0x1550]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1550,
+ },
+ [0x1551]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1551,
+ },
+ [0x1552]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1552,
+ },
+ [0x1553]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1553,
+ },
+ [0x1554]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1554,
+ },
+ [0x1555]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1555,
+ },
+ [0x1556]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1556,
+ },
+ [0x1557]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1557,
+ },
+ [0x1558]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1558,
+ },
+ [0x1559]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1559,
+ },
+ [0x155A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x155A,
+ },
+ [0x155B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x155B,
+ },
+ [0x155C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x155C,
+ },
+ [0x155D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x155D,
+ },
+ [0x155E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x155E,
+ },
+ [0x155F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x155F,
+ },
+ [0x1560]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1560,
+ },
+ [0x1561]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1561,
+ },
+ [0x1562]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1562,
+ },
+ [0x1563]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1563,
+ },
+ [0x1564]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1564,
+ },
+ [0x1565]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1565,
+ },
+ [0x1566]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1566,
+ },
+ [0x1567]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1567,
+ },
+ [0x1568]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1568,
+ },
+ [0x1569]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1569,
+ },
+ [0x156A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x156A,
+ },
+ [0x156B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x156B,
+ },
+ [0x156C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x156C,
+ },
+ [0x156D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x156D,
+ },
+ [0x156E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x156E,
+ },
+ [0x156F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x156F,
+ },
+ [0x1570]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1570,
+ },
+ [0x1571]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1571,
+ },
+ [0x1572]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1572,
+ },
+ [0x1573]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1573,
+ },
+ [0x1574]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1574,
+ },
+ [0x1575]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1575,
+ },
+ [0x1576]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1576,
+ },
+ [0x1577]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1577,
+ },
+ [0x1578]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1578,
+ },
+ [0x1579]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1579,
+ },
+ [0x157A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x157A,
+ },
+ [0x157B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x157B,
+ },
+ [0x157C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x157C,
+ },
+ [0x157D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x157D,
+ },
+ [0x157E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x157E,
+ },
+ [0x157F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x157F,
+ },
+ [0x1580]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1580,
+ },
+ [0x1581]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1581,
+ },
+ [0x1582]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1582,
+ },
+ [0x1583]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1583,
+ },
+ [0x1584]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1584,
+ },
+ [0x1585]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1585,
+ },
+ [0x1586]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1586,
+ },
+ [0x1587]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1587,
+ },
+ [0x1588]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1588,
+ },
+ [0x1589]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1589,
+ },
+ [0x158A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x158A,
+ },
+ [0x158B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x158B,
+ },
+ [0x158C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x158C,
+ },
+ [0x158D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x158D,
+ },
+ [0x158E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x158E,
+ },
+ [0x158F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x158F,
+ },
+ [0x1590]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1590,
+ },
+ [0x1591]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1591,
+ },
+ [0x1592]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1592,
+ },
+ [0x1593]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1593,
+ },
+ [0x1594]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1594,
+ },
+ [0x1595]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1595,
+ },
+ [0x1596]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1596,
+ },
+ [0x1597]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1597,
+ },
+ [0x1598]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1598,
+ },
+ [0x1599]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1599,
+ },
+ [0x159A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x159A,
+ },
+ [0x159B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x159B,
+ },
+ [0x159C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x159C,
+ },
+ [0x159D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x159D,
+ },
+ [0x159E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x159E,
+ },
+ [0x159F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x159F,
+ },
+ [0x15A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A0,
+ },
+ [0x15A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A1,
+ },
+ [0x15A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A2,
+ },
+ [0x15A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A3,
+ },
+ [0x15A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A4,
+ },
+ [0x15A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A5,
+ },
+ [0x15A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A6,
+ },
+ [0x15A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A7,
+ },
+ [0x15A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A8,
+ },
+ [0x15A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15A9,
+ },
+ [0x15AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15AA,
+ },
+ [0x15AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15AB,
+ },
+ [0x15AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15AC,
+ },
+ [0x15AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15AD,
+ },
+ [0x15AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15AE,
+ },
+ [0x15AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15AF,
+ },
+ [0x15B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B0,
+ },
+ [0x15B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B1,
+ },
+ [0x15B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B2,
+ },
+ [0x15B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B3,
+ },
+ [0x15B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B4,
+ },
+ [0x15B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B5,
+ },
+ [0x15B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B6,
+ },
+ [0x15B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B7,
+ },
+ [0x15B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B8,
+ },
+ [0x15B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15B9,
+ },
+ [0x15BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15BA,
+ },
+ [0x15BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15BB,
+ },
+ [0x15BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15BC,
+ },
+ [0x15BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15BD,
+ },
+ [0x15BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15BE,
+ },
+ [0x15BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15BF,
+ },
+ [0x15C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C0,
+ },
+ [0x15C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C1,
+ },
+ [0x15C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C2,
+ },
+ [0x15C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C3,
+ },
+ [0x15C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C4,
+ },
+ [0x15C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C5,
+ },
+ [0x15C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C6,
+ },
+ [0x15C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C7,
+ },
+ [0x15C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C8,
+ },
+ [0x15C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15C9,
+ },
+ [0x15CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15CA,
+ },
+ [0x15CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15CB,
+ },
+ [0x15CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15CC,
+ },
+ [0x15CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15CD,
+ },
+ [0x15CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15CE,
+ },
+ [0x15CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15CF,
+ },
+ [0x15D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D0,
+ },
+ [0x15D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D1,
+ },
+ [0x15D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D2,
+ },
+ [0x15D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D3,
+ },
+ [0x15D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D4,
+ },
+ [0x15D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D5,
+ },
+ [0x15D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D6,
+ },
+ [0x15D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D7,
+ },
+ [0x15D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D8,
+ },
+ [0x15D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15D9,
+ },
+ [0x15DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15DA,
+ },
+ [0x15DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15DB,
+ },
+ [0x15DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15DC,
+ },
+ [0x15DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15DD,
+ },
+ [0x15DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15DE,
+ },
+ [0x15DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15DF,
+ },
+ [0x15E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E0,
+ },
+ [0x15E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E1,
+ },
+ [0x15E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E2,
+ },
+ [0x15E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E3,
+ },
+ [0x15E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E4,
+ },
+ [0x15E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E5,
+ },
+ [0x15E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E6,
+ },
+ [0x15E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E7,
+ },
+ [0x15E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E8,
+ },
+ [0x15E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15E9,
+ },
+ [0x15EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15EA,
+ },
+ [0x15EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15EB,
+ },
+ [0x15EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15EC,
+ },
+ [0x15ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15ED,
+ },
+ [0x15EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15EE,
+ },
+ [0x15EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15EF,
+ },
+ [0x15F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F0,
+ },
+ [0x15F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F1,
+ },
+ [0x15F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F2,
+ },
+ [0x15F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F3,
+ },
+ [0x15F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F4,
+ },
+ [0x15F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F5,
+ },
+ [0x15F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F6,
+ },
+ [0x15F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F7,
+ },
+ [0x15F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F8,
+ },
+ [0x15F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15F9,
+ },
+ [0x15FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15FA,
+ },
+ [0x15FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15FB,
+ },
+ [0x15FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15FC,
+ },
+ [0x15FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15FD,
+ },
+ [0x15FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15FE,
+ },
+ [0x15FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x15FF,
+ },
+ [0x1600]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1600,
+ },
+ [0x1601]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1601,
+ },
+ [0x1602]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1602,
+ },
+ [0x1603]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1603,
+ },
+ [0x1604]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1604,
+ },
+ [0x1605]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1605,
+ },
+ [0x1606]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1606,
+ },
+ [0x1607]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1607,
+ },
+ [0x1608]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1608,
+ },
+ [0x1609]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1609,
+ },
+ [0x160A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x160A,
+ },
+ [0x160B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x160B,
+ },
+ [0x160C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x160C,
+ },
+ [0x160D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x160D,
+ },
+ [0x160E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x160E,
+ },
+ [0x160F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x160F,
+ },
+ [0x1610]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1610,
+ },
+ [0x1611]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1611,
+ },
+ [0x1612]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1612,
+ },
+ [0x1613]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1613,
+ },
+ [0x1614]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1614,
+ },
+ [0x1615]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1615,
+ },
+ [0x1616]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1616,
+ },
+ [0x1617]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1617,
+ },
+ [0x1618]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1618,
+ },
+ [0x1619]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1619,
+ },
+ [0x161A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x161A,
+ },
+ [0x161B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x161B,
+ },
+ [0x161C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x161C,
+ },
+ [0x161D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x161D,
+ },
+ [0x161E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x161E,
+ },
+ [0x161F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x161F,
+ },
+ [0x1620]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1620,
+ },
+ [0x1621]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1621,
+ },
+ [0x1622]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1622,
+ },
+ [0x1623]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1623,
+ },
+ [0x1624]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1624,
+ },
+ [0x1625]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1625,
+ },
+ [0x1626]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1626,
+ },
+ [0x1627]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1627,
+ },
+ [0x1628]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1628,
+ },
+ [0x1629]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1629,
+ },
+ [0x162A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x162A,
+ },
+ [0x162B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x162B,
+ },
+ [0x162C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x162C,
+ },
+ [0x162D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x162D,
+ },
+ [0x162E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x162E,
+ },
+ [0x162F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x162F,
+ },
+ [0x1630]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1630,
+ },
+ [0x1631]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1631,
+ },
+ [0x1632]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1632,
+ },
+ [0x1633]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1633,
+ },
+ [0x1634]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1634,
+ },
+ [0x1635]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1635,
+ },
+ [0x1636]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1636,
+ },
+ [0x1637]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1637,
+ },
+ [0x1638]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1638,
+ },
+ [0x1639]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1639,
+ },
+ [0x163A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x163A,
+ },
+ [0x163B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x163B,
+ },
+ [0x163C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x163C,
+ },
+ [0x163D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x163D,
+ },
+ [0x163E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x163E,
+ },
+ [0x163F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x163F,
+ },
+ [0x1640]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1640,
+ },
+ [0x1641]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1641,
+ },
+ [0x1642]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1642,
+ },
+ [0x1643]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1643,
+ },
+ [0x1644]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1644,
+ },
+ [0x1645]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1645,
+ },
+ [0x1646]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1646,
+ },
+ [0x1647]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1647,
+ },
+ [0x1648]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1648,
+ },
+ [0x1649]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1649,
+ },
+ [0x164A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x164A,
+ },
+ [0x164B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x164B,
+ },
+ [0x164C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x164C,
+ },
+ [0x164D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x164D,
+ },
+ [0x164E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x164E,
+ },
+ [0x164F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x164F,
+ },
+ [0x1650]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1650,
+ },
+ [0x1651]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1651,
+ },
+ [0x1652]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1652,
+ },
+ [0x1653]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1653,
+ },
+ [0x1654]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1654,
+ },
+ [0x1655]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1655,
+ },
+ [0x1656]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1656,
+ },
+ [0x1657]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1657,
+ },
+ [0x1658]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1658,
+ },
+ [0x1659]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1659,
+ },
+ [0x165A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x165A,
+ },
+ [0x165B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x165B,
+ },
+ [0x165C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x165C,
+ },
+ [0x165D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x165D,
+ },
+ [0x165E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x165E,
+ },
+ [0x165F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x165F,
+ },
+ [0x1660]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1660,
+ },
+ [0x1661]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1661,
+ },
+ [0x1662]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1662,
+ },
+ [0x1663]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1663,
+ },
+ [0x1664]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1664,
+ },
+ [0x1665]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1665,
+ },
+ [0x1666]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1666,
+ },
+ [0x1667]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1667,
+ },
+ [0x1668]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1668,
+ },
+ [0x1669]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1669,
+ },
+ [0x166A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166A,
+ },
+ [0x166B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166B,
+ },
+ [0x166C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166C,
+ },
+ [0x166D]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166D,
+ },
+ [0x166E]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166E,
+ },
+ [0x166F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x166F,
+ },
+ [0x1670]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1670,
+ },
+ [0x1671]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1671,
+ },
+ [0x1672]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1672,
+ },
+ [0x1673]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1673,
+ },
+ [0x1674]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1674,
+ },
+ [0x1675]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1675,
+ },
+ [0x1676]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1676,
+ },
+ [0x1677]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1677,
+ },
+ [0x1678]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1678,
+ },
+ [0x1679]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1679,
+ },
+ [0x167A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167A,
+ },
+ [0x167B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167B,
+ },
+ [0x167C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167C,
+ },
+ [0x167D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167D,
+ },
+ [0x167E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167E,
+ },
+ [0x167F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x167F,
+ },
+ [0x1680]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ unicodeslot=0x1680,
+ },
+ [0x1681]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681,
+ },
+ [0x1682]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682,
+ },
+ [0x1683]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683,
+ },
+ [0x1684]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684,
+ },
+ [0x1685]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685,
+ },
+ [0x1686]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686,
+ },
+ [0x1687]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687,
+ },
+ [0x1688]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688,
+ },
+ [0x1689]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689,
+ },
+ [0x168A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A,
+ },
+ [0x168B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B,
+ },
+ [0x168C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C,
+ },
+ [0x168D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D,
+ },
+ [0x168E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E,
+ },
+ [0x168F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F,
+ },
+ [0x1690]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690,
+ },
+ [0x1691]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691,
+ },
+ [0x1692]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692,
+ },
+ [0x1693]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693,
+ },
+ [0x1694]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694,
+ },
+ [0x1695]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695,
+ },
+ [0x1696]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696,
+ },
+ [0x1697]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697,
+ },
+ [0x1698]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698,
+ },
+ [0x1699]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699,
+ },
+ [0x169A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A,
+ },
+ [0x169B]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x169C,
+ unicodeslot=0x169B,
+ },
+ [0x169C]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x169B,
+ unicodeslot=0x169C,
+ },
+ [0x16A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0,
+ },
+ [0x16A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1,
+ },
+ [0x16A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2,
+ },
+ [0x16A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A3,
+ },
+ [0x16A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4,
+ },
+ [0x16A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A5,
+ },
+ [0x16A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A6,
+ },
+ [0x16A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A7,
+ },
+ [0x16A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A8,
+ },
+ [0x16A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A9,
+ },
+ [0x16AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AA,
+ },
+ [0x16AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AB,
+ },
+ [0x16AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AC,
+ },
+ [0x16AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD,
+ },
+ [0x16AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE,
+ },
+ [0x16AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AF,
+ },
+ [0x16B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0,
+ },
+ [0x16B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1,
+ },
+ [0x16B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2,
+ },
+ [0x16B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3,
+ },
+ [0x16B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B4,
+ },
+ [0x16B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B5,
+ },
+ [0x16B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6,
+ },
+ [0x16B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B7,
+ },
+ [0x16B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8,
+ },
+ [0x16B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B9,
+ },
+ [0x16BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16BA,
+ },
+ [0x16BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16BB,
+ },
+ [0x16BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16BC,
+ },
+ [0x16BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16BD,
+ },
+ [0x16BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16BE,
+ },
+ [0x16BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16BF,
+ },
+ [0x16C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C0,
+ },
+ [0x16C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C1,
+ },
+ [0x16C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C2,
+ },
+ [0x16C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C3,
+ },
+ [0x16C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C4,
+ },
+ [0x16C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C5,
+ },
+ [0x16C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C6,
+ },
+ [0x16C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C7,
+ },
+ [0x16C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C8,
+ },
+ [0x16C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16C9,
+ },
+ [0x16CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16CA,
+ },
+ [0x16CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16CB,
+ },
+ [0x16CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16CC,
+ },
+ [0x16CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16CD,
+ },
+ [0x16CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16CE,
+ },
+ [0x16CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16CF,
+ },
+ [0x16D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D0,
+ },
+ [0x16D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D1,
+ },
+ [0x16D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D2,
+ },
+ [0x16D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D3,
+ },
+ [0x16D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D4,
+ },
+ [0x16D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D5,
+ },
+ [0x16D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D6,
+ },
+ [0x16D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D7,
+ },
+ [0x16D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D8,
+ },
+ [0x16D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16D9,
+ },
+ [0x16DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16DA,
+ },
+ [0x16DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16DB,
+ },
+ [0x16DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16DC,
+ },
+ [0x16DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16DD,
+ },
+ [0x16DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16DE,
+ },
+ [0x16DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16DF,
+ },
+ [0x16E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E0,
+ },
+ [0x16E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E1,
+ },
+ [0x16E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E2,
+ },
+ [0x16E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E3,
+ },
+ [0x16E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4,
+ },
+ [0x16E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5,
+ },
+ [0x16E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6,
+ },
+ [0x16E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7,
+ },
+ [0x16E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8,
+ },
+ [0x16E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E9,
+ },
+ [0x16EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16EA,
+ },
+ [0x16EB]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16EB,
+ },
+ [0x16EC]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16EC,
+ },
+ [0x16ED]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16ED,
+ },
+ [0x16EE]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16EE,
+ },
+ [0x16EF]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16EF,
+ },
+ [0x16F0]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0,
+ },
+ [0x16F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1,
+ },
+ [0x16F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2,
+ },
+ [0x16F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3,
+ },
+ [0x16F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F4,
+ },
+ [0x16F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F5,
+ },
+ [0x16F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F6,
+ },
+ [0x16F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F7,
+ },
+ [0x16F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F8,
+ },
+ [0x1700]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1700,
+ },
+ [0x1701]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1701,
+ },
+ [0x1702]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1702,
+ },
+ [0x1703]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1703,
+ },
+ [0x1704]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1704,
+ },
+ [0x1705]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1705,
+ },
+ [0x1706]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1706,
+ },
+ [0x1707]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1707,
+ },
+ [0x1708]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1708,
+ },
+ [0x1709]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1709,
+ },
+ [0x170A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x170A,
+ },
+ [0x170B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x170B,
+ },
+ [0x170C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x170C,
+ },
+ [0x170E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x170E,
+ },
+ [0x170F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x170F,
+ },
+ [0x1710]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1710,
+ },
+ [0x1711]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1711,
+ },
+ [0x1712]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1712,
+ },
+ [0x1713]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1713,
+ },
+ [0x1714]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1714,
+ },
+ [0x1720]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1720,
+ },
+ [0x1721]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1721,
+ },
+ [0x1722]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1722,
+ },
+ [0x1723]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1723,
+ },
+ [0x1724]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1724,
+ },
+ [0x1725]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1725,
+ },
+ [0x1726]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1726,
+ },
+ [0x1727]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1727,
+ },
+ [0x1728]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1728,
+ },
+ [0x1729]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1729,
+ },
+ [0x172A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x172A,
+ },
+ [0x172B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x172B,
+ },
+ [0x172C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x172C,
+ },
+ [0x172D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x172D,
+ },
+ [0x172E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x172E,
+ },
+ [0x172F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x172F,
+ },
+ [0x1730]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1730,
+ },
+ [0x1731]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1731,
+ },
+ [0x1732]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1732,
+ },
+ [0x1733]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1733,
+ },
+ [0x1734]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1734,
+ },
+ [0x1735]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1735,
+ },
+ [0x1736]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1736,
+ },
+ [0x1740]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1740,
+ },
+ [0x1741]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1741,
+ },
+ [0x1742]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1742,
+ },
+ [0x1743]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1743,
+ },
+ [0x1744]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1744,
+ },
+ [0x1745]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1745,
+ },
+ [0x1746]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1746,
+ },
+ [0x1747]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1747,
+ },
+ [0x1748]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1748,
+ },
+ [0x1749]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1749,
+ },
+ [0x174A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x174A,
+ },
+ [0x174B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x174B,
+ },
+ [0x174C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x174C,
+ },
+ [0x174D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x174D,
+ },
+ [0x174E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x174E,
+ },
+ [0x174F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x174F,
+ },
+ [0x1750]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1750,
+ },
+ [0x1751]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1751,
+ },
+ [0x1752]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1752,
+ },
+ [0x1753]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1753,
+ },
+ [0x1760]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1760,
+ },
+ [0x1761]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1761,
+ },
+ [0x1762]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1762,
+ },
+ [0x1763]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1763,
+ },
+ [0x1764]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1764,
+ },
+ [0x1765]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1765,
+ },
+ [0x1766]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1766,
+ },
+ [0x1767]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1767,
+ },
+ [0x1768]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1768,
+ },
+ [0x1769]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1769,
+ },
+ [0x176A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x176A,
+ },
+ [0x176B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x176B,
+ },
+ [0x176C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x176C,
+ },
+ [0x176E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x176E,
+ },
+ [0x176F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x176F,
+ },
+ [0x1770]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1770,
+ },
+ [0x1772]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1772,
+ },
+ [0x1773]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1773,
+ },
+ [0x1780]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1780,
+ },
+ [0x1781]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1781,
+ },
+ [0x1782]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1782,
+ },
+ [0x1783]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1783,
+ },
+ [0x1784]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1784,
+ },
+ [0x1785]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1785,
+ },
+ [0x1786]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1786,
+ },
+ [0x1787]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1787,
+ },
+ [0x1788]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1788,
+ },
+ [0x1789]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1789,
+ },
+ [0x178A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x178A,
+ },
+ [0x178B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x178B,
+ },
+ [0x178C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x178C,
+ },
+ [0x178D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x178D,
+ },
+ [0x178E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x178E,
+ },
+ [0x178F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x178F,
+ },
+ [0x1790]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1790,
+ },
+ [0x1791]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1791,
+ },
+ [0x1792]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1792,
+ },
+ [0x1793]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1793,
+ },
+ [0x1794]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1794,
+ },
+ [0x1795]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1795,
+ },
+ [0x1796]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1796,
+ },
+ [0x1797]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1797,
+ },
+ [0x1798]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1798,
+ },
+ [0x1799]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1799,
+ },
+ [0x179A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x179A,
+ },
+ [0x179B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x179B,
+ },
+ [0x179C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x179C,
+ },
+ [0x179D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x179D,
+ },
+ [0x179E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x179E,
+ },
+ [0x179F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x179F,
+ },
+ [0x17A0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A0,
+ },
+ [0x17A1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A1,
+ },
+ [0x17A2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A2,
+ },
+ [0x17A3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A3,
+ },
+ [0x17A4]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A4,
+ },
+ [0x17A5]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A5,
+ },
+ [0x17A6]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A6,
+ },
+ [0x17A7]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A7,
+ },
+ [0x17A8]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A8,
+ },
+ [0x17A9]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17A9,
+ },
+ [0x17AA]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17AA,
+ },
+ [0x17AB]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17AB,
+ },
+ [0x17AC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17AC,
+ },
+ [0x17AD]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17AD,
+ },
+ [0x17AE]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17AE,
+ },
+ [0x17AF]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17AF,
+ },
+ [0x17B0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17B0,
+ },
+ [0x17B1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17B1,
+ },
+ [0x17B2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17B2,
+ },
+ [0x17B3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17B3,
+ },
+ [0x17B4]={
+ category="cf",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17B4,
+ },
+ [0x17B5]={
+ category="cf",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17B5,
+ },
+ [0x17B6]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17B6,
+ },
+ [0x17B7]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17B7,
+ },
+ [0x17B8]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17B8,
+ },
+ [0x17B9]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17B9,
+ },
+ [0x17BA]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17BA,
+ },
+ [0x17BB]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17BB,
+ },
+ [0x17BC]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17BC,
+ },
+ [0x17BD]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17BD,
+ },
+ [0x17BE]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17BE,
+ },
+ [0x17BF]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17BF,
+ },
+ [0x17C0]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C0,
+ },
+ [0x17C1]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C1,
+ },
+ [0x17C2]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C2,
+ },
+ [0x17C3]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C3,
+ },
+ [0x17C4]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C4,
+ },
+ [0x17C5]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C5,
+ },
+ [0x17C6]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17C6,
+ },
+ [0x17C7]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C7,
+ },
+ [0x17C8]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17C8,
+ },
+ [0x17C9]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17C9,
+ },
+ [0x17CA]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17CA,
+ },
+ [0x17CB]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17CB,
+ },
+ [0x17CC]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17CC,
+ },
+ [0x17CD]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17CD,
+ },
+ [0x17CE]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17CE,
+ },
+ [0x17CF]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17CF,
+ },
+ [0x17D0]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17D0,
+ },
+ [0x17D1]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17D1,
+ },
+ [0x17D2]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17D2,
+ },
+ [0x17D3]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17D3,
+ },
+ [0x17D4]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x17D4,
+ },
+ [0x17D5]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x17D5,
+ },
+ [0x17D6]={
+ category="po",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x17D6,
+ },
+ [0x17D7]={
+ category="lm",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17D7,
+ },
+ [0x17D8]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x17D8,
+ },
+ [0x17D9]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x17D9,
+ },
+ [0x17DA]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x17DA,
+ },
+ [0x17DB]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x17DB,
+ },
+ [0x17DC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x17DC,
+ },
+ [0x17DD]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x17DD,
+ },
+ [0x17E0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E0,
+ },
+ [0x17E1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E1,
+ },
+ [0x17E2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E2,
+ },
+ [0x17E3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E3,
+ },
+ [0x17E4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E4,
+ },
+ [0x17E5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E5,
+ },
+ [0x17E6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E6,
+ },
+ [0x17E7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E7,
+ },
+ [0x17E8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E8,
+ },
+ [0x17E9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x17E9,
+ },
+ [0x17F0]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F0,
+ },
+ [0x17F1]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F1,
+ },
+ [0x17F2]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F2,
+ },
+ [0x17F3]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F3,
+ },
+ [0x17F4]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F4,
+ },
+ [0x17F5]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F5,
+ },
+ [0x17F6]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F6,
+ },
+ [0x17F7]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F7,
+ },
+ [0x17F8]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F8,
+ },
+ [0x17F9]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x17F9,
+ },
+ [0x1800]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1800,
+ },
+ [0x1801]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1801,
+ },
+ [0x1802]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x1802,
+ },
+ [0x1803]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x1803,
+ },
+ [0x1804]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x1804,
+ },
+ [0x1805]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x1805,
+ },
+ [0x1806]={
+ category="pd",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x1806,
+ },
+ [0x1807]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1807,
+ },
+ [0x1808]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x1808,
+ },
+ [0x1809]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x1809,
+ },
+ [0x180A]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x180A,
+ },
+ [0x180B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x180B,
+ },
+ [0x180C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x180C,
+ },
+ [0x180D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x180D,
+ },
+ [0x180E]={
+ category="zs",
+ direction="bn",
+ linebreak="gl",
+ unicodeslot=0x180E,
+ },
+ [0x1810]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1810,
+ },
+ [0x1811]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1811,
+ },
+ [0x1812]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1812,
+ },
+ [0x1813]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1813,
+ },
+ [0x1814]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1814,
+ },
+ [0x1815]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1815,
+ },
+ [0x1816]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1816,
+ },
+ [0x1817]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1817,
+ },
+ [0x1818]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1818,
+ },
+ [0x1819]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1819,
+ },
+ [0x1820]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1820,
+ },
+ [0x1821]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1821,
+ },
+ [0x1822]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1822,
+ },
+ [0x1823]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1823,
+ },
+ [0x1824]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1824,
+ },
+ [0x1825]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1825,
+ },
+ [0x1826]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1826,
+ },
+ [0x1827]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1827,
+ },
+ [0x1828]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1828,
+ },
+ [0x1829]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1829,
+ },
+ [0x182A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182A,
+ },
+ [0x182B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182B,
+ },
+ [0x182C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182C,
+ },
+ [0x182D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182D,
+ },
+ [0x182E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182E,
+ },
+ [0x182F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x182F,
+ },
+ [0x1830]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1830,
+ },
+ [0x1831]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1831,
+ },
+ [0x1832]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1832,
+ },
+ [0x1833]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1833,
+ },
+ [0x1834]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1834,
+ },
+ [0x1835]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1835,
+ },
+ [0x1836]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1836,
+ },
+ [0x1837]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1837,
+ },
+ [0x1838]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1838,
+ },
+ [0x1839]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1839,
+ },
+ [0x183A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183A,
+ },
+ [0x183B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183B,
+ },
+ [0x183C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183C,
+ },
+ [0x183D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183D,
+ },
+ [0x183E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183E,
+ },
+ [0x183F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x183F,
+ },
+ [0x1840]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1840,
+ },
+ [0x1841]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1841,
+ },
+ [0x1842]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1842,
+ },
+ [0x1843]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1843,
+ },
+ [0x1844]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1844,
+ },
+ [0x1845]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1845,
+ },
+ [0x1846]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1846,
+ },
+ [0x1847]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1847,
+ },
+ [0x1848]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1848,
+ },
+ [0x1849]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1849,
+ },
+ [0x184A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184A,
+ },
+ [0x184B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184B,
+ },
+ [0x184C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184C,
+ },
+ [0x184D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184D,
+ },
+ [0x184E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184E,
+ },
+ [0x184F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x184F,
+ },
+ [0x1850]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1850,
+ },
+ [0x1851]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1851,
+ },
+ [0x1852]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1852,
+ },
+ [0x1853]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1853,
+ },
+ [0x1854]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1854,
+ },
+ [0x1855]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1855,
+ },
+ [0x1856]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1856,
+ },
+ [0x1857]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1857,
+ },
+ [0x1858]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1858,
+ },
+ [0x1859]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1859,
+ },
+ [0x185A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185A,
+ },
+ [0x185B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185B,
+ },
+ [0x185C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185C,
+ },
+ [0x185D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185D,
+ },
+ [0x185E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185E,
+ },
+ [0x185F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x185F,
+ },
+ [0x1860]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1860,
+ },
+ [0x1861]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1861,
+ },
+ [0x1862]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1862,
+ },
+ [0x1863]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1863,
+ },
+ [0x1864]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1864,
+ },
+ [0x1865]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1865,
+ },
+ [0x1866]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1866,
+ },
+ [0x1867]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1867,
+ },
+ [0x1868]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1868,
+ },
+ [0x1869]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1869,
+ },
+ [0x186A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186A,
+ },
+ [0x186B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186B,
+ },
+ [0x186C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186C,
+ },
+ [0x186D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186D,
+ },
+ [0x186E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186E,
+ },
+ [0x186F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x186F,
+ },
+ [0x1870]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1870,
+ },
+ [0x1871]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1871,
+ },
+ [0x1872]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1872,
+ },
+ [0x1873]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1873,
+ },
+ [0x1874]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1874,
+ },
+ [0x1875]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1875,
+ },
+ [0x1876]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1876,
+ },
+ [0x1877]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1877,
+ },
+ [0x1878]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1878,
+ },
+ [0x1880]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1880,
+ },
+ [0x1881]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1881,
+ },
+ [0x1882]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1882,
+ },
+ [0x1883]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1883,
+ },
+ [0x1884]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1884,
+ },
+ [0x1885]={
+ category="lo",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1885,
+ },
+ [0x1886]={
+ category="lo",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1886,
+ },
+ [0x1887]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1887,
+ },
+ [0x1888]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1888,
+ },
+ [0x1889]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1889,
+ },
+ [0x188A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188A,
+ },
+ [0x188B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188B,
+ },
+ [0x188C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188C,
+ },
+ [0x188D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188D,
+ },
+ [0x188E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188E,
+ },
+ [0x188F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x188F,
+ },
+ [0x1890]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1890,
+ },
+ [0x1891]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1891,
+ },
+ [0x1892]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1892,
+ },
+ [0x1893]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1893,
+ },
+ [0x1894]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1894,
+ },
+ [0x1895]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1895,
+ },
+ [0x1896]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1896,
+ },
+ [0x1897]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1897,
+ },
+ [0x1898]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1898,
+ },
+ [0x1899]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1899,
+ },
+ [0x189A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189A,
+ },
+ [0x189B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189B,
+ },
+ [0x189C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189C,
+ },
+ [0x189D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189D,
+ },
+ [0x189E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189E,
+ },
+ [0x189F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x189F,
+ },
+ [0x18A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A0,
+ },
+ [0x18A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A1,
+ },
+ [0x18A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A2,
+ },
+ [0x18A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A3,
+ },
+ [0x18A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A4,
+ },
+ [0x18A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A5,
+ },
+ [0x18A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A6,
+ },
+ [0x18A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A7,
+ },
+ [0x18A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18A8,
+ },
+ [0x18A9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x18A9,
+ },
+ [0x18AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18AA,
+ },
+ [0x18B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B0,
+ },
+ [0x18B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B1,
+ },
+ [0x18B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B2,
+ },
+ [0x18B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B3,
+ },
+ [0x18B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B4,
+ },
+ [0x18B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B5,
+ },
+ [0x18B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B6,
+ },
+ [0x18B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B7,
+ },
+ [0x18B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B8,
+ },
+ [0x18B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18B9,
+ },
+ [0x18BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18BA,
+ },
+ [0x18BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18BB,
+ },
+ [0x18BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18BC,
+ },
+ [0x18BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18BD,
+ },
+ [0x18BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18BE,
+ },
+ [0x18BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18BF,
+ },
+ [0x18C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C0,
+ },
+ [0x18C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C1,
+ },
+ [0x18C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C2,
+ },
+ [0x18C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C3,
+ },
+ [0x18C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C4,
+ },
+ [0x18C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C5,
+ },
+ [0x18C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C6,
+ },
+ [0x18C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C7,
+ },
+ [0x18C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C8,
+ },
+ [0x18C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18C9,
+ },
+ [0x18CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18CA,
+ },
+ [0x18CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18CB,
+ },
+ [0x18CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18CC,
+ },
+ [0x18CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18CD,
+ },
+ [0x18CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18CE,
+ },
+ [0x18CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18CF,
+ },
+ [0x18D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D0,
+ },
+ [0x18D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D1,
+ },
+ [0x18D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D2,
+ },
+ [0x18D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D3,
+ },
+ [0x18D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D4,
+ },
+ [0x18D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D5,
+ },
+ [0x18D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D6,
+ },
+ [0x18D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D7,
+ },
+ [0x18D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D8,
+ },
+ [0x18D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18D9,
+ },
+ [0x18DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18DA,
+ },
+ [0x18DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18DB,
+ },
+ [0x18DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18DC,
+ },
+ [0x18DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18DD,
+ },
+ [0x18DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18DE,
+ },
+ [0x18DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18DF,
+ },
+ [0x18E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E0,
+ },
+ [0x18E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E1,
+ },
+ [0x18E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E2,
+ },
+ [0x18E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E3,
+ },
+ [0x18E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E4,
+ },
+ [0x18E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E5,
+ },
+ [0x18E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E6,
+ },
+ [0x18E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E7,
+ },
+ [0x18E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E8,
+ },
+ [0x18E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18E9,
+ },
+ [0x18EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18EA,
+ },
+ [0x18EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18EB,
+ },
+ [0x18EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18EC,
+ },
+ [0x18ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18ED,
+ },
+ [0x18EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18EE,
+ },
+ [0x18EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18EF,
+ },
+ [0x18F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F0,
+ },
+ [0x18F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F1,
+ },
+ [0x18F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F2,
+ },
+ [0x18F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F3,
+ },
+ [0x18F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F4,
+ },
+ [0x18F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x18F5,
+ },
+ [0x1900]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1900,
+ },
+ [0x1901]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1901,
+ },
+ [0x1902]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1902,
+ },
+ [0x1903]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1903,
+ },
+ [0x1904]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1904,
+ },
+ [0x1905]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1905,
+ },
+ [0x1906]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1906,
+ },
+ [0x1907]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1907,
+ },
+ [0x1908]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1908,
+ },
+ [0x1909]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1909,
+ },
+ [0x190A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190A,
+ },
+ [0x190B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190B,
+ },
+ [0x190C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190C,
+ },
+ [0x190D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190D,
+ },
+ [0x190E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190E,
+ },
+ [0x190F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x190F,
+ },
+ [0x1910]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1910,
+ },
+ [0x1911]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1911,
+ },
+ [0x1912]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1912,
+ },
+ [0x1913]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1913,
+ },
+ [0x1914]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1914,
+ },
+ [0x1915]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1915,
+ },
+ [0x1916]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1916,
+ },
+ [0x1917]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1917,
+ },
+ [0x1918]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1918,
+ },
+ [0x1919]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1919,
+ },
+ [0x191A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x191A,
+ },
+ [0x191B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x191B,
+ },
+ [0x191C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x191C,
+ },
+ [0x191D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x191D,
+ },
+ [0x191E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x191E,
+ },
+ [0x1920]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1920,
+ },
+ [0x1921]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1921,
+ },
+ [0x1922]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1922,
+ },
+ [0x1923]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1923,
+ },
+ [0x1924]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1924,
+ },
+ [0x1925]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1925,
+ },
+ [0x1926]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1926,
+ },
+ [0x1927]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1927,
+ },
+ [0x1928]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1928,
+ },
+ [0x1929]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1929,
+ },
+ [0x192A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x192A,
+ },
+ [0x192B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x192B,
+ },
+ [0x1930]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1930,
+ },
+ [0x1931]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1931,
+ },
+ [0x1932]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1932,
+ },
+ [0x1933]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1933,
+ },
+ [0x1934]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1934,
+ },
+ [0x1935]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1935,
+ },
+ [0x1936]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1936,
+ },
+ [0x1937]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1937,
+ },
+ [0x1938]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1938,
+ },
+ [0x1939]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1939,
+ },
+ [0x193A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x193A,
+ },
+ [0x193B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x193B,
+ },
+ [0x1940]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1940,
+ },
+ [0x1944]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x1944,
+ },
+ [0x1945]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x1945,
+ },
+ [0x1946]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1946,
+ },
+ [0x1947]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1947,
+ },
+ [0x1948]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1948,
+ },
+ [0x1949]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1949,
+ },
+ [0x194A]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x194A,
+ },
+ [0x194B]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x194B,
+ },
+ [0x194C]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x194C,
+ },
+ [0x194D]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x194D,
+ },
+ [0x194E]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x194E,
+ },
+ [0x194F]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x194F,
+ },
+ [0x1950]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1950,
+ },
+ [0x1951]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1951,
+ },
+ [0x1952]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1952,
+ },
+ [0x1953]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1953,
+ },
+ [0x1954]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1954,
+ },
+ [0x1955]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1955,
+ },
+ [0x1956]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1956,
+ },
+ [0x1957]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1957,
+ },
+ [0x1958]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1958,
+ },
+ [0x1959]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1959,
+ },
+ [0x195A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x195A,
+ },
+ [0x195B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x195B,
+ },
+ [0x195C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x195C,
+ },
+ [0x195D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x195D,
+ },
+ [0x195E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x195E,
+ },
+ [0x195F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x195F,
+ },
+ [0x1960]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1960,
+ },
+ [0x1961]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1961,
+ },
+ [0x1962]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1962,
+ },
+ [0x1963]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1963,
+ },
+ [0x1964]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1964,
+ },
+ [0x1965]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1965,
+ },
+ [0x1966]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1966,
+ },
+ [0x1967]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1967,
+ },
+ [0x1968]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1968,
+ },
+ [0x1969]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1969,
+ },
+ [0x196A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x196A,
+ },
+ [0x196B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x196B,
+ },
+ [0x196C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x196C,
+ },
+ [0x196D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x196D,
+ },
+ [0x1970]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1970,
+ },
+ [0x1971]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1971,
+ },
+ [0x1972]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1972,
+ },
+ [0x1973]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1973,
+ },
+ [0x1974]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1974,
+ },
+ [0x1980]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1980,
+ },
+ [0x1981]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1981,
+ },
+ [0x1982]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1982,
+ },
+ [0x1983]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1983,
+ },
+ [0x1984]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1984,
+ },
+ [0x1985]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1985,
+ },
+ [0x1986]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1986,
+ },
+ [0x1987]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1987,
+ },
+ [0x1988]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1988,
+ },
+ [0x1989]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1989,
+ },
+ [0x198A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x198A,
+ },
+ [0x198B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x198B,
+ },
+ [0x198C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x198C,
+ },
+ [0x198D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x198D,
+ },
+ [0x198E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x198E,
+ },
+ [0x198F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x198F,
+ },
+ [0x1990]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1990,
+ },
+ [0x1991]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1991,
+ },
+ [0x1992]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1992,
+ },
+ [0x1993]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1993,
+ },
+ [0x1994]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1994,
+ },
+ [0x1995]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1995,
+ },
+ [0x1996]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1996,
+ },
+ [0x1997]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1997,
+ },
+ [0x1998]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1998,
+ },
+ [0x1999]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1999,
+ },
+ [0x199A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x199A,
+ },
+ [0x199B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x199B,
+ },
+ [0x199C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x199C,
+ },
+ [0x199D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x199D,
+ },
+ [0x199E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x199E,
+ },
+ [0x199F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x199F,
+ },
+ [0x19A0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A0,
+ },
+ [0x19A1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A1,
+ },
+ [0x19A2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A2,
+ },
+ [0x19A3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A3,
+ },
+ [0x19A4]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A4,
+ },
+ [0x19A5]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A5,
+ },
+ [0x19A6]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A6,
+ },
+ [0x19A7]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A7,
+ },
+ [0x19A8]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A8,
+ },
+ [0x19A9]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19A9,
+ },
+ [0x19AA]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19AA,
+ },
+ [0x19AB]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19AB,
+ },
+ [0x19B0]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B0,
+ },
+ [0x19B1]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B1,
+ },
+ [0x19B2]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B2,
+ },
+ [0x19B3]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B3,
+ },
+ [0x19B4]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B4,
+ },
+ [0x19B5]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B5,
+ },
+ [0x19B6]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B6,
+ },
+ [0x19B7]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B7,
+ },
+ [0x19B8]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B8,
+ },
+ [0x19B9]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19B9,
+ },
+ [0x19BA]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19BA,
+ },
+ [0x19BB]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19BB,
+ },
+ [0x19BC]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19BC,
+ },
+ [0x19BD]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19BD,
+ },
+ [0x19BE]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19BE,
+ },
+ [0x19BF]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19BF,
+ },
+ [0x19C0]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C0,
+ },
+ [0x19C1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C1,
+ },
+ [0x19C2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C2,
+ },
+ [0x19C3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C3,
+ },
+ [0x19C4]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C4,
+ },
+ [0x19C5]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C5,
+ },
+ [0x19C6]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C6,
+ },
+ [0x19C7]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C7,
+ },
+ [0x19C8]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C8,
+ },
+ [0x19C9]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19C9,
+ },
+ [0x19D0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D0,
+ },
+ [0x19D1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D1,
+ },
+ [0x19D2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D2,
+ },
+ [0x19D3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D3,
+ },
+ [0x19D4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D4,
+ },
+ [0x19D5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D5,
+ },
+ [0x19D6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D6,
+ },
+ [0x19D7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D7,
+ },
+ [0x19D8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D8,
+ },
+ [0x19D9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x19D9,
+ },
+ [0x19DA]={
+ category="no",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x19DA,
+ },
+ [0x19DE]={
+ category="po",
+ direction="on",
+ linebreak="sa",
+ unicodeslot=0x19DE,
+ },
+ [0x19DF]={
+ category="po",
+ direction="on",
+ linebreak="sa",
+ unicodeslot=0x19DF,
+ },
+ [0x19E0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E0,
+ },
+ [0x19E1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E1,
+ },
+ [0x19E2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E2,
+ },
+ [0x19E3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E3,
+ },
+ [0x19E4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E4,
+ },
+ [0x19E5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E5,
+ },
+ [0x19E6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E6,
+ },
+ [0x19E7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E7,
+ },
+ [0x19E8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E8,
+ },
+ [0x19E9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19E9,
+ },
+ [0x19EA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19EA,
+ },
+ [0x19EB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19EB,
+ },
+ [0x19EC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19EC,
+ },
+ [0x19ED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19ED,
+ },
+ [0x19EE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19EE,
+ },
+ [0x19EF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19EF,
+ },
+ [0x19F0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F0,
+ },
+ [0x19F1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F1,
+ },
+ [0x19F2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F2,
+ },
+ [0x19F3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F3,
+ },
+ [0x19F4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F4,
+ },
+ [0x19F5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F5,
+ },
+ [0x19F6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F6,
+ },
+ [0x19F7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F7,
+ },
+ [0x19F8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F8,
+ },
+ [0x19F9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19F9,
+ },
+ [0x19FA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19FA,
+ },
+ [0x19FB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19FB,
+ },
+ [0x19FC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19FC,
+ },
+ [0x19FD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19FD,
+ },
+ [0x19FE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19FE,
+ },
+ [0x19FF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x19FF,
+ },
+ [0x1A00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A00,
+ },
+ [0x1A01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A01,
+ },
+ [0x1A02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A02,
+ },
+ [0x1A03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A03,
+ },
+ [0x1A04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A04,
+ },
+ [0x1A05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A05,
+ },
+ [0x1A06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A06,
+ },
+ [0x1A07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A07,
+ },
+ [0x1A08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A08,
+ },
+ [0x1A09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A09,
+ },
+ [0x1A0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A0A,
+ },
+ [0x1A0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A0B,
+ },
+ [0x1A0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A0C,
+ },
+ [0x1A0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A0D,
+ },
+ [0x1A0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A0E,
+ },
+ [0x1A0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A0F,
+ },
+ [0x1A10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A10,
+ },
+ [0x1A11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A11,
+ },
+ [0x1A12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A12,
+ },
+ [0x1A13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A13,
+ },
+ [0x1A14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A14,
+ },
+ [0x1A15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A15,
+ },
+ [0x1A16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A16,
+ },
+ [0x1A17]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1A17,
+ },
+ [0x1A18]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1A18,
+ },
+ [0x1A19]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1A19,
+ },
+ [0x1A1A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1A1A,
+ },
+ [0x1A1B]={
+ category="mc",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1A1B,
+ },
+ [0x1A1E]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A1E,
+ },
+ [0x1A1F]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1A1F,
+ },
+ [0x1A20]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A20,
+ },
+ [0x1A21]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A21,
+ },
+ [0x1A22]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A22,
+ },
+ [0x1A23]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A23,
+ },
+ [0x1A24]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A24,
+ },
+ [0x1A25]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A25,
+ },
+ [0x1A26]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A26,
+ },
+ [0x1A27]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A27,
+ },
+ [0x1A28]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A28,
+ },
+ [0x1A29]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A29,
+ },
+ [0x1A2A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A2A,
+ },
+ [0x1A2B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A2B,
+ },
+ [0x1A2C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A2C,
+ },
+ [0x1A2D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A2D,
+ },
+ [0x1A2E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A2E,
+ },
+ [0x1A2F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A2F,
+ },
+ [0x1A30]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A30,
+ },
+ [0x1A31]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A31,
+ },
+ [0x1A32]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A32,
+ },
+ [0x1A33]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A33,
+ },
+ [0x1A34]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A34,
+ },
+ [0x1A35]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A35,
+ },
+ [0x1A36]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A36,
+ },
+ [0x1A37]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A37,
+ },
+ [0x1A38]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A38,
+ },
+ [0x1A39]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A39,
+ },
+ [0x1A3A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A3A,
+ },
+ [0x1A3B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A3B,
+ },
+ [0x1A3C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A3C,
+ },
+ [0x1A3D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A3D,
+ },
+ [0x1A3E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A3E,
+ },
+ [0x1A3F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A3F,
+ },
+ [0x1A40]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A40,
+ },
+ [0x1A41]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A41,
+ },
+ [0x1A42]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A42,
+ },
+ [0x1A43]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A43,
+ },
+ [0x1A44]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A44,
+ },
+ [0x1A45]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A45,
+ },
+ [0x1A46]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A46,
+ },
+ [0x1A47]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A47,
+ },
+ [0x1A48]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A48,
+ },
+ [0x1A49]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A49,
+ },
+ [0x1A4A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A4A,
+ },
+ [0x1A4B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A4B,
+ },
+ [0x1A4C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A4C,
+ },
+ [0x1A4D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A4D,
+ },
+ [0x1A4E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A4E,
+ },
+ [0x1A4F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A4F,
+ },
+ [0x1A50]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A50,
+ },
+ [0x1A51]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A51,
+ },
+ [0x1A52]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A52,
+ },
+ [0x1A53]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A53,
+ },
+ [0x1A54]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A54,
+ },
+ [0x1A55]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A55,
+ },
+ [0x1A56]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A56,
+ },
+ [0x1A57]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A57,
+ },
+ [0x1A58]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A58,
+ },
+ [0x1A59]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A59,
+ },
+ [0x1A5A]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A5A,
+ },
+ [0x1A5B]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A5B,
+ },
+ [0x1A5C]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A5C,
+ },
+ [0x1A5D]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A5D,
+ },
+ [0x1A5E]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A5E,
+ },
+ [0x1A60]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A60,
+ },
+ [0x1A61]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A61,
+ },
+ [0x1A62]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A62,
+ },
+ [0x1A63]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A63,
+ },
+ [0x1A64]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A64,
+ },
+ [0x1A65]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A65,
+ },
+ [0x1A66]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A66,
+ },
+ [0x1A67]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A67,
+ },
+ [0x1A68]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A68,
+ },
+ [0x1A69]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A69,
+ },
+ [0x1A6A]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A6A,
+ },
+ [0x1A6B]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A6B,
+ },
+ [0x1A6C]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A6C,
+ },
+ [0x1A6D]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A6D,
+ },
+ [0x1A6E]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A6E,
+ },
+ [0x1A6F]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A6F,
+ },
+ [0x1A70]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A70,
+ },
+ [0x1A71]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A71,
+ },
+ [0x1A72]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1A72,
+ },
+ [0x1A73]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A73,
+ },
+ [0x1A74]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A74,
+ },
+ [0x1A75]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A75,
+ },
+ [0x1A76]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A76,
+ },
+ [0x1A77]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A77,
+ },
+ [0x1A78]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A78,
+ },
+ [0x1A79]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A79,
+ },
+ [0x1A7A]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A7A,
+ },
+ [0x1A7B]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A7B,
+ },
+ [0x1A7C]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1A7C,
+ },
+ [0x1A7F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1A7F,
+ },
+ [0x1A80]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A80,
+ },
+ [0x1A81]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A81,
+ },
+ [0x1A82]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A82,
+ },
+ [0x1A83]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A83,
+ },
+ [0x1A84]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A84,
+ },
+ [0x1A85]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A85,
+ },
+ [0x1A86]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A86,
+ },
+ [0x1A87]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A87,
+ },
+ [0x1A88]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A88,
+ },
+ [0x1A89]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A89,
+ },
+ [0x1A90]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A90,
+ },
+ [0x1A91]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A91,
+ },
+ [0x1A92]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A92,
+ },
+ [0x1A93]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A93,
+ },
+ [0x1A94]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A94,
+ },
+ [0x1A95]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A95,
+ },
+ [0x1A96]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A96,
+ },
+ [0x1A97]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A97,
+ },
+ [0x1A98]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A98,
+ },
+ [0x1A99]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1A99,
+ },
+ [0x1AA0]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA0,
+ },
+ [0x1AA1]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA1,
+ },
+ [0x1AA2]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA2,
+ },
+ [0x1AA3]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA3,
+ },
+ [0x1AA4]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA4,
+ },
+ [0x1AA5]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA5,
+ },
+ [0x1AA6]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA6,
+ },
+ [0x1AA7]={
+ category="lm",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA7,
+ },
+ [0x1AA8]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA8,
+ },
+ [0x1AA9]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AA9,
+ },
+ [0x1AAA]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AAA,
+ },
+ [0x1AAB]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AAB,
+ },
+ [0x1AAC]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AAC,
+ },
+ [0x1AAD]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1AAD,
+ },
+ [0x1AB0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB0,
+ },
+ [0x1AB1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB1,
+ },
+ [0x1AB2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB2,
+ },
+ [0x1AB3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB3,
+ },
+ [0x1AB4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB4,
+ },
+ [0x1AB5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB5,
+ },
+ [0x1AB6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB6,
+ },
+ [0x1AB7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB7,
+ },
+ [0x1AB8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB8,
+ },
+ [0x1AB9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1AB9,
+ },
+ [0x1ABA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1ABA,
+ },
+ [0x1ABB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1ABB,
+ },
+ [0x1ABC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1ABC,
+ },
+ [0x1ABD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1ABD,
+ },
+ [0x1ABE]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1ABE,
+ },
+ [0x1B00]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B00,
+ },
+ [0x1B01]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B01,
+ },
+ [0x1B02]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B02,
+ },
+ [0x1B03]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B03,
+ },
+ [0x1B04]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1B04,
+ },
+ [0x1B05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B05,
+ },
+ [0x1B06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B05, 0x1B35 },
+ unicodeslot=0x1B06,
+ },
+ [0x1B07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B07,
+ },
+ [0x1B08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B07, 0x1B35 },
+ unicodeslot=0x1B08,
+ },
+ [0x1B09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B09,
+ },
+ [0x1B0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B09, 0x1B35 },
+ unicodeslot=0x1B0A,
+ },
+ [0x1B0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B0B,
+ },
+ [0x1B0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0B, 0x1B35 },
+ unicodeslot=0x1B0C,
+ },
+ [0x1B0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B0D,
+ },
+ [0x1B0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0D, 0x1B35 },
+ unicodeslot=0x1B0E,
+ },
+ [0x1B0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B0F,
+ },
+ [0x1B10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B10,
+ },
+ [0x1B11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B11,
+ },
+ [0x1B12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B11, 0x1B35 },
+ unicodeslot=0x1B12,
+ },
+ [0x1B13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B13,
+ },
+ [0x1B14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B14,
+ },
+ [0x1B15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B15,
+ },
+ [0x1B16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B16,
+ },
+ [0x1B17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B17,
+ },
+ [0x1B18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B18,
+ },
+ [0x1B19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B19,
+ },
+ [0x1B1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1A,
+ },
+ [0x1B1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1B,
+ },
+ [0x1B1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1C,
+ },
+ [0x1B1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1D,
+ },
+ [0x1B1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1E,
+ },
+ [0x1B1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B1F,
+ },
+ [0x1B20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B20,
+ },
+ [0x1B21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B21,
+ },
+ [0x1B22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B22,
+ },
+ [0x1B23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B23,
+ },
+ [0x1B24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B24,
+ },
+ [0x1B25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B25,
+ },
+ [0x1B26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B26,
+ },
+ [0x1B27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B27,
+ },
+ [0x1B28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B28,
+ },
+ [0x1B29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B29,
+ },
+ [0x1B2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2A,
+ },
+ [0x1B2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2B,
+ },
+ [0x1B2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2C,
+ },
+ [0x1B2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2D,
+ },
+ [0x1B2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2E,
+ },
+ [0x1B2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B2F,
+ },
+ [0x1B30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B30,
+ },
+ [0x1B31]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B31,
+ },
+ [0x1B32]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B32,
+ },
+ [0x1B33]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B33,
+ },
+ [0x1B34]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B34,
+ },
+ [0x1B35]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1B35,
+ },
+ [0x1B36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B36,
+ },
+ [0x1B37]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B37,
+ },
+ [0x1B38]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B38,
+ },
+ [0x1B39]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B39,
+ },
+ [0x1B3A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B3A,
+ },
+ [0x1B3B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x1B3A, 0x1B35 },
+ unicodeslot=0x1B3B,
+ },
+ [0x1B3C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B3C,
+ },
+ [0x1B3D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x1B3C, 0x1B35 },
+ unicodeslot=0x1B3D,
+ },
+ [0x1B3E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1B3E,
+ },
+ [0x1B3F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1B3F,
+ },
+ [0x1B40]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x1B3E, 0x1B35 },
+ unicodeslot=0x1B40,
+ },
+ [0x1B41]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x1B3F, 0x1B35 },
+ unicodeslot=0x1B41,
+ },
+ [0x1B42]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B42,
+ },
+ [0x1B43]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x1B42, 0x1B35 },
+ unicodeslot=0x1B43,
+ },
+ [0x1B44]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1B44,
+ },
+ [0x1B45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B45,
+ },
+ [0x1B46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B46,
+ },
+ [0x1B47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B47,
+ },
+ [0x1B48]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B48,
+ },
+ [0x1B49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B49,
+ },
+ [0x1B4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B4A,
+ },
+ [0x1B4B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B4B,
+ },
+ [0x1B50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B50,
+ },
+ [0x1B51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B51,
+ },
+ [0x1B52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B52,
+ },
+ [0x1B53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B53,
+ },
+ [0x1B54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B54,
+ },
+ [0x1B55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B55,
+ },
+ [0x1B56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B56,
+ },
+ [0x1B57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B57,
+ },
+ [0x1B58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B58,
+ },
+ [0x1B59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1B59,
+ },
+ [0x1B5A]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1B5A,
+ },
+ [0x1B5B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1B5B,
+ },
+ [0x1B5C]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B5C,
+ },
+ [0x1B5D]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1B5D,
+ },
+ [0x1B5E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1B5E,
+ },
+ [0x1B5F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1B5F,
+ },
+ [0x1B60]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1B60,
+ },
+ [0x1B61]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B61,
+ },
+ [0x1B62]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B62,
+ },
+ [0x1B63]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B63,
+ },
+ [0x1B64]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B64,
+ },
+ [0x1B65]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B65,
+ },
+ [0x1B66]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B66,
+ },
+ [0x1B67]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B67,
+ },
+ [0x1B68]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B68,
+ },
+ [0x1B69]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B69,
+ },
+ [0x1B6A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B6A,
+ },
+ [0x1B6B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B6B,
+ },
+ [0x1B6C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B6C,
+ },
+ [0x1B6D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B6D,
+ },
+ [0x1B6E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B6E,
+ },
+ [0x1B6F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B6F,
+ },
+ [0x1B70]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B70,
+ },
+ [0x1B71]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B71,
+ },
+ [0x1B72]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B72,
+ },
+ [0x1B73]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B73,
+ },
+ [0x1B74]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B74,
+ },
+ [0x1B75]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B75,
+ },
+ [0x1B76]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B76,
+ },
+ [0x1B77]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B77,
+ },
+ [0x1B78]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B78,
+ },
+ [0x1B79]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B79,
+ },
+ [0x1B7A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B7A,
+ },
+ [0x1B7B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B7B,
+ },
+ [0x1B7C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B7C,
+ },
+ [0x1B80]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B80,
+ },
+ [0x1B81]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1B81,
+ },
+ [0x1B82]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1B82,
+ },
+ [0x1B83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B83,
+ },
+ [0x1B84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B84,
+ },
+ [0x1B85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B85,
+ },
+ [0x1B86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B86,
+ },
+ [0x1B87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B87,
+ },
+ [0x1B88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B88,
+ },
+ [0x1B89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B89,
+ },
+ [0x1B8A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8A,
+ },
+ [0x1B8B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8B,
+ },
+ [0x1B8C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8C,
+ },
+ [0x1B8D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8D,
+ },
+ [0x1B8E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8E,
+ },
+ [0x1B8F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B8F,
+ },
+ [0x1B90]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B90,
+ },
+ [0x1B91]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B91,
+ },
+ [0x1B92]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B92,
+ },
+ [0x1B93]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B93,
+ },
+ [0x1B94]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B94,
+ },
+ [0x1B95]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B95,
+ },
+ [0x1B96]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B96,
+ },
+ [0x1B97]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B97,
+ },
+ [0x1B98]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B98,
+ },
+ [0x1B99]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B99,
+ },
+ [0x1B9A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9A,
+ },
+ [0x1B9B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9B,
+ },
+ [0x1B9C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9C,
+ },
+ [0x1B9D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9D,
+ },
+ [0x1B9E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9E,
+ },
+ [0x1B9F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1B9F,
+ },
+ [0x1BA0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BA0,
+ },
+ [0x1BA1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BA1,
+ },
+ [0x1BA2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BA2,
+ },
+ [0x1BA3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BA3,
+ },
+ [0x1BA4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BA4,
+ },
+ [0x1BA5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BA5,
+ },
+ [0x1BA6]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BA6,
+ },
+ [0x1BA7]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BA7,
+ },
+ [0x1BA8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BA8,
+ },
+ [0x1BA9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BA9,
+ },
+ [0x1BAA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BAA,
+ },
+ [0x1BAB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BAB,
+ },
+ [0x1BAC]={
+ category="mc",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BAC,
+ },
+ [0x1BAD]={
+ category="mc",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BAD,
+ },
+ [0x1BAE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BAE,
+ },
+ [0x1BAF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BAF,
+ },
+ [0x1BB0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB0,
+ },
+ [0x1BB1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB1,
+ },
+ [0x1BB2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB2,
+ },
+ [0x1BB3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB3,
+ },
+ [0x1BB4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB4,
+ },
+ [0x1BB5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB5,
+ },
+ [0x1BB6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB6,
+ },
+ [0x1BB7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB7,
+ },
+ [0x1BB8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB8,
+ },
+ [0x1BB9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1BB9,
+ },
+ [0x1BBA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BBA,
+ },
+ [0x1BBB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BBB,
+ },
+ [0x1BBC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BBC,
+ },
+ [0x1BBD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BBD,
+ },
+ [0x1BBE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BBE,
+ },
+ [0x1BBF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BBF,
+ },
+ [0x1BC0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0,
+ },
+ [0x1BC1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1,
+ },
+ [0x1BC2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2,
+ },
+ [0x1BC3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3,
+ },
+ [0x1BC4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4,
+ },
+ [0x1BC5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5,
+ },
+ [0x1BC6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC6,
+ },
+ [0x1BC7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC7,
+ },
+ [0x1BC8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC8,
+ },
+ [0x1BC9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC9,
+ },
+ [0x1BCA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BCA,
+ },
+ [0x1BCB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BCB,
+ },
+ [0x1BCC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BCC,
+ },
+ [0x1BCD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BCD,
+ },
+ [0x1BCE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BCE,
+ },
+ [0x1BCF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BCF,
+ },
+ [0x1BD0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD0,
+ },
+ [0x1BD1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD1,
+ },
+ [0x1BD2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD2,
+ },
+ [0x1BD3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD3,
+ },
+ [0x1BD4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD4,
+ },
+ [0x1BD5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD5,
+ },
+ [0x1BD6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD6,
+ },
+ [0x1BD7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD7,
+ },
+ [0x1BD8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD8,
+ },
+ [0x1BD9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BD9,
+ },
+ [0x1BDA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BDA,
+ },
+ [0x1BDB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BDB,
+ },
+ [0x1BDC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BDC,
+ },
+ [0x1BDD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BDD,
+ },
+ [0x1BDE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BDE,
+ },
+ [0x1BDF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BDF,
+ },
+ [0x1BE0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE0,
+ },
+ [0x1BE1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE1,
+ },
+ [0x1BE2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE2,
+ },
+ [0x1BE3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE3,
+ },
+ [0x1BE4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE4,
+ },
+ [0x1BE5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BE5,
+ },
+ [0x1BE6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BE6,
+ },
+ [0x1BE7]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BE7,
+ },
+ [0x1BE8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BE8,
+ },
+ [0x1BE9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BE9,
+ },
+ [0x1BEA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BEA,
+ },
+ [0x1BEB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BEB,
+ },
+ [0x1BEC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BEC,
+ },
+ [0x1BED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BED,
+ },
+ [0x1BEE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BEE,
+ },
+ [0x1BEF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BEF,
+ },
+ [0x1BF0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BF0,
+ },
+ [0x1BF1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BF1,
+ },
+ [0x1BF2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BF2,
+ },
+ [0x1BF3]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1BF3,
+ },
+ [0x1BFC]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BFC,
+ },
+ [0x1BFD]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BFD,
+ },
+ [0x1BFE]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BFE,
+ },
+ [0x1BFF]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BFF,
+ },
+ [0x1C00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C00,
+ },
+ [0x1C01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C01,
+ },
+ [0x1C02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C02,
+ },
+ [0x1C03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C03,
+ },
+ [0x1C04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C04,
+ },
+ [0x1C05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C05,
+ },
+ [0x1C06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C06,
+ },
+ [0x1C07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C07,
+ },
+ [0x1C08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C08,
+ },
+ [0x1C09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C09,
+ },
+ [0x1C0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0A,
+ },
+ [0x1C0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0B,
+ },
+ [0x1C0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0C,
+ },
+ [0x1C0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0D,
+ },
+ [0x1C0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0E,
+ },
+ [0x1C0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C0F,
+ },
+ [0x1C10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C10,
+ },
+ [0x1C11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C11,
+ },
+ [0x1C12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C12,
+ },
+ [0x1C13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C13,
+ },
+ [0x1C14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C14,
+ },
+ [0x1C15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C15,
+ },
+ [0x1C16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C16,
+ },
+ [0x1C17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C17,
+ },
+ [0x1C18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C18,
+ },
+ [0x1C19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C19,
+ },
+ [0x1C1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1A,
+ },
+ [0x1C1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1B,
+ },
+ [0x1C1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1C,
+ },
+ [0x1C1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1D,
+ },
+ [0x1C1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1E,
+ },
+ [0x1C1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C1F,
+ },
+ [0x1C20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C20,
+ },
+ [0x1C21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C21,
+ },
+ [0x1C22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C22,
+ },
+ [0x1C23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C23,
+ },
+ [0x1C24]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C24,
+ },
+ [0x1C25]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C25,
+ },
+ [0x1C26]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C26,
+ },
+ [0x1C27]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C27,
+ },
+ [0x1C28]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C28,
+ },
+ [0x1C29]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C29,
+ },
+ [0x1C2A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C2A,
+ },
+ [0x1C2B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C2B,
+ },
+ [0x1C2C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C2C,
+ },
+ [0x1C2D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C2D,
+ },
+ [0x1C2E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C2E,
+ },
+ [0x1C2F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C2F,
+ },
+ [0x1C30]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C30,
+ },
+ [0x1C31]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C31,
+ },
+ [0x1C32]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C32,
+ },
+ [0x1C33]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C33,
+ },
+ [0x1C34]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C34,
+ },
+ [0x1C35]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1C35,
+ },
+ [0x1C36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C36,
+ },
+ [0x1C37]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1C37,
+ },
+ [0x1C3B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C3B,
+ },
+ [0x1C3C]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C3C,
+ },
+ [0x1C3D]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C3D,
+ },
+ [0x1C3E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C3E,
+ },
+ [0x1C3F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C3F,
+ },
+ [0x1C40]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C40,
+ },
+ [0x1C41]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C41,
+ },
+ [0x1C42]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C42,
+ },
+ [0x1C43]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C43,
+ },
+ [0x1C44]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C44,
+ },
+ [0x1C45]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C45,
+ },
+ [0x1C46]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C46,
+ },
+ [0x1C47]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C47,
+ },
+ [0x1C48]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C48,
+ },
+ [0x1C49]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C49,
+ },
+ [0x1C4D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C4D,
+ },
+ [0x1C4E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C4E,
+ },
+ [0x1C4F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C4F,
+ },
+ [0x1C50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C50,
+ },
+ [0x1C51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C51,
+ },
+ [0x1C52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C52,
+ },
+ [0x1C53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C53,
+ },
+ [0x1C54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C54,
+ },
+ [0x1C55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C55,
+ },
+ [0x1C56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C56,
+ },
+ [0x1C57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C57,
+ },
+ [0x1C58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C58,
+ },
+ [0x1C59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1C59,
+ },
+ [0x1C5A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C5A,
+ },
+ [0x1C5B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C5B,
+ },
+ [0x1C5C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C5C,
+ },
+ [0x1C5D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C5D,
+ },
+ [0x1C5E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C5E,
+ },
+ [0x1C5F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C5F,
+ },
+ [0x1C60]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C60,
+ },
+ [0x1C61]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C61,
+ },
+ [0x1C62]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C62,
+ },
+ [0x1C63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C63,
+ },
+ [0x1C64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C64,
+ },
+ [0x1C65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C65,
+ },
+ [0x1C66]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C66,
+ },
+ [0x1C67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C67,
+ },
+ [0x1C68]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C68,
+ },
+ [0x1C69]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C69,
+ },
+ [0x1C6A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C6A,
+ },
+ [0x1C6B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C6B,
+ },
+ [0x1C6C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C6C,
+ },
+ [0x1C6D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C6D,
+ },
+ [0x1C6E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C6E,
+ },
+ [0x1C6F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C6F,
+ },
+ [0x1C70]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C70,
+ },
+ [0x1C71]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C71,
+ },
+ [0x1C72]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C72,
+ },
+ [0x1C73]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C73,
+ },
+ [0x1C74]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C74,
+ },
+ [0x1C75]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C75,
+ },
+ [0x1C76]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C76,
+ },
+ [0x1C77]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C77,
+ },
+ [0x1C78]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C78,
+ },
+ [0x1C79]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C79,
+ },
+ [0x1C7A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C7A,
+ },
+ [0x1C7B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C7B,
+ },
+ [0x1C7C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C7C,
+ },
+ [0x1C7D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C7D,
+ },
+ [0x1C7E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C7E,
+ },
+ [0x1C7F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1C7F,
+ },
+ [0x1C80]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C80,
+ },
+ [0x1C81]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C81,
+ },
+ [0x1C82]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C82,
+ },
+ [0x1C83]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C83,
+ },
+ [0x1C84]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C84,
+ },
+ [0x1C85]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C85,
+ },
+ [0x1C86]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C86,
+ },
+ [0x1C87]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C87,
+ },
+ [0x1C88]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C88,
+ },
+ [0x1C90]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C90,
+ },
+ [0x1C91]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C91,
+ },
+ [0x1C92]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C92,
+ },
+ [0x1C93]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C93,
+ },
+ [0x1C94]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C94,
+ },
+ [0x1C95]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C95,
+ },
+ [0x1C96]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C96,
+ },
+ [0x1C97]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C97,
+ },
+ [0x1C98]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C98,
+ },
+ [0x1C99]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C99,
+ },
+ [0x1C9A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C9A,
+ },
+ [0x1C9B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C9B,
+ },
+ [0x1C9C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C9C,
+ },
+ [0x1C9D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C9D,
+ },
+ [0x1C9E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C9E,
+ },
+ [0x1C9F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1C9F,
+ },
+ [0x1CA0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA0,
+ },
+ [0x1CA1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA1,
+ },
+ [0x1CA2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA2,
+ },
+ [0x1CA3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA3,
+ },
+ [0x1CA4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA4,
+ },
+ [0x1CA5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA5,
+ },
+ [0x1CA6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA6,
+ },
+ [0x1CA7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA7,
+ },
+ [0x1CA8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA8,
+ },
+ [0x1CA9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CA9,
+ },
+ [0x1CAA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CAA,
+ },
+ [0x1CAB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CAB,
+ },
+ [0x1CAC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CAC,
+ },
+ [0x1CAD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CAD,
+ },
+ [0x1CAE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CAE,
+ },
+ [0x1CAF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CAF,
+ },
+ [0x1CB0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB0,
+ },
+ [0x1CB1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB1,
+ },
+ [0x1CB2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB2,
+ },
+ [0x1CB3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB3,
+ },
+ [0x1CB4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB4,
+ },
+ [0x1CB5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB5,
+ },
+ [0x1CB6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB6,
+ },
+ [0x1CB7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB7,
+ },
+ [0x1CB8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB8,
+ },
+ [0x1CB9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CB9,
+ },
+ [0x1CBA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CBA,
+ },
+ [0x1CBD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CBD,
+ },
+ [0x1CBE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CBE,
+ },
+ [0x1CBF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CBF,
+ },
+ [0x1CC0]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC0,
+ },
+ [0x1CC1]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC1,
+ },
+ [0x1CC2]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC2,
+ },
+ [0x1CC3]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC3,
+ },
+ [0x1CC4]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC4,
+ },
+ [0x1CC5]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC5,
+ },
+ [0x1CC6]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC6,
+ },
+ [0x1CC7]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CC7,
+ },
+ [0x1CD0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD0,
+ },
+ [0x1CD1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD1,
+ },
+ [0x1CD2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD2,
+ },
+ [0x1CD3]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CD3,
+ },
+ [0x1CD4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD4,
+ },
+ [0x1CD5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD5,
+ },
+ [0x1CD6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD6,
+ },
+ [0x1CD7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD7,
+ },
+ [0x1CD8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD8,
+ },
+ [0x1CD9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CD9,
+ },
+ [0x1CDA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CDA,
+ },
+ [0x1CDB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CDB,
+ },
+ [0x1CDC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CDC,
+ },
+ [0x1CDD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CDD,
+ },
+ [0x1CDE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CDE,
+ },
+ [0x1CDF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CDF,
+ },
+ [0x1CE0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE0,
+ },
+ [0x1CE1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1CE1,
+ },
+ [0x1CE2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE2,
+ },
+ [0x1CE3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE3,
+ },
+ [0x1CE4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE4,
+ },
+ [0x1CE5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE5,
+ },
+ [0x1CE6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE6,
+ },
+ [0x1CE7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE7,
+ },
+ [0x1CE8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CE8,
+ },
+ [0x1CE9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CE9,
+ },
+ [0x1CEA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CEA,
+ },
+ [0x1CEB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CEB,
+ },
+ [0x1CEC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CEC,
+ },
+ [0x1CED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CED,
+ },
+ [0x1CEE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CEE,
+ },
+ [0x1CEF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CEF,
+ },
+ [0x1CF0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CF0,
+ },
+ [0x1CF1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CF1,
+ },
+ [0x1CF2]={
+ category="mc",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CF2,
+ },
+ [0x1CF3]={
+ category="mc",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CF3,
+ },
+ [0x1CF4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CF4,
+ },
+ [0x1CF5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CF5,
+ },
+ [0x1CF6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CF6,
+ },
+ [0x1CF7]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1CF7,
+ },
+ [0x1CF8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CF8,
+ },
+ [0x1CF9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1CF9,
+ },
+ [0x1CFA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1CFA,
+ },
+ [0x1D00]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00,
+ },
+ [0x1D01]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01,
+ },
+ [0x1D02]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02,
+ },
+ [0x1D03]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03,
+ },
+ [0x1D04]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04,
+ },
+ [0x1D05]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05,
+ },
+ [0x1D06]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06,
+ },
+ [0x1D07]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07,
+ },
+ [0x1D08]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08,
+ },
+ [0x1D09]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09,
+ },
+ [0x1D0A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A,
+ },
+ [0x1D0B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B,
+ },
+ [0x1D0C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C,
+ },
+ [0x1D0D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D,
+ },
+ [0x1D0E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E,
+ },
+ [0x1D0F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F,
+ },
+ [0x1D10]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10,
+ },
+ [0x1D11]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11,
+ },
+ [0x1D12]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12,
+ },
+ [0x1D13]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13,
+ },
+ [0x1D14]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14,
+ },
+ [0x1D15]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D15,
+ },
+ [0x1D16]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D16,
+ },
+ [0x1D17]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D17,
+ },
+ [0x1D18]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D18,
+ },
+ [0x1D19]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19,
+ },
+ [0x1D1A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A,
+ },
+ [0x1D1B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B,
+ },
+ [0x1D1C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C,
+ },
+ [0x1D1D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D,
+ },
+ [0x1D1E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E,
+ },
+ [0x1D1F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1F,
+ },
+ [0x1D20]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D20,
+ },
+ [0x1D21]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D21,
+ },
+ [0x1D22]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D22,
+ },
+ [0x1D23]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D23,
+ },
+ [0x1D24]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D24,
+ },
+ [0x1D25]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D25,
+ },
+ [0x1D26]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D26,
+ },
+ [0x1D27]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D27,
+ },
+ [0x1D28]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D28,
+ },
+ [0x1D29]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D29,
+ },
+ [0x1D2A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2A,
+ },
+ [0x1D2B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2B,
+ },
+ [0x1D2C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x41 },
+ unicodeslot=0x1D2C,
+ },
+ [0x1D2D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0xC6 },
+ unicodeslot=0x1D2D,
+ },
+ [0x1D2E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x42 },
+ unicodeslot=0x1D2E,
+ },
+ [0x1D2F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2F,
+ },
+ [0x1D30]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x44 },
+ unicodeslot=0x1D30,
+ },
+ [0x1D31]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x45 },
+ unicodeslot=0x1D31,
+ },
+ [0x1D32]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x18E },
+ unicodeslot=0x1D32,
+ },
+ [0x1D33]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x47 },
+ unicodeslot=0x1D33,
+ },
+ [0x1D34]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x48 },
+ unicodeslot=0x1D34,
+ },
+ [0x1D35]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x49 },
+ unicodeslot=0x1D35,
+ },
+ [0x1D36]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x4A },
+ unicodeslot=0x1D36,
+ },
+ [0x1D37]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x4B },
+ unicodeslot=0x1D37,
+ },
+ [0x1D38]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x4C },
+ unicodeslot=0x1D38,
+ },
+ [0x1D39]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x4D },
+ unicodeslot=0x1D39,
+ },
+ [0x1D3A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x4E },
+ unicodeslot=0x1D3A,
+ },
+ [0x1D3B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D3B,
+ },
+ [0x1D3C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x4F },
+ unicodeslot=0x1D3C,
+ },
+ [0x1D3D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x222 },
+ unicodeslot=0x1D3D,
+ },
+ [0x1D3E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x50 },
+ unicodeslot=0x1D3E,
+ },
+ [0x1D3F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x52 },
+ unicodeslot=0x1D3F,
+ },
+ [0x1D40]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x54 },
+ unicodeslot=0x1D40,
+ },
+ [0x1D41]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x55 },
+ unicodeslot=0x1D41,
+ },
+ [0x1D42]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x57 },
+ unicodeslot=0x1D42,
+ },
+ [0x1D43]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x61 },
+ unicodeslot=0x1D43,
+ },
+ [0x1D44]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x250 },
+ unicodeslot=0x1D44,
+ },
+ [0x1D45]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x251 },
+ unicodeslot=0x1D45,
+ },
+ [0x1D46]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D02 },
+ unicodeslot=0x1D46,
+ },
+ [0x1D47]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x62 },
+ unicodeslot=0x1D47,
+ },
+ [0x1D48]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x64 },
+ unicodeslot=0x1D48,
+ },
+ [0x1D49]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x65 },
+ unicodeslot=0x1D49,
+ },
+ [0x1D4A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x259 },
+ unicodeslot=0x1D4A,
+ },
+ [0x1D4B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x25B },
+ unicodeslot=0x1D4B,
+ },
+ [0x1D4C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x25C },
+ unicodeslot=0x1D4C,
+ },
+ [0x1D4D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x67 },
+ unicodeslot=0x1D4D,
+ },
+ [0x1D4E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D4E,
+ },
+ [0x1D4F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x6B },
+ unicodeslot=0x1D4F,
+ },
+ [0x1D50]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x6D },
+ unicodeslot=0x1D50,
+ },
+ [0x1D51]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x14B },
+ unicodeslot=0x1D51,
+ },
+ [0x1D52]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x6F },
+ unicodeslot=0x1D52,
+ },
+ [0x1D53]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x254 },
+ unicodeslot=0x1D53,
+ },
+ [0x1D54]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D16 },
+ unicodeslot=0x1D54,
+ },
+ [0x1D55]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D17 },
+ unicodeslot=0x1D55,
+ },
+ [0x1D56]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x70 },
+ unicodeslot=0x1D56,
+ },
+ [0x1D57]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x74 },
+ unicodeslot=0x1D57,
+ },
+ [0x1D58]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x75 },
+ unicodeslot=0x1D58,
+ },
+ [0x1D59]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D1D },
+ unicodeslot=0x1D59,
+ },
+ [0x1D5A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x26F },
+ unicodeslot=0x1D5A,
+ },
+ [0x1D5B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x76 },
+ unicodeslot=0x1D5B,
+ },
+ [0x1D5C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D25 },
+ unicodeslot=0x1D5C,
+ },
+ [0x1D5D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x3B2 },
+ unicodeslot=0x1D5D,
+ },
+ [0x1D5E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x3B3 },
+ unicodeslot=0x1D5E,
+ },
+ [0x1D5F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x3B4 },
+ unicodeslot=0x1D5F,
+ },
+ [0x1D60]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x3C6 },
+ unicodeslot=0x1D60,
+ },
+ [0x1D61]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x3C7 },
+ unicodeslot=0x1D61,
+ },
+ [0x1D62]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x69 },
+ unicodeslot=0x1D62,
+ },
+ [0x1D63]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x72 },
+ unicodeslot=0x1D63,
+ },
+ [0x1D64]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x75 },
+ unicodeslot=0x1D64,
+ },
+ [0x1D65]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x76 },
+ unicodeslot=0x1D65,
+ },
+ [0x1D66]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x3B2 },
+ unicodeslot=0x1D66,
+ },
+ [0x1D67]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x3B3 },
+ unicodeslot=0x1D67,
+ },
+ [0x1D68]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x3C1 },
+ unicodeslot=0x1D68,
+ },
+ [0x1D69]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x3C6 },
+ unicodeslot=0x1D69,
+ },
+ [0x1D6A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x3C7 },
+ unicodeslot=0x1D6A,
+ },
+ [0x1D6B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D6B,
+ },
+ [0x1D6C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D6C,
+ },
+ [0x1D6D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D6D,
+ },
+ [0x1D6E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D6E,
+ },
+ [0x1D6F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D6F,
+ },
+ [0x1D70]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D70,
+ },
+ [0x1D71]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D71,
+ },
+ [0x1D72]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D72,
+ },
+ [0x1D73]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D73,
+ },
+ [0x1D74]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D74,
+ },
+ [0x1D75]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D75,
+ },
+ [0x1D76]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D76,
+ },
+ [0x1D77]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D77,
+ },
+ [0x1D78]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x43D },
+ unicodeslot=0x1D78,
+ },
+ [0x1D79]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D79,
+ },
+ [0x1D7A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D7A,
+ },
+ [0x1D7B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D7B,
+ },
+ [0x1D7C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D7C,
+ },
+ [0x1D7D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D7D,
+ },
+ [0x1D7E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D7E,
+ },
+ [0x1D7F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D7F,
+ },
+ [0x1D80]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80,
+ },
+ [0x1D81]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81,
+ },
+ [0x1D82]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82,
+ },
+ [0x1D83]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83,
+ },
+ [0x1D84]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84,
+ },
+ [0x1D85]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85,
+ },
+ [0x1D86]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86,
+ },
+ [0x1D87]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87,
+ },
+ [0x1D88]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88,
+ },
+ [0x1D89]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89,
+ },
+ [0x1D8A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A,
+ },
+ [0x1D8B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B,
+ },
+ [0x1D8C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C,
+ },
+ [0x1D8D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D,
+ },
+ [0x1D8E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E,
+ },
+ [0x1D8F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F,
+ },
+ [0x1D90]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90,
+ },
+ [0x1D91]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91,
+ },
+ [0x1D92]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92,
+ },
+ [0x1D93]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93,
+ },
+ [0x1D94]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94,
+ },
+ [0x1D95]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95,
+ },
+ [0x1D96]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96,
+ },
+ [0x1D97]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97,
+ },
+ [0x1D98]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98,
+ },
+ [0x1D99]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99,
+ },
+ [0x1D9A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A,
+ },
+ [0x1D9B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x252 },
+ unicodeslot=0x1D9B,
+ },
+ [0x1D9C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x63 },
+ unicodeslot=0x1D9C,
+ },
+ [0x1D9D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x255 },
+ unicodeslot=0x1D9D,
+ },
+ [0x1D9E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0xF0 },
+ unicodeslot=0x1D9E,
+ },
+ [0x1D9F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x25C },
+ unicodeslot=0x1D9F,
+ },
+ [0x1DA0]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x66 },
+ unicodeslot=0x1DA0,
+ },
+ [0x1DA1]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x25F },
+ unicodeslot=0x1DA1,
+ },
+ [0x1DA2]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x261 },
+ unicodeslot=0x1DA2,
+ },
+ [0x1DA3]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x265 },
+ unicodeslot=0x1DA3,
+ },
+ [0x1DA4]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x268 },
+ unicodeslot=0x1DA4,
+ },
+ [0x1DA5]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x269 },
+ unicodeslot=0x1DA5,
+ },
+ [0x1DA6]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x26A },
+ unicodeslot=0x1DA6,
+ },
+ [0x1DA7]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D7B },
+ unicodeslot=0x1DA7,
+ },
+ [0x1DA8]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x29D },
+ unicodeslot=0x1DA8,
+ },
+ [0x1DA9]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x26D },
+ unicodeslot=0x1DA9,
+ },
+ [0x1DAA]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D85 },
+ unicodeslot=0x1DAA,
+ },
+ [0x1DAB]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x29F },
+ unicodeslot=0x1DAB,
+ },
+ [0x1DAC]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x271 },
+ unicodeslot=0x1DAC,
+ },
+ [0x1DAD]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x270 },
+ unicodeslot=0x1DAD,
+ },
+ [0x1DAE]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x272 },
+ unicodeslot=0x1DAE,
+ },
+ [0x1DAF]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x273 },
+ unicodeslot=0x1DAF,
+ },
+ [0x1DB0]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x274 },
+ unicodeslot=0x1DB0,
+ },
+ [0x1DB1]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x275 },
+ unicodeslot=0x1DB1,
+ },
+ [0x1DB2]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x278 },
+ unicodeslot=0x1DB2,
+ },
+ [0x1DB3]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x282 },
+ unicodeslot=0x1DB3,
+ },
+ [0x1DB4]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x283 },
+ unicodeslot=0x1DB4,
+ },
+ [0x1DB5]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1AB },
+ unicodeslot=0x1DB5,
+ },
+ [0x1DB6]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x289 },
+ unicodeslot=0x1DB6,
+ },
+ [0x1DB7]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x28A },
+ unicodeslot=0x1DB7,
+ },
+ [0x1DB8]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x1D1C },
+ unicodeslot=0x1DB8,
+ },
+ [0x1DB9]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x28B },
+ unicodeslot=0x1DB9,
+ },
+ [0x1DBA]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x28C },
+ unicodeslot=0x1DBA,
+ },
+ [0x1DBB]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x7A },
+ unicodeslot=0x1DBB,
+ },
+ [0x1DBC]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x290 },
+ unicodeslot=0x1DBC,
+ },
+ [0x1DBD]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x291 },
+ unicodeslot=0x1DBD,
+ },
+ [0x1DBE]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x292 },
+ unicodeslot=0x1DBE,
+ },
+ [0x1DBF]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x3B8 },
+ unicodeslot=0x1DBF,
+ },
+ [0x1DC0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC0,
+ },
+ [0x1DC1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC1,
+ },
+ [0x1DC2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC2,
+ },
+ [0x1DC3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC3,
+ },
+ [0x1DC4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC4,
+ },
+ [0x1DC5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC5,
+ },
+ [0x1DC6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC6,
+ },
+ [0x1DC7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC7,
+ },
+ [0x1DC8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC8,
+ },
+ [0x1DC9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DC9,
+ },
+ [0x1DCA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DCA,
+ },
+ [0x1DCB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DCB,
+ },
+ [0x1DCC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DCC,
+ },
+ [0x1DCD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DCD,
+ },
+ [0x1DCE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DCE,
+ },
+ [0x1DCF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DCF,
+ },
+ [0x1DD0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD0,
+ },
+ [0x1DD1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD1,
+ },
+ [0x1DD2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD2,
+ },
+ [0x1DD3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD3,
+ },
+ [0x1DD4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD4,
+ },
+ [0x1DD5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD5,
+ },
+ [0x1DD6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD6,
+ },
+ [0x1DD7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD7,
+ },
+ [0x1DD8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD8,
+ },
+ [0x1DD9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DD9,
+ },
+ [0x1DDA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DDA,
+ },
+ [0x1DDB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DDB,
+ },
+ [0x1DDC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DDC,
+ },
+ [0x1DDD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DDD,
+ },
+ [0x1DDE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DDE,
+ },
+ [0x1DDF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DDF,
+ },
+ [0x1DE0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE0,
+ },
+ [0x1DE1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE1,
+ },
+ [0x1DE2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE2,
+ },
+ [0x1DE3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE3,
+ },
+ [0x1DE4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE4,
+ },
+ [0x1DE5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE5,
+ },
+ [0x1DE6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE6,
+ },
+ [0x1DE7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE7,
+ },
+ [0x1DE8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE8,
+ },
+ [0x1DE9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DE9,
+ },
+ [0x1DEA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DEA,
+ },
+ [0x1DEB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DEB,
+ },
+ [0x1DEC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DEC,
+ },
+ [0x1DED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DED,
+ },
+ [0x1DEE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DEE,
+ },
+ [0x1DEF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DEF,
+ },
+ [0x1DF0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF0,
+ },
+ [0x1DF1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF1,
+ },
+ [0x1DF2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF2,
+ },
+ [0x1DF3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF3,
+ },
+ [0x1DF4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF4,
+ },
+ [0x1DF5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF5,
+ },
+ [0x1DF6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF6,
+ },
+ [0x1DF7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF7,
+ },
+ [0x1DF8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF8,
+ },
+ [0x1DF9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DF9,
+ },
+ [0x1DFB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DFB,
+ },
+ [0x1DFC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DFC,
+ },
+ [0x1DFD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DFD,
+ },
+ [0x1DFE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DFE,
+ },
+ [0x1DFF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DFF,
+ },
+ [0x1E00]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x325 },
+ unicodeslot=0x1E00,
+ },
+ [0x1E01]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x325 },
+ unicodeslot=0x1E01,
+ },
+ [0x1E02]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x42, 0x307 },
+ unicodeslot=0x1E02,
+ },
+ [0x1E03]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x62, 0x307 },
+ unicodeslot=0x1E03,
+ },
+ [0x1E04]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x42, 0x323 },
+ unicodeslot=0x1E04,
+ },
+ [0x1E05]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x62, 0x323 },
+ unicodeslot=0x1E05,
+ },
+ [0x1E06]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x42, 0x331 },
+ unicodeslot=0x1E06,
+ },
+ [0x1E07]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x62, 0x331 },
+ unicodeslot=0x1E07,
+ },
+ [0x1E08]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC7, 0x301 },
+ unicodeslot=0x1E08,
+ },
+ [0x1E09]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE7, 0x301 },
+ unicodeslot=0x1E09,
+ },
+ [0x1E0A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44, 0x307 },
+ unicodeslot=0x1E0A,
+ },
+ [0x1E0B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x64, 0x307 },
+ unicodeslot=0x1E0B,
+ },
+ [0x1E0C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44, 0x323 },
+ unicodeslot=0x1E0C,
+ },
+ [0x1E0D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x64, 0x323 },
+ unicodeslot=0x1E0D,
+ },
+ [0x1E0E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44, 0x331 },
+ unicodeslot=0x1E0E,
+ },
+ [0x1E0F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x64, 0x331 },
+ unicodeslot=0x1E0F,
+ },
+ [0x1E10]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44, 0x327 },
+ unicodeslot=0x1E10,
+ },
+ [0x1E11]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x64, 0x327 },
+ unicodeslot=0x1E11,
+ },
+ [0x1E12]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x44, 0x32D },
+ unicodeslot=0x1E12,
+ },
+ [0x1E13]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x64, 0x32D },
+ unicodeslot=0x1E13,
+ },
+ [0x1E14]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x112, 0x300 },
+ unicodeslot=0x1E14,
+ },
+ [0x1E15]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x113, 0x300 },
+ unicodeslot=0x1E15,
+ },
+ [0x1E16]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x112, 0x301 },
+ unicodeslot=0x1E16,
+ },
+ [0x1E17]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x113, 0x301 },
+ unicodeslot=0x1E17,
+ },
+ [0x1E18]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x32D },
+ unicodeslot=0x1E18,
+ },
+ [0x1E19]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x32D },
+ unicodeslot=0x1E19,
+ },
+ [0x1E1A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x330 },
+ unicodeslot=0x1E1A,
+ },
+ [0x1E1B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x330 },
+ unicodeslot=0x1E1B,
+ },
+ [0x1E1C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x228, 0x306 },
+ unicodeslot=0x1E1C,
+ },
+ [0x1E1D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x229, 0x306 },
+ unicodeslot=0x1E1D,
+ },
+ [0x1E1E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x46, 0x307 },
+ unicodeslot=0x1E1E,
+ },
+ [0x1E1F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x66, 0x307 },
+ unicodeslot=0x1E1F,
+ },
+ [0x1E20]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x47, 0x304 },
+ unicodeslot=0x1E20,
+ },
+ [0x1E21]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x67, 0x304 },
+ unicodeslot=0x1E21,
+ },
+ [0x1E22]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x307 },
+ unicodeslot=0x1E22,
+ },
+ [0x1E23]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x307 },
+ unicodeslot=0x1E23,
+ },
+ [0x1E24]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x323 },
+ unicodeslot=0x1E24,
+ },
+ [0x1E25]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x323 },
+ unicodeslot=0x1E25,
+ },
+ [0x1E26]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x308 },
+ unicodeslot=0x1E26,
+ },
+ [0x1E27]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x308 },
+ unicodeslot=0x1E27,
+ },
+ [0x1E28]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x327 },
+ unicodeslot=0x1E28,
+ },
+ [0x1E29]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x327 },
+ unicodeslot=0x1E29,
+ },
+ [0x1E2A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x48, 0x32E },
+ unicodeslot=0x1E2A,
+ },
+ [0x1E2B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x32E },
+ unicodeslot=0x1E2B,
+ },
+ [0x1E2C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x330 },
+ unicodeslot=0x1E2C,
+ },
+ [0x1E2D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x330 },
+ unicodeslot=0x1E2D,
+ },
+ [0x1E2E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xCF, 0x301 },
+ unicodeslot=0x1E2E,
+ },
+ [0x1E2F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xEF, 0x301 },
+ unicodeslot=0x1E2F,
+ },
+ [0x1E30]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4B, 0x301 },
+ unicodeslot=0x1E30,
+ },
+ [0x1E31]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6B, 0x301 },
+ unicodeslot=0x1E31,
+ },
+ [0x1E32]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4B, 0x323 },
+ unicodeslot=0x1E32,
+ },
+ [0x1E33]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6B, 0x323 },
+ unicodeslot=0x1E33,
+ },
+ [0x1E34]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4B, 0x331 },
+ unicodeslot=0x1E34,
+ },
+ [0x1E35]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6B, 0x331 },
+ unicodeslot=0x1E35,
+ },
+ [0x1E36]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4C, 0x323 },
+ unicodeslot=0x1E36,
+ },
+ [0x1E37]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6C, 0x323 },
+ unicodeslot=0x1E37,
+ },
+ [0x1E38]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1E36, 0x304 },
+ unicodeslot=0x1E38,
+ },
+ [0x1E39]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1E37, 0x304 },
+ unicodeslot=0x1E39,
+ },
+ [0x1E3A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4C, 0x331 },
+ unicodeslot=0x1E3A,
+ },
+ [0x1E3B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6C, 0x331 },
+ unicodeslot=0x1E3B,
+ },
+ [0x1E3C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4C, 0x32D },
+ unicodeslot=0x1E3C,
+ },
+ [0x1E3D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6C, 0x32D },
+ unicodeslot=0x1E3D,
+ },
+ [0x1E3E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4D, 0x301 },
+ unicodeslot=0x1E3E,
+ },
+ [0x1E3F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6D, 0x301 },
+ unicodeslot=0x1E3F,
+ },
+ [0x1E40]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4D, 0x307 },
+ unicodeslot=0x1E40,
+ },
+ [0x1E41]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6D, 0x307 },
+ unicodeslot=0x1E41,
+ },
+ [0x1E42]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4D, 0x323 },
+ unicodeslot=0x1E42,
+ },
+ [0x1E43]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6D, 0x323 },
+ unicodeslot=0x1E43,
+ },
+ [0x1E44]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x307 },
+ unicodeslot=0x1E44,
+ },
+ [0x1E45]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x307 },
+ unicodeslot=0x1E45,
+ },
+ [0x1E46]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x323 },
+ unicodeslot=0x1E46,
+ },
+ [0x1E47]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x323 },
+ unicodeslot=0x1E47,
+ },
+ [0x1E48]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x331 },
+ unicodeslot=0x1E48,
+ },
+ [0x1E49]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x331 },
+ unicodeslot=0x1E49,
+ },
+ [0x1E4A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4E, 0x32D },
+ unicodeslot=0x1E4A,
+ },
+ [0x1E4B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6E, 0x32D },
+ unicodeslot=0x1E4B,
+ },
+ [0x1E4C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD5, 0x301 },
+ unicodeslot=0x1E4C,
+ },
+ [0x1E4D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF5, 0x301 },
+ unicodeslot=0x1E4D,
+ },
+ [0x1E4E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD5, 0x308 },
+ unicodeslot=0x1E4E,
+ },
+ [0x1E4F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF5, 0x308 },
+ unicodeslot=0x1E4F,
+ },
+ [0x1E50]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x14C, 0x300 },
+ unicodeslot=0x1E50,
+ },
+ [0x1E51]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x14D, 0x300 },
+ unicodeslot=0x1E51,
+ },
+ [0x1E52]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x14C, 0x301 },
+ unicodeslot=0x1E52,
+ },
+ [0x1E53]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x14D, 0x301 },
+ unicodeslot=0x1E53,
+ },
+ [0x1E54]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x50, 0x301 },
+ unicodeslot=0x1E54,
+ },
+ [0x1E55]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x70, 0x301 },
+ unicodeslot=0x1E55,
+ },
+ [0x1E56]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x50, 0x307 },
+ unicodeslot=0x1E56,
+ },
+ [0x1E57]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x70, 0x307 },
+ unicodeslot=0x1E57,
+ },
+ [0x1E58]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x307 },
+ unicodeslot=0x1E58,
+ },
+ [0x1E59]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x307 },
+ unicodeslot=0x1E59,
+ },
+ [0x1E5A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x323 },
+ unicodeslot=0x1E5A,
+ },
+ [0x1E5B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x323 },
+ unicodeslot=0x1E5B,
+ },
+ [0x1E5C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1E5A, 0x304 },
+ unicodeslot=0x1E5C,
+ },
+ [0x1E5D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1E5B, 0x304 },
+ unicodeslot=0x1E5D,
+ },
+ [0x1E5E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x52, 0x331 },
+ unicodeslot=0x1E5E,
+ },
+ [0x1E5F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x72, 0x331 },
+ unicodeslot=0x1E5F,
+ },
+ [0x1E60]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x307 },
+ unicodeslot=0x1E60,
+ },
+ [0x1E61]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x307 },
+ unicodeslot=0x1E61,
+ },
+ [0x1E62]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x53, 0x323 },
+ unicodeslot=0x1E62,
+ },
+ [0x1E63]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x73, 0x323 },
+ unicodeslot=0x1E63,
+ },
+ [0x1E64]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x15A, 0x307 },
+ unicodeslot=0x1E64,
+ },
+ [0x1E65]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x15B, 0x307 },
+ unicodeslot=0x1E65,
+ },
+ [0x1E66]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x160, 0x307 },
+ unicodeslot=0x1E66,
+ },
+ [0x1E67]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x161, 0x307 },
+ unicodeslot=0x1E67,
+ },
+ [0x1E68]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1E62, 0x307 },
+ unicodeslot=0x1E68,
+ },
+ [0x1E69]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1E63, 0x307 },
+ unicodeslot=0x1E69,
+ },
+ [0x1E6A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x307 },
+ unicodeslot=0x1E6A,
+ },
+ [0x1E6B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x307 },
+ unicodeslot=0x1E6B,
+ },
+ [0x1E6C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x323 },
+ unicodeslot=0x1E6C,
+ },
+ [0x1E6D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x323 },
+ unicodeslot=0x1E6D,
+ },
+ [0x1E6E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x331 },
+ unicodeslot=0x1E6E,
+ },
+ [0x1E6F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x331 },
+ unicodeslot=0x1E6F,
+ },
+ [0x1E70]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x54, 0x32D },
+ unicodeslot=0x1E70,
+ },
+ [0x1E71]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x32D },
+ unicodeslot=0x1E71,
+ },
+ [0x1E72]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x324 },
+ unicodeslot=0x1E72,
+ },
+ [0x1E73]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x324 },
+ unicodeslot=0x1E73,
+ },
+ [0x1E74]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x330 },
+ unicodeslot=0x1E74,
+ },
+ [0x1E75]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x330 },
+ unicodeslot=0x1E75,
+ },
+ [0x1E76]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x32D },
+ unicodeslot=0x1E76,
+ },
+ [0x1E77]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x32D },
+ unicodeslot=0x1E77,
+ },
+ [0x1E78]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x168, 0x301 },
+ unicodeslot=0x1E78,
+ },
+ [0x1E79]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x169, 0x301 },
+ unicodeslot=0x1E79,
+ },
+ [0x1E7A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x16A, 0x308 },
+ unicodeslot=0x1E7A,
+ },
+ [0x1E7B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x16B, 0x308 },
+ unicodeslot=0x1E7B,
+ },
+ [0x1E7C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x56, 0x303 },
+ unicodeslot=0x1E7C,
+ },
+ [0x1E7D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x76, 0x303 },
+ unicodeslot=0x1E7D,
+ },
+ [0x1E7E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x56, 0x323 },
+ unicodeslot=0x1E7E,
+ },
+ [0x1E7F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x76, 0x323 },
+ unicodeslot=0x1E7F,
+ },
+ [0x1E80]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x57, 0x300 },
+ unicodeslot=0x1E80,
+ },
+ [0x1E81]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x300 },
+ unicodeslot=0x1E81,
+ },
+ [0x1E82]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x57, 0x301 },
+ unicodeslot=0x1E82,
+ },
+ [0x1E83]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x301 },
+ unicodeslot=0x1E83,
+ },
+ [0x1E84]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x57, 0x308 },
+ unicodeslot=0x1E84,
+ },
+ [0x1E85]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x308 },
+ unicodeslot=0x1E85,
+ },
+ [0x1E86]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x57, 0x307 },
+ unicodeslot=0x1E86,
+ },
+ [0x1E87]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x307 },
+ unicodeslot=0x1E87,
+ },
+ [0x1E88]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x57, 0x323 },
+ unicodeslot=0x1E88,
+ },
+ [0x1E89]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x323 },
+ unicodeslot=0x1E89,
+ },
+ [0x1E8A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x58, 0x307 },
+ unicodeslot=0x1E8A,
+ },
+ [0x1E8B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x78, 0x307 },
+ unicodeslot=0x1E8B,
+ },
+ [0x1E8C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x58, 0x308 },
+ unicodeslot=0x1E8C,
+ },
+ [0x1E8D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x78, 0x308 },
+ unicodeslot=0x1E8D,
+ },
+ [0x1E8E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x307 },
+ unicodeslot=0x1E8E,
+ },
+ [0x1E8F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x307 },
+ unicodeslot=0x1E8F,
+ },
+ [0x1E90]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x5A, 0x302 },
+ unicodeslot=0x1E90,
+ },
+ [0x1E91]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x7A, 0x302 },
+ unicodeslot=0x1E91,
+ },
+ [0x1E92]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x5A, 0x323 },
+ unicodeslot=0x1E92,
+ },
+ [0x1E93]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x7A, 0x323 },
+ unicodeslot=0x1E93,
+ },
+ [0x1E94]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x5A, 0x331 },
+ unicodeslot=0x1E94,
+ },
+ [0x1E95]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x7A, 0x331 },
+ unicodeslot=0x1E95,
+ },
+ [0x1E96]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x68, 0x331 },
+ unicodeslot=0x1E96,
+ },
+ [0x1E97]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x74, 0x308 },
+ unicodeslot=0x1E97,
+ },
+ [0x1E98]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x77, 0x30A },
+ unicodeslot=0x1E98,
+ },
+ [0x1E99]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x30A },
+ unicodeslot=0x1E99,
+ },
+ [0x1E9A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x61, 0x2BE },
+ unicodeslot=0x1E9A,
+ },
+ [0x1E9B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x17F, 0x307 },
+ unicodeslot=0x1E9B,
+ },
+ [0x1E9C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E9C,
+ },
+ [0x1E9D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E9D,
+ },
+ [0x1E9E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E9E,
+ },
+ [0x1E9F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E9F,
+ },
+ [0x1EA0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x323 },
+ unicodeslot=0x1EA0,
+ },
+ [0x1EA1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x323 },
+ unicodeslot=0x1EA1,
+ },
+ [0x1EA2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x41, 0x309 },
+ unicodeslot=0x1EA2,
+ },
+ [0x1EA3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x61, 0x309 },
+ unicodeslot=0x1EA3,
+ },
+ [0x1EA4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC2, 0x301 },
+ unicodeslot=0x1EA4,
+ },
+ [0x1EA5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE2, 0x301 },
+ unicodeslot=0x1EA5,
+ },
+ [0x1EA6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC2, 0x300 },
+ unicodeslot=0x1EA6,
+ },
+ [0x1EA7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE2, 0x300 },
+ unicodeslot=0x1EA7,
+ },
+ [0x1EA8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC2, 0x309 },
+ unicodeslot=0x1EA8,
+ },
+ [0x1EA9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE2, 0x309 },
+ unicodeslot=0x1EA9,
+ },
+ [0x1EAA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xC2, 0x303 },
+ unicodeslot=0x1EAA,
+ },
+ [0x1EAB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xE2, 0x303 },
+ unicodeslot=0x1EAB,
+ },
+ [0x1EAC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EA0, 0x302 },
+ unicodeslot=0x1EAC,
+ },
+ [0x1EAD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EA1, 0x302 },
+ unicodeslot=0x1EAD,
+ },
+ [0x1EAE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x102, 0x301 },
+ unicodeslot=0x1EAE,
+ },
+ [0x1EAF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x103, 0x301 },
+ unicodeslot=0x1EAF,
+ },
+ [0x1EB0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x102, 0x300 },
+ unicodeslot=0x1EB0,
+ },
+ [0x1EB1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x103, 0x300 },
+ unicodeslot=0x1EB1,
+ },
+ [0x1EB2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x102, 0x309 },
+ unicodeslot=0x1EB2,
+ },
+ [0x1EB3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x103, 0x309 },
+ unicodeslot=0x1EB3,
+ },
+ [0x1EB4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x102, 0x303 },
+ unicodeslot=0x1EB4,
+ },
+ [0x1EB5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x103, 0x303 },
+ unicodeslot=0x1EB5,
+ },
+ [0x1EB6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EA0, 0x306 },
+ unicodeslot=0x1EB6,
+ },
+ [0x1EB7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EA1, 0x306 },
+ unicodeslot=0x1EB7,
+ },
+ [0x1EB8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x323 },
+ unicodeslot=0x1EB8,
+ },
+ [0x1EB9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x323 },
+ unicodeslot=0x1EB9,
+ },
+ [0x1EBA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x309 },
+ unicodeslot=0x1EBA,
+ },
+ [0x1EBB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x309 },
+ unicodeslot=0x1EBB,
+ },
+ [0x1EBC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x45, 0x303 },
+ unicodeslot=0x1EBC,
+ },
+ [0x1EBD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x65, 0x303 },
+ unicodeslot=0x1EBD,
+ },
+ [0x1EBE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xCA, 0x301 },
+ unicodeslot=0x1EBE,
+ },
+ [0x1EBF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xEA, 0x301 },
+ unicodeslot=0x1EBF,
+ },
+ [0x1EC0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xCA, 0x300 },
+ unicodeslot=0x1EC0,
+ },
+ [0x1EC1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xEA, 0x300 },
+ unicodeslot=0x1EC1,
+ },
+ [0x1EC2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xCA, 0x309 },
+ unicodeslot=0x1EC2,
+ },
+ [0x1EC3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xEA, 0x309 },
+ unicodeslot=0x1EC3,
+ },
+ [0x1EC4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xCA, 0x303 },
+ unicodeslot=0x1EC4,
+ },
+ [0x1EC5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xEA, 0x303 },
+ unicodeslot=0x1EC5,
+ },
+ [0x1EC6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EB8, 0x302 },
+ unicodeslot=0x1EC6,
+ },
+ [0x1EC7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1EB9, 0x302 },
+ unicodeslot=0x1EC7,
+ },
+ [0x1EC8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x309 },
+ unicodeslot=0x1EC8,
+ },
+ [0x1EC9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x309 },
+ unicodeslot=0x1EC9,
+ },
+ [0x1ECA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x49, 0x323 },
+ unicodeslot=0x1ECA,
+ },
+ [0x1ECB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x69, 0x323 },
+ unicodeslot=0x1ECB,
+ },
+ [0x1ECC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x323 },
+ unicodeslot=0x1ECC,
+ },
+ [0x1ECD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x323 },
+ unicodeslot=0x1ECD,
+ },
+ [0x1ECE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4F, 0x309 },
+ unicodeslot=0x1ECE,
+ },
+ [0x1ECF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x6F, 0x309 },
+ unicodeslot=0x1ECF,
+ },
+ [0x1ED0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD4, 0x301 },
+ unicodeslot=0x1ED0,
+ },
+ [0x1ED1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF4, 0x301 },
+ unicodeslot=0x1ED1,
+ },
+ [0x1ED2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD4, 0x300 },
+ unicodeslot=0x1ED2,
+ },
+ [0x1ED3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF4, 0x300 },
+ unicodeslot=0x1ED3,
+ },
+ [0x1ED4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD4, 0x309 },
+ unicodeslot=0x1ED4,
+ },
+ [0x1ED5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF4, 0x309 },
+ unicodeslot=0x1ED5,
+ },
+ [0x1ED6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xD4, 0x303 },
+ unicodeslot=0x1ED6,
+ },
+ [0x1ED7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0xF4, 0x303 },
+ unicodeslot=0x1ED7,
+ },
+ [0x1ED8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1ECC, 0x302 },
+ unicodeslot=0x1ED8,
+ },
+ [0x1ED9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1ECD, 0x302 },
+ unicodeslot=0x1ED9,
+ },
+ [0x1EDA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A0, 0x301 },
+ unicodeslot=0x1EDA,
+ },
+ [0x1EDB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A1, 0x301 },
+ unicodeslot=0x1EDB,
+ },
+ [0x1EDC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A0, 0x300 },
+ unicodeslot=0x1EDC,
+ },
+ [0x1EDD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A1, 0x300 },
+ unicodeslot=0x1EDD,
+ },
+ [0x1EDE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A0, 0x309 },
+ unicodeslot=0x1EDE,
+ },
+ [0x1EDF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A1, 0x309 },
+ unicodeslot=0x1EDF,
+ },
+ [0x1EE0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A0, 0x303 },
+ unicodeslot=0x1EE0,
+ },
+ [0x1EE1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A1, 0x303 },
+ unicodeslot=0x1EE1,
+ },
+ [0x1EE2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A0, 0x323 },
+ unicodeslot=0x1EE2,
+ },
+ [0x1EE3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1A1, 0x323 },
+ unicodeslot=0x1EE3,
+ },
+ [0x1EE4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x323 },
+ unicodeslot=0x1EE4,
+ },
+ [0x1EE5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x323 },
+ unicodeslot=0x1EE5,
+ },
+ [0x1EE6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x55, 0x309 },
+ unicodeslot=0x1EE6,
+ },
+ [0x1EE7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x75, 0x309 },
+ unicodeslot=0x1EE7,
+ },
+ [0x1EE8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1AF, 0x301 },
+ unicodeslot=0x1EE8,
+ },
+ [0x1EE9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0, 0x301 },
+ unicodeslot=0x1EE9,
+ },
+ [0x1EEA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1AF, 0x300 },
+ unicodeslot=0x1EEA,
+ },
+ [0x1EEB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0, 0x300 },
+ unicodeslot=0x1EEB,
+ },
+ [0x1EEC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1AF, 0x309 },
+ unicodeslot=0x1EEC,
+ },
+ [0x1EED]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0, 0x309 },
+ unicodeslot=0x1EED,
+ },
+ [0x1EEE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1AF, 0x303 },
+ unicodeslot=0x1EEE,
+ },
+ [0x1EEF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0, 0x303 },
+ unicodeslot=0x1EEF,
+ },
+ [0x1EF0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1AF, 0x323 },
+ unicodeslot=0x1EF0,
+ },
+ [0x1EF1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1B0, 0x323 },
+ unicodeslot=0x1EF1,
+ },
+ [0x1EF2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x300 },
+ unicodeslot=0x1EF2,
+ },
+ [0x1EF3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x300 },
+ unicodeslot=0x1EF3,
+ },
+ [0x1EF4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x323 },
+ unicodeslot=0x1EF4,
+ },
+ [0x1EF5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x323 },
+ unicodeslot=0x1EF5,
+ },
+ [0x1EF6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x309 },
+ unicodeslot=0x1EF6,
+ },
+ [0x1EF7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x309 },
+ unicodeslot=0x1EF7,
+ },
+ [0x1EF8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x59, 0x303 },
+ unicodeslot=0x1EF8,
+ },
+ [0x1EF9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x79, 0x303 },
+ unicodeslot=0x1EF9,
+ },
+ [0x1EFA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1EFA,
+ },
+ [0x1EFB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1EFB,
+ },
+ [0x1EFC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1EFC,
+ },
+ [0x1EFD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1EFD,
+ },
+ [0x1EFE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1EFE,
+ },
+ [0x1EFF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1EFF,
+ },
+ [0x1F00]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x313 },
+ unicodeslot=0x1F00,
+ },
+ [0x1F01]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x314 },
+ unicodeslot=0x1F01,
+ },
+ [0x1F02]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F00, 0x300 },
+ unicodeslot=0x1F02,
+ },
+ [0x1F03]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F01, 0x300 },
+ unicodeslot=0x1F03,
+ },
+ [0x1F04]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F00, 0x301 },
+ unicodeslot=0x1F04,
+ },
+ [0x1F05]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F01, 0x301 },
+ unicodeslot=0x1F05,
+ },
+ [0x1F06]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F00, 0x342 },
+ unicodeslot=0x1F06,
+ },
+ [0x1F07]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F01, 0x342 },
+ unicodeslot=0x1F07,
+ },
+ [0x1F08]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x313 },
+ unicodeslot=0x1F08,
+ },
+ [0x1F09]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x314 },
+ unicodeslot=0x1F09,
+ },
+ [0x1F0A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F08, 0x300 },
+ unicodeslot=0x1F0A,
+ },
+ [0x1F0B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F09, 0x300 },
+ unicodeslot=0x1F0B,
+ },
+ [0x1F0C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F08, 0x301 },
+ unicodeslot=0x1F0C,
+ },
+ [0x1F0D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F09, 0x301 },
+ unicodeslot=0x1F0D,
+ },
+ [0x1F0E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F08, 0x342 },
+ unicodeslot=0x1F0E,
+ },
+ [0x1F0F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F09, 0x342 },
+ unicodeslot=0x1F0F,
+ },
+ [0x1F10]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B5, 0x313 },
+ unicodeslot=0x1F10,
+ },
+ [0x1F11]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B5, 0x314 },
+ unicodeslot=0x1F11,
+ },
+ [0x1F12]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F10, 0x300 },
+ unicodeslot=0x1F12,
+ },
+ [0x1F13]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F11, 0x300 },
+ unicodeslot=0x1F13,
+ },
+ [0x1F14]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F10, 0x301 },
+ unicodeslot=0x1F14,
+ },
+ [0x1F15]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F11, 0x301 },
+ unicodeslot=0x1F15,
+ },
+ [0x1F18]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x395, 0x313 },
+ unicodeslot=0x1F18,
+ },
+ [0x1F19]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x395, 0x314 },
+ unicodeslot=0x1F19,
+ },
+ [0x1F1A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F18, 0x300 },
+ unicodeslot=0x1F1A,
+ },
+ [0x1F1B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F19, 0x300 },
+ unicodeslot=0x1F1B,
+ },
+ [0x1F1C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F18, 0x301 },
+ unicodeslot=0x1F1C,
+ },
+ [0x1F1D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F19, 0x301 },
+ unicodeslot=0x1F1D,
+ },
+ [0x1F20]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B7, 0x313 },
+ unicodeslot=0x1F20,
+ },
+ [0x1F21]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B7, 0x314 },
+ unicodeslot=0x1F21,
+ },
+ [0x1F22]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F20, 0x300 },
+ unicodeslot=0x1F22,
+ },
+ [0x1F23]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F21, 0x300 },
+ unicodeslot=0x1F23,
+ },
+ [0x1F24]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F20, 0x301 },
+ unicodeslot=0x1F24,
+ },
+ [0x1F25]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F21, 0x301 },
+ unicodeslot=0x1F25,
+ },
+ [0x1F26]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F20, 0x342 },
+ unicodeslot=0x1F26,
+ },
+ [0x1F27]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F21, 0x342 },
+ unicodeslot=0x1F27,
+ },
+ [0x1F28]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x397, 0x313 },
+ unicodeslot=0x1F28,
+ },
+ [0x1F29]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x397, 0x314 },
+ unicodeslot=0x1F29,
+ },
+ [0x1F2A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F28, 0x300 },
+ unicodeslot=0x1F2A,
+ },
+ [0x1F2B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F29, 0x300 },
+ unicodeslot=0x1F2B,
+ },
+ [0x1F2C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F28, 0x301 },
+ unicodeslot=0x1F2C,
+ },
+ [0x1F2D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F29, 0x301 },
+ unicodeslot=0x1F2D,
+ },
+ [0x1F2E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F28, 0x342 },
+ unicodeslot=0x1F2E,
+ },
+ [0x1F2F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F29, 0x342 },
+ unicodeslot=0x1F2F,
+ },
+ [0x1F30]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x313 },
+ unicodeslot=0x1F30,
+ },
+ [0x1F31]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x314 },
+ unicodeslot=0x1F31,
+ },
+ [0x1F32]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F30, 0x300 },
+ unicodeslot=0x1F32,
+ },
+ [0x1F33]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F31, 0x300 },
+ unicodeslot=0x1F33,
+ },
+ [0x1F34]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F30, 0x301 },
+ unicodeslot=0x1F34,
+ },
+ [0x1F35]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F31, 0x301 },
+ unicodeslot=0x1F35,
+ },
+ [0x1F36]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F30, 0x342 },
+ unicodeslot=0x1F36,
+ },
+ [0x1F37]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F31, 0x342 },
+ unicodeslot=0x1F37,
+ },
+ [0x1F38]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x313 },
+ unicodeslot=0x1F38,
+ },
+ [0x1F39]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x314 },
+ unicodeslot=0x1F39,
+ },
+ [0x1F3A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F38, 0x300 },
+ unicodeslot=0x1F3A,
+ },
+ [0x1F3B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F39, 0x300 },
+ unicodeslot=0x1F3B,
+ },
+ [0x1F3C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F38, 0x301 },
+ unicodeslot=0x1F3C,
+ },
+ [0x1F3D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F39, 0x301 },
+ unicodeslot=0x1F3D,
+ },
+ [0x1F3E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F38, 0x342 },
+ unicodeslot=0x1F3E,
+ },
+ [0x1F3F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F39, 0x342 },
+ unicodeslot=0x1F3F,
+ },
+ [0x1F40]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3BF, 0x313 },
+ unicodeslot=0x1F40,
+ },
+ [0x1F41]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3BF, 0x314 },
+ unicodeslot=0x1F41,
+ },
+ [0x1F42]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F40, 0x300 },
+ unicodeslot=0x1F42,
+ },
+ [0x1F43]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F41, 0x300 },
+ unicodeslot=0x1F43,
+ },
+ [0x1F44]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F40, 0x301 },
+ unicodeslot=0x1F44,
+ },
+ [0x1F45]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F41, 0x301 },
+ unicodeslot=0x1F45,
+ },
+ [0x1F48]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x39F, 0x313 },
+ unicodeslot=0x1F48,
+ },
+ [0x1F49]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x39F, 0x314 },
+ unicodeslot=0x1F49,
+ },
+ [0x1F4A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F48, 0x300 },
+ unicodeslot=0x1F4A,
+ },
+ [0x1F4B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F49, 0x300 },
+ unicodeslot=0x1F4B,
+ },
+ [0x1F4C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F48, 0x301 },
+ unicodeslot=0x1F4C,
+ },
+ [0x1F4D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F49, 0x301 },
+ unicodeslot=0x1F4D,
+ },
+ [0x1F50]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x313 },
+ unicodeslot=0x1F50,
+ },
+ [0x1F51]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x314 },
+ unicodeslot=0x1F51,
+ },
+ [0x1F52]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F50, 0x300 },
+ unicodeslot=0x1F52,
+ },
+ [0x1F53]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F51, 0x300 },
+ unicodeslot=0x1F53,
+ },
+ [0x1F54]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F50, 0x301 },
+ unicodeslot=0x1F54,
+ },
+ [0x1F55]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F51, 0x301 },
+ unicodeslot=0x1F55,
+ },
+ [0x1F56]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F50, 0x342 },
+ unicodeslot=0x1F56,
+ },
+ [0x1F57]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F51, 0x342 },
+ unicodeslot=0x1F57,
+ },
+ [0x1F59]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A5, 0x314 },
+ unicodeslot=0x1F59,
+ },
+ [0x1F5B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F59, 0x300 },
+ unicodeslot=0x1F5B,
+ },
+ [0x1F5D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F59, 0x301 },
+ unicodeslot=0x1F5D,
+ },
+ [0x1F5F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F59, 0x342 },
+ unicodeslot=0x1F5F,
+ },
+ [0x1F60]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C9, 0x313 },
+ unicodeslot=0x1F60,
+ },
+ [0x1F61]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C9, 0x314 },
+ unicodeslot=0x1F61,
+ },
+ [0x1F62]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F60, 0x300 },
+ unicodeslot=0x1F62,
+ },
+ [0x1F63]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F61, 0x300 },
+ unicodeslot=0x1F63,
+ },
+ [0x1F64]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F60, 0x301 },
+ unicodeslot=0x1F64,
+ },
+ [0x1F65]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F61, 0x301 },
+ unicodeslot=0x1F65,
+ },
+ [0x1F66]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F60, 0x342 },
+ unicodeslot=0x1F66,
+ },
+ [0x1F67]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F61, 0x342 },
+ unicodeslot=0x1F67,
+ },
+ [0x1F68]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A9, 0x313 },
+ unicodeslot=0x1F68,
+ },
+ [0x1F69]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A9, 0x314 },
+ unicodeslot=0x1F69,
+ },
+ [0x1F6A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F68, 0x300 },
+ unicodeslot=0x1F6A,
+ },
+ [0x1F6B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F69, 0x300 },
+ unicodeslot=0x1F6B,
+ },
+ [0x1F6C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F68, 0x301 },
+ unicodeslot=0x1F6C,
+ },
+ [0x1F6D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F69, 0x301 },
+ unicodeslot=0x1F6D,
+ },
+ [0x1F6E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F68, 0x342 },
+ unicodeslot=0x1F6E,
+ },
+ [0x1F6F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F69, 0x342 },
+ unicodeslot=0x1F6F,
+ },
+ [0x1F70]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x300 },
+ unicodeslot=0x1F70,
+ },
+ [0x1F71]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3AC },
+ unicodeslot=0x1F71,
+ },
+ [0x1F72]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B5, 0x300 },
+ unicodeslot=0x1F72,
+ },
+ [0x1F73]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3AD },
+ unicodeslot=0x1F73,
+ },
+ [0x1F74]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B7, 0x300 },
+ unicodeslot=0x1F74,
+ },
+ [0x1F75]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3AE },
+ unicodeslot=0x1F75,
+ },
+ [0x1F76]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x300 },
+ unicodeslot=0x1F76,
+ },
+ [0x1F77]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3AF },
+ unicodeslot=0x1F77,
+ },
+ [0x1F78]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3BF, 0x300 },
+ unicodeslot=0x1F78,
+ },
+ [0x1F79]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CC },
+ unicodeslot=0x1F79,
+ },
+ [0x1F7A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x300 },
+ unicodeslot=0x1F7A,
+ },
+ [0x1F7B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CD },
+ unicodeslot=0x1F7B,
+ },
+ [0x1F7C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C9, 0x300 },
+ unicodeslot=0x1F7C,
+ },
+ [0x1F7D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CE },
+ unicodeslot=0x1F7D,
+ },
+ [0x1F80]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F00, 0x345 },
+ unicodeslot=0x1F80,
+ },
+ [0x1F81]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F01, 0x345 },
+ unicodeslot=0x1F81,
+ },
+ [0x1F82]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F02, 0x345 },
+ unicodeslot=0x1F82,
+ },
+ [0x1F83]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F03, 0x345 },
+ unicodeslot=0x1F83,
+ },
+ [0x1F84]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F04, 0x345 },
+ unicodeslot=0x1F84,
+ },
+ [0x1F85]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F05, 0x345 },
+ unicodeslot=0x1F85,
+ },
+ [0x1F86]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F06, 0x345 },
+ unicodeslot=0x1F86,
+ },
+ [0x1F87]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F07, 0x345 },
+ unicodeslot=0x1F87,
+ },
+ [0x1F88]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F08, 0x345 },
+ unicodeslot=0x1F88,
+ },
+ [0x1F89]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F09, 0x345 },
+ unicodeslot=0x1F89,
+ },
+ [0x1F8A]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F0A, 0x345 },
+ unicodeslot=0x1F8A,
+ },
+ [0x1F8B]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F0B, 0x345 },
+ unicodeslot=0x1F8B,
+ },
+ [0x1F8C]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F0C, 0x345 },
+ unicodeslot=0x1F8C,
+ },
+ [0x1F8D]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F0D, 0x345 },
+ unicodeslot=0x1F8D,
+ },
+ [0x1F8E]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F0E, 0x345 },
+ unicodeslot=0x1F8E,
+ },
+ [0x1F8F]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F0F, 0x345 },
+ unicodeslot=0x1F8F,
+ },
+ [0x1F90]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F20, 0x345 },
+ unicodeslot=0x1F90,
+ },
+ [0x1F91]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F21, 0x345 },
+ unicodeslot=0x1F91,
+ },
+ [0x1F92]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F22, 0x345 },
+ unicodeslot=0x1F92,
+ },
+ [0x1F93]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F23, 0x345 },
+ unicodeslot=0x1F93,
+ },
+ [0x1F94]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F24, 0x345 },
+ unicodeslot=0x1F94,
+ },
+ [0x1F95]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F25, 0x345 },
+ unicodeslot=0x1F95,
+ },
+ [0x1F96]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F26, 0x345 },
+ unicodeslot=0x1F96,
+ },
+ [0x1F97]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F27, 0x345 },
+ unicodeslot=0x1F97,
+ },
+ [0x1F98]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F28, 0x345 },
+ unicodeslot=0x1F98,
+ },
+ [0x1F99]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F29, 0x345 },
+ unicodeslot=0x1F99,
+ },
+ [0x1F9A]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F2A, 0x345 },
+ unicodeslot=0x1F9A,
+ },
+ [0x1F9B]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F2B, 0x345 },
+ unicodeslot=0x1F9B,
+ },
+ [0x1F9C]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F2C, 0x345 },
+ unicodeslot=0x1F9C,
+ },
+ [0x1F9D]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F2D, 0x345 },
+ unicodeslot=0x1F9D,
+ },
+ [0x1F9E]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F2E, 0x345 },
+ unicodeslot=0x1F9E,
+ },
+ [0x1F9F]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F2F, 0x345 },
+ unicodeslot=0x1F9F,
+ },
+ [0x1FA0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F60, 0x345 },
+ unicodeslot=0x1FA0,
+ },
+ [0x1FA1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F61, 0x345 },
+ unicodeslot=0x1FA1,
+ },
+ [0x1FA2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F62, 0x345 },
+ unicodeslot=0x1FA2,
+ },
+ [0x1FA3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F63, 0x345 },
+ unicodeslot=0x1FA3,
+ },
+ [0x1FA4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F64, 0x345 },
+ unicodeslot=0x1FA4,
+ },
+ [0x1FA5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F65, 0x345 },
+ unicodeslot=0x1FA5,
+ },
+ [0x1FA6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F66, 0x345 },
+ unicodeslot=0x1FA6,
+ },
+ [0x1FA7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F67, 0x345 },
+ unicodeslot=0x1FA7,
+ },
+ [0x1FA8]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F68, 0x345 },
+ unicodeslot=0x1FA8,
+ },
+ [0x1FA9]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F69, 0x345 },
+ unicodeslot=0x1FA9,
+ },
+ [0x1FAA]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F6A, 0x345 },
+ unicodeslot=0x1FAA,
+ },
+ [0x1FAB]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F6B, 0x345 },
+ unicodeslot=0x1FAB,
+ },
+ [0x1FAC]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F6C, 0x345 },
+ unicodeslot=0x1FAC,
+ },
+ [0x1FAD]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F6D, 0x345 },
+ unicodeslot=0x1FAD,
+ },
+ [0x1FAE]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F6E, 0x345 },
+ unicodeslot=0x1FAE,
+ },
+ [0x1FAF]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F6F, 0x345 },
+ unicodeslot=0x1FAF,
+ },
+ [0x1FB0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x306 },
+ unicodeslot=0x1FB0,
+ },
+ [0x1FB1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x304 },
+ unicodeslot=0x1FB1,
+ },
+ [0x1FB2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F70, 0x345 },
+ unicodeslot=0x1FB2,
+ },
+ [0x1FB3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x345 },
+ unicodeslot=0x1FB3,
+ },
+ [0x1FB4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3AC, 0x345 },
+ unicodeslot=0x1FB4,
+ },
+ [0x1FB6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B1, 0x342 },
+ unicodeslot=0x1FB6,
+ },
+ [0x1FB7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1FB6, 0x345 },
+ unicodeslot=0x1FB7,
+ },
+ [0x1FB8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x306 },
+ unicodeslot=0x1FB8,
+ },
+ [0x1FB9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x304 },
+ unicodeslot=0x1FB9,
+ },
+ [0x1FBA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x300 },
+ unicodeslot=0x1FBA,
+ },
+ [0x1FBB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x386 },
+ unicodeslot=0x1FBB,
+ },
+ [0x1FBC]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x391, 0x345 },
+ unicodeslot=0x1FBC,
+ },
+ [0x1FBD]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x313 },
+ unicodeslot=0x1FBD,
+ },
+ [0x1FBE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9 },
+ unicodeslot=0x1FBE,
+ },
+ [0x1FBF]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x313 },
+ unicodeslot=0x1FBF,
+ },
+ [0x1FC0]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x342 },
+ unicodeslot=0x1FC0,
+ },
+ [0x1FC1]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0xA8, 0x342 },
+ unicodeslot=0x1FC1,
+ },
+ [0x1FC2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F74, 0x345 },
+ unicodeslot=0x1FC2,
+ },
+ [0x1FC3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B7, 0x345 },
+ unicodeslot=0x1FC3,
+ },
+ [0x1FC4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3AE, 0x345 },
+ unicodeslot=0x1FC4,
+ },
+ [0x1FC6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B7, 0x342 },
+ unicodeslot=0x1FC6,
+ },
+ [0x1FC7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1FC6, 0x345 },
+ unicodeslot=0x1FC7,
+ },
+ [0x1FC8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x395, 0x300 },
+ unicodeslot=0x1FC8,
+ },
+ [0x1FC9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x388 },
+ unicodeslot=0x1FC9,
+ },
+ [0x1FCA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x397, 0x300 },
+ unicodeslot=0x1FCA,
+ },
+ [0x1FCB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x389 },
+ unicodeslot=0x1FCB,
+ },
+ [0x1FCC]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x397, 0x345 },
+ unicodeslot=0x1FCC,
+ },
+ [0x1FCD]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x1FBF, 0x300 },
+ unicodeslot=0x1FCD,
+ },
+ [0x1FCE]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x1FBF, 0x301 },
+ unicodeslot=0x1FCE,
+ },
+ [0x1FCF]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x1FBF, 0x342 },
+ unicodeslot=0x1FCF,
+ },
+ [0x1FD0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x306 },
+ unicodeslot=0x1FD0,
+ },
+ [0x1FD1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x304 },
+ unicodeslot=0x1FD1,
+ },
+ [0x1FD2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CA, 0x300 },
+ unicodeslot=0x1FD2,
+ },
+ [0x1FD3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x390 },
+ unicodeslot=0x1FD3,
+ },
+ [0x1FD6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B9, 0x342 },
+ unicodeslot=0x1FD6,
+ },
+ [0x1FD7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CA, 0x342 },
+ unicodeslot=0x1FD7,
+ },
+ [0x1FD8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x306 },
+ unicodeslot=0x1FD8,
+ },
+ [0x1FD9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x304 },
+ unicodeslot=0x1FD9,
+ },
+ [0x1FDA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x399, 0x300 },
+ unicodeslot=0x1FDA,
+ },
+ [0x1FDB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x38A },
+ unicodeslot=0x1FDB,
+ },
+ [0x1FDD]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x1FFE, 0x300 },
+ unicodeslot=0x1FDD,
+ },
+ [0x1FDE]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x1FFE, 0x301 },
+ unicodeslot=0x1FDE,
+ },
+ [0x1FDF]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x1FFE, 0x342 },
+ unicodeslot=0x1FDF,
+ },
+ [0x1FE0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x306 },
+ unicodeslot=0x1FE0,
+ },
+ [0x1FE1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x304 },
+ unicodeslot=0x1FE1,
+ },
+ [0x1FE2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CB, 0x300 },
+ unicodeslot=0x1FE2,
+ },
+ [0x1FE3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3B0 },
+ unicodeslot=0x1FE3,
+ },
+ [0x1FE4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C1, 0x313 },
+ unicodeslot=0x1FE4,
+ },
+ [0x1FE5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C1, 0x314 },
+ unicodeslot=0x1FE5,
+ },
+ [0x1FE6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C5, 0x342 },
+ unicodeslot=0x1FE6,
+ },
+ [0x1FE7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CB, 0x342 },
+ unicodeslot=0x1FE7,
+ },
+ [0x1FE8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A5, 0x306 },
+ unicodeslot=0x1FE8,
+ },
+ [0x1FE9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A5, 0x304 },
+ unicodeslot=0x1FE9,
+ },
+ [0x1FEA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A5, 0x300 },
+ unicodeslot=0x1FEA,
+ },
+ [0x1FEB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x38E },
+ unicodeslot=0x1FEB,
+ },
+ [0x1FEC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A1, 0x314 },
+ unicodeslot=0x1FEC,
+ },
+ [0x1FED]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0xA8, 0x300 },
+ unicodeslot=0x1FED,
+ },
+ [0x1FEE]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x385 },
+ unicodeslot=0x1FEE,
+ },
+ [0x1FEF]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x60 },
+ unicodeslot=0x1FEF,
+ },
+ [0x1FF2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1F7C, 0x345 },
+ unicodeslot=0x1FF2,
+ },
+ [0x1FF3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C9, 0x345 },
+ unicodeslot=0x1FF3,
+ },
+ [0x1FF4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3CE, 0x345 },
+ unicodeslot=0x1FF4,
+ },
+ [0x1FF6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3C9, 0x342 },
+ unicodeslot=0x1FF6,
+ },
+ [0x1FF7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1FF6, 0x345 },
+ unicodeslot=0x1FF7,
+ },
+ [0x1FF8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x39F, 0x300 },
+ unicodeslot=0x1FF8,
+ },
+ [0x1FF9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x38C },
+ unicodeslot=0x1FF9,
+ },
+ [0x1FFA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A9, 0x300 },
+ unicodeslot=0x1FFA,
+ },
+ [0x1FFB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x38F },
+ unicodeslot=0x1FFB,
+ },
+ [0x1FFC]={
+ category="lt",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A9, 0x345 },
+ unicodeslot=0x1FFC,
+ },
+ [0x1FFD]={
+ category="sk",
+ direction="on",
+ linebreak="bb",
+ specials={ "char", 0xB4 },
+ unicodeslot=0x1FFD,
+ },
+ [0x1FFE]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x314 },
+ unicodeslot=0x1FFE,
+ },
+ [0x2000]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "char", 0x2002 },
+ unicodeslot=0x2000,
+ },
+ [0x2001]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "char", 0x2003 },
+ unicodeslot=0x2001,
+ },
+ [0x2002]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2002,
+ },
+ [0x2003]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2003,
+ },
+ [0x2004]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2004,
+ },
+ [0x2005]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2005,
+ },
+ [0x2006]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2006,
+ },
+ [0x2007]={
+ category="zs",
+ direction="ws",
+ linebreak="gl",
+ specials={ "nobreak", 0x20 },
+ unicodeslot=0x2007,
+ },
+ [0x2008]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2008,
+ },
+ [0x2009]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x2009,
+ },
+ [0x200A]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x200A,
+ },
+ [0x200B]={
+ category="cf",
+ direction="bn",
+ linebreak="zw",
+ unicodeslot=0x200B,
+ },
+ [0x200C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x200C,
+ },
+ [0x200D]={
+ category="cf",
+ direction="bn",
+ linebreak="zwj",
+ unicodeslot=0x200D,
+ },
+ [0x200E]={
+ category="cf",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x200E,
+ },
+ [0x200F]={
+ category="cf",
+ direction="r",
+ linebreak="cm",
+ unicodeslot=0x200F,
+ },
+ [0x2010]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2010,
+ },
+ [0x2011]={
+ category="pd",
+ direction="on",
+ linebreak="gl",
+ specials={ "nobreak", 0x2010 },
+ unicodeslot=0x2011,
+ },
+ [0x2012]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2012,
+ },
+ [0x2013]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2013,
+ },
+ [0x2014]={
+ category="pd",
+ direction="on",
+ linebreak="b2",
+ unicodeslot=0x2014,
+ },
+ [0x2015]={
+ category="pd",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2015,
+ },
+ [0x2016]={
+ category="po",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2016,
+ },
+ [0x2017]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x333 },
+ unicodeslot=0x2017,
+ },
+ [0x2018]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2018,
+ },
+ [0x2019]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2019,
+ },
+ [0x201A]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0x201A,
+ },
+ [0x201B]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x201B,
+ },
+ [0x201C]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x201C,
+ },
+ [0x201D]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x201D,
+ },
+ [0x201E]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0x201E,
+ },
+ [0x201F]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x201F,
+ },
+ [0x2020]={
+ category="po",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2020,
+ },
+ [0x2021]={
+ category="po",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2021,
+ },
+ [0x2022]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2022,
+ },
+ [0x2023]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2023,
+ },
+ [0x2024]={
+ category="po",
+ direction="on",
+ linebreak="in",
+ specials={ "compat", 0x2E },
+ unicodeslot=0x2024,
+ },
+ [0x2025]={
+ category="po",
+ direction="on",
+ linebreak="in",
+ specials={ "compat", 0x2E, 0x2E },
+ unicodeslot=0x2025,
+ },
+ [0x2026]={
+ category="po",
+ direction="on",
+ linebreak="in",
+ specials={ "compat", 0x2E, 0x2E, 0x2E },
+ unicodeslot=0x2026,
+ },
+ [0x2027]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2027,
+ },
+ [0x2028]={
+ category="zl",
+ direction="ws",
+ linebreak="bk",
+ unicodeslot=0x2028,
+ },
+ [0x2029]={
+ category="zp",
+ direction="b",
+ linebreak="bk",
+ unicodeslot=0x2029,
+ },
+ [0x202A]={
+ category="cf",
+ direction="lre",
+ linebreak="cm",
+ unicodeslot=0x202A,
+ },
+ [0x202B]={
+ category="cf",
+ direction="rle",
+ linebreak="cm",
+ unicodeslot=0x202B,
+ },
+ [0x202C]={
+ category="cf",
+ direction="pdf",
+ linebreak="cm",
+ unicodeslot=0x202C,
+ },
+ [0x202D]={
+ category="cf",
+ direction="lro",
+ linebreak="cm",
+ unicodeslot=0x202D,
+ },
+ [0x202E]={
+ category="cf",
+ direction="rlo",
+ linebreak="cm",
+ unicodeslot=0x202E,
+ },
+ [0x202F]={
+ category="zs",
+ direction="cs",
+ linebreak="gl",
+ specials={ "nobreak", 0x20 },
+ unicodeslot=0x202F,
+ },
+ [0x2030]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x2030,
+ },
+ [0x2031]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x2031,
+ },
+ [0x2032]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x2032,
+ },
+ [0x2033]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ specials={ "compat", 0x2032, 0x2032 },
+ unicodeslot=0x2033,
+ },
+ [0x2034]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ specials={ "compat", 0x2032, 0x2032, 0x2032 },
+ unicodeslot=0x2034,
+ },
+ [0x2035]={
+ category="po",
+ direction="on",
+ linebreak="po",
+ unicodeslot=0x2035,
+ },
+ [0x2036]={
+ category="po",
+ direction="on",
+ linebreak="po",
+ specials={ "compat", 0x2035, 0x2035 },
+ unicodeslot=0x2036,
+ },
+ [0x2037]={
+ category="po",
+ direction="on",
+ linebreak="po",
+ specials={ "compat", 0x2035, 0x2035, 0x2035 },
+ unicodeslot=0x2037,
+ },
+ [0x2038]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2038,
+ },
+ [0x2039]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x203A,
+ textclass="open",
+ unicodeslot=0x2039,
+ },
+ [0x203A]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2039,
+ textclass="close",
+ unicodeslot=0x203A,
+ },
+ [0x203B]={
+ category="po",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x203B,
+ },
+ [0x203C]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "compat", 0x21, 0x21 },
+ unicodeslot=0x203C,
+ },
+ [0x203D]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x203D,
+ },
+ [0x203E]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x20, 0x305 },
+ unicodeslot=0x203E,
+ },
+ [0x203F]={
+ category="pc",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x203F,
+ },
+ [0x2040]={
+ category="pc",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2040,
+ },
+ [0x2041]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2041,
+ },
+ [0x2042]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2042,
+ },
+ [0x2043]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2043,
+ },
+ [0x2044]={
+ category="sm",
+ direction="cs",
+ linebreak="is",
+ unicodeslot=0x2044,
+ },
+ [0x2045]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2046,
+ unicodeslot=0x2045,
+ },
+ [0x2046]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2045,
+ unicodeslot=0x2046,
+ },
+ [0x2047]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "compat", 0x3F, 0x3F },
+ unicodeslot=0x2047,
+ },
+ [0x2048]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "compat", 0x3F, 0x21 },
+ unicodeslot=0x2048,
+ },
+ [0x2049]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "compat", 0x21, 0x3F },
+ unicodeslot=0x2049,
+ },
+ [0x204A]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x204A,
+ },
+ [0x204B]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x204B,
+ },
+ [0x204C]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x204C,
+ },
+ [0x204D]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x204D,
+ },
+ [0x204E]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x204E,
+ },
+ [0x204F]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x204F,
+ },
+ [0x2050]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2050,
+ },
+ [0x2051]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2051,
+ },
+ [0x2052]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2052,
+ },
+ [0x2053]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2053,
+ },
+ [0x2054]={
+ category="pc",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2054,
+ },
+ [0x2055]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2055,
+ },
+ [0x2056]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2056,
+ },
+ [0x2057]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x2032, 0x2032, 0x2032, 0x2032 },
+ unicodeslot=0x2057,
+ },
+ [0x2058]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2058,
+ },
+ [0x2059]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2059,
+ },
+ [0x205A]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x205A,
+ },
+ [0x205B]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x205B,
+ },
+ [0x205C]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x205C,
+ },
+ [0x205D]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x205D,
+ },
+ [0x205E]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x205E,
+ },
+ [0x205F]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "compat", 0x20 },
+ unicodeslot=0x205F,
+ },
+ [0x2060]={
+ category="cf",
+ direction="bn",
+ linebreak="wj",
+ unicodeslot=0x2060,
+ },
+ [0x2061]={
+ category="cf",
+ direction="bn",
+ linebreak="al",
+ unicodeslot=0x2061,
+ },
+ [0x2062]={
+ category="cf",
+ direction="bn",
+ linebreak="al",
+ unicodeslot=0x2062,
+ },
+ [0x2063]={
+ category="cf",
+ direction="bn",
+ linebreak="al",
+ unicodeslot=0x2063,
+ },
+ [0x2064]={
+ category="cf",
+ direction="bn",
+ linebreak="al",
+ unicodeslot=0x2064,
+ },
+ [0x2066]={
+ category="cf",
+ direction="lri",
+ linebreak="cm",
+ unicodeslot=0x2066,
+ },
+ [0x2067]={
+ category="cf",
+ direction="rli",
+ linebreak="cm",
+ unicodeslot=0x2067,
+ },
+ [0x2068]={
+ category="cf",
+ direction="fsi",
+ linebreak="cm",
+ unicodeslot=0x2068,
+ },
+ [0x2069]={
+ category="cf",
+ direction="pdi",
+ linebreak="cm",
+ unicodeslot=0x2069,
+ },
+ [0x206A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x206A,
+ },
+ [0x206B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x206B,
+ },
+ [0x206C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x206C,
+ },
+ [0x206D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x206D,
+ },
+ [0x206E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x206E,
+ },
+ [0x206F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x206F,
+ },
+ [0x2070]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "super", 0x30 },
+ unicodeslot=0x2070,
+ },
+ [0x2071]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x69 },
+ unicodeslot=0x2071,
+ },
+ [0x2074]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "super", 0x34 },
+ unicodeslot=0x2074,
+ },
+ [0x2075]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "super", 0x35 },
+ unicodeslot=0x2075,
+ },
+ [0x2076]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "super", 0x36 },
+ unicodeslot=0x2076,
+ },
+ [0x2077]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "super", 0x37 },
+ unicodeslot=0x2077,
+ },
+ [0x2078]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "super", 0x38 },
+ unicodeslot=0x2078,
+ },
+ [0x2079]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "super", 0x39 },
+ unicodeslot=0x2079,
+ },
+ [0x207A]={
+ category="sm",
+ direction="es",
+ linebreak="al",
+ specials={ "super", 0x2B },
+ unicodeslot=0x207A,
+ },
+ [0x207B]={
+ category="sm",
+ direction="es",
+ linebreak="al",
+ specials={ "super", 0x2212 },
+ unicodeslot=0x207B,
+ },
+ [0x207C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "super", 0x3D },
+ unicodeslot=0x207C,
+ },
+ [0x207D]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x207E,
+ specials={ "super", 0x28 },
+ textclass="open",
+ unicodeslot=0x207D,
+ },
+ [0x207E]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x207D,
+ specials={ "super", 0x29 },
+ textclass="close",
+ unicodeslot=0x207E,
+ },
+ [0x207F]={
+ category="ll",
+ direction="l",
+ linebreak="ai",
+ specials={ "super", 0x6E },
+ unicodeslot=0x207F,
+ },
+ [0x2080]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "sub", 0x30 },
+ unicodeslot=0x2080,
+ },
+ [0x2081]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "sub", 0x31 },
+ unicodeslot=0x2081,
+ },
+ [0x2082]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "sub", 0x32 },
+ unicodeslot=0x2082,
+ },
+ [0x2083]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "sub", 0x33 },
+ unicodeslot=0x2083,
+ },
+ [0x2084]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "sub", 0x34 },
+ unicodeslot=0x2084,
+ },
+ [0x2085]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "sub", 0x35 },
+ unicodeslot=0x2085,
+ },
+ [0x2086]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "sub", 0x36 },
+ unicodeslot=0x2086,
+ },
+ [0x2087]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "sub", 0x37 },
+ unicodeslot=0x2087,
+ },
+ [0x2088]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "sub", 0x38 },
+ unicodeslot=0x2088,
+ },
+ [0x2089]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ specials={ "sub", 0x39 },
+ unicodeslot=0x2089,
+ },
+ [0x208A]={
+ category="sm",
+ direction="es",
+ linebreak="al",
+ specials={ "sub", 0x2B },
+ unicodeslot=0x208A,
+ },
+ [0x208B]={
+ category="sm",
+ direction="es",
+ linebreak="al",
+ specials={ "sub", 0x2212 },
+ unicodeslot=0x208B,
+ },
+ [0x208C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "sub", 0x3D },
+ unicodeslot=0x208C,
+ },
+ [0x208D]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x208E,
+ specials={ "sub", 0x28 },
+ textclass="open",
+ unicodeslot=0x208D,
+ },
+ [0x208E]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x208D,
+ specials={ "sub", 0x29 },
+ textclass="close",
+ unicodeslot=0x208E,
+ },
+ [0x2090]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x61 },
+ unicodeslot=0x2090,
+ },
+ [0x2091]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x65 },
+ unicodeslot=0x2091,
+ },
+ [0x2092]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x6F },
+ unicodeslot=0x2092,
+ },
+ [0x2093]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x78 },
+ unicodeslot=0x2093,
+ },
+ [0x2094]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x259 },
+ unicodeslot=0x2094,
+ },
+ [0x2095]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x68 },
+ unicodeslot=0x2095,
+ },
+ [0x2096]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x6B },
+ unicodeslot=0x2096,
+ },
+ [0x2097]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x6C },
+ unicodeslot=0x2097,
+ },
+ [0x2098]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x6D },
+ unicodeslot=0x2098,
+ },
+ [0x2099]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x6E },
+ unicodeslot=0x2099,
+ },
+ [0x209A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x70 },
+ unicodeslot=0x209A,
+ },
+ [0x209B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x73 },
+ unicodeslot=0x209B,
+ },
+ [0x209C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x74 },
+ unicodeslot=0x209C,
+ },
+ [0x20A0]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A0,
+ },
+ [0x20A1]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A1,
+ },
+ [0x20A2]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A2,
+ },
+ [0x20A3]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A3,
+ },
+ [0x20A4]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A4,
+ },
+ [0x20A5]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A5,
+ },
+ [0x20A6]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A6,
+ },
+ [0x20A7]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x20A7,
+ },
+ [0x20A8]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ specials={ "compat", 0x52, 0x73 },
+ unicodeslot=0x20A8,
+ },
+ [0x20A9]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20A9,
+ },
+ [0x20AA]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20AA,
+ },
+ [0x20AB]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20AB,
+ },
+ [0x20AC]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20AC,
+ },
+ [0x20AD]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20AD,
+ },
+ [0x20AE]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20AE,
+ },
+ [0x20AF]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20AF,
+ },
+ [0x20B0]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B0,
+ },
+ [0x20B1]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B1,
+ },
+ [0x20B2]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B2,
+ },
+ [0x20B3]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B3,
+ },
+ [0x20B4]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B4,
+ },
+ [0x20B5]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B5,
+ },
+ [0x20B6]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x20B6,
+ },
+ [0x20B7]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B7,
+ },
+ [0x20B8]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B8,
+ },
+ [0x20B9]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20B9,
+ },
+ [0x20BA]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20BA,
+ },
+ [0x20BB]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x20BB,
+ },
+ [0x20BC]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20BC,
+ },
+ [0x20BD]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20BD,
+ },
+ [0x20BE]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x20BE,
+ },
+ [0x20BF]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x20BF,
+ },
+ [0x20D0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D0,
+ },
+ [0x20D1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D1,
+ },
+ [0x20D2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D2,
+ },
+ [0x20D3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D3,
+ },
+ [0x20D4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D4,
+ },
+ [0x20D5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D5,
+ },
+ [0x20D6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D6,
+ },
+ [0x20D7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D7,
+ },
+ [0x20D8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D8,
+ },
+ [0x20D9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20D9,
+ },
+ [0x20DA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20DA,
+ },
+ [0x20DB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20DB,
+ },
+ [0x20DC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20DC,
+ },
+ [0x20DD]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20DD,
+ },
+ [0x20DE]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20DE,
+ },
+ [0x20DF]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20DF,
+ },
+ [0x20E0]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E0,
+ },
+ [0x20E1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E1,
+ },
+ [0x20E2]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E2,
+ },
+ [0x20E3]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E3,
+ },
+ [0x20E4]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E4,
+ },
+ [0x20E5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E5,
+ },
+ [0x20E6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E6,
+ },
+ [0x20E7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E7,
+ },
+ [0x20E8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E8,
+ },
+ [0x20E9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20E9,
+ },
+ [0x20EA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20EA,
+ },
+ [0x20EB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20EB,
+ },
+ [0x20EC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20EC,
+ },
+ [0x20ED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20ED,
+ },
+ [0x20EE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20EE,
+ },
+ [0x20EF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20EF,
+ },
+ [0x20F0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x20F0,
+ },
+ [0x2100]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x61, 0x2F, 0x63 },
+ unicodeslot=0x2100,
+ },
+ [0x2101]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x61, 0x2F, 0x73 },
+ unicodeslot=0x2101,
+ },
+ [0x2102]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x2102,
+ },
+ [0x2103]={
+ category="so",
+ direction="on",
+ linebreak="po",
+ specials={ "compat", 0xB0, 0x43 },
+ unicodeslot=0x2103,
+ },
+ [0x2104]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2104,
+ },
+ [0x2105]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x63, 0x2F, 0x6F },
+ unicodeslot=0x2105,
+ },
+ [0x2106]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x63, 0x2F, 0x75 },
+ unicodeslot=0x2106,
+ },
+ [0x2107]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x190 },
+ unicodeslot=0x2107,
+ },
+ [0x2108]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2108,
+ },
+ [0x2109]={
+ category="so",
+ direction="on",
+ linebreak="po",
+ specials={ "compat", 0xB0, 0x46 },
+ unicodeslot=0x2109,
+ },
+ [0x210A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x210A,
+ },
+ [0x210B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x210B,
+ },
+ [0x210C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x210C,
+ },
+ [0x210D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x210D,
+ },
+ [0x210E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x210E,
+ },
+ [0x210F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x127 },
+ unicodeslot=0x210F,
+ },
+ [0x2110]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x2110,
+ },
+ [0x2111]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x2111,
+ },
+ [0x2112]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x2112,
+ },
+ [0x2113]={
+ category="ll",
+ direction="l",
+ linebreak="ai",
+ specials={ "font", 0x6C },
+ unicodeslot=0x2113,
+ },
+ [0x2114]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2114,
+ },
+ [0x2115]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x2115,
+ },
+ [0x2116]={
+ category="so",
+ direction="on",
+ linebreak="pr",
+ specials={ "compat", 0x4E, 0x6F },
+ unicodeslot=0x2116,
+ },
+ [0x2117]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2117,
+ },
+ [0x2118]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2118,
+ },
+ [0x2119]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x2119,
+ },
+ [0x211A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x211A,
+ },
+ [0x211B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x211B,
+ },
+ [0x211C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x211C,
+ },
+ [0x211D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x211D,
+ },
+ [0x211E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x211E,
+ },
+ [0x211F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x211F,
+ },
+ [0x2120]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "super", 0x53, 0x4D },
+ unicodeslot=0x2120,
+ },
+ [0x2121]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x54, 0x45, 0x4C },
+ unicodeslot=0x2121,
+ },
+ [0x2122]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ specials={ "super", 0x54, 0x4D },
+ unicodeslot=0x2122,
+ },
+ [0x2123]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2123,
+ },
+ [0x2124]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x2124,
+ },
+ [0x2125]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2125,
+ },
+ [0x2126]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x3A9 },
+ unicodeslot=0x2126,
+ },
+ [0x2127]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2127,
+ },
+ [0x2128]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x2128,
+ },
+ [0x2129]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2129,
+ },
+ [0x212A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x4B },
+ unicodeslot=0x212A,
+ },
+ [0x212B]={
+ category="lu",
+ direction="l",
+ linebreak="ai",
+ specials={ "char", 0xC5 },
+ unicodeslot=0x212B,
+ },
+ [0x212C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x212C,
+ },
+ [0x212D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x212D,
+ },
+ [0x212E]={
+ category="so",
+ direction="et",
+ linebreak="al",
+ unicodeslot=0x212E,
+ },
+ [0x212F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x212F,
+ },
+ [0x2130]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x2130,
+ },
+ [0x2131]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x2131,
+ },
+ [0x2132]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2132,
+ },
+ [0x2133]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x2133,
+ },
+ [0x2134]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x2134,
+ },
+ [0x2135]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x5D0 },
+ unicodeslot=0x2135,
+ },
+ [0x2136]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x5D1 },
+ unicodeslot=0x2136,
+ },
+ [0x2137]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x5D2 },
+ unicodeslot=0x2137,
+ },
+ [0x2138]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x5D3 },
+ unicodeslot=0x2138,
+ },
+ [0x2139]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x2139,
+ },
+ [0x213A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x213A,
+ },
+ [0x213B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x46, 0x41, 0x58 },
+ unicodeslot=0x213B,
+ },
+ [0x213C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C0 },
+ unicodeslot=0x213C,
+ },
+ [0x213D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B3 },
+ unicodeslot=0x213D,
+ },
+ [0x213E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x393 },
+ unicodeslot=0x213E,
+ },
+ [0x213F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A0 },
+ unicodeslot=0x213F,
+ },
+ [0x2140]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "font", 0x2211 },
+ unicodeslot=0x2140,
+ },
+ [0x2141]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2141,
+ },
+ [0x2142]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2142,
+ },
+ [0x2143]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2143,
+ },
+ [0x2144]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2144,
+ },
+ [0x2145]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x2145,
+ },
+ [0x2146]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x2146,
+ },
+ [0x2147]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x2147,
+ },
+ [0x2148]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x2148,
+ },
+ [0x2149]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x2149,
+ },
+ [0x214A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x214A,
+ },
+ [0x214B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x214B,
+ },
+ [0x214C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x214C,
+ },
+ [0x214D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x214D,
+ },
+ [0x214E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x214E,
+ },
+ [0x214F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x214F,
+ },
+ [0x2150]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x31, 0x2044, 0x37 },
+ unicodeslot=0x2150,
+ },
+ [0x2151]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x31, 0x2044, 0x39 },
+ unicodeslot=0x2151,
+ },
+ [0x2152]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x31, 0x2044, 0x31, 0x30 },
+ unicodeslot=0x2152,
+ },
+ [0x2153]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x31, 0x2044, 0x33 },
+ unicodeslot=0x2153,
+ },
+ [0x2154]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x32, 0x2044, 0x33 },
+ unicodeslot=0x2154,
+ },
+ [0x2155]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x31, 0x2044, 0x35 },
+ unicodeslot=0x2155,
+ },
+ [0x2156]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x32, 0x2044, 0x35 },
+ unicodeslot=0x2156,
+ },
+ [0x2157]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x33, 0x2044, 0x35 },
+ unicodeslot=0x2157,
+ },
+ [0x2158]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x34, 0x2044, 0x35 },
+ unicodeslot=0x2158,
+ },
+ [0x2159]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x31, 0x2044, 0x36 },
+ unicodeslot=0x2159,
+ },
+ [0x215A]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x35, 0x2044, 0x36 },
+ unicodeslot=0x215A,
+ },
+ [0x215B]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x31, 0x2044, 0x38 },
+ unicodeslot=0x215B,
+ },
+ [0x215C]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x33, 0x2044, 0x38 },
+ unicodeslot=0x215C,
+ },
+ [0x215D]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x35, 0x2044, 0x38 },
+ unicodeslot=0x215D,
+ },
+ [0x215E]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x37, 0x2044, 0x38 },
+ unicodeslot=0x215E,
+ },
+ [0x215F]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ specials={ "fraction", 0x31, 0x2044 },
+ unicodeslot=0x215F,
+ },
+ [0x2160]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x49 },
+ unicodeslot=0x2160,
+ },
+ [0x2161]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x49, 0x49 },
+ unicodeslot=0x2161,
+ },
+ [0x2162]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x49, 0x49, 0x49 },
+ unicodeslot=0x2162,
+ },
+ [0x2163]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x49, 0x56 },
+ unicodeslot=0x2163,
+ },
+ [0x2164]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x56 },
+ unicodeslot=0x2164,
+ },
+ [0x2165]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x56, 0x49 },
+ unicodeslot=0x2165,
+ },
+ [0x2166]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x56, 0x49, 0x49 },
+ unicodeslot=0x2166,
+ },
+ [0x2167]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x56, 0x49, 0x49, 0x49 },
+ unicodeslot=0x2167,
+ },
+ [0x2168]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x49, 0x58 },
+ unicodeslot=0x2168,
+ },
+ [0x2169]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x58 },
+ unicodeslot=0x2169,
+ },
+ [0x216A]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x58, 0x49 },
+ unicodeslot=0x216A,
+ },
+ [0x216B]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x58, 0x49, 0x49 },
+ unicodeslot=0x216B,
+ },
+ [0x216C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4C },
+ unicodeslot=0x216C,
+ },
+ [0x216D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x43 },
+ unicodeslot=0x216D,
+ },
+ [0x216E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x44 },
+ unicodeslot=0x216E,
+ },
+ [0x216F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x4D },
+ unicodeslot=0x216F,
+ },
+ [0x2170]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x69 },
+ unicodeslot=0x2170,
+ },
+ [0x2171]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x69, 0x69 },
+ unicodeslot=0x2171,
+ },
+ [0x2172]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x69, 0x69, 0x69 },
+ unicodeslot=0x2172,
+ },
+ [0x2173]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x69, 0x76 },
+ unicodeslot=0x2173,
+ },
+ [0x2174]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x76 },
+ unicodeslot=0x2174,
+ },
+ [0x2175]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x76, 0x69 },
+ unicodeslot=0x2175,
+ },
+ [0x2176]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x76, 0x69, 0x69 },
+ unicodeslot=0x2176,
+ },
+ [0x2177]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x76, 0x69, 0x69, 0x69 },
+ unicodeslot=0x2177,
+ },
+ [0x2178]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x69, 0x78 },
+ unicodeslot=0x2178,
+ },
+ [0x2179]={
+ category="nl",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x78 },
+ unicodeslot=0x2179,
+ },
+ [0x217A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x78, 0x69 },
+ unicodeslot=0x217A,
+ },
+ [0x217B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x78, 0x69, 0x69 },
+ unicodeslot=0x217B,
+ },
+ [0x217C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x6C },
+ unicodeslot=0x217C,
+ },
+ [0x217D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x63 },
+ unicodeslot=0x217D,
+ },
+ [0x217E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x64 },
+ unicodeslot=0x217E,
+ },
+ [0x217F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x6D },
+ unicodeslot=0x217F,
+ },
+ [0x2180]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2180,
+ },
+ [0x2181]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2181,
+ },
+ [0x2182]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2182,
+ },
+ [0x2183]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2183,
+ },
+ [0x2184]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2184,
+ },
+ [0x2185]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2185,
+ },
+ [0x2186]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2186,
+ },
+ [0x2187]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2187,
+ },
+ [0x2188]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2188,
+ },
+ [0x2189]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "fraction", 0x30, 0x2044, 0x33 },
+ unicodeslot=0x2189,
+ },
+ [0x218A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x218A,
+ },
+ [0x218B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x218B,
+ },
+ [0x2190]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2190,
+ },
+ [0x2191]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2191,
+ },
+ [0x2192]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2192,
+ },
+ [0x2193]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2193,
+ },
+ [0x2194]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2194,
+ },
+ [0x2195]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2195,
+ },
+ [0x2196]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2196,
+ },
+ [0x2197]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2197,
+ },
+ [0x2198]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2198,
+ },
+ [0x2199]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2199,
+ },
+ [0x219A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2190, 0x338 },
+ unicodeslot=0x219A,
+ },
+ [0x219B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2192, 0x338 },
+ unicodeslot=0x219B,
+ },
+ [0x219C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x219C,
+ },
+ [0x219D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x219D,
+ },
+ [0x219E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x219E,
+ },
+ [0x219F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x219F,
+ },
+ [0x21A0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A0,
+ },
+ [0x21A1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A1,
+ },
+ [0x21A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A2,
+ },
+ [0x21A3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A3,
+ },
+ [0x21A4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A4,
+ },
+ [0x21A5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A5,
+ },
+ [0x21A6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A6,
+ },
+ [0x21A7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A7,
+ },
+ [0x21A8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A8,
+ },
+ [0x21A9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21A9,
+ },
+ [0x21AA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21AA,
+ },
+ [0x21AB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21AB,
+ },
+ [0x21AC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21AC,
+ },
+ [0x21AD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21AD,
+ },
+ [0x21AE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2194, 0x338 },
+ unicodeslot=0x21AE,
+ },
+ [0x21AF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21AF,
+ },
+ [0x21B0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B0,
+ },
+ [0x21B1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B1,
+ },
+ [0x21B2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B2,
+ },
+ [0x21B3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B3,
+ },
+ [0x21B4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B4,
+ },
+ [0x21B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B5,
+ },
+ [0x21B6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B6,
+ },
+ [0x21B7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B7,
+ },
+ [0x21B8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B8,
+ },
+ [0x21B9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21B9,
+ },
+ [0x21BA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21BA,
+ },
+ [0x21BB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21BB,
+ },
+ [0x21BC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21BC,
+ },
+ [0x21BD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21BD,
+ },
+ [0x21BE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21BE,
+ },
+ [0x21BF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21BF,
+ },
+ [0x21C0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C0,
+ },
+ [0x21C1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C1,
+ },
+ [0x21C2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C2,
+ },
+ [0x21C3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C3,
+ },
+ [0x21C4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C4,
+ },
+ [0x21C5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C5,
+ },
+ [0x21C6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C6,
+ },
+ [0x21C7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C7,
+ },
+ [0x21C8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C8,
+ },
+ [0x21C9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21C9,
+ },
+ [0x21CA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21CA,
+ },
+ [0x21CB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21CB,
+ },
+ [0x21CC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21CC,
+ },
+ [0x21CD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x21D0, 0x338 },
+ unicodeslot=0x21CD,
+ },
+ [0x21CE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x21D4, 0x338 },
+ unicodeslot=0x21CE,
+ },
+ [0x21CF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x21D2, 0x338 },
+ unicodeslot=0x21CF,
+ },
+ [0x21D0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D0,
+ },
+ [0x21D1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D1,
+ },
+ [0x21D2]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x21D2,
+ },
+ [0x21D3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D3,
+ },
+ [0x21D4]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x21D4,
+ },
+ [0x21D5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D5,
+ },
+ [0x21D6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D6,
+ },
+ [0x21D7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D7,
+ },
+ [0x21D8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D8,
+ },
+ [0x21D9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21D9,
+ },
+ [0x21DA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21DA,
+ },
+ [0x21DB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21DB,
+ },
+ [0x21DC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21DC,
+ },
+ [0x21DD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21DD,
+ },
+ [0x21DE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21DE,
+ },
+ [0x21DF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21DF,
+ },
+ [0x21E0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E0,
+ },
+ [0x21E1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E1,
+ },
+ [0x21E2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E2,
+ },
+ [0x21E3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E3,
+ },
+ [0x21E4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E4,
+ },
+ [0x21E5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E5,
+ },
+ [0x21E6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E6,
+ },
+ [0x21E7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E7,
+ },
+ [0x21E8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E8,
+ },
+ [0x21E9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21E9,
+ },
+ [0x21EA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21EA,
+ },
+ [0x21EB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21EB,
+ },
+ [0x21EC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21EC,
+ },
+ [0x21ED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21ED,
+ },
+ [0x21EE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21EE,
+ },
+ [0x21EF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21EF,
+ },
+ [0x21F0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F0,
+ },
+ [0x21F1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F1,
+ },
+ [0x21F2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F2,
+ },
+ [0x21F3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F3,
+ },
+ [0x21F4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F4,
+ },
+ [0x21F5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F5,
+ },
+ [0x21F6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F6,
+ },
+ [0x21F7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F7,
+ },
+ [0x21F8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F8,
+ },
+ [0x21F9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21F9,
+ },
+ [0x21FA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21FA,
+ },
+ [0x21FB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21FB,
+ },
+ [0x21FC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21FC,
+ },
+ [0x21FD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21FD,
+ },
+ [0x21FE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21FE,
+ },
+ [0x21FF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x21FF,
+ },
+ [0x2200]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2200,
+ },
+ [0x2201]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2201,
+ },
+ [0x2202]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2202,
+ },
+ [0x2203]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2203,
+ },
+ [0x2204]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2203, 0x338 },
+ unicodeslot=0x2204,
+ },
+ [0x2205]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2205,
+ },
+ [0x2206]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2206,
+ },
+ [0x2207]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2207,
+ },
+ [0x2208]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x220B,
+ unicodeslot=0x2208,
+ },
+ [0x2209]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x220C,
+ specials={ "char", 0x2208, 0x338 },
+ unicodeslot=0x2209,
+ },
+ [0x220A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x220D,
+ unicodeslot=0x220A,
+ },
+ [0x220B]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2208,
+ unicodeslot=0x220B,
+ },
+ [0x220C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2209,
+ specials={ "char", 0x220B, 0x338 },
+ unicodeslot=0x220C,
+ },
+ [0x220D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x220A,
+ unicodeslot=0x220D,
+ },
+ [0x220E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x220E,
+ },
+ [0x220F]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x220F,
+ },
+ [0x2210]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2210,
+ },
+ [0x2211]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2211,
+ },
+ [0x2212]={
+ category="sm",
+ direction="es",
+ linebreak="pr",
+ unicodeslot=0x2212,
+ },
+ [0x2213]={
+ category="sm",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x2213,
+ },
+ [0x2214]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2214,
+ },
+ [0x2215]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x29F5,
+ unicodeslot=0x2215,
+ },
+ [0x2216]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2216,
+ },
+ [0x2217]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2217,
+ },
+ [0x2218]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2218,
+ },
+ [0x2219]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2219,
+ },
+ [0x221A]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x221A,
+ },
+ [0x221B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x221B,
+ },
+ [0x221C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x221C,
+ },
+ [0x221D]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x221D,
+ },
+ [0x221E]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x221E,
+ },
+ [0x221F]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2BFE,
+ unicodeslot=0x221F,
+ },
+ [0x2220]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x29A3,
+ unicodeslot=0x2220,
+ },
+ [0x2221]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x299B,
+ unicodeslot=0x2221,
+ },
+ [0x2222]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29A0,
+ unicodeslot=0x2222,
+ },
+ [0x2223]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2223,
+ },
+ [0x2224]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AEE,
+ specials={ "char", 0x2223, 0x338 },
+ unicodeslot=0x2224,
+ },
+ [0x2225]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2225,
+ },
+ [0x2226]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2225, 0x338 },
+ unicodeslot=0x2226,
+ },
+ [0x2227]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2227,
+ },
+ [0x2228]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2228,
+ },
+ [0x2229]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2229,
+ },
+ [0x222A]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x222A,
+ },
+ [0x222B]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x222B,
+ },
+ [0x222C]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x222B, 0x222B },
+ unicodeslot=0x222C,
+ },
+ [0x222D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x222B, 0x222B, 0x222B },
+ unicodeslot=0x222D,
+ },
+ [0x222E]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x222E,
+ },
+ [0x222F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x222E, 0x222E },
+ unicodeslot=0x222F,
+ },
+ [0x2230]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x222E, 0x222E, 0x222E },
+ unicodeslot=0x2230,
+ },
+ [0x2231]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2231,
+ },
+ [0x2232]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2232,
+ },
+ [0x2233]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2233,
+ },
+ [0x2234]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2234,
+ },
+ [0x2235]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2235,
+ },
+ [0x2236]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2236,
+ },
+ [0x2237]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2237,
+ },
+ [0x2238]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2238,
+ },
+ [0x2239]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2239,
+ },
+ [0x223A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x223A,
+ },
+ [0x223B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x223B,
+ },
+ [0x223C]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x223D,
+ unicodeslot=0x223C,
+ },
+ [0x223D]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x223C,
+ unicodeslot=0x223D,
+ },
+ [0x223E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x223E,
+ },
+ [0x223F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x223F,
+ },
+ [0x2240]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2240,
+ },
+ [0x2241]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x223C, 0x338 },
+ unicodeslot=0x2241,
+ },
+ [0x2242]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2242,
+ },
+ [0x2243]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22CD,
+ unicodeslot=0x2243,
+ },
+ [0x2244]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2243, 0x338 },
+ unicodeslot=0x2244,
+ },
+ [0x2245]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x224C,
+ unicodeslot=0x2245,
+ },
+ [0x2246]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2246,
+ },
+ [0x2247]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2245, 0x338 },
+ unicodeslot=0x2247,
+ },
+ [0x2248]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2248,
+ },
+ [0x2249]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2248, 0x338 },
+ unicodeslot=0x2249,
+ },
+ [0x224A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x224A,
+ },
+ [0x224B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x224B,
+ },
+ [0x224C]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2245,
+ unicodeslot=0x224C,
+ },
+ [0x224D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x224D,
+ },
+ [0x224E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x224E,
+ },
+ [0x224F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x224F,
+ },
+ [0x2250]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2250,
+ },
+ [0x2251]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2251,
+ },
+ [0x2252]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2253,
+ unicodeslot=0x2252,
+ },
+ [0x2253]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2252,
+ unicodeslot=0x2253,
+ },
+ [0x2254]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2255,
+ unicodeslot=0x2254,
+ },
+ [0x2255]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2254,
+ unicodeslot=0x2255,
+ },
+ [0x2256]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2256,
+ },
+ [0x2257]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2257,
+ },
+ [0x2258]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2258,
+ },
+ [0x2259]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2259,
+ },
+ [0x225A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x225A,
+ },
+ [0x225B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x225B,
+ },
+ [0x225C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x225C,
+ },
+ [0x225D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x225D,
+ },
+ [0x225E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x225E,
+ },
+ [0x225F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x225F,
+ },
+ [0x2260]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ specials={ "char", 0x3D, 0x338 },
+ unicodeslot=0x2260,
+ },
+ [0x2261]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2261,
+ },
+ [0x2262]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2261, 0x338 },
+ unicodeslot=0x2262,
+ },
+ [0x2263]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2263,
+ },
+ [0x2264]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2265,
+ unicodeslot=0x2264,
+ },
+ [0x2265]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2264,
+ unicodeslot=0x2265,
+ },
+ [0x2266]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2267,
+ unicodeslot=0x2266,
+ },
+ [0x2267]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2266,
+ unicodeslot=0x2267,
+ },
+ [0x2268]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2269,
+ unicodeslot=0x2268,
+ },
+ [0x2269]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2268,
+ unicodeslot=0x2269,
+ },
+ [0x226A]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x226B,
+ unicodeslot=0x226A,
+ },
+ [0x226B]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x226A,
+ unicodeslot=0x226B,
+ },
+ [0x226C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x226C,
+ },
+ [0x226D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x224D, 0x338 },
+ unicodeslot=0x226D,
+ },
+ [0x226E]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x226F,
+ specials={ "char", 0x3C, 0x338 },
+ unicodeslot=0x226E,
+ },
+ [0x226F]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x226E,
+ specials={ "char", 0x3E, 0x338 },
+ unicodeslot=0x226F,
+ },
+ [0x2270]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2271,
+ specials={ "char", 0x2264, 0x338 },
+ unicodeslot=0x2270,
+ },
+ [0x2271]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2270,
+ specials={ "char", 0x2265, 0x338 },
+ unicodeslot=0x2271,
+ },
+ [0x2272]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2273,
+ unicodeslot=0x2272,
+ },
+ [0x2273]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2272,
+ unicodeslot=0x2273,
+ },
+ [0x2274]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2275,
+ specials={ "char", 0x2272, 0x338 },
+ unicodeslot=0x2274,
+ },
+ [0x2275]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2274,
+ specials={ "char", 0x2273, 0x338 },
+ unicodeslot=0x2275,
+ },
+ [0x2276]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2277,
+ unicodeslot=0x2276,
+ },
+ [0x2277]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2276,
+ unicodeslot=0x2277,
+ },
+ [0x2278]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2279,
+ specials={ "char", 0x2276, 0x338 },
+ unicodeslot=0x2278,
+ },
+ [0x2279]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2278,
+ specials={ "char", 0x2277, 0x338 },
+ unicodeslot=0x2279,
+ },
+ [0x227A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x227B,
+ unicodeslot=0x227A,
+ },
+ [0x227B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x227A,
+ unicodeslot=0x227B,
+ },
+ [0x227C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x227D,
+ unicodeslot=0x227C,
+ },
+ [0x227D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x227C,
+ unicodeslot=0x227D,
+ },
+ [0x227E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x227F,
+ unicodeslot=0x227E,
+ },
+ [0x227F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x227E,
+ unicodeslot=0x227F,
+ },
+ [0x2280]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2281,
+ specials={ "char", 0x227A, 0x338 },
+ unicodeslot=0x2280,
+ },
+ [0x2281]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2280,
+ specials={ "char", 0x227B, 0x338 },
+ unicodeslot=0x2281,
+ },
+ [0x2282]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2283,
+ unicodeslot=0x2282,
+ },
+ [0x2283]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2282,
+ unicodeslot=0x2283,
+ },
+ [0x2284]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2285,
+ specials={ "char", 0x2282, 0x338 },
+ unicodeslot=0x2284,
+ },
+ [0x2285]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2284,
+ specials={ "char", 0x2283, 0x338 },
+ unicodeslot=0x2285,
+ },
+ [0x2286]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2287,
+ unicodeslot=0x2286,
+ },
+ [0x2287]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ mirror=0x2286,
+ unicodeslot=0x2287,
+ },
+ [0x2288]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2289,
+ specials={ "char", 0x2286, 0x338 },
+ unicodeslot=0x2288,
+ },
+ [0x2289]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2288,
+ specials={ "char", 0x2287, 0x338 },
+ unicodeslot=0x2289,
+ },
+ [0x228A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x228B,
+ unicodeslot=0x228A,
+ },
+ [0x228B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x228A,
+ unicodeslot=0x228B,
+ },
+ [0x228C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x228C,
+ },
+ [0x228D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x228D,
+ },
+ [0x228E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x228E,
+ },
+ [0x228F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2290,
+ unicodeslot=0x228F,
+ },
+ [0x2290]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x228F,
+ unicodeslot=0x2290,
+ },
+ [0x2291]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2292,
+ unicodeslot=0x2291,
+ },
+ [0x2292]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2291,
+ unicodeslot=0x2292,
+ },
+ [0x2293]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2293,
+ },
+ [0x2294]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2294,
+ },
+ [0x2295]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2295,
+ },
+ [0x2296]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2296,
+ },
+ [0x2297]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2297,
+ },
+ [0x2298]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29B8,
+ unicodeslot=0x2298,
+ },
+ [0x2299]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2299,
+ },
+ [0x229A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x229A,
+ },
+ [0x229B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x229B,
+ },
+ [0x229C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x229C,
+ },
+ [0x229D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x229D,
+ },
+ [0x229E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x229E,
+ },
+ [0x229F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x229F,
+ },
+ [0x22A0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22A0,
+ },
+ [0x22A1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22A1,
+ },
+ [0x22A2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22A3,
+ unicodeslot=0x22A2,
+ },
+ [0x22A3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22A2,
+ unicodeslot=0x22A3,
+ },
+ [0x22A4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22A4,
+ },
+ [0x22A5]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x22A5,
+ },
+ [0x22A6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ADE,
+ unicodeslot=0x22A6,
+ },
+ [0x22A7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22A7,
+ },
+ [0x22A8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AE4,
+ unicodeslot=0x22A8,
+ },
+ [0x22A9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AE3,
+ unicodeslot=0x22A9,
+ },
+ [0x22AA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22AA,
+ },
+ [0x22AB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AE5,
+ unicodeslot=0x22AB,
+ },
+ [0x22AC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x22A2, 0x338 },
+ unicodeslot=0x22AC,
+ },
+ [0x22AD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x22A8, 0x338 },
+ unicodeslot=0x22AD,
+ },
+ [0x22AE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x22A9, 0x338 },
+ unicodeslot=0x22AE,
+ },
+ [0x22AF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x22AB, 0x338 },
+ unicodeslot=0x22AF,
+ },
+ [0x22B0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B1,
+ unicodeslot=0x22B0,
+ },
+ [0x22B1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B0,
+ unicodeslot=0x22B1,
+ },
+ [0x22B2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B3,
+ unicodeslot=0x22B2,
+ },
+ [0x22B3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B2,
+ unicodeslot=0x22B3,
+ },
+ [0x22B4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B5,
+ unicodeslot=0x22B4,
+ },
+ [0x22B5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B4,
+ unicodeslot=0x22B5,
+ },
+ [0x22B6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B7,
+ unicodeslot=0x22B6,
+ },
+ [0x22B7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B6,
+ unicodeslot=0x22B7,
+ },
+ [0x22B8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27DC,
+ unicodeslot=0x22B8,
+ },
+ [0x22B9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22B9,
+ },
+ [0x22BA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22BA,
+ },
+ [0x22BB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22BB,
+ },
+ [0x22BC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22BC,
+ },
+ [0x22BD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22BD,
+ },
+ [0x22BE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22BE,
+ },
+ [0x22BF]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x22BF,
+ },
+ [0x22C0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C0,
+ },
+ [0x22C1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C1,
+ },
+ [0x22C2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C2,
+ },
+ [0x22C3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C3,
+ },
+ [0x22C4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C4,
+ },
+ [0x22C5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C5,
+ },
+ [0x22C6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C6,
+ },
+ [0x22C7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C7,
+ },
+ [0x22C8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22C8,
+ },
+ [0x22C9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22CA,
+ unicodeslot=0x22C9,
+ },
+ [0x22CA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22C9,
+ unicodeslot=0x22CA,
+ },
+ [0x22CB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22CC,
+ unicodeslot=0x22CB,
+ },
+ [0x22CC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22CB,
+ unicodeslot=0x22CC,
+ },
+ [0x22CD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2243,
+ unicodeslot=0x22CD,
+ },
+ [0x22CE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22CE,
+ },
+ [0x22CF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22CF,
+ },
+ [0x22D0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22D1,
+ unicodeslot=0x22D0,
+ },
+ [0x22D1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22D0,
+ unicodeslot=0x22D1,
+ },
+ [0x22D2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22D2,
+ },
+ [0x22D3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22D3,
+ },
+ [0x22D4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22D4,
+ },
+ [0x22D5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22D5,
+ },
+ [0x22D6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22D7,
+ unicodeslot=0x22D6,
+ },
+ [0x22D7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22D6,
+ unicodeslot=0x22D7,
+ },
+ [0x22D8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22D9,
+ unicodeslot=0x22D8,
+ },
+ [0x22D9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22D8,
+ unicodeslot=0x22D9,
+ },
+ [0x22DA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22DB,
+ unicodeslot=0x22DA,
+ },
+ [0x22DB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22DA,
+ unicodeslot=0x22DB,
+ },
+ [0x22DC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22DD,
+ unicodeslot=0x22DC,
+ },
+ [0x22DD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22DC,
+ unicodeslot=0x22DD,
+ },
+ [0x22DE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22DF,
+ unicodeslot=0x22DE,
+ },
+ [0x22DF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22DE,
+ unicodeslot=0x22DF,
+ },
+ [0x22E0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E1,
+ specials={ "char", 0x227C, 0x338 },
+ unicodeslot=0x22E0,
+ },
+ [0x22E1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E0,
+ specials={ "char", 0x227D, 0x338 },
+ unicodeslot=0x22E1,
+ },
+ [0x22E2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E3,
+ specials={ "char", 0x2291, 0x338 },
+ unicodeslot=0x22E2,
+ },
+ [0x22E3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E2,
+ specials={ "char", 0x2292, 0x338 },
+ unicodeslot=0x22E3,
+ },
+ [0x22E4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E5,
+ unicodeslot=0x22E4,
+ },
+ [0x22E5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E4,
+ unicodeslot=0x22E5,
+ },
+ [0x22E6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E7,
+ unicodeslot=0x22E6,
+ },
+ [0x22E7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E6,
+ unicodeslot=0x22E7,
+ },
+ [0x22E8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E9,
+ unicodeslot=0x22E8,
+ },
+ [0x22E9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22E8,
+ unicodeslot=0x22E9,
+ },
+ [0x22EA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22EB,
+ specials={ "char", 0x22B2, 0x338 },
+ unicodeslot=0x22EA,
+ },
+ [0x22EB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22EA,
+ specials={ "char", 0x22B3, 0x338 },
+ unicodeslot=0x22EB,
+ },
+ [0x22EC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22ED,
+ specials={ "char", 0x22B4, 0x338 },
+ unicodeslot=0x22EC,
+ },
+ [0x22ED]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22EC,
+ specials={ "char", 0x22B5, 0x338 },
+ unicodeslot=0x22ED,
+ },
+ [0x22EE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22EE,
+ },
+ [0x22EF]={
+ category="sm",
+ direction="on",
+ linebreak="in",
+ unicodeslot=0x22EF,
+ },
+ [0x22F0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F1,
+ unicodeslot=0x22F0,
+ },
+ [0x22F1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F0,
+ unicodeslot=0x22F1,
+ },
+ [0x22F2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22FA,
+ unicodeslot=0x22F2,
+ },
+ [0x22F3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22FB,
+ unicodeslot=0x22F3,
+ },
+ [0x22F4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22FC,
+ unicodeslot=0x22F4,
+ },
+ [0x22F5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22F5,
+ },
+ [0x22F6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22FD,
+ unicodeslot=0x22F6,
+ },
+ [0x22F7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22FE,
+ unicodeslot=0x22F7,
+ },
+ [0x22F8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22F8,
+ },
+ [0x22F9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22F9,
+ },
+ [0x22FA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F2,
+ unicodeslot=0x22FA,
+ },
+ [0x22FB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F3,
+ unicodeslot=0x22FB,
+ },
+ [0x22FC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F4,
+ unicodeslot=0x22FC,
+ },
+ [0x22FD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F6,
+ unicodeslot=0x22FD,
+ },
+ [0x22FE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22F7,
+ unicodeslot=0x22FE,
+ },
+ [0x22FF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x22FF,
+ },
+ [0x2300]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2300,
+ },
+ [0x2301]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2301,
+ },
+ [0x2302]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2302,
+ },
+ [0x2303]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2303,
+ },
+ [0x2304]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2304,
+ },
+ [0x2305]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2305,
+ },
+ [0x2306]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2306,
+ },
+ [0x2307]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2307,
+ },
+ [0x2308]={
+ category="sm",
+ direction="on",
+ linebreak="op",
+ mirror=0x2309,
+ unicodeslot=0x2308,
+ },
+ [0x2309]={
+ category="sm",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2308,
+ unicodeslot=0x2309,
+ },
+ [0x230A]={
+ category="sm",
+ direction="on",
+ linebreak="op",
+ mirror=0x230B,
+ unicodeslot=0x230A,
+ },
+ [0x230B]={
+ category="sm",
+ direction="on",
+ linebreak="cl",
+ mirror=0x230A,
+ unicodeslot=0x230B,
+ },
+ [0x230C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x230C,
+ },
+ [0x230D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x230D,
+ },
+ [0x230E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x230E,
+ },
+ [0x230F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x230F,
+ },
+ [0x2310]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2310,
+ },
+ [0x2311]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2311,
+ },
+ [0x2312]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2312,
+ },
+ [0x2313]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2313,
+ },
+ [0x2314]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2314,
+ },
+ [0x2315]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2315,
+ },
+ [0x2316]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2316,
+ },
+ [0x2317]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2317,
+ },
+ [0x2318]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2318,
+ },
+ [0x2319]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2319,
+ },
+ [0x231A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x231A,
+ },
+ [0x231B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x231B,
+ },
+ [0x231C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x231C,
+ },
+ [0x231D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x231D,
+ },
+ [0x231E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x231E,
+ },
+ [0x231F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x231F,
+ },
+ [0x2320]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2320,
+ },
+ [0x2321]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2321,
+ },
+ [0x2322]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2322,
+ },
+ [0x2323]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2323,
+ },
+ [0x2324]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2324,
+ },
+ [0x2325]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2325,
+ },
+ [0x2326]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2326,
+ },
+ [0x2327]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2327,
+ },
+ [0x2328]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2328,
+ },
+ [0x2329]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x232A,
+ specials={ "char", 0x3008 },
+ unicodeslot=0x2329,
+ },
+ [0x232A]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2329,
+ specials={ "char", 0x3009 },
+ unicodeslot=0x232A,
+ },
+ [0x232B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x232B,
+ },
+ [0x232C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x232C,
+ },
+ [0x232D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x232D,
+ },
+ [0x232E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x232E,
+ },
+ [0x232F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x232F,
+ },
+ [0x2330]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2330,
+ },
+ [0x2331]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2331,
+ },
+ [0x2332]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2332,
+ },
+ [0x2333]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2333,
+ },
+ [0x2334]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2334,
+ },
+ [0x2335]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2335,
+ },
+ [0x2336]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2336,
+ },
+ [0x2337]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2337,
+ },
+ [0x2338]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2338,
+ },
+ [0x2339]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2339,
+ },
+ [0x233A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x233A,
+ },
+ [0x233B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x233B,
+ },
+ [0x233C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x233C,
+ },
+ [0x233D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x233D,
+ },
+ [0x233E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x233E,
+ },
+ [0x233F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x233F,
+ },
+ [0x2340]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2340,
+ },
+ [0x2341]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2341,
+ },
+ [0x2342]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2342,
+ },
+ [0x2343]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2343,
+ },
+ [0x2344]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2344,
+ },
+ [0x2345]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2345,
+ },
+ [0x2346]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2346,
+ },
+ [0x2347]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2347,
+ },
+ [0x2348]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2348,
+ },
+ [0x2349]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2349,
+ },
+ [0x234A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234A,
+ },
+ [0x234B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234B,
+ },
+ [0x234C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234C,
+ },
+ [0x234D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234D,
+ },
+ [0x234E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234E,
+ },
+ [0x234F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x234F,
+ },
+ [0x2350]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2350,
+ },
+ [0x2351]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2351,
+ },
+ [0x2352]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2352,
+ },
+ [0x2353]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2353,
+ },
+ [0x2354]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2354,
+ },
+ [0x2355]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2355,
+ },
+ [0x2356]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2356,
+ },
+ [0x2357]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2357,
+ },
+ [0x2358]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2358,
+ },
+ [0x2359]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2359,
+ },
+ [0x235A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235A,
+ },
+ [0x235B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235B,
+ },
+ [0x235C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235C,
+ },
+ [0x235D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235D,
+ },
+ [0x235E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235E,
+ },
+ [0x235F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x235F,
+ },
+ [0x2360]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2360,
+ },
+ [0x2361]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2361,
+ },
+ [0x2362]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2362,
+ },
+ [0x2363]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2363,
+ },
+ [0x2364]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2364,
+ },
+ [0x2365]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2365,
+ },
+ [0x2366]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2366,
+ },
+ [0x2367]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2367,
+ },
+ [0x2368]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2368,
+ },
+ [0x2369]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2369,
+ },
+ [0x236A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236A,
+ },
+ [0x236B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236B,
+ },
+ [0x236C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236C,
+ },
+ [0x236D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236D,
+ },
+ [0x236E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236E,
+ },
+ [0x236F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x236F,
+ },
+ [0x2370]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2370,
+ },
+ [0x2371]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2371,
+ },
+ [0x2372]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2372,
+ },
+ [0x2373]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2373,
+ },
+ [0x2374]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2374,
+ },
+ [0x2375]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2375,
+ },
+ [0x2376]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2376,
+ },
+ [0x2377]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2377,
+ },
+ [0x2378]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2378,
+ },
+ [0x2379]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2379,
+ },
+ [0x237A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x237A,
+ },
+ [0x237B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x237B,
+ },
+ [0x237C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x237C,
+ },
+ [0x237D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x237D,
+ },
+ [0x237E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x237E,
+ },
+ [0x237F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x237F,
+ },
+ [0x2380]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2380,
+ },
+ [0x2381]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2381,
+ },
+ [0x2382]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2382,
+ },
+ [0x2383]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2383,
+ },
+ [0x2384]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2384,
+ },
+ [0x2385]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2385,
+ },
+ [0x2386]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2386,
+ },
+ [0x2387]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2387,
+ },
+ [0x2388]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2388,
+ },
+ [0x2389]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2389,
+ },
+ [0x238A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x238A,
+ },
+ [0x238B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x238B,
+ },
+ [0x238C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x238C,
+ },
+ [0x238D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x238D,
+ },
+ [0x238E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x238E,
+ },
+ [0x238F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x238F,
+ },
+ [0x2390]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2390,
+ },
+ [0x2391]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2391,
+ },
+ [0x2392]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2392,
+ },
+ [0x2393]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2393,
+ },
+ [0x2394]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2394,
+ },
+ [0x2395]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2395,
+ },
+ [0x2396]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2396,
+ },
+ [0x2397]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2397,
+ },
+ [0x2398]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2398,
+ },
+ [0x2399]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2399,
+ },
+ [0x239A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x239A,
+ },
+ [0x239B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x239B,
+ },
+ [0x239C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x239C,
+ },
+ [0x239D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x239D,
+ },
+ [0x239E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x239E,
+ },
+ [0x239F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x239F,
+ },
+ [0x23A0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A0,
+ },
+ [0x23A1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A1,
+ },
+ [0x23A2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A2,
+ },
+ [0x23A3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A3,
+ },
+ [0x23A4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A4,
+ },
+ [0x23A5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A5,
+ },
+ [0x23A6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A6,
+ },
+ [0x23A7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A7,
+ },
+ [0x23A8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A8,
+ },
+ [0x23A9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23A9,
+ },
+ [0x23AA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23AA,
+ },
+ [0x23AB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23AB,
+ },
+ [0x23AC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23AC,
+ },
+ [0x23AD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23AD,
+ },
+ [0x23AE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23AE,
+ },
+ [0x23AF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23AF,
+ },
+ [0x23B0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B0,
+ },
+ [0x23B1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B1,
+ },
+ [0x23B2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B2,
+ },
+ [0x23B3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B3,
+ },
+ [0x23B4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B4,
+ },
+ [0x23B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B5,
+ },
+ [0x23B6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B6,
+ },
+ [0x23B7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B7,
+ },
+ [0x23B8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B8,
+ },
+ [0x23B9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23B9,
+ },
+ [0x23BA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23BA,
+ },
+ [0x23BB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23BB,
+ },
+ [0x23BC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23BC,
+ },
+ [0x23BD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23BD,
+ },
+ [0x23BE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23BE,
+ },
+ [0x23BF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23BF,
+ },
+ [0x23C0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C0,
+ },
+ [0x23C1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C1,
+ },
+ [0x23C2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C2,
+ },
+ [0x23C3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C3,
+ },
+ [0x23C4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C4,
+ },
+ [0x23C5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C5,
+ },
+ [0x23C6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C6,
+ },
+ [0x23C7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C7,
+ },
+ [0x23C8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C8,
+ },
+ [0x23C9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23C9,
+ },
+ [0x23CA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23CA,
+ },
+ [0x23CB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23CB,
+ },
+ [0x23CC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23CC,
+ },
+ [0x23CD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23CD,
+ },
+ [0x23CE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23CE,
+ },
+ [0x23CF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23CF,
+ },
+ [0x23D0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D0,
+ },
+ [0x23D1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D1,
+ },
+ [0x23D2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D2,
+ },
+ [0x23D3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D3,
+ },
+ [0x23D4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D4,
+ },
+ [0x23D5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D5,
+ },
+ [0x23D6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D6,
+ },
+ [0x23D7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D7,
+ },
+ [0x23D8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D8,
+ },
+ [0x23D9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23D9,
+ },
+ [0x23DA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23DA,
+ },
+ [0x23DB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23DB,
+ },
+ [0x23DC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23DC,
+ },
+ [0x23DD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23DD,
+ },
+ [0x23DE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23DE,
+ },
+ [0x23DF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23DF,
+ },
+ [0x23E0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E0,
+ },
+ [0x23E1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E1,
+ },
+ [0x23E2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E2,
+ },
+ [0x23E3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E3,
+ },
+ [0x23E4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E4,
+ },
+ [0x23E5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E5,
+ },
+ [0x23E6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E6,
+ },
+ [0x23E7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E7,
+ },
+ [0x23E8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E8,
+ },
+ [0x23E9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23E9,
+ },
+ [0x23EA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23EA,
+ },
+ [0x23EB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23EB,
+ },
+ [0x23EC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23EC,
+ },
+ [0x23ED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23ED,
+ },
+ [0x23EE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23EE,
+ },
+ [0x23EF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23EF,
+ },
+ [0x23F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x23F0,
+ },
+ [0x23F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x23F1,
+ },
+ [0x23F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x23F2,
+ },
+ [0x23F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x23F3,
+ },
+ [0x23F4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23F4,
+ },
+ [0x23F5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23F5,
+ },
+ [0x23F6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23F6,
+ },
+ [0x23F7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23F7,
+ },
+ [0x23F8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23F8,
+ },
+ [0x23F9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23F9,
+ },
+ [0x23FA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23FA,
+ },
+ [0x23FB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23FB,
+ },
+ [0x23FC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23FC,
+ },
+ [0x23FD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23FD,
+ },
+ [0x23FE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23FE,
+ },
+ [0x23FF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x23FF,
+ },
+ [0x2400]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2400,
+ },
+ [0x2401]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2401,
+ },
+ [0x2402]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2402,
+ },
+ [0x2403]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2403,
+ },
+ [0x2404]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2404,
+ },
+ [0x2405]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2405,
+ },
+ [0x2406]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2406,
+ },
+ [0x2407]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2407,
+ },
+ [0x2408]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2408,
+ },
+ [0x2409]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2409,
+ },
+ [0x240A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x240A,
+ },
+ [0x240B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x240B,
+ },
+ [0x240C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x240C,
+ },
+ [0x240D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x240D,
+ },
+ [0x240E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x240E,
+ },
+ [0x240F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x240F,
+ },
+ [0x2410]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2410,
+ },
+ [0x2411]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2411,
+ },
+ [0x2412]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2412,
+ },
+ [0x2413]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2413,
+ },
+ [0x2414]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2414,
+ },
+ [0x2415]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2415,
+ },
+ [0x2416]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2416,
+ },
+ [0x2417]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2417,
+ },
+ [0x2418]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2418,
+ },
+ [0x2419]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2419,
+ },
+ [0x241A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x241A,
+ },
+ [0x241B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x241B,
+ },
+ [0x241C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x241C,
+ },
+ [0x241D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x241D,
+ },
+ [0x241E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x241E,
+ },
+ [0x241F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x241F,
+ },
+ [0x2420]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2420,
+ },
+ [0x2421]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2421,
+ },
+ [0x2422]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2422,
+ },
+ [0x2423]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2423,
+ },
+ [0x2424]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2424,
+ },
+ [0x2425]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2425,
+ },
+ [0x2426]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2426,
+ },
+ [0x2440]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2440,
+ },
+ [0x2441]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2441,
+ },
+ [0x2442]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2442,
+ },
+ [0x2443]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2443,
+ },
+ [0x2444]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2444,
+ },
+ [0x2445]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2445,
+ },
+ [0x2446]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2446,
+ },
+ [0x2447]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2447,
+ },
+ [0x2448]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2448,
+ },
+ [0x2449]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2449,
+ },
+ [0x244A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x244A,
+ },
+ [0x2460]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31 },
+ unicodeslot=0x2460,
+ },
+ [0x2461]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x32 },
+ unicodeslot=0x2461,
+ },
+ [0x2462]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x33 },
+ unicodeslot=0x2462,
+ },
+ [0x2463]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x34 },
+ unicodeslot=0x2463,
+ },
+ [0x2464]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x35 },
+ unicodeslot=0x2464,
+ },
+ [0x2465]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x36 },
+ unicodeslot=0x2465,
+ },
+ [0x2466]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x37 },
+ unicodeslot=0x2466,
+ },
+ [0x2467]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x38 },
+ unicodeslot=0x2467,
+ },
+ [0x2468]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x39 },
+ unicodeslot=0x2468,
+ },
+ [0x2469]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x30 },
+ unicodeslot=0x2469,
+ },
+ [0x246A]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x31 },
+ unicodeslot=0x246A,
+ },
+ [0x246B]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x32 },
+ unicodeslot=0x246B,
+ },
+ [0x246C]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x33 },
+ unicodeslot=0x246C,
+ },
+ [0x246D]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x34 },
+ unicodeslot=0x246D,
+ },
+ [0x246E]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x35 },
+ unicodeslot=0x246E,
+ },
+ [0x246F]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x36 },
+ unicodeslot=0x246F,
+ },
+ [0x2470]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x37 },
+ unicodeslot=0x2470,
+ },
+ [0x2471]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x38 },
+ unicodeslot=0x2471,
+ },
+ [0x2472]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x31, 0x39 },
+ unicodeslot=0x2472,
+ },
+ [0x2473]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x32, 0x30 },
+ unicodeslot=0x2473,
+ },
+ [0x2474]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x29 },
+ unicodeslot=0x2474,
+ },
+ [0x2475]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x32, 0x29 },
+ unicodeslot=0x2475,
+ },
+ [0x2476]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x33, 0x29 },
+ unicodeslot=0x2476,
+ },
+ [0x2477]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x34, 0x29 },
+ unicodeslot=0x2477,
+ },
+ [0x2478]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x35, 0x29 },
+ unicodeslot=0x2478,
+ },
+ [0x2479]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x36, 0x29 },
+ unicodeslot=0x2479,
+ },
+ [0x247A]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x37, 0x29 },
+ unicodeslot=0x247A,
+ },
+ [0x247B]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x38, 0x29 },
+ unicodeslot=0x247B,
+ },
+ [0x247C]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x39, 0x29 },
+ unicodeslot=0x247C,
+ },
+ [0x247D]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x30, 0x29 },
+ unicodeslot=0x247D,
+ },
+ [0x247E]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x31, 0x29 },
+ unicodeslot=0x247E,
+ },
+ [0x247F]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x32, 0x29 },
+ unicodeslot=0x247F,
+ },
+ [0x2480]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x33, 0x29 },
+ unicodeslot=0x2480,
+ },
+ [0x2481]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x34, 0x29 },
+ unicodeslot=0x2481,
+ },
+ [0x2482]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x35, 0x29 },
+ unicodeslot=0x2482,
+ },
+ [0x2483]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x36, 0x29 },
+ unicodeslot=0x2483,
+ },
+ [0x2484]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x37, 0x29 },
+ unicodeslot=0x2484,
+ },
+ [0x2485]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x38, 0x29 },
+ unicodeslot=0x2485,
+ },
+ [0x2486]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x31, 0x39, 0x29 },
+ unicodeslot=0x2486,
+ },
+ [0x2487]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x32, 0x30, 0x29 },
+ unicodeslot=0x2487,
+ },
+ [0x2488]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x2E },
+ unicodeslot=0x2488,
+ },
+ [0x2489]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x32, 0x2E },
+ unicodeslot=0x2489,
+ },
+ [0x248A]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x33, 0x2E },
+ unicodeslot=0x248A,
+ },
+ [0x248B]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x34, 0x2E },
+ unicodeslot=0x248B,
+ },
+ [0x248C]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x35, 0x2E },
+ unicodeslot=0x248C,
+ },
+ [0x248D]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x36, 0x2E },
+ unicodeslot=0x248D,
+ },
+ [0x248E]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x37, 0x2E },
+ unicodeslot=0x248E,
+ },
+ [0x248F]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x38, 0x2E },
+ unicodeslot=0x248F,
+ },
+ [0x2490]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x39, 0x2E },
+ unicodeslot=0x2490,
+ },
+ [0x2491]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x30, 0x2E },
+ unicodeslot=0x2491,
+ },
+ [0x2492]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x31, 0x2E },
+ unicodeslot=0x2492,
+ },
+ [0x2493]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x32, 0x2E },
+ unicodeslot=0x2493,
+ },
+ [0x2494]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x33, 0x2E },
+ unicodeslot=0x2494,
+ },
+ [0x2495]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x34, 0x2E },
+ unicodeslot=0x2495,
+ },
+ [0x2496]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x35, 0x2E },
+ unicodeslot=0x2496,
+ },
+ [0x2497]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x36, 0x2E },
+ unicodeslot=0x2497,
+ },
+ [0x2498]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x37, 0x2E },
+ unicodeslot=0x2498,
+ },
+ [0x2499]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x38, 0x2E },
+ unicodeslot=0x2499,
+ },
+ [0x249A]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x39, 0x2E },
+ unicodeslot=0x249A,
+ },
+ [0x249B]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x32, 0x30, 0x2E },
+ unicodeslot=0x249B,
+ },
+ [0x249C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x61, 0x29 },
+ unicodeslot=0x249C,
+ },
+ [0x249D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x62, 0x29 },
+ unicodeslot=0x249D,
+ },
+ [0x249E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x63, 0x29 },
+ unicodeslot=0x249E,
+ },
+ [0x249F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x64, 0x29 },
+ unicodeslot=0x249F,
+ },
+ [0x24A0]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x65, 0x29 },
+ unicodeslot=0x24A0,
+ },
+ [0x24A1]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x66, 0x29 },
+ unicodeslot=0x24A1,
+ },
+ [0x24A2]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x67, 0x29 },
+ unicodeslot=0x24A2,
+ },
+ [0x24A3]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x68, 0x29 },
+ unicodeslot=0x24A3,
+ },
+ [0x24A4]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x69, 0x29 },
+ unicodeslot=0x24A4,
+ },
+ [0x24A5]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x6A, 0x29 },
+ unicodeslot=0x24A5,
+ },
+ [0x24A6]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x6B, 0x29 },
+ unicodeslot=0x24A6,
+ },
+ [0x24A7]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x6C, 0x29 },
+ unicodeslot=0x24A7,
+ },
+ [0x24A8]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x6D, 0x29 },
+ unicodeslot=0x24A8,
+ },
+ [0x24A9]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x6E, 0x29 },
+ unicodeslot=0x24A9,
+ },
+ [0x24AA]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x6F, 0x29 },
+ unicodeslot=0x24AA,
+ },
+ [0x24AB]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x70, 0x29 },
+ unicodeslot=0x24AB,
+ },
+ [0x24AC]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x71, 0x29 },
+ unicodeslot=0x24AC,
+ },
+ [0x24AD]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x72, 0x29 },
+ unicodeslot=0x24AD,
+ },
+ [0x24AE]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x73, 0x29 },
+ unicodeslot=0x24AE,
+ },
+ [0x24AF]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x74, 0x29 },
+ unicodeslot=0x24AF,
+ },
+ [0x24B0]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x75, 0x29 },
+ unicodeslot=0x24B0,
+ },
+ [0x24B1]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x76, 0x29 },
+ unicodeslot=0x24B1,
+ },
+ [0x24B2]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x77, 0x29 },
+ unicodeslot=0x24B2,
+ },
+ [0x24B3]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x78, 0x29 },
+ unicodeslot=0x24B3,
+ },
+ [0x24B4]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x79, 0x29 },
+ unicodeslot=0x24B4,
+ },
+ [0x24B5]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x7A, 0x29 },
+ unicodeslot=0x24B5,
+ },
+ [0x24B6]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x41 },
+ unicodeslot=0x24B6,
+ },
+ [0x24B7]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x42 },
+ unicodeslot=0x24B7,
+ },
+ [0x24B8]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x43 },
+ unicodeslot=0x24B8,
+ },
+ [0x24B9]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x44 },
+ unicodeslot=0x24B9,
+ },
+ [0x24BA]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x45 },
+ unicodeslot=0x24BA,
+ },
+ [0x24BB]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x46 },
+ unicodeslot=0x24BB,
+ },
+ [0x24BC]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x47 },
+ unicodeslot=0x24BC,
+ },
+ [0x24BD]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x48 },
+ unicodeslot=0x24BD,
+ },
+ [0x24BE]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x49 },
+ unicodeslot=0x24BE,
+ },
+ [0x24BF]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x4A },
+ unicodeslot=0x24BF,
+ },
+ [0x24C0]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x4B },
+ unicodeslot=0x24C0,
+ },
+ [0x24C1]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x4C },
+ unicodeslot=0x24C1,
+ },
+ [0x24C2]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x4D },
+ unicodeslot=0x24C2,
+ },
+ [0x24C3]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x4E },
+ unicodeslot=0x24C3,
+ },
+ [0x24C4]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x4F },
+ unicodeslot=0x24C4,
+ },
+ [0x24C5]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x50 },
+ unicodeslot=0x24C5,
+ },
+ [0x24C6]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x51 },
+ unicodeslot=0x24C6,
+ },
+ [0x24C7]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x52 },
+ unicodeslot=0x24C7,
+ },
+ [0x24C8]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x53 },
+ unicodeslot=0x24C8,
+ },
+ [0x24C9]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x54 },
+ unicodeslot=0x24C9,
+ },
+ [0x24CA]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x55 },
+ unicodeslot=0x24CA,
+ },
+ [0x24CB]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x56 },
+ unicodeslot=0x24CB,
+ },
+ [0x24CC]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x57 },
+ unicodeslot=0x24CC,
+ },
+ [0x24CD]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x58 },
+ unicodeslot=0x24CD,
+ },
+ [0x24CE]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x59 },
+ unicodeslot=0x24CE,
+ },
+ [0x24CF]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x5A },
+ unicodeslot=0x24CF,
+ },
+ [0x24D0]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x61 },
+ unicodeslot=0x24D0,
+ },
+ [0x24D1]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x62 },
+ unicodeslot=0x24D1,
+ },
+ [0x24D2]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x63 },
+ unicodeslot=0x24D2,
+ },
+ [0x24D3]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x64 },
+ unicodeslot=0x24D3,
+ },
+ [0x24D4]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x65 },
+ unicodeslot=0x24D4,
+ },
+ [0x24D5]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x66 },
+ unicodeslot=0x24D5,
+ },
+ [0x24D6]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x67 },
+ unicodeslot=0x24D6,
+ },
+ [0x24D7]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x68 },
+ unicodeslot=0x24D7,
+ },
+ [0x24D8]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x69 },
+ unicodeslot=0x24D8,
+ },
+ [0x24D9]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x6A },
+ unicodeslot=0x24D9,
+ },
+ [0x24DA]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x6B },
+ unicodeslot=0x24DA,
+ },
+ [0x24DB]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x6C },
+ unicodeslot=0x24DB,
+ },
+ [0x24DC]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x6D },
+ unicodeslot=0x24DC,
+ },
+ [0x24DD]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x6E },
+ unicodeslot=0x24DD,
+ },
+ [0x24DE]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x6F },
+ unicodeslot=0x24DE,
+ },
+ [0x24DF]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x70 },
+ unicodeslot=0x24DF,
+ },
+ [0x24E0]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x71 },
+ unicodeslot=0x24E0,
+ },
+ [0x24E1]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x72 },
+ unicodeslot=0x24E1,
+ },
+ [0x24E2]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x73 },
+ unicodeslot=0x24E2,
+ },
+ [0x24E3]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x74 },
+ unicodeslot=0x24E3,
+ },
+ [0x24E4]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x75 },
+ unicodeslot=0x24E4,
+ },
+ [0x24E5]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x76 },
+ unicodeslot=0x24E5,
+ },
+ [0x24E6]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x77 },
+ unicodeslot=0x24E6,
+ },
+ [0x24E7]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x78 },
+ unicodeslot=0x24E7,
+ },
+ [0x24E8]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x79 },
+ unicodeslot=0x24E8,
+ },
+ [0x24E9]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x7A },
+ unicodeslot=0x24E9,
+ },
+ [0x24EA]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ specials={ "circle", 0x30 },
+ unicodeslot=0x24EA,
+ },
+ [0x24EB]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24EB,
+ },
+ [0x24EC]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24EC,
+ },
+ [0x24ED]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24ED,
+ },
+ [0x24EE]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24EE,
+ },
+ [0x24EF]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24EF,
+ },
+ [0x24F0]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F0,
+ },
+ [0x24F1]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F1,
+ },
+ [0x24F2]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F2,
+ },
+ [0x24F3]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F3,
+ },
+ [0x24F4]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F4,
+ },
+ [0x24F5]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F5,
+ },
+ [0x24F6]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F6,
+ },
+ [0x24F7]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F7,
+ },
+ [0x24F8]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F8,
+ },
+ [0x24F9]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24F9,
+ },
+ [0x24FA]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24FA,
+ },
+ [0x24FB]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24FB,
+ },
+ [0x24FC]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24FC,
+ },
+ [0x24FD]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24FD,
+ },
+ [0x24FE]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x24FE,
+ },
+ [0x24FF]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x24FF,
+ },
+ [0x2500]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2500,
+ },
+ [0x2501]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2501,
+ },
+ [0x2502]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2502,
+ },
+ [0x2503]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2503,
+ },
+ [0x2504]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2504,
+ },
+ [0x2505]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2505,
+ },
+ [0x2506]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2506,
+ },
+ [0x2507]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2507,
+ },
+ [0x2508]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2508,
+ },
+ [0x2509]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2509,
+ },
+ [0x250A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x250A,
+ },
+ [0x250B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x250B,
+ },
+ [0x250C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x250C,
+ },
+ [0x250D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x250D,
+ },
+ [0x250E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x250E,
+ },
+ [0x250F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x250F,
+ },
+ [0x2510]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2510,
+ },
+ [0x2511]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2511,
+ },
+ [0x2512]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2512,
+ },
+ [0x2513]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2513,
+ },
+ [0x2514]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2514,
+ },
+ [0x2515]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2515,
+ },
+ [0x2516]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2516,
+ },
+ [0x2517]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2517,
+ },
+ [0x2518]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2518,
+ },
+ [0x2519]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2519,
+ },
+ [0x251A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x251A,
+ },
+ [0x251B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x251B,
+ },
+ [0x251C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x251C,
+ },
+ [0x251D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x251D,
+ },
+ [0x251E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x251E,
+ },
+ [0x251F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x251F,
+ },
+ [0x2520]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2520,
+ },
+ [0x2521]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2521,
+ },
+ [0x2522]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2522,
+ },
+ [0x2523]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2523,
+ },
+ [0x2524]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2524,
+ },
+ [0x2525]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2525,
+ },
+ [0x2526]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2526,
+ },
+ [0x2527]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2527,
+ },
+ [0x2528]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2528,
+ },
+ [0x2529]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2529,
+ },
+ [0x252A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x252A,
+ },
+ [0x252B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x252B,
+ },
+ [0x252C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x252C,
+ },
+ [0x252D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x252D,
+ },
+ [0x252E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x252E,
+ },
+ [0x252F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x252F,
+ },
+ [0x2530]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2530,
+ },
+ [0x2531]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2531,
+ },
+ [0x2532]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2532,
+ },
+ [0x2533]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2533,
+ },
+ [0x2534]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2534,
+ },
+ [0x2535]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2535,
+ },
+ [0x2536]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2536,
+ },
+ [0x2537]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2537,
+ },
+ [0x2538]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2538,
+ },
+ [0x2539]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2539,
+ },
+ [0x253A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x253A,
+ },
+ [0x253B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x253B,
+ },
+ [0x253C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x253C,
+ },
+ [0x253D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x253D,
+ },
+ [0x253E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x253E,
+ },
+ [0x253F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x253F,
+ },
+ [0x2540]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2540,
+ },
+ [0x2541]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2541,
+ },
+ [0x2542]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2542,
+ },
+ [0x2543]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2543,
+ },
+ [0x2544]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2544,
+ },
+ [0x2545]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2545,
+ },
+ [0x2546]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2546,
+ },
+ [0x2547]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2547,
+ },
+ [0x2548]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2548,
+ },
+ [0x2549]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2549,
+ },
+ [0x254A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x254A,
+ },
+ [0x254B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x254B,
+ },
+ [0x254C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x254C,
+ },
+ [0x254D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x254D,
+ },
+ [0x254E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x254E,
+ },
+ [0x254F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x254F,
+ },
+ [0x2550]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2550,
+ },
+ [0x2551]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2551,
+ },
+ [0x2552]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2552,
+ },
+ [0x2553]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2553,
+ },
+ [0x2554]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2554,
+ },
+ [0x2555]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2555,
+ },
+ [0x2556]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2556,
+ },
+ [0x2557]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2557,
+ },
+ [0x2558]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2558,
+ },
+ [0x2559]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2559,
+ },
+ [0x255A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x255A,
+ },
+ [0x255B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x255B,
+ },
+ [0x255C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x255C,
+ },
+ [0x255D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x255D,
+ },
+ [0x255E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x255E,
+ },
+ [0x255F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x255F,
+ },
+ [0x2560]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2560,
+ },
+ [0x2561]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2561,
+ },
+ [0x2562]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2562,
+ },
+ [0x2563]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2563,
+ },
+ [0x2564]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2564,
+ },
+ [0x2565]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2565,
+ },
+ [0x2566]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2566,
+ },
+ [0x2567]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2567,
+ },
+ [0x2568]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2568,
+ },
+ [0x2569]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2569,
+ },
+ [0x256A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x256A,
+ },
+ [0x256B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x256B,
+ },
+ [0x256C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x256C,
+ },
+ [0x256D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x256D,
+ },
+ [0x256E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x256E,
+ },
+ [0x256F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x256F,
+ },
+ [0x2570]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2570,
+ },
+ [0x2571]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2571,
+ },
+ [0x2572]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2572,
+ },
+ [0x2573]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2573,
+ },
+ [0x2574]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2574,
+ },
+ [0x2575]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2575,
+ },
+ [0x2576]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2576,
+ },
+ [0x2577]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2577,
+ },
+ [0x2578]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2578,
+ },
+ [0x2579]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2579,
+ },
+ [0x257A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x257A,
+ },
+ [0x257B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x257B,
+ },
+ [0x257C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x257C,
+ },
+ [0x257D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x257D,
+ },
+ [0x257E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x257E,
+ },
+ [0x257F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x257F,
+ },
+ [0x2580]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2580,
+ },
+ [0x2581]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2581,
+ },
+ [0x2582]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2582,
+ },
+ [0x2583]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2583,
+ },
+ [0x2584]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2584,
+ },
+ [0x2585]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2585,
+ },
+ [0x2586]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2586,
+ },
+ [0x2587]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2587,
+ },
+ [0x2588]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2588,
+ },
+ [0x2589]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2589,
+ },
+ [0x258A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x258A,
+ },
+ [0x258B]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x258B,
+ },
+ [0x258C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x258C,
+ },
+ [0x258D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x258D,
+ },
+ [0x258E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x258E,
+ },
+ [0x258F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x258F,
+ },
+ [0x2590]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2590,
+ },
+ [0x2591]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2591,
+ },
+ [0x2592]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2592,
+ },
+ [0x2593]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2593,
+ },
+ [0x2594]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2594,
+ },
+ [0x2595]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2595,
+ },
+ [0x2596]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2596,
+ },
+ [0x2597]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2597,
+ },
+ [0x2598]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2598,
+ },
+ [0x2599]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2599,
+ },
+ [0x259A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x259A,
+ },
+ [0x259B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x259B,
+ },
+ [0x259C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x259C,
+ },
+ [0x259D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x259D,
+ },
+ [0x259E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x259E,
+ },
+ [0x259F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x259F,
+ },
+ [0x25A0]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A0,
+ },
+ [0x25A1]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A1,
+ },
+ [0x25A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25A2,
+ },
+ [0x25A3]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A3,
+ },
+ [0x25A4]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A4,
+ },
+ [0x25A5]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A5,
+ },
+ [0x25A6]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A6,
+ },
+ [0x25A7]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A7,
+ },
+ [0x25A8]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A8,
+ },
+ [0x25A9]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25A9,
+ },
+ [0x25AA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25AA,
+ },
+ [0x25AB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25AB,
+ },
+ [0x25AC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25AC,
+ },
+ [0x25AD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25AD,
+ },
+ [0x25AE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25AE,
+ },
+ [0x25AF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25AF,
+ },
+ [0x25B0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25B0,
+ },
+ [0x25B1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25B1,
+ },
+ [0x25B2]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25B2,
+ },
+ [0x25B3]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25B3,
+ },
+ [0x25B4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25B4,
+ },
+ [0x25B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25B5,
+ },
+ [0x25B6]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25B6,
+ },
+ [0x25B7]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25B7,
+ },
+ [0x25B8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25B8,
+ },
+ [0x25B9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25B9,
+ },
+ [0x25BA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25BA,
+ },
+ [0x25BB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25BB,
+ },
+ [0x25BC]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25BC,
+ },
+ [0x25BD]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25BD,
+ },
+ [0x25BE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25BE,
+ },
+ [0x25BF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25BF,
+ },
+ [0x25C0]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25C0,
+ },
+ [0x25C1]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25C1,
+ },
+ [0x25C2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25C2,
+ },
+ [0x25C3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25C3,
+ },
+ [0x25C4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25C4,
+ },
+ [0x25C5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25C5,
+ },
+ [0x25C6]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25C6,
+ },
+ [0x25C7]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25C7,
+ },
+ [0x25C8]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25C8,
+ },
+ [0x25C9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25C9,
+ },
+ [0x25CA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25CA,
+ },
+ [0x25CB]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25CB,
+ },
+ [0x25CC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25CC,
+ },
+ [0x25CD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25CD,
+ },
+ [0x25CE]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25CE,
+ },
+ [0x25CF]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25CF,
+ },
+ [0x25D0]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25D0,
+ },
+ [0x25D1]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25D1,
+ },
+ [0x25D2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D2,
+ },
+ [0x25D3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D3,
+ },
+ [0x25D4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D4,
+ },
+ [0x25D5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D5,
+ },
+ [0x25D6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D6,
+ },
+ [0x25D7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D7,
+ },
+ [0x25D8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D8,
+ },
+ [0x25D9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25D9,
+ },
+ [0x25DA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25DA,
+ },
+ [0x25DB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25DB,
+ },
+ [0x25DC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25DC,
+ },
+ [0x25DD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25DD,
+ },
+ [0x25DE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25DE,
+ },
+ [0x25DF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25DF,
+ },
+ [0x25E0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25E0,
+ },
+ [0x25E1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25E1,
+ },
+ [0x25E2]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25E2,
+ },
+ [0x25E3]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25E3,
+ },
+ [0x25E4]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25E4,
+ },
+ [0x25E5]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25E5,
+ },
+ [0x25E6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25E6,
+ },
+ [0x25E7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25E7,
+ },
+ [0x25E8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25E8,
+ },
+ [0x25E9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25E9,
+ },
+ [0x25EA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25EA,
+ },
+ [0x25EB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25EB,
+ },
+ [0x25EC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25EC,
+ },
+ [0x25ED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25ED,
+ },
+ [0x25EE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25EE,
+ },
+ [0x25EF]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x25EF,
+ },
+ [0x25F0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F0,
+ },
+ [0x25F1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F1,
+ },
+ [0x25F2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F2,
+ },
+ [0x25F3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F3,
+ },
+ [0x25F4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F4,
+ },
+ [0x25F5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F5,
+ },
+ [0x25F6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F6,
+ },
+ [0x25F7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F7,
+ },
+ [0x25F8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F8,
+ },
+ [0x25F9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25F9,
+ },
+ [0x25FA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25FA,
+ },
+ [0x25FB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25FB,
+ },
+ [0x25FC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25FC,
+ },
+ [0x25FD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25FD,
+ },
+ [0x25FE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25FE,
+ },
+ [0x25FF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x25FF,
+ },
+ [0x2600]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2600,
+ },
+ [0x2601]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2601,
+ },
+ [0x2602]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2602,
+ },
+ [0x2603]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2603,
+ },
+ [0x2604]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2604,
+ },
+ [0x2605]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2605,
+ },
+ [0x2606]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2606,
+ },
+ [0x2607]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2607,
+ },
+ [0x2608]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2608,
+ },
+ [0x2609]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2609,
+ },
+ [0x260A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x260A,
+ },
+ [0x260B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x260B,
+ },
+ [0x260C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x260C,
+ },
+ [0x260D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x260D,
+ },
+ [0x260E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x260E,
+ },
+ [0x260F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x260F,
+ },
+ [0x2610]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2610,
+ },
+ [0x2611]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2611,
+ },
+ [0x2612]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2612,
+ },
+ [0x2613]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2613,
+ },
+ [0x2614]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2614,
+ },
+ [0x2615]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2615,
+ },
+ [0x2616]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2616,
+ },
+ [0x2617]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2617,
+ },
+ [0x2618]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2618,
+ },
+ [0x2619]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2619,
+ },
+ [0x261A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x261A,
+ },
+ [0x261B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x261B,
+ },
+ [0x261C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x261C,
+ },
+ [0x261D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x261D,
+ },
+ [0x261E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x261E,
+ },
+ [0x261F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x261F,
+ },
+ [0x2620]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2620,
+ },
+ [0x2621]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2621,
+ },
+ [0x2622]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2622,
+ },
+ [0x2623]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2623,
+ },
+ [0x2624]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2624,
+ },
+ [0x2625]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2625,
+ },
+ [0x2626]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2626,
+ },
+ [0x2627]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2627,
+ },
+ [0x2628]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2628,
+ },
+ [0x2629]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2629,
+ },
+ [0x262A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x262A,
+ },
+ [0x262B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x262B,
+ },
+ [0x262C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x262C,
+ },
+ [0x262D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x262D,
+ },
+ [0x262E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x262E,
+ },
+ [0x262F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x262F,
+ },
+ [0x2630]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2630,
+ },
+ [0x2631]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2631,
+ },
+ [0x2632]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2632,
+ },
+ [0x2633]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2633,
+ },
+ [0x2634]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2634,
+ },
+ [0x2635]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2635,
+ },
+ [0x2636]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2636,
+ },
+ [0x2637]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2637,
+ },
+ [0x2638]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2638,
+ },
+ [0x2639]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2639,
+ },
+ [0x263A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x263A,
+ },
+ [0x263B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x263B,
+ },
+ [0x263C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x263C,
+ },
+ [0x263D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x263D,
+ },
+ [0x263E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x263E,
+ },
+ [0x263F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x263F,
+ },
+ [0x2640]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2640,
+ },
+ [0x2641]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2641,
+ },
+ [0x2642]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2642,
+ },
+ [0x2643]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2643,
+ },
+ [0x2644]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2644,
+ },
+ [0x2645]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2645,
+ },
+ [0x2646]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2646,
+ },
+ [0x2647]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2647,
+ },
+ [0x2648]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2648,
+ },
+ [0x2649]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2649,
+ },
+ [0x264A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x264A,
+ },
+ [0x264B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x264B,
+ },
+ [0x264C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x264C,
+ },
+ [0x264D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x264D,
+ },
+ [0x264E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x264E,
+ },
+ [0x264F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x264F,
+ },
+ [0x2650]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2650,
+ },
+ [0x2651]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2651,
+ },
+ [0x2652]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2652,
+ },
+ [0x2653]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2653,
+ },
+ [0x2654]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2654,
+ },
+ [0x2655]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2655,
+ },
+ [0x2656]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2656,
+ },
+ [0x2657]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2657,
+ },
+ [0x2658]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2658,
+ },
+ [0x2659]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2659,
+ },
+ [0x265A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x265A,
+ },
+ [0x265B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x265B,
+ },
+ [0x265C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x265C,
+ },
+ [0x265D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x265D,
+ },
+ [0x265E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x265E,
+ },
+ [0x265F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x265F,
+ },
+ [0x2660]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2660,
+ },
+ [0x2661]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2661,
+ },
+ [0x2662]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2662,
+ },
+ [0x2663]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2663,
+ },
+ [0x2664]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2664,
+ },
+ [0x2665]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2665,
+ },
+ [0x2666]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2666,
+ },
+ [0x2667]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2667,
+ },
+ [0x2668]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2668,
+ },
+ [0x2669]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2669,
+ },
+ [0x266A]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x266A,
+ },
+ [0x266B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x266B,
+ },
+ [0x266C]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x266C,
+ },
+ [0x266D]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x266D,
+ },
+ [0x266E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x266E,
+ },
+ [0x266F]={
+ category="sm",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x266F,
+ },
+ [0x2670]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2670,
+ },
+ [0x2671]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2671,
+ },
+ [0x2672]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2672,
+ },
+ [0x2673]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2673,
+ },
+ [0x2674]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2674,
+ },
+ [0x2675]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2675,
+ },
+ [0x2676]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2676,
+ },
+ [0x2677]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2677,
+ },
+ [0x2678]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2678,
+ },
+ [0x2679]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2679,
+ },
+ [0x267A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x267A,
+ },
+ [0x267B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x267B,
+ },
+ [0x267C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x267C,
+ },
+ [0x267D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x267D,
+ },
+ [0x267E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x267E,
+ },
+ [0x267F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x267F,
+ },
+ [0x2680]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2680,
+ },
+ [0x2681]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2681,
+ },
+ [0x2682]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2682,
+ },
+ [0x2683]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2683,
+ },
+ [0x2684]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2684,
+ },
+ [0x2685]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2685,
+ },
+ [0x2686]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2686,
+ },
+ [0x2687]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2687,
+ },
+ [0x2688]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2688,
+ },
+ [0x2689]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2689,
+ },
+ [0x268A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x268A,
+ },
+ [0x268B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x268B,
+ },
+ [0x268C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x268C,
+ },
+ [0x268D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x268D,
+ },
+ [0x268E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x268E,
+ },
+ [0x268F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x268F,
+ },
+ [0x2690]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2690,
+ },
+ [0x2691]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2691,
+ },
+ [0x2692]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2692,
+ },
+ [0x2693]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2693,
+ },
+ [0x2694]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2694,
+ },
+ [0x2695]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2695,
+ },
+ [0x2696]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2696,
+ },
+ [0x2697]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2697,
+ },
+ [0x2698]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2698,
+ },
+ [0x2699]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2699,
+ },
+ [0x269A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x269A,
+ },
+ [0x269B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x269B,
+ },
+ [0x269C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x269C,
+ },
+ [0x269D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x269D,
+ },
+ [0x269E]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x269E,
+ },
+ [0x269F]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x269F,
+ },
+ [0x26A0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A0,
+ },
+ [0x26A1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A1,
+ },
+ [0x26A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A2,
+ },
+ [0x26A3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A3,
+ },
+ [0x26A4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A4,
+ },
+ [0x26A5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A5,
+ },
+ [0x26A6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A6,
+ },
+ [0x26A7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A7,
+ },
+ [0x26A8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A8,
+ },
+ [0x26A9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26A9,
+ },
+ [0x26AA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26AA,
+ },
+ [0x26AB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26AB,
+ },
+ [0x26AC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x26AC,
+ },
+ [0x26AD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26AD,
+ },
+ [0x26AE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26AE,
+ },
+ [0x26AF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26AF,
+ },
+ [0x26B0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B0,
+ },
+ [0x26B1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B1,
+ },
+ [0x26B2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B2,
+ },
+ [0x26B3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B3,
+ },
+ [0x26B4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B4,
+ },
+ [0x26B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B5,
+ },
+ [0x26B6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B6,
+ },
+ [0x26B7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B7,
+ },
+ [0x26B8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B8,
+ },
+ [0x26B9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26B9,
+ },
+ [0x26BA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26BA,
+ },
+ [0x26BB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26BB,
+ },
+ [0x26BC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26BC,
+ },
+ [0x26BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26BD,
+ },
+ [0x26BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26BE,
+ },
+ [0x26BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26BF,
+ },
+ [0x26C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C0,
+ },
+ [0x26C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C1,
+ },
+ [0x26C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C2,
+ },
+ [0x26C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C3,
+ },
+ [0x26C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C4,
+ },
+ [0x26C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C5,
+ },
+ [0x26C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C6,
+ },
+ [0x26C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C7,
+ },
+ [0x26C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26C8,
+ },
+ [0x26C9]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26C9,
+ },
+ [0x26CA]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26CA,
+ },
+ [0x26CB]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26CB,
+ },
+ [0x26CC]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26CC,
+ },
+ [0x26CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26CD,
+ },
+ [0x26CE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26CE,
+ },
+ [0x26CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26CF,
+ },
+ [0x26D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26D0,
+ },
+ [0x26D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26D1,
+ },
+ [0x26D2]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26D2,
+ },
+ [0x26D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26D3,
+ },
+ [0x26D4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26D4,
+ },
+ [0x26D5]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26D5,
+ },
+ [0x26D6]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26D6,
+ },
+ [0x26D7]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26D7,
+ },
+ [0x26D8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26D8,
+ },
+ [0x26D9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26D9,
+ },
+ [0x26DA]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26DA,
+ },
+ [0x26DB]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26DB,
+ },
+ [0x26DC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26DC,
+ },
+ [0x26DD]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26DD,
+ },
+ [0x26DE]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26DE,
+ },
+ [0x26DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26DF,
+ },
+ [0x26E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26E0,
+ },
+ [0x26E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26E1,
+ },
+ [0x26E2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26E2,
+ },
+ [0x26E3]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26E3,
+ },
+ [0x26E4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26E4,
+ },
+ [0x26E5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26E5,
+ },
+ [0x26E6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26E6,
+ },
+ [0x26E7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x26E7,
+ },
+ [0x26E8]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26E8,
+ },
+ [0x26E9]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26E9,
+ },
+ [0x26EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26EA,
+ },
+ [0x26EB]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26EB,
+ },
+ [0x26EC]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26EC,
+ },
+ [0x26ED]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26ED,
+ },
+ [0x26EE]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26EE,
+ },
+ [0x26EF]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26EF,
+ },
+ [0x26F0]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26F0,
+ },
+ [0x26F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F1,
+ },
+ [0x26F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F2,
+ },
+ [0x26F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F3,
+ },
+ [0x26F4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F4,
+ },
+ [0x26F5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F5,
+ },
+ [0x26F6]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26F6,
+ },
+ [0x26F7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F7,
+ },
+ [0x26F8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26F8,
+ },
+ [0x26F9]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x26F9,
+ },
+ [0x26FA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26FA,
+ },
+ [0x26FB]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26FB,
+ },
+ [0x26FC]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x26FC,
+ },
+ [0x26FD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26FD,
+ },
+ [0x26FE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26FE,
+ },
+ [0x26FF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x26FF,
+ },
+ [0x2700]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2700,
+ },
+ [0x2701]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2701,
+ },
+ [0x2702]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2702,
+ },
+ [0x2703]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2703,
+ },
+ [0x2704]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2704,
+ },
+ [0x2705]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2705,
+ },
+ [0x2706]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2706,
+ },
+ [0x2707]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2707,
+ },
+ [0x2708]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2708,
+ },
+ [0x2709]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2709,
+ },
+ [0x270A]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x270A,
+ },
+ [0x270B]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x270B,
+ },
+ [0x270C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x270C,
+ },
+ [0x270D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x270D,
+ },
+ [0x270E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x270E,
+ },
+ [0x270F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x270F,
+ },
+ [0x2710]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2710,
+ },
+ [0x2711]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2711,
+ },
+ [0x2712]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2712,
+ },
+ [0x2713]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2713,
+ },
+ [0x2714]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2714,
+ },
+ [0x2715]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2715,
+ },
+ [0x2716]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2716,
+ },
+ [0x2717]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2717,
+ },
+ [0x2718]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2718,
+ },
+ [0x2719]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2719,
+ },
+ [0x271A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x271A,
+ },
+ [0x271B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x271B,
+ },
+ [0x271C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x271C,
+ },
+ [0x271D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x271D,
+ },
+ [0x271E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x271E,
+ },
+ [0x271F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x271F,
+ },
+ [0x2720]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2720,
+ },
+ [0x2721]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2721,
+ },
+ [0x2722]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2722,
+ },
+ [0x2723]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2723,
+ },
+ [0x2724]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2724,
+ },
+ [0x2725]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2725,
+ },
+ [0x2726]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2726,
+ },
+ [0x2727]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2727,
+ },
+ [0x2728]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2728,
+ },
+ [0x2729]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2729,
+ },
+ [0x272A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x272A,
+ },
+ [0x272B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x272B,
+ },
+ [0x272C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x272C,
+ },
+ [0x272D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x272D,
+ },
+ [0x272E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x272E,
+ },
+ [0x272F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x272F,
+ },
+ [0x2730]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2730,
+ },
+ [0x2731]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2731,
+ },
+ [0x2732]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2732,
+ },
+ [0x2733]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2733,
+ },
+ [0x2734]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2734,
+ },
+ [0x2735]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2735,
+ },
+ [0x2736]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2736,
+ },
+ [0x2737]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2737,
+ },
+ [0x2738]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2738,
+ },
+ [0x2739]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2739,
+ },
+ [0x273A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x273A,
+ },
+ [0x273B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x273B,
+ },
+ [0x273C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x273C,
+ },
+ [0x273D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x273D,
+ },
+ [0x273E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x273E,
+ },
+ [0x273F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x273F,
+ },
+ [0x2740]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2740,
+ },
+ [0x2741]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2741,
+ },
+ [0x2742]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2742,
+ },
+ [0x2743]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2743,
+ },
+ [0x2744]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2744,
+ },
+ [0x2745]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2745,
+ },
+ [0x2746]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2746,
+ },
+ [0x2747]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2747,
+ },
+ [0x2748]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2748,
+ },
+ [0x2749]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2749,
+ },
+ [0x274A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x274A,
+ },
+ [0x274B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x274B,
+ },
+ [0x274C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x274C,
+ },
+ [0x274D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x274D,
+ },
+ [0x274E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x274E,
+ },
+ [0x274F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x274F,
+ },
+ [0x2750]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2750,
+ },
+ [0x2751]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2751,
+ },
+ [0x2752]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2752,
+ },
+ [0x2753]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2753,
+ },
+ [0x2754]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2754,
+ },
+ [0x2755]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2755,
+ },
+ [0x2756]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2756,
+ },
+ [0x2757]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2757,
+ },
+ [0x2758]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2758,
+ },
+ [0x2759]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2759,
+ },
+ [0x275A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x275A,
+ },
+ [0x275B]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x275B,
+ },
+ [0x275C]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x275C,
+ },
+ [0x275D]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x275D,
+ },
+ [0x275E]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x275E,
+ },
+ [0x275F]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x275F,
+ },
+ [0x2760]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2760,
+ },
+ [0x2761]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2761,
+ },
+ [0x2762]={
+ category="so",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x2762,
+ },
+ [0x2763]={
+ category="so",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x2763,
+ },
+ [0x2764]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2764,
+ },
+ [0x2765]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2765,
+ },
+ [0x2766]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2766,
+ },
+ [0x2767]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2767,
+ },
+ [0x2768]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2769,
+ unicodeslot=0x2768,
+ },
+ [0x2769]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2768,
+ unicodeslot=0x2769,
+ },
+ [0x276A]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x276B,
+ unicodeslot=0x276A,
+ },
+ [0x276B]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x276A,
+ unicodeslot=0x276B,
+ },
+ [0x276C]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x276D,
+ unicodeslot=0x276C,
+ },
+ [0x276D]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x276C,
+ unicodeslot=0x276D,
+ },
+ [0x276E]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x276F,
+ unicodeslot=0x276E,
+ },
+ [0x276F]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x276E,
+ unicodeslot=0x276F,
+ },
+ [0x2770]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2771,
+ unicodeslot=0x2770,
+ },
+ [0x2771]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2770,
+ unicodeslot=0x2771,
+ },
+ [0x2772]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2773,
+ unicodeslot=0x2772,
+ },
+ [0x2773]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2772,
+ unicodeslot=0x2773,
+ },
+ [0x2774]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2775,
+ unicodeslot=0x2774,
+ },
+ [0x2775]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2774,
+ unicodeslot=0x2775,
+ },
+ [0x2776]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2776,
+ },
+ [0x2777]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2777,
+ },
+ [0x2778]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2778,
+ },
+ [0x2779]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2779,
+ },
+ [0x277A]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x277A,
+ },
+ [0x277B]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x277B,
+ },
+ [0x277C]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x277C,
+ },
+ [0x277D]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x277D,
+ },
+ [0x277E]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x277E,
+ },
+ [0x277F]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x277F,
+ },
+ [0x2780]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2780,
+ },
+ [0x2781]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2781,
+ },
+ [0x2782]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2782,
+ },
+ [0x2783]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2783,
+ },
+ [0x2784]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2784,
+ },
+ [0x2785]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2785,
+ },
+ [0x2786]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2786,
+ },
+ [0x2787]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2787,
+ },
+ [0x2788]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2788,
+ },
+ [0x2789]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2789,
+ },
+ [0x278A]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x278A,
+ },
+ [0x278B]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x278B,
+ },
+ [0x278C]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x278C,
+ },
+ [0x278D]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x278D,
+ },
+ [0x278E]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x278E,
+ },
+ [0x278F]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x278F,
+ },
+ [0x2790]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2790,
+ },
+ [0x2791]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2791,
+ },
+ [0x2792]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2792,
+ },
+ [0x2793]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2793,
+ },
+ [0x2794]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2794,
+ },
+ [0x2795]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2795,
+ },
+ [0x2796]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2796,
+ },
+ [0x2797]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2797,
+ },
+ [0x2798]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2798,
+ },
+ [0x2799]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2799,
+ },
+ [0x279A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x279A,
+ },
+ [0x279B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x279B,
+ },
+ [0x279C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x279C,
+ },
+ [0x279D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x279D,
+ },
+ [0x279E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x279E,
+ },
+ [0x279F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x279F,
+ },
+ [0x27A0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A0,
+ },
+ [0x27A1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A1,
+ },
+ [0x27A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A2,
+ },
+ [0x27A3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A3,
+ },
+ [0x27A4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A4,
+ },
+ [0x27A5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A5,
+ },
+ [0x27A6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A6,
+ },
+ [0x27A7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A7,
+ },
+ [0x27A8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A8,
+ },
+ [0x27A9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27A9,
+ },
+ [0x27AA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27AA,
+ },
+ [0x27AB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27AB,
+ },
+ [0x27AC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27AC,
+ },
+ [0x27AD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27AD,
+ },
+ [0x27AE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27AE,
+ },
+ [0x27AF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27AF,
+ },
+ [0x27B0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B0,
+ },
+ [0x27B1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B1,
+ },
+ [0x27B2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B2,
+ },
+ [0x27B3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B3,
+ },
+ [0x27B4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B4,
+ },
+ [0x27B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B5,
+ },
+ [0x27B6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B6,
+ },
+ [0x27B7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B7,
+ },
+ [0x27B8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B8,
+ },
+ [0x27B9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27B9,
+ },
+ [0x27BA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27BA,
+ },
+ [0x27BB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27BB,
+ },
+ [0x27BC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27BC,
+ },
+ [0x27BD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27BD,
+ },
+ [0x27BE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27BE,
+ },
+ [0x27BF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27BF,
+ },
+ [0x27C0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27C0,
+ },
+ [0x27C1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27C1,
+ },
+ [0x27C2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27C2,
+ },
+ [0x27C3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27C4,
+ unicodeslot=0x27C3,
+ },
+ [0x27C4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27C3,
+ unicodeslot=0x27C4,
+ },
+ [0x27C5]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x27C6,
+ unicodeslot=0x27C5,
+ },
+ [0x27C6]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x27C5,
+ unicodeslot=0x27C6,
+ },
+ [0x27C7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27C7,
+ },
+ [0x27C8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27C9,
+ unicodeslot=0x27C8,
+ },
+ [0x27C9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27C8,
+ unicodeslot=0x27C9,
+ },
+ [0x27CA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27CA,
+ },
+ [0x27CB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27CD,
+ unicodeslot=0x27CB,
+ },
+ [0x27CC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27CC,
+ },
+ [0x27CD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27CB,
+ unicodeslot=0x27CD,
+ },
+ [0x27CE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27CE,
+ },
+ [0x27CF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27CF,
+ },
+ [0x27D0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D0,
+ },
+ [0x27D1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D1,
+ },
+ [0x27D2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D2,
+ },
+ [0x27D3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D3,
+ },
+ [0x27D4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D4,
+ },
+ [0x27D5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27D6,
+ unicodeslot=0x27D5,
+ },
+ [0x27D6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27D5,
+ unicodeslot=0x27D6,
+ },
+ [0x27D7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D7,
+ },
+ [0x27D8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D8,
+ },
+ [0x27D9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27D9,
+ },
+ [0x27DA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27DA,
+ },
+ [0x27DB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27DB,
+ },
+ [0x27DC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22B8,
+ unicodeslot=0x27DC,
+ },
+ [0x27DD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27DE,
+ unicodeslot=0x27DD,
+ },
+ [0x27DE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27DD,
+ unicodeslot=0x27DE,
+ },
+ [0x27DF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27DF,
+ },
+ [0x27E0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27E0,
+ },
+ [0x27E1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27E1,
+ },
+ [0x27E2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27E3,
+ unicodeslot=0x27E2,
+ },
+ [0x27E3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27E2,
+ unicodeslot=0x27E3,
+ },
+ [0x27E4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27E5,
+ unicodeslot=0x27E4,
+ },
+ [0x27E5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x27E4,
+ unicodeslot=0x27E5,
+ },
+ [0x27E6]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x27E7,
+ unicodeslot=0x27E6,
+ },
+ [0x27E7]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x27E6,
+ unicodeslot=0x27E7,
+ },
+ [0x27E8]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x27E9,
+ unicodeslot=0x27E8,
+ },
+ [0x27E9]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x27E8,
+ unicodeslot=0x27E9,
+ },
+ [0x27EA]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x27EB,
+ unicodeslot=0x27EA,
+ },
+ [0x27EB]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x27EA,
+ unicodeslot=0x27EB,
+ },
+ [0x27EC]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x27ED,
+ unicodeslot=0x27EC,
+ },
+ [0x27ED]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x27EC,
+ unicodeslot=0x27ED,
+ },
+ [0x27EE]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x27EF,
+ unicodeslot=0x27EE,
+ },
+ [0x27EF]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x27EE,
+ unicodeslot=0x27EF,
+ },
+ [0x27F0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F0,
+ },
+ [0x27F1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F1,
+ },
+ [0x27F2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F2,
+ },
+ [0x27F3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F3,
+ },
+ [0x27F4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F4,
+ },
+ [0x27F5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F5,
+ },
+ [0x27F6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F6,
+ },
+ [0x27F7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F7,
+ },
+ [0x27F8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F8,
+ },
+ [0x27F9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27F9,
+ },
+ [0x27FA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27FA,
+ },
+ [0x27FB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27FB,
+ },
+ [0x27FC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27FC,
+ },
+ [0x27FD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27FD,
+ },
+ [0x27FE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27FE,
+ },
+ [0x27FF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x27FF,
+ },
+ [0x2800]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2800,
+ },
+ [0x2801]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2801,
+ },
+ [0x2802]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2802,
+ },
+ [0x2803]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2803,
+ },
+ [0x2804]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2804,
+ },
+ [0x2805]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2805,
+ },
+ [0x2806]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2806,
+ },
+ [0x2807]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2807,
+ },
+ [0x2808]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2808,
+ },
+ [0x2809]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2809,
+ },
+ [0x280A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280A,
+ },
+ [0x280B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280B,
+ },
+ [0x280C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280C,
+ },
+ [0x280D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280D,
+ },
+ [0x280E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280E,
+ },
+ [0x280F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x280F,
+ },
+ [0x2810]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2810,
+ },
+ [0x2811]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2811,
+ },
+ [0x2812]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2812,
+ },
+ [0x2813]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2813,
+ },
+ [0x2814]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2814,
+ },
+ [0x2815]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2815,
+ },
+ [0x2816]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2816,
+ },
+ [0x2817]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2817,
+ },
+ [0x2818]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2818,
+ },
+ [0x2819]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2819,
+ },
+ [0x281A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281A,
+ },
+ [0x281B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281B,
+ },
+ [0x281C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281C,
+ },
+ [0x281D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281D,
+ },
+ [0x281E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281E,
+ },
+ [0x281F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x281F,
+ },
+ [0x2820]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2820,
+ },
+ [0x2821]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2821,
+ },
+ [0x2822]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2822,
+ },
+ [0x2823]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2823,
+ },
+ [0x2824]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2824,
+ },
+ [0x2825]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2825,
+ },
+ [0x2826]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2826,
+ },
+ [0x2827]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2827,
+ },
+ [0x2828]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2828,
+ },
+ [0x2829]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2829,
+ },
+ [0x282A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282A,
+ },
+ [0x282B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282B,
+ },
+ [0x282C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282C,
+ },
+ [0x282D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282D,
+ },
+ [0x282E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282E,
+ },
+ [0x282F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x282F,
+ },
+ [0x2830]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2830,
+ },
+ [0x2831]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2831,
+ },
+ [0x2832]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2832,
+ },
+ [0x2833]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2833,
+ },
+ [0x2834]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2834,
+ },
+ [0x2835]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2835,
+ },
+ [0x2836]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2836,
+ },
+ [0x2837]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2837,
+ },
+ [0x2838]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2838,
+ },
+ [0x2839]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2839,
+ },
+ [0x283A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283A,
+ },
+ [0x283B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283B,
+ },
+ [0x283C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283C,
+ },
+ [0x283D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283D,
+ },
+ [0x283E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283E,
+ },
+ [0x283F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x283F,
+ },
+ [0x2840]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2840,
+ },
+ [0x2841]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2841,
+ },
+ [0x2842]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2842,
+ },
+ [0x2843]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2843,
+ },
+ [0x2844]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2844,
+ },
+ [0x2845]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2845,
+ },
+ [0x2846]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2846,
+ },
+ [0x2847]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2847,
+ },
+ [0x2848]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2848,
+ },
+ [0x2849]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2849,
+ },
+ [0x284A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284A,
+ },
+ [0x284B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284B,
+ },
+ [0x284C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284C,
+ },
+ [0x284D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284D,
+ },
+ [0x284E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284E,
+ },
+ [0x284F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x284F,
+ },
+ [0x2850]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2850,
+ },
+ [0x2851]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2851,
+ },
+ [0x2852]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2852,
+ },
+ [0x2853]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2853,
+ },
+ [0x2854]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2854,
+ },
+ [0x2855]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2855,
+ },
+ [0x2856]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2856,
+ },
+ [0x2857]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2857,
+ },
+ [0x2858]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2858,
+ },
+ [0x2859]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2859,
+ },
+ [0x285A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285A,
+ },
+ [0x285B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285B,
+ },
+ [0x285C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285C,
+ },
+ [0x285D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285D,
+ },
+ [0x285E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285E,
+ },
+ [0x285F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x285F,
+ },
+ [0x2860]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2860,
+ },
+ [0x2861]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2861,
+ },
+ [0x2862]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2862,
+ },
+ [0x2863]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2863,
+ },
+ [0x2864]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2864,
+ },
+ [0x2865]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2865,
+ },
+ [0x2866]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2866,
+ },
+ [0x2867]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2867,
+ },
+ [0x2868]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2868,
+ },
+ [0x2869]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2869,
+ },
+ [0x286A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286A,
+ },
+ [0x286B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286B,
+ },
+ [0x286C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286C,
+ },
+ [0x286D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286D,
+ },
+ [0x286E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286E,
+ },
+ [0x286F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x286F,
+ },
+ [0x2870]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2870,
+ },
+ [0x2871]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2871,
+ },
+ [0x2872]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2872,
+ },
+ [0x2873]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2873,
+ },
+ [0x2874]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2874,
+ },
+ [0x2875]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2875,
+ },
+ [0x2876]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2876,
+ },
+ [0x2877]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2877,
+ },
+ [0x2878]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2878,
+ },
+ [0x2879]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2879,
+ },
+ [0x287A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287A,
+ },
+ [0x287B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287B,
+ },
+ [0x287C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287C,
+ },
+ [0x287D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287D,
+ },
+ [0x287E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287E,
+ },
+ [0x287F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x287F,
+ },
+ [0x2880]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2880,
+ },
+ [0x2881]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2881,
+ },
+ [0x2882]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2882,
+ },
+ [0x2883]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2883,
+ },
+ [0x2884]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2884,
+ },
+ [0x2885]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2885,
+ },
+ [0x2886]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2886,
+ },
+ [0x2887]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2887,
+ },
+ [0x2888]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2888,
+ },
+ [0x2889]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2889,
+ },
+ [0x288A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288A,
+ },
+ [0x288B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288B,
+ },
+ [0x288C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288C,
+ },
+ [0x288D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288D,
+ },
+ [0x288E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288E,
+ },
+ [0x288F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x288F,
+ },
+ [0x2890]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2890,
+ },
+ [0x2891]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2891,
+ },
+ [0x2892]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2892,
+ },
+ [0x2893]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2893,
+ },
+ [0x2894]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2894,
+ },
+ [0x2895]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2895,
+ },
+ [0x2896]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2896,
+ },
+ [0x2897]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2897,
+ },
+ [0x2898]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2898,
+ },
+ [0x2899]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2899,
+ },
+ [0x289A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289A,
+ },
+ [0x289B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289B,
+ },
+ [0x289C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289C,
+ },
+ [0x289D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289D,
+ },
+ [0x289E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289E,
+ },
+ [0x289F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x289F,
+ },
+ [0x28A0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A0,
+ },
+ [0x28A1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A1,
+ },
+ [0x28A2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A2,
+ },
+ [0x28A3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A3,
+ },
+ [0x28A4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A4,
+ },
+ [0x28A5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A5,
+ },
+ [0x28A6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A6,
+ },
+ [0x28A7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A7,
+ },
+ [0x28A8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A8,
+ },
+ [0x28A9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28A9,
+ },
+ [0x28AA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28AA,
+ },
+ [0x28AB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28AB,
+ },
+ [0x28AC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28AC,
+ },
+ [0x28AD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28AD,
+ },
+ [0x28AE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28AE,
+ },
+ [0x28AF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28AF,
+ },
+ [0x28B0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B0,
+ },
+ [0x28B1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B1,
+ },
+ [0x28B2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B2,
+ },
+ [0x28B3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B3,
+ },
+ [0x28B4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B4,
+ },
+ [0x28B5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B5,
+ },
+ [0x28B6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B6,
+ },
+ [0x28B7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B7,
+ },
+ [0x28B8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B8,
+ },
+ [0x28B9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28B9,
+ },
+ [0x28BA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28BA,
+ },
+ [0x28BB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28BB,
+ },
+ [0x28BC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28BC,
+ },
+ [0x28BD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28BD,
+ },
+ [0x28BE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28BE,
+ },
+ [0x28BF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28BF,
+ },
+ [0x28C0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C0,
+ },
+ [0x28C1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C1,
+ },
+ [0x28C2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C2,
+ },
+ [0x28C3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C3,
+ },
+ [0x28C4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C4,
+ },
+ [0x28C5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C5,
+ },
+ [0x28C6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C6,
+ },
+ [0x28C7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C7,
+ },
+ [0x28C8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C8,
+ },
+ [0x28C9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28C9,
+ },
+ [0x28CA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28CA,
+ },
+ [0x28CB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28CB,
+ },
+ [0x28CC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28CC,
+ },
+ [0x28CD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28CD,
+ },
+ [0x28CE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28CE,
+ },
+ [0x28CF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28CF,
+ },
+ [0x28D0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D0,
+ },
+ [0x28D1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D1,
+ },
+ [0x28D2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D2,
+ },
+ [0x28D3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D3,
+ },
+ [0x28D4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D4,
+ },
+ [0x28D5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D5,
+ },
+ [0x28D6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D6,
+ },
+ [0x28D7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D7,
+ },
+ [0x28D8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D8,
+ },
+ [0x28D9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28D9,
+ },
+ [0x28DA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28DA,
+ },
+ [0x28DB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28DB,
+ },
+ [0x28DC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28DC,
+ },
+ [0x28DD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28DD,
+ },
+ [0x28DE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28DE,
+ },
+ [0x28DF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28DF,
+ },
+ [0x28E0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E0,
+ },
+ [0x28E1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E1,
+ },
+ [0x28E2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E2,
+ },
+ [0x28E3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E3,
+ },
+ [0x28E4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E4,
+ },
+ [0x28E5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E5,
+ },
+ [0x28E6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E6,
+ },
+ [0x28E7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E7,
+ },
+ [0x28E8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E8,
+ },
+ [0x28E9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28E9,
+ },
+ [0x28EA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28EA,
+ },
+ [0x28EB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28EB,
+ },
+ [0x28EC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28EC,
+ },
+ [0x28ED]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28ED,
+ },
+ [0x28EE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28EE,
+ },
+ [0x28EF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28EF,
+ },
+ [0x28F0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F0,
+ },
+ [0x28F1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F1,
+ },
+ [0x28F2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F2,
+ },
+ [0x28F3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F3,
+ },
+ [0x28F4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F4,
+ },
+ [0x28F5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F5,
+ },
+ [0x28F6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F6,
+ },
+ [0x28F7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F7,
+ },
+ [0x28F8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F8,
+ },
+ [0x28F9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28F9,
+ },
+ [0x28FA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28FA,
+ },
+ [0x28FB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28FB,
+ },
+ [0x28FC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28FC,
+ },
+ [0x28FD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28FD,
+ },
+ [0x28FE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28FE,
+ },
+ [0x28FF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x28FF,
+ },
+ [0x2900]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2900,
+ },
+ [0x2901]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2901,
+ },
+ [0x2902]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2902,
+ },
+ [0x2903]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2903,
+ },
+ [0x2904]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2904,
+ },
+ [0x2905]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2905,
+ },
+ [0x2906]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2906,
+ },
+ [0x2907]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2907,
+ },
+ [0x2908]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2908,
+ },
+ [0x2909]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2909,
+ },
+ [0x290A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x290A,
+ },
+ [0x290B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x290B,
+ },
+ [0x290C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x290C,
+ },
+ [0x290D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x290D,
+ },
+ [0x290E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x290E,
+ },
+ [0x290F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x290F,
+ },
+ [0x2910]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2910,
+ },
+ [0x2911]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2911,
+ },
+ [0x2912]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2912,
+ },
+ [0x2913]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2913,
+ },
+ [0x2914]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2914,
+ },
+ [0x2915]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2915,
+ },
+ [0x2916]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2916,
+ },
+ [0x2917]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2917,
+ },
+ [0x2918]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2918,
+ },
+ [0x2919]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2919,
+ },
+ [0x291A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x291A,
+ },
+ [0x291B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x291B,
+ },
+ [0x291C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x291C,
+ },
+ [0x291D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x291D,
+ },
+ [0x291E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x291E,
+ },
+ [0x291F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x291F,
+ },
+ [0x2920]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2920,
+ },
+ [0x2921]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2921,
+ },
+ [0x2922]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2922,
+ },
+ [0x2923]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2923,
+ },
+ [0x2924]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2924,
+ },
+ [0x2925]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2925,
+ },
+ [0x2926]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2926,
+ },
+ [0x2927]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2927,
+ },
+ [0x2928]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2928,
+ },
+ [0x2929]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2929,
+ },
+ [0x292A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x292A,
+ },
+ [0x292B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x292B,
+ },
+ [0x292C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x292C,
+ },
+ [0x292D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x292D,
+ },
+ [0x292E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x292E,
+ },
+ [0x292F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x292F,
+ },
+ [0x2930]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2930,
+ },
+ [0x2931]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2931,
+ },
+ [0x2932]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2932,
+ },
+ [0x2933]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2933,
+ },
+ [0x2934]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2934,
+ },
+ [0x2935]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2935,
+ },
+ [0x2936]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2936,
+ },
+ [0x2937]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2937,
+ },
+ [0x2938]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2938,
+ },
+ [0x2939]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2939,
+ },
+ [0x293A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x293A,
+ },
+ [0x293B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x293B,
+ },
+ [0x293C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x293C,
+ },
+ [0x293D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x293D,
+ },
+ [0x293E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x293E,
+ },
+ [0x293F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x293F,
+ },
+ [0x2940]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2940,
+ },
+ [0x2941]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2941,
+ },
+ [0x2942]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2942,
+ },
+ [0x2943]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2943,
+ },
+ [0x2944]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2944,
+ },
+ [0x2945]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2945,
+ },
+ [0x2946]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2946,
+ },
+ [0x2947]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2947,
+ },
+ [0x2948]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2948,
+ },
+ [0x2949]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2949,
+ },
+ [0x294A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x294A,
+ },
+ [0x294B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x294B,
+ },
+ [0x294C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x294C,
+ },
+ [0x294D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x294D,
+ },
+ [0x294E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x294E,
+ },
+ [0x294F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x294F,
+ },
+ [0x2950]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2950,
+ },
+ [0x2951]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2951,
+ },
+ [0x2952]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2952,
+ },
+ [0x2953]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2953,
+ },
+ [0x2954]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2954,
+ },
+ [0x2955]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2955,
+ },
+ [0x2956]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2956,
+ },
+ [0x2957]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2957,
+ },
+ [0x2958]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2958,
+ },
+ [0x2959]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2959,
+ },
+ [0x295A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x295A,
+ },
+ [0x295B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x295B,
+ },
+ [0x295C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x295C,
+ },
+ [0x295D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x295D,
+ },
+ [0x295E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x295E,
+ },
+ [0x295F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x295F,
+ },
+ [0x2960]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2960,
+ },
+ [0x2961]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2961,
+ },
+ [0x2962]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2962,
+ },
+ [0x2963]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2963,
+ },
+ [0x2964]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2964,
+ },
+ [0x2965]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2965,
+ },
+ [0x2966]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2966,
+ },
+ [0x2967]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2967,
+ },
+ [0x2968]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2968,
+ },
+ [0x2969]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2969,
+ },
+ [0x296A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x296A,
+ },
+ [0x296B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x296B,
+ },
+ [0x296C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x296C,
+ },
+ [0x296D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x296D,
+ },
+ [0x296E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x296E,
+ },
+ [0x296F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x296F,
+ },
+ [0x2970]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2970,
+ },
+ [0x2971]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2971,
+ },
+ [0x2972]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2972,
+ },
+ [0x2973]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2973,
+ },
+ [0x2974]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2974,
+ },
+ [0x2975]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2975,
+ },
+ [0x2976]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2976,
+ },
+ [0x2977]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2977,
+ },
+ [0x2978]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2978,
+ },
+ [0x2979]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2979,
+ },
+ [0x297A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x297A,
+ },
+ [0x297B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x297B,
+ },
+ [0x297C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x297C,
+ },
+ [0x297D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x297D,
+ },
+ [0x297E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x297E,
+ },
+ [0x297F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x297F,
+ },
+ [0x2980]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2980,
+ },
+ [0x2981]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2981,
+ },
+ [0x2982]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2982,
+ },
+ [0x2983]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2984,
+ unicodeslot=0x2983,
+ },
+ [0x2984]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2983,
+ unicodeslot=0x2984,
+ },
+ [0x2985]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2986,
+ unicodeslot=0x2985,
+ },
+ [0x2986]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2985,
+ unicodeslot=0x2986,
+ },
+ [0x2987]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2988,
+ unicodeslot=0x2987,
+ },
+ [0x2988]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2987,
+ unicodeslot=0x2988,
+ },
+ [0x2989]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x298A,
+ unicodeslot=0x2989,
+ },
+ [0x298A]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2989,
+ unicodeslot=0x298A,
+ },
+ [0x298B]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x298C,
+ unicodeslot=0x298B,
+ },
+ [0x298C]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x298B,
+ unicodeslot=0x298C,
+ },
+ [0x298D]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2990,
+ unicodeslot=0x298D,
+ },
+ [0x298E]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x298F,
+ unicodeslot=0x298E,
+ },
+ [0x298F]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x298E,
+ unicodeslot=0x298F,
+ },
+ [0x2990]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x298D,
+ unicodeslot=0x2990,
+ },
+ [0x2991]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2992,
+ unicodeslot=0x2991,
+ },
+ [0x2992]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2991,
+ unicodeslot=0x2992,
+ },
+ [0x2993]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2994,
+ unicodeslot=0x2993,
+ },
+ [0x2994]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2993,
+ unicodeslot=0x2994,
+ },
+ [0x2995]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2996,
+ unicodeslot=0x2995,
+ },
+ [0x2996]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2995,
+ unicodeslot=0x2996,
+ },
+ [0x2997]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2998,
+ textclass="open",
+ unicodeslot=0x2997,
+ },
+ [0x2998]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2997,
+ textclass="close",
+ unicodeslot=0x2998,
+ },
+ [0x2999]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2999,
+ },
+ [0x299A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x299A,
+ },
+ [0x299B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2221,
+ unicodeslot=0x299B,
+ },
+ [0x299C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x299C,
+ },
+ [0x299D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x299D,
+ },
+ [0x299E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x299E,
+ },
+ [0x299F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x299F,
+ },
+ [0x29A0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2222,
+ unicodeslot=0x29A0,
+ },
+ [0x29A1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29A1,
+ },
+ [0x29A2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29A2,
+ },
+ [0x29A3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2220,
+ unicodeslot=0x29A3,
+ },
+ [0x29A4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29A5,
+ unicodeslot=0x29A4,
+ },
+ [0x29A5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29A4,
+ unicodeslot=0x29A5,
+ },
+ [0x29A6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29A6,
+ },
+ [0x29A7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29A7,
+ },
+ [0x29A8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29A9,
+ unicodeslot=0x29A8,
+ },
+ [0x29A9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29A8,
+ unicodeslot=0x29A9,
+ },
+ [0x29AA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29AB,
+ unicodeslot=0x29AA,
+ },
+ [0x29AB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29AA,
+ unicodeslot=0x29AB,
+ },
+ [0x29AC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29AD,
+ unicodeslot=0x29AC,
+ },
+ [0x29AD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29AC,
+ unicodeslot=0x29AD,
+ },
+ [0x29AE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29AF,
+ unicodeslot=0x29AE,
+ },
+ [0x29AF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29AE,
+ unicodeslot=0x29AF,
+ },
+ [0x29B0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B0,
+ },
+ [0x29B1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B1,
+ },
+ [0x29B2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B2,
+ },
+ [0x29B3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B3,
+ },
+ [0x29B4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B4,
+ },
+ [0x29B5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B5,
+ },
+ [0x29B6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B6,
+ },
+ [0x29B7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B7,
+ },
+ [0x29B8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2298,
+ unicodeslot=0x29B8,
+ },
+ [0x29B9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29B9,
+ },
+ [0x29BA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29BA,
+ },
+ [0x29BB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29BB,
+ },
+ [0x29BC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29BC,
+ },
+ [0x29BD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29BD,
+ },
+ [0x29BE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29BE,
+ },
+ [0x29BF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29BF,
+ },
+ [0x29C0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29C1,
+ unicodeslot=0x29C0,
+ },
+ [0x29C1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29C0,
+ unicodeslot=0x29C1,
+ },
+ [0x29C2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29C2,
+ },
+ [0x29C3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29C3,
+ },
+ [0x29C4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29C5,
+ unicodeslot=0x29C4,
+ },
+ [0x29C5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29C4,
+ unicodeslot=0x29C5,
+ },
+ [0x29C6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29C6,
+ },
+ [0x29C7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29C7,
+ },
+ [0x29C8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29C8,
+ },
+ [0x29C9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29C9,
+ },
+ [0x29CA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29CA,
+ },
+ [0x29CB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29CB,
+ },
+ [0x29CC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29CC,
+ },
+ [0x29CD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29CD,
+ },
+ [0x29CE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29CE,
+ },
+ [0x29CF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29D0,
+ unicodeslot=0x29CF,
+ },
+ [0x29D0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29CF,
+ unicodeslot=0x29D0,
+ },
+ [0x29D1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29D2,
+ unicodeslot=0x29D1,
+ },
+ [0x29D2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29D1,
+ unicodeslot=0x29D2,
+ },
+ [0x29D3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29D3,
+ },
+ [0x29D4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29D5,
+ unicodeslot=0x29D4,
+ },
+ [0x29D5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29D4,
+ unicodeslot=0x29D5,
+ },
+ [0x29D6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29D6,
+ },
+ [0x29D7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29D7,
+ },
+ [0x29D8]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x29D9,
+ unicodeslot=0x29D8,
+ },
+ [0x29D9]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x29D8,
+ unicodeslot=0x29D9,
+ },
+ [0x29DA]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x29DB,
+ unicodeslot=0x29DA,
+ },
+ [0x29DB]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x29DA,
+ unicodeslot=0x29DB,
+ },
+ [0x29DC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29DC,
+ },
+ [0x29DD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29DD,
+ },
+ [0x29DE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29DE,
+ },
+ [0x29DF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29DF,
+ },
+ [0x29E0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E0,
+ },
+ [0x29E1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E1,
+ },
+ [0x29E2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E2,
+ },
+ [0x29E3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E3,
+ },
+ [0x29E4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E4,
+ },
+ [0x29E5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E5,
+ },
+ [0x29E6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E6,
+ },
+ [0x29E7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29E7,
+ },
+ [0x29E8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29E9,
+ unicodeslot=0x29E8,
+ },
+ [0x29E9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29E8,
+ unicodeslot=0x29E9,
+ },
+ [0x29EA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29EA,
+ },
+ [0x29EB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29EB,
+ },
+ [0x29EC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29EC,
+ },
+ [0x29ED]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29ED,
+ },
+ [0x29EE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29EE,
+ },
+ [0x29EF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29EF,
+ },
+ [0x29F0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F0,
+ },
+ [0x29F1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F1,
+ },
+ [0x29F2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F2,
+ },
+ [0x29F3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F3,
+ },
+ [0x29F4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F4,
+ },
+ [0x29F5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2215,
+ unicodeslot=0x29F5,
+ },
+ [0x29F6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F6,
+ },
+ [0x29F7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29F7,
+ },
+ [0x29F8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29F9,
+ unicodeslot=0x29F8,
+ },
+ [0x29F9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x29F8,
+ unicodeslot=0x29F9,
+ },
+ [0x29FA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29FA,
+ },
+ [0x29FB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29FB,
+ },
+ [0x29FC]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x29FD,
+ unicodeslot=0x29FC,
+ },
+ [0x29FD]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x29FC,
+ unicodeslot=0x29FD,
+ },
+ [0x29FE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29FE,
+ },
+ [0x29FF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x29FF,
+ },
+ [0x2A00]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A00,
+ },
+ [0x2A01]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A01,
+ },
+ [0x2A02]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A02,
+ },
+ [0x2A03]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A03,
+ },
+ [0x2A04]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A04,
+ },
+ [0x2A05]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A05,
+ },
+ [0x2A06]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A06,
+ },
+ [0x2A07]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A07,
+ },
+ [0x2A08]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A08,
+ },
+ [0x2A09]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A09,
+ },
+ [0x2A0A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A0A,
+ },
+ [0x2A0B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A0B,
+ },
+ [0x2A0C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x222B, 0x222B, 0x222B, 0x222B },
+ unicodeslot=0x2A0C,
+ },
+ [0x2A0D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A0D,
+ },
+ [0x2A0E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A0E,
+ },
+ [0x2A0F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A0F,
+ },
+ [0x2A10]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A10,
+ },
+ [0x2A11]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A11,
+ },
+ [0x2A12]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A12,
+ },
+ [0x2A13]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A13,
+ },
+ [0x2A14]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A14,
+ },
+ [0x2A15]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A15,
+ },
+ [0x2A16]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A16,
+ },
+ [0x2A17]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A17,
+ },
+ [0x2A18]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A18,
+ },
+ [0x2A19]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A19,
+ },
+ [0x2A1A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A1A,
+ },
+ [0x2A1B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A1B,
+ },
+ [0x2A1C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A1C,
+ },
+ [0x2A1D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A1D,
+ },
+ [0x2A1E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A1E,
+ },
+ [0x2A1F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A1F,
+ },
+ [0x2A20]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A20,
+ },
+ [0x2A21]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A21,
+ },
+ [0x2A22]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A22,
+ },
+ [0x2A23]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A23,
+ },
+ [0x2A24]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A24,
+ },
+ [0x2A25]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A25,
+ },
+ [0x2A26]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A26,
+ },
+ [0x2A27]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A27,
+ },
+ [0x2A28]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A28,
+ },
+ [0x2A29]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A29,
+ },
+ [0x2A2A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A2A,
+ },
+ [0x2A2B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A2C,
+ unicodeslot=0x2A2B,
+ },
+ [0x2A2C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A2B,
+ unicodeslot=0x2A2C,
+ },
+ [0x2A2D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A2E,
+ unicodeslot=0x2A2D,
+ },
+ [0x2A2E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A2D,
+ unicodeslot=0x2A2E,
+ },
+ [0x2A2F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A2F,
+ },
+ [0x2A30]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A30,
+ },
+ [0x2A31]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A31,
+ },
+ [0x2A32]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A32,
+ },
+ [0x2A33]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A33,
+ },
+ [0x2A34]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A35,
+ unicodeslot=0x2A34,
+ },
+ [0x2A35]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A34,
+ unicodeslot=0x2A35,
+ },
+ [0x2A36]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A36,
+ },
+ [0x2A37]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A37,
+ },
+ [0x2A38]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A38,
+ },
+ [0x2A39]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A39,
+ },
+ [0x2A3A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A3A,
+ },
+ [0x2A3B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A3B,
+ },
+ [0x2A3C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A3D,
+ unicodeslot=0x2A3C,
+ },
+ [0x2A3D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A3C,
+ unicodeslot=0x2A3D,
+ },
+ [0x2A3E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A3E,
+ },
+ [0x2A3F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A3F,
+ },
+ [0x2A40]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A40,
+ },
+ [0x2A41]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A41,
+ },
+ [0x2A42]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A42,
+ },
+ [0x2A43]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A43,
+ },
+ [0x2A44]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A44,
+ },
+ [0x2A45]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A45,
+ },
+ [0x2A46]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A46,
+ },
+ [0x2A47]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A47,
+ },
+ [0x2A48]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A48,
+ },
+ [0x2A49]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A49,
+ },
+ [0x2A4A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A4A,
+ },
+ [0x2A4B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A4B,
+ },
+ [0x2A4C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A4C,
+ },
+ [0x2A4D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A4D,
+ },
+ [0x2A4E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A4E,
+ },
+ [0x2A4F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A4F,
+ },
+ [0x2A50]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A50,
+ },
+ [0x2A51]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A51,
+ },
+ [0x2A52]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A52,
+ },
+ [0x2A53]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A53,
+ },
+ [0x2A54]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A54,
+ },
+ [0x2A55]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A55,
+ },
+ [0x2A56]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A56,
+ },
+ [0x2A57]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A57,
+ },
+ [0x2A58]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A58,
+ },
+ [0x2A59]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A59,
+ },
+ [0x2A5A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A5A,
+ },
+ [0x2A5B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A5B,
+ },
+ [0x2A5C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A5C,
+ },
+ [0x2A5D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A5D,
+ },
+ [0x2A5E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A5E,
+ },
+ [0x2A5F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A5F,
+ },
+ [0x2A60]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A60,
+ },
+ [0x2A61]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A61,
+ },
+ [0x2A62]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A62,
+ },
+ [0x2A63]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A63,
+ },
+ [0x2A64]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A65,
+ unicodeslot=0x2A64,
+ },
+ [0x2A65]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A64,
+ unicodeslot=0x2A65,
+ },
+ [0x2A66]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A66,
+ },
+ [0x2A67]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A67,
+ },
+ [0x2A68]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A68,
+ },
+ [0x2A69]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A69,
+ },
+ [0x2A6A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A6A,
+ },
+ [0x2A6B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A6B,
+ },
+ [0x2A6C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A6C,
+ },
+ [0x2A6D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A6D,
+ },
+ [0x2A6E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A6E,
+ },
+ [0x2A6F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A6F,
+ },
+ [0x2A70]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A70,
+ },
+ [0x2A71]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A71,
+ },
+ [0x2A72]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A72,
+ },
+ [0x2A73]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A73,
+ },
+ [0x2A74]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x3A, 0x3A, 0x3D },
+ unicodeslot=0x2A74,
+ },
+ [0x2A75]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x3D, 0x3D },
+ unicodeslot=0x2A75,
+ },
+ [0x2A76]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "compat", 0x3D, 0x3D, 0x3D },
+ unicodeslot=0x2A76,
+ },
+ [0x2A77]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A77,
+ },
+ [0x2A78]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2A78,
+ },
+ [0x2A79]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A7A,
+ unicodeslot=0x2A79,
+ },
+ [0x2A7A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A79,
+ unicodeslot=0x2A7A,
+ },
+ [0x2A7B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A7C,
+ unicodeslot=0x2A7B,
+ },
+ [0x2A7C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A7B,
+ unicodeslot=0x2A7C,
+ },
+ [0x2A7D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A7E,
+ unicodeslot=0x2A7D,
+ },
+ [0x2A7E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A7D,
+ unicodeslot=0x2A7E,
+ },
+ [0x2A7F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A80,
+ unicodeslot=0x2A7F,
+ },
+ [0x2A80]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A7F,
+ unicodeslot=0x2A80,
+ },
+ [0x2A81]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A82,
+ unicodeslot=0x2A81,
+ },
+ [0x2A82]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A81,
+ unicodeslot=0x2A82,
+ },
+ [0x2A83]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A84,
+ unicodeslot=0x2A83,
+ },
+ [0x2A84]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A83,
+ unicodeslot=0x2A84,
+ },
+ [0x2A85]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A86,
+ unicodeslot=0x2A85,
+ },
+ [0x2A86]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A85,
+ unicodeslot=0x2A86,
+ },
+ [0x2A87]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A88,
+ unicodeslot=0x2A87,
+ },
+ [0x2A88]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A87,
+ unicodeslot=0x2A88,
+ },
+ [0x2A89]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A8A,
+ unicodeslot=0x2A89,
+ },
+ [0x2A8A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A89,
+ unicodeslot=0x2A8A,
+ },
+ [0x2A8B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A8C,
+ unicodeslot=0x2A8B,
+ },
+ [0x2A8C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A8B,
+ unicodeslot=0x2A8C,
+ },
+ [0x2A8D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A8E,
+ unicodeslot=0x2A8D,
+ },
+ [0x2A8E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A8D,
+ unicodeslot=0x2A8E,
+ },
+ [0x2A8F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A90,
+ unicodeslot=0x2A8F,
+ },
+ [0x2A90]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A8F,
+ unicodeslot=0x2A90,
+ },
+ [0x2A91]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A92,
+ unicodeslot=0x2A91,
+ },
+ [0x2A92]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A91,
+ unicodeslot=0x2A92,
+ },
+ [0x2A93]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A94,
+ unicodeslot=0x2A93,
+ },
+ [0x2A94]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A93,
+ unicodeslot=0x2A94,
+ },
+ [0x2A95]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A96,
+ unicodeslot=0x2A95,
+ },
+ [0x2A96]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A95,
+ unicodeslot=0x2A96,
+ },
+ [0x2A97]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A98,
+ unicodeslot=0x2A97,
+ },
+ [0x2A98]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A97,
+ unicodeslot=0x2A98,
+ },
+ [0x2A99]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A9A,
+ unicodeslot=0x2A99,
+ },
+ [0x2A9A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A99,
+ unicodeslot=0x2A9A,
+ },
+ [0x2A9B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A9C,
+ unicodeslot=0x2A9B,
+ },
+ [0x2A9C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A9B,
+ unicodeslot=0x2A9C,
+ },
+ [0x2A9D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A9E,
+ unicodeslot=0x2A9D,
+ },
+ [0x2A9E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A9D,
+ unicodeslot=0x2A9E,
+ },
+ [0x2A9F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA0,
+ unicodeslot=0x2A9F,
+ },
+ [0x2AA0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2A9F,
+ unicodeslot=0x2AA0,
+ },
+ [0x2AA1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA2,
+ unicodeslot=0x2AA1,
+ },
+ [0x2AA2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA1,
+ unicodeslot=0x2AA2,
+ },
+ [0x2AA3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AA3,
+ },
+ [0x2AA4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AA4,
+ },
+ [0x2AA5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AA5,
+ },
+ [0x2AA6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA7,
+ unicodeslot=0x2AA6,
+ },
+ [0x2AA7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA6,
+ unicodeslot=0x2AA7,
+ },
+ [0x2AA8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA9,
+ unicodeslot=0x2AA8,
+ },
+ [0x2AA9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AA8,
+ unicodeslot=0x2AA9,
+ },
+ [0x2AAA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AAB,
+ unicodeslot=0x2AAA,
+ },
+ [0x2AAB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AAA,
+ unicodeslot=0x2AAB,
+ },
+ [0x2AAC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AAD,
+ unicodeslot=0x2AAC,
+ },
+ [0x2AAD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AAC,
+ unicodeslot=0x2AAD,
+ },
+ [0x2AAE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AAE,
+ },
+ [0x2AAF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB0,
+ unicodeslot=0x2AAF,
+ },
+ [0x2AB0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AAF,
+ unicodeslot=0x2AB0,
+ },
+ [0x2AB1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB2,
+ unicodeslot=0x2AB1,
+ },
+ [0x2AB2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB1,
+ unicodeslot=0x2AB2,
+ },
+ [0x2AB3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB4,
+ unicodeslot=0x2AB3,
+ },
+ [0x2AB4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB3,
+ unicodeslot=0x2AB4,
+ },
+ [0x2AB5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB6,
+ unicodeslot=0x2AB5,
+ },
+ [0x2AB6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB5,
+ unicodeslot=0x2AB6,
+ },
+ [0x2AB7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB8,
+ unicodeslot=0x2AB7,
+ },
+ [0x2AB8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB7,
+ unicodeslot=0x2AB8,
+ },
+ [0x2AB9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ABA,
+ unicodeslot=0x2AB9,
+ },
+ [0x2ABA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AB9,
+ unicodeslot=0x2ABA,
+ },
+ [0x2ABB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ABC,
+ unicodeslot=0x2ABB,
+ },
+ [0x2ABC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ABB,
+ unicodeslot=0x2ABC,
+ },
+ [0x2ABD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ABE,
+ unicodeslot=0x2ABD,
+ },
+ [0x2ABE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ABD,
+ unicodeslot=0x2ABE,
+ },
+ [0x2ABF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC0,
+ unicodeslot=0x2ABF,
+ },
+ [0x2AC0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ABF,
+ unicodeslot=0x2AC0,
+ },
+ [0x2AC1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC2,
+ unicodeslot=0x2AC1,
+ },
+ [0x2AC2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC1,
+ unicodeslot=0x2AC2,
+ },
+ [0x2AC3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC4,
+ unicodeslot=0x2AC3,
+ },
+ [0x2AC4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC3,
+ unicodeslot=0x2AC4,
+ },
+ [0x2AC5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC6,
+ unicodeslot=0x2AC5,
+ },
+ [0x2AC6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC5,
+ unicodeslot=0x2AC6,
+ },
+ [0x2AC7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC8,
+ unicodeslot=0x2AC7,
+ },
+ [0x2AC8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC7,
+ unicodeslot=0x2AC8,
+ },
+ [0x2AC9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ACA,
+ unicodeslot=0x2AC9,
+ },
+ [0x2ACA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AC9,
+ unicodeslot=0x2ACA,
+ },
+ [0x2ACB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ACC,
+ unicodeslot=0x2ACB,
+ },
+ [0x2ACC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ACB,
+ unicodeslot=0x2ACC,
+ },
+ [0x2ACD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ACE,
+ unicodeslot=0x2ACD,
+ },
+ [0x2ACE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ACD,
+ unicodeslot=0x2ACE,
+ },
+ [0x2ACF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD0,
+ unicodeslot=0x2ACF,
+ },
+ [0x2AD0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2ACF,
+ unicodeslot=0x2AD0,
+ },
+ [0x2AD1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD2,
+ unicodeslot=0x2AD1,
+ },
+ [0x2AD2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD1,
+ unicodeslot=0x2AD2,
+ },
+ [0x2AD3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD4,
+ unicodeslot=0x2AD3,
+ },
+ [0x2AD4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD3,
+ unicodeslot=0x2AD4,
+ },
+ [0x2AD5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD6,
+ unicodeslot=0x2AD5,
+ },
+ [0x2AD6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AD5,
+ unicodeslot=0x2AD6,
+ },
+ [0x2AD7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AD7,
+ },
+ [0x2AD8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AD8,
+ },
+ [0x2AD9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AD9,
+ },
+ [0x2ADA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2ADA,
+ },
+ [0x2ADB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2ADB,
+ },
+ [0x2ADC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "char", 0x2ADD, 0x338 },
+ unicodeslot=0x2ADC,
+ },
+ [0x2ADD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2ADD,
+ },
+ [0x2ADE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22A6,
+ unicodeslot=0x2ADE,
+ },
+ [0x2ADF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2ADF,
+ },
+ [0x2AE0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE0,
+ },
+ [0x2AE1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE1,
+ },
+ [0x2AE2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE2,
+ },
+ [0x2AE3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22A9,
+ unicodeslot=0x2AE3,
+ },
+ [0x2AE4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22A8,
+ unicodeslot=0x2AE4,
+ },
+ [0x2AE5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x22AB,
+ unicodeslot=0x2AE5,
+ },
+ [0x2AE6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE6,
+ },
+ [0x2AE7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE7,
+ },
+ [0x2AE8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE8,
+ },
+ [0x2AE9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AE9,
+ },
+ [0x2AEA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AEA,
+ },
+ [0x2AEB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AEB,
+ },
+ [0x2AEC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AED,
+ unicodeslot=0x2AEC,
+ },
+ [0x2AED]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AEC,
+ unicodeslot=0x2AED,
+ },
+ [0x2AEE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2224,
+ unicodeslot=0x2AEE,
+ },
+ [0x2AEF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AEF,
+ },
+ [0x2AF0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF0,
+ },
+ [0x2AF1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF1,
+ },
+ [0x2AF2]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF2,
+ },
+ [0x2AF3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF3,
+ },
+ [0x2AF4]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF4,
+ },
+ [0x2AF5]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF5,
+ },
+ [0x2AF6]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AF6,
+ },
+ [0x2AF7]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AF8,
+ unicodeslot=0x2AF7,
+ },
+ [0x2AF8]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AF7,
+ unicodeslot=0x2AF8,
+ },
+ [0x2AF9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AFA,
+ unicodeslot=0x2AF9,
+ },
+ [0x2AFA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ mirror=0x2AF9,
+ unicodeslot=0x2AFA,
+ },
+ [0x2AFB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AFB,
+ },
+ [0x2AFC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AFC,
+ },
+ [0x2AFD]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AFD,
+ },
+ [0x2AFE]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AFE,
+ },
+ [0x2AFF]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2AFF,
+ },
+ [0x2B00]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B00,
+ },
+ [0x2B01]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B01,
+ },
+ [0x2B02]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B02,
+ },
+ [0x2B03]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B03,
+ },
+ [0x2B04]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B04,
+ },
+ [0x2B05]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B05,
+ },
+ [0x2B06]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B06,
+ },
+ [0x2B07]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B07,
+ },
+ [0x2B08]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B08,
+ },
+ [0x2B09]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B09,
+ },
+ [0x2B0A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B0A,
+ },
+ [0x2B0B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B0B,
+ },
+ [0x2B0C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B0C,
+ },
+ [0x2B0D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B0D,
+ },
+ [0x2B0E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B0E,
+ },
+ [0x2B0F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B0F,
+ },
+ [0x2B10]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B10,
+ },
+ [0x2B11]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B11,
+ },
+ [0x2B12]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B12,
+ },
+ [0x2B13]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B13,
+ },
+ [0x2B14]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B14,
+ },
+ [0x2B15]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B15,
+ },
+ [0x2B16]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B16,
+ },
+ [0x2B17]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B17,
+ },
+ [0x2B18]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B18,
+ },
+ [0x2B19]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B19,
+ },
+ [0x2B1A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B1A,
+ },
+ [0x2B1B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B1B,
+ },
+ [0x2B1C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B1C,
+ },
+ [0x2B1D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B1D,
+ },
+ [0x2B1E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B1E,
+ },
+ [0x2B1F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B1F,
+ },
+ [0x2B20]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B20,
+ },
+ [0x2B21]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B21,
+ },
+ [0x2B22]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B22,
+ },
+ [0x2B23]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B23,
+ },
+ [0x2B24]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B24,
+ },
+ [0x2B25]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B25,
+ },
+ [0x2B26]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B26,
+ },
+ [0x2B27]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B27,
+ },
+ [0x2B28]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B28,
+ },
+ [0x2B29]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B29,
+ },
+ [0x2B2A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B2A,
+ },
+ [0x2B2B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B2B,
+ },
+ [0x2B2C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B2C,
+ },
+ [0x2B2D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B2D,
+ },
+ [0x2B2E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B2E,
+ },
+ [0x2B2F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B2F,
+ },
+ [0x2B30]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B30,
+ },
+ [0x2B31]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B31,
+ },
+ [0x2B32]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B32,
+ },
+ [0x2B33]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B33,
+ },
+ [0x2B34]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B34,
+ },
+ [0x2B35]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B35,
+ },
+ [0x2B36]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B36,
+ },
+ [0x2B37]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B37,
+ },
+ [0x2B38]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B38,
+ },
+ [0x2B39]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B39,
+ },
+ [0x2B3A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B3A,
+ },
+ [0x2B3B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B3B,
+ },
+ [0x2B3C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B3C,
+ },
+ [0x2B3D]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B3D,
+ },
+ [0x2B3E]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B3E,
+ },
+ [0x2B3F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B3F,
+ },
+ [0x2B40]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B40,
+ },
+ [0x2B41]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B41,
+ },
+ [0x2B42]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B42,
+ },
+ [0x2B43]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B43,
+ },
+ [0x2B44]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B44,
+ },
+ [0x2B45]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B45,
+ },
+ [0x2B46]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B46,
+ },
+ [0x2B47]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B47,
+ },
+ [0x2B48]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B48,
+ },
+ [0x2B49]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B49,
+ },
+ [0x2B4A]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B4A,
+ },
+ [0x2B4B]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B4B,
+ },
+ [0x2B4C]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B4C,
+ },
+ [0x2B4D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B4D,
+ },
+ [0x2B4E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B4E,
+ },
+ [0x2B4F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B4F,
+ },
+ [0x2B50]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B50,
+ },
+ [0x2B51]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B51,
+ },
+ [0x2B52]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B52,
+ },
+ [0x2B53]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B53,
+ },
+ [0x2B54]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B54,
+ },
+ [0x2B55]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2B55,
+ },
+ [0x2B56]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2B56,
+ },
+ [0x2B57]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2B57,
+ },
+ [0x2B58]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2B58,
+ },
+ [0x2B59]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x2B59,
+ },
+ [0x2B5A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B5A,
+ },
+ [0x2B5B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B5B,
+ },
+ [0x2B5C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B5C,
+ },
+ [0x2B5D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B5D,
+ },
+ [0x2B5E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B5E,
+ },
+ [0x2B5F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B5F,
+ },
+ [0x2B60]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B60,
+ },
+ [0x2B61]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B61,
+ },
+ [0x2B62]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B62,
+ },
+ [0x2B63]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B63,
+ },
+ [0x2B64]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B64,
+ },
+ [0x2B65]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B65,
+ },
+ [0x2B66]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B66,
+ },
+ [0x2B67]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B67,
+ },
+ [0x2B68]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B68,
+ },
+ [0x2B69]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B69,
+ },
+ [0x2B6A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B6A,
+ },
+ [0x2B6B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B6B,
+ },
+ [0x2B6C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B6C,
+ },
+ [0x2B6D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B6D,
+ },
+ [0x2B6E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B6E,
+ },
+ [0x2B6F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B6F,
+ },
+ [0x2B70]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B70,
+ },
+ [0x2B71]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B71,
+ },
+ [0x2B72]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B72,
+ },
+ [0x2B73]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B73,
+ },
+ [0x2B76]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B76,
+ },
+ [0x2B77]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B77,
+ },
+ [0x2B78]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B78,
+ },
+ [0x2B79]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B79,
+ },
+ [0x2B7A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B7A,
+ },
+ [0x2B7B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B7B,
+ },
+ [0x2B7C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B7C,
+ },
+ [0x2B7D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B7D,
+ },
+ [0x2B7E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B7E,
+ },
+ [0x2B7F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B7F,
+ },
+ [0x2B80]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B80,
+ },
+ [0x2B81]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B81,
+ },
+ [0x2B82]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B82,
+ },
+ [0x2B83]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B83,
+ },
+ [0x2B84]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B84,
+ },
+ [0x2B85]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B85,
+ },
+ [0x2B86]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B86,
+ },
+ [0x2B87]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B87,
+ },
+ [0x2B88]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B88,
+ },
+ [0x2B89]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B89,
+ },
+ [0x2B8A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B8A,
+ },
+ [0x2B8B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B8B,
+ },
+ [0x2B8C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B8C,
+ },
+ [0x2B8D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B8D,
+ },
+ [0x2B8E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B8E,
+ },
+ [0x2B8F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B8F,
+ },
+ [0x2B90]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B90,
+ },
+ [0x2B91]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B91,
+ },
+ [0x2B92]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B92,
+ },
+ [0x2B93]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B93,
+ },
+ [0x2B94]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B94,
+ },
+ [0x2B95]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B95,
+ },
+ [0x2B98]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B98,
+ },
+ [0x2B99]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B99,
+ },
+ [0x2B9A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9A,
+ },
+ [0x2B9B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9B,
+ },
+ [0x2B9C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9C,
+ },
+ [0x2B9D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9D,
+ },
+ [0x2B9E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9E,
+ },
+ [0x2B9F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2B9F,
+ },
+ [0x2BA0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA0,
+ },
+ [0x2BA1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA1,
+ },
+ [0x2BA2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA2,
+ },
+ [0x2BA3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA3,
+ },
+ [0x2BA4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA4,
+ },
+ [0x2BA5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA5,
+ },
+ [0x2BA6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA6,
+ },
+ [0x2BA7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA7,
+ },
+ [0x2BA8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA8,
+ },
+ [0x2BA9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BA9,
+ },
+ [0x2BAA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BAA,
+ },
+ [0x2BAB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BAB,
+ },
+ [0x2BAC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BAC,
+ },
+ [0x2BAD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BAD,
+ },
+ [0x2BAE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BAE,
+ },
+ [0x2BAF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BAF,
+ },
+ [0x2BB0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB0,
+ },
+ [0x2BB1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB1,
+ },
+ [0x2BB2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB2,
+ },
+ [0x2BB3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB3,
+ },
+ [0x2BB4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB4,
+ },
+ [0x2BB5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB5,
+ },
+ [0x2BB6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB6,
+ },
+ [0x2BB7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB7,
+ },
+ [0x2BB8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB8,
+ },
+ [0x2BB9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BB9,
+ },
+ [0x2BBA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BBA,
+ },
+ [0x2BBB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BBB,
+ },
+ [0x2BBC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BBC,
+ },
+ [0x2BBD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BBD,
+ },
+ [0x2BBE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BBE,
+ },
+ [0x2BBF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BBF,
+ },
+ [0x2BC0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC0,
+ },
+ [0x2BC1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC1,
+ },
+ [0x2BC2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC2,
+ },
+ [0x2BC3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC3,
+ },
+ [0x2BC4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC4,
+ },
+ [0x2BC5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC5,
+ },
+ [0x2BC6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC6,
+ },
+ [0x2BC7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC7,
+ },
+ [0x2BC8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC8,
+ },
+ [0x2BC9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BC9,
+ },
+ [0x2BCA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BCA,
+ },
+ [0x2BCB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BCB,
+ },
+ [0x2BCC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BCC,
+ },
+ [0x2BCD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BCD,
+ },
+ [0x2BCE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BCE,
+ },
+ [0x2BCF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BCF,
+ },
+ [0x2BD0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD0,
+ },
+ [0x2BD1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD1,
+ },
+ [0x2BD2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD2,
+ },
+ [0x2BD3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD3,
+ },
+ [0x2BD4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD4,
+ },
+ [0x2BD5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD5,
+ },
+ [0x2BD6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD6,
+ },
+ [0x2BD7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD7,
+ },
+ [0x2BD8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD8,
+ },
+ [0x2BD9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BD9,
+ },
+ [0x2BDA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BDA,
+ },
+ [0x2BDB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BDB,
+ },
+ [0x2BDC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BDC,
+ },
+ [0x2BDD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BDD,
+ },
+ [0x2BDE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BDE,
+ },
+ [0x2BDF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BDF,
+ },
+ [0x2BE0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE0,
+ },
+ [0x2BE1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE1,
+ },
+ [0x2BE2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE2,
+ },
+ [0x2BE3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE3,
+ },
+ [0x2BE4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE4,
+ },
+ [0x2BE5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE5,
+ },
+ [0x2BE6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE6,
+ },
+ [0x2BE7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE7,
+ },
+ [0x2BE8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE8,
+ },
+ [0x2BE9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BE9,
+ },
+ [0x2BEA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BEA,
+ },
+ [0x2BEB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BEB,
+ },
+ [0x2BEC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BEC,
+ },
+ [0x2BED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BED,
+ },
+ [0x2BEE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BEE,
+ },
+ [0x2BEF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BEF,
+ },
+ [0x2BF0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF0,
+ },
+ [0x2BF1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF1,
+ },
+ [0x2BF2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF2,
+ },
+ [0x2BF3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF3,
+ },
+ [0x2BF4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF4,
+ },
+ [0x2BF5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF5,
+ },
+ [0x2BF6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF6,
+ },
+ [0x2BF7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF7,
+ },
+ [0x2BF8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF8,
+ },
+ [0x2BF9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BF9,
+ },
+ [0x2BFA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BFA,
+ },
+ [0x2BFB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BFB,
+ },
+ [0x2BFC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BFC,
+ },
+ [0x2BFD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BFD,
+ },
+ [0x2BFE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ mirror=0x221F,
+ unicodeslot=0x2BFE,
+ },
+ [0x2BFF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2BFF,
+ },
+ [0x2C00]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C00,
+ },
+ [0x2C01]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C01,
+ },
+ [0x2C02]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C02,
+ },
+ [0x2C03]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C03,
+ },
+ [0x2C04]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C04,
+ },
+ [0x2C05]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C05,
+ },
+ [0x2C06]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C06,
+ },
+ [0x2C07]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C07,
+ },
+ [0x2C08]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C08,
+ },
+ [0x2C09]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C09,
+ },
+ [0x2C0A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0A,
+ },
+ [0x2C0B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0B,
+ },
+ [0x2C0C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0C,
+ },
+ [0x2C0D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0D,
+ },
+ [0x2C0E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0E,
+ },
+ [0x2C0F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C0F,
+ },
+ [0x2C10]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C10,
+ },
+ [0x2C11]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C11,
+ },
+ [0x2C12]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C12,
+ },
+ [0x2C13]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C13,
+ },
+ [0x2C14]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C14,
+ },
+ [0x2C15]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C15,
+ },
+ [0x2C16]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C16,
+ },
+ [0x2C17]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C17,
+ },
+ [0x2C18]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C18,
+ },
+ [0x2C19]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C19,
+ },
+ [0x2C1A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1A,
+ },
+ [0x2C1B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1B,
+ },
+ [0x2C1C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1C,
+ },
+ [0x2C1D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1D,
+ },
+ [0x2C1E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1E,
+ },
+ [0x2C1F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C1F,
+ },
+ [0x2C20]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C20,
+ },
+ [0x2C21]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C21,
+ },
+ [0x2C22]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C22,
+ },
+ [0x2C23]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C23,
+ },
+ [0x2C24]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C24,
+ },
+ [0x2C25]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C25,
+ },
+ [0x2C26]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C26,
+ },
+ [0x2C27]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C27,
+ },
+ [0x2C28]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C28,
+ },
+ [0x2C29]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C29,
+ },
+ [0x2C2A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C2A,
+ },
+ [0x2C2B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C2B,
+ },
+ [0x2C2C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C2C,
+ },
+ [0x2C2D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C2D,
+ },
+ [0x2C2E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C2E,
+ },
+ [0x2C30]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C30,
+ },
+ [0x2C31]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C31,
+ },
+ [0x2C32]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C32,
+ },
+ [0x2C33]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C33,
+ },
+ [0x2C34]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C34,
+ },
+ [0x2C35]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C35,
+ },
+ [0x2C36]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C36,
+ },
+ [0x2C37]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C37,
+ },
+ [0x2C38]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C38,
+ },
+ [0x2C39]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C39,
+ },
+ [0x2C3A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C3A,
+ },
+ [0x2C3B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C3B,
+ },
+ [0x2C3C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C3C,
+ },
+ [0x2C3D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C3D,
+ },
+ [0x2C3E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C3E,
+ },
+ [0x2C3F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C3F,
+ },
+ [0x2C40]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C40,
+ },
+ [0x2C41]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C41,
+ },
+ [0x2C42]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C42,
+ },
+ [0x2C43]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C43,
+ },
+ [0x2C44]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C44,
+ },
+ [0x2C45]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C45,
+ },
+ [0x2C46]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C46,
+ },
+ [0x2C47]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C47,
+ },
+ [0x2C48]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C48,
+ },
+ [0x2C49]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C49,
+ },
+ [0x2C4A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C4A,
+ },
+ [0x2C4B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C4B,
+ },
+ [0x2C4C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C4C,
+ },
+ [0x2C4D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C4D,
+ },
+ [0x2C4E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C4E,
+ },
+ [0x2C4F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C4F,
+ },
+ [0x2C50]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C50,
+ },
+ [0x2C51]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C51,
+ },
+ [0x2C52]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C52,
+ },
+ [0x2C53]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C53,
+ },
+ [0x2C54]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C54,
+ },
+ [0x2C55]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C55,
+ },
+ [0x2C56]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C56,
+ },
+ [0x2C57]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C57,
+ },
+ [0x2C58]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C58,
+ },
+ [0x2C59]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C59,
+ },
+ [0x2C5A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C5A,
+ },
+ [0x2C5B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C5B,
+ },
+ [0x2C5C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C5C,
+ },
+ [0x2C5D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C5D,
+ },
+ [0x2C5E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C5E,
+ },
+ [0x2C60]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C60,
+ },
+ [0x2C61]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C61,
+ },
+ [0x2C62]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C62,
+ },
+ [0x2C63]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C63,
+ },
+ [0x2C64]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C64,
+ },
+ [0x2C65]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C65,
+ },
+ [0x2C66]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C66,
+ },
+ [0x2C67]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C67,
+ },
+ [0x2C68]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C68,
+ },
+ [0x2C69]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C69,
+ },
+ [0x2C6A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C6A,
+ },
+ [0x2C6B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C6B,
+ },
+ [0x2C6C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C6C,
+ },
+ [0x2C6D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C6D,
+ },
+ [0x2C6E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C6E,
+ },
+ [0x2C6F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C6F,
+ },
+ [0x2C70]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C70,
+ },
+ [0x2C71]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C71,
+ },
+ [0x2C72]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C72,
+ },
+ [0x2C73]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C73,
+ },
+ [0x2C74]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C74,
+ },
+ [0x2C75]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C75,
+ },
+ [0x2C76]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C76,
+ },
+ [0x2C77]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C77,
+ },
+ [0x2C78]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C78,
+ },
+ [0x2C79]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C79,
+ },
+ [0x2C7A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C7A,
+ },
+ [0x2C7B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C7B,
+ },
+ [0x2C7C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "sub", 0x6A },
+ unicodeslot=0x2C7C,
+ },
+ [0x2C7D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x56 },
+ unicodeslot=0x2C7D,
+ },
+ [0x2C7E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C7E,
+ },
+ [0x2C7F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C7F,
+ },
+ [0x2C80]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C80,
+ },
+ [0x2C81]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C81,
+ },
+ [0x2C82]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C82,
+ },
+ [0x2C83]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C83,
+ },
+ [0x2C84]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C84,
+ },
+ [0x2C85]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C85,
+ },
+ [0x2C86]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C86,
+ },
+ [0x2C87]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C87,
+ },
+ [0x2C88]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C88,
+ },
+ [0x2C89]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C89,
+ },
+ [0x2C8A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C8A,
+ },
+ [0x2C8B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C8B,
+ },
+ [0x2C8C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C8C,
+ },
+ [0x2C8D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C8D,
+ },
+ [0x2C8E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C8E,
+ },
+ [0x2C8F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C8F,
+ },
+ [0x2C90]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C90,
+ },
+ [0x2C91]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C91,
+ },
+ [0x2C92]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C92,
+ },
+ [0x2C93]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C93,
+ },
+ [0x2C94]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C94,
+ },
+ [0x2C95]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C95,
+ },
+ [0x2C96]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C96,
+ },
+ [0x2C97]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C97,
+ },
+ [0x2C98]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C98,
+ },
+ [0x2C99]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C99,
+ },
+ [0x2C9A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C9A,
+ },
+ [0x2C9B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C9B,
+ },
+ [0x2C9C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C9C,
+ },
+ [0x2C9D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C9D,
+ },
+ [0x2C9E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C9E,
+ },
+ [0x2C9F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2C9F,
+ },
+ [0x2CA0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA0,
+ },
+ [0x2CA1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA1,
+ },
+ [0x2CA2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA2,
+ },
+ [0x2CA3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA3,
+ },
+ [0x2CA4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA4,
+ },
+ [0x2CA5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA5,
+ },
+ [0x2CA6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA6,
+ },
+ [0x2CA7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA7,
+ },
+ [0x2CA8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA8,
+ },
+ [0x2CA9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CA9,
+ },
+ [0x2CAA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CAA,
+ },
+ [0x2CAB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CAB,
+ },
+ [0x2CAC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CAC,
+ },
+ [0x2CAD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CAD,
+ },
+ [0x2CAE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CAE,
+ },
+ [0x2CAF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CAF,
+ },
+ [0x2CB0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB0,
+ },
+ [0x2CB1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB1,
+ },
+ [0x2CB2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB2,
+ },
+ [0x2CB3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB3,
+ },
+ [0x2CB4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB4,
+ },
+ [0x2CB5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB5,
+ },
+ [0x2CB6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB6,
+ },
+ [0x2CB7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB7,
+ },
+ [0x2CB8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB8,
+ },
+ [0x2CB9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CB9,
+ },
+ [0x2CBA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CBA,
+ },
+ [0x2CBB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CBB,
+ },
+ [0x2CBC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CBC,
+ },
+ [0x2CBD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CBD,
+ },
+ [0x2CBE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CBE,
+ },
+ [0x2CBF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CBF,
+ },
+ [0x2CC0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC0,
+ },
+ [0x2CC1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC1,
+ },
+ [0x2CC2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC2,
+ },
+ [0x2CC3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC3,
+ },
+ [0x2CC4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC4,
+ },
+ [0x2CC5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC5,
+ },
+ [0x2CC6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC6,
+ },
+ [0x2CC7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC7,
+ },
+ [0x2CC8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC8,
+ },
+ [0x2CC9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CC9,
+ },
+ [0x2CCA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CCA,
+ },
+ [0x2CCB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CCB,
+ },
+ [0x2CCC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CCC,
+ },
+ [0x2CCD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CCD,
+ },
+ [0x2CCE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CCE,
+ },
+ [0x2CCF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CCF,
+ },
+ [0x2CD0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD0,
+ },
+ [0x2CD1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD1,
+ },
+ [0x2CD2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD2,
+ },
+ [0x2CD3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD3,
+ },
+ [0x2CD4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD4,
+ },
+ [0x2CD5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD5,
+ },
+ [0x2CD6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD6,
+ },
+ [0x2CD7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD7,
+ },
+ [0x2CD8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD8,
+ },
+ [0x2CD9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CD9,
+ },
+ [0x2CDA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CDA,
+ },
+ [0x2CDB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CDB,
+ },
+ [0x2CDC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CDC,
+ },
+ [0x2CDD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CDD,
+ },
+ [0x2CDE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CDE,
+ },
+ [0x2CDF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CDF,
+ },
+ [0x2CE0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CE0,
+ },
+ [0x2CE1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CE1,
+ },
+ [0x2CE2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CE2,
+ },
+ [0x2CE3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CE3,
+ },
+ [0x2CE4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CE4,
+ },
+ [0x2CE5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CE5,
+ },
+ [0x2CE6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CE6,
+ },
+ [0x2CE7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CE7,
+ },
+ [0x2CE8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CE8,
+ },
+ [0x2CE9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CE9,
+ },
+ [0x2CEA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CEA,
+ },
+ [0x2CEB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CEB,
+ },
+ [0x2CEC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CEC,
+ },
+ [0x2CED]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CED,
+ },
+ [0x2CEE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CEE,
+ },
+ [0x2CEF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2CEF,
+ },
+ [0x2CF0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2CF0,
+ },
+ [0x2CF1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2CF1,
+ },
+ [0x2CF2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CF2,
+ },
+ [0x2CF3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2CF3,
+ },
+ [0x2CF9]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x2CF9,
+ },
+ [0x2CFA]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2CFA,
+ },
+ [0x2CFB]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2CFB,
+ },
+ [0x2CFC]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2CFC,
+ },
+ [0x2CFD]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2CFD,
+ },
+ [0x2CFE]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x2CFE,
+ },
+ [0x2CFF]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2CFF,
+ },
+ [0x2D00]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D00,
+ },
+ [0x2D01]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D01,
+ },
+ [0x2D02]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D02,
+ },
+ [0x2D03]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D03,
+ },
+ [0x2D04]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D04,
+ },
+ [0x2D05]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D05,
+ },
+ [0x2D06]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D06,
+ },
+ [0x2D07]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D07,
+ },
+ [0x2D08]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D08,
+ },
+ [0x2D09]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D09,
+ },
+ [0x2D0A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D0A,
+ },
+ [0x2D0B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D0B,
+ },
+ [0x2D0C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D0C,
+ },
+ [0x2D0D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D0D,
+ },
+ [0x2D0E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D0E,
+ },
+ [0x2D0F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D0F,
+ },
+ [0x2D10]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D10,
+ },
+ [0x2D11]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D11,
+ },
+ [0x2D12]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D12,
+ },
+ [0x2D13]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D13,
+ },
+ [0x2D14]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D14,
+ },
+ [0x2D15]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D15,
+ },
+ [0x2D16]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D16,
+ },
+ [0x2D17]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D17,
+ },
+ [0x2D18]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D18,
+ },
+ [0x2D19]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D19,
+ },
+ [0x2D1A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1A,
+ },
+ [0x2D1B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1B,
+ },
+ [0x2D1C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1C,
+ },
+ [0x2D1D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1D,
+ },
+ [0x2D1E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1E,
+ },
+ [0x2D1F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D1F,
+ },
+ [0x2D20]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D20,
+ },
+ [0x2D21]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D21,
+ },
+ [0x2D22]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D22,
+ },
+ [0x2D23]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D23,
+ },
+ [0x2D24]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D24,
+ },
+ [0x2D25]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D25,
+ },
+ [0x2D27]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D27,
+ },
+ [0x2D2D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D2D,
+ },
+ [0x2D30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D30,
+ },
+ [0x2D31]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D31,
+ },
+ [0x2D32]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D32,
+ },
+ [0x2D33]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D33,
+ },
+ [0x2D34]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D34,
+ },
+ [0x2D35]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D35,
+ },
+ [0x2D36]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D36,
+ },
+ [0x2D37]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D37,
+ },
+ [0x2D38]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D38,
+ },
+ [0x2D39]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D39,
+ },
+ [0x2D3A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D3A,
+ },
+ [0x2D3B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D3B,
+ },
+ [0x2D3C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D3C,
+ },
+ [0x2D3D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D3D,
+ },
+ [0x2D3E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D3E,
+ },
+ [0x2D3F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D3F,
+ },
+ [0x2D40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D40,
+ },
+ [0x2D41]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D41,
+ },
+ [0x2D42]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D42,
+ },
+ [0x2D43]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D43,
+ },
+ [0x2D44]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D44,
+ },
+ [0x2D45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D45,
+ },
+ [0x2D46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D46,
+ },
+ [0x2D47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D47,
+ },
+ [0x2D48]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D48,
+ },
+ [0x2D49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D49,
+ },
+ [0x2D4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D4A,
+ },
+ [0x2D4B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D4B,
+ },
+ [0x2D4C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D4C,
+ },
+ [0x2D4D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D4D,
+ },
+ [0x2D4E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D4E,
+ },
+ [0x2D4F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D4F,
+ },
+ [0x2D50]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D50,
+ },
+ [0x2D51]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D51,
+ },
+ [0x2D52]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D52,
+ },
+ [0x2D53]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D53,
+ },
+ [0x2D54]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D54,
+ },
+ [0x2D55]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D55,
+ },
+ [0x2D56]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D56,
+ },
+ [0x2D57]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D57,
+ },
+ [0x2D58]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D58,
+ },
+ [0x2D59]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D59,
+ },
+ [0x2D5A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D5A,
+ },
+ [0x2D5B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D5B,
+ },
+ [0x2D5C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D5C,
+ },
+ [0x2D5D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D5D,
+ },
+ [0x2D5E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D5E,
+ },
+ [0x2D5F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D5F,
+ },
+ [0x2D60]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D60,
+ },
+ [0x2D61]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D61,
+ },
+ [0x2D62]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D62,
+ },
+ [0x2D63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D63,
+ },
+ [0x2D64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D64,
+ },
+ [0x2D65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D65,
+ },
+ [0x2D66]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D66,
+ },
+ [0x2D67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D67,
+ },
+ [0x2D6F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x2D61 },
+ unicodeslot=0x2D6F,
+ },
+ [0x2D70]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x2D70,
+ },
+ [0x2D7F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2D7F,
+ },
+ [0x2D80]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D80,
+ },
+ [0x2D81]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D81,
+ },
+ [0x2D82]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D82,
+ },
+ [0x2D83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D83,
+ },
+ [0x2D84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D84,
+ },
+ [0x2D85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D85,
+ },
+ [0x2D86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D86,
+ },
+ [0x2D87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D87,
+ },
+ [0x2D88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D88,
+ },
+ [0x2D89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D89,
+ },
+ [0x2D8A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D8A,
+ },
+ [0x2D8B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D8B,
+ },
+ [0x2D8C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D8C,
+ },
+ [0x2D8D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D8D,
+ },
+ [0x2D8E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D8E,
+ },
+ [0x2D8F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D8F,
+ },
+ [0x2D90]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D90,
+ },
+ [0x2D91]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D91,
+ },
+ [0x2D92]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D92,
+ },
+ [0x2D93]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D93,
+ },
+ [0x2D94]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D94,
+ },
+ [0x2D95]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D95,
+ },
+ [0x2D96]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2D96,
+ },
+ [0x2DA0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA0,
+ },
+ [0x2DA1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA1,
+ },
+ [0x2DA2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA2,
+ },
+ [0x2DA3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA3,
+ },
+ [0x2DA4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA4,
+ },
+ [0x2DA5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA5,
+ },
+ [0x2DA6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA6,
+ },
+ [0x2DA8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA8,
+ },
+ [0x2DA9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DA9,
+ },
+ [0x2DAA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DAA,
+ },
+ [0x2DAB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DAB,
+ },
+ [0x2DAC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DAC,
+ },
+ [0x2DAD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DAD,
+ },
+ [0x2DAE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DAE,
+ },
+ [0x2DB0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB0,
+ },
+ [0x2DB1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB1,
+ },
+ [0x2DB2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB2,
+ },
+ [0x2DB3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB3,
+ },
+ [0x2DB4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB4,
+ },
+ [0x2DB5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB5,
+ },
+ [0x2DB6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB6,
+ },
+ [0x2DB8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB8,
+ },
+ [0x2DB9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DB9,
+ },
+ [0x2DBA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DBA,
+ },
+ [0x2DBB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DBB,
+ },
+ [0x2DBC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DBC,
+ },
+ [0x2DBD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DBD,
+ },
+ [0x2DBE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DBE,
+ },
+ [0x2DC0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC0,
+ },
+ [0x2DC1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC1,
+ },
+ [0x2DC2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC2,
+ },
+ [0x2DC3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC3,
+ },
+ [0x2DC4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC4,
+ },
+ [0x2DC5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC5,
+ },
+ [0x2DC6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC6,
+ },
+ [0x2DC8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC8,
+ },
+ [0x2DC9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DC9,
+ },
+ [0x2DCA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DCA,
+ },
+ [0x2DCB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DCB,
+ },
+ [0x2DCC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DCC,
+ },
+ [0x2DCD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DCD,
+ },
+ [0x2DCE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DCE,
+ },
+ [0x2DD0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD0,
+ },
+ [0x2DD1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD1,
+ },
+ [0x2DD2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD2,
+ },
+ [0x2DD3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD3,
+ },
+ [0x2DD4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD4,
+ },
+ [0x2DD5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD5,
+ },
+ [0x2DD6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD6,
+ },
+ [0x2DD8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD8,
+ },
+ [0x2DD9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DD9,
+ },
+ [0x2DDA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DDA,
+ },
+ [0x2DDB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DDB,
+ },
+ [0x2DDC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DDC,
+ },
+ [0x2DDD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DDD,
+ },
+ [0x2DDE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x2DDE,
+ },
+ [0x2DE0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE0,
+ },
+ [0x2DE1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE1,
+ },
+ [0x2DE2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE2,
+ },
+ [0x2DE3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE3,
+ },
+ [0x2DE4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE4,
+ },
+ [0x2DE5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE5,
+ },
+ [0x2DE6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE6,
+ },
+ [0x2DE7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE7,
+ },
+ [0x2DE8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE8,
+ },
+ [0x2DE9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DE9,
+ },
+ [0x2DEA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DEA,
+ },
+ [0x2DEB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DEB,
+ },
+ [0x2DEC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DEC,
+ },
+ [0x2DED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DED,
+ },
+ [0x2DEE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DEE,
+ },
+ [0x2DEF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DEF,
+ },
+ [0x2DF0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF0,
+ },
+ [0x2DF1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF1,
+ },
+ [0x2DF2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF2,
+ },
+ [0x2DF3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF3,
+ },
+ [0x2DF4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF4,
+ },
+ [0x2DF5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF5,
+ },
+ [0x2DF6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF6,
+ },
+ [0x2DF7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF7,
+ },
+ [0x2DF8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF8,
+ },
+ [0x2DF9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DF9,
+ },
+ [0x2DFA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DFA,
+ },
+ [0x2DFB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DFB,
+ },
+ [0x2DFC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DFC,
+ },
+ [0x2DFD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DFD,
+ },
+ [0x2DFE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DFE,
+ },
+ [0x2DFF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x2DFF,
+ },
+ [0x2E00]={
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2E00,
+ },
+ [0x2E01]={
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2E01,
+ },
+ [0x2E02]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E03,
+ unicodeslot=0x2E02,
+ },
+ [0x2E03]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E02,
+ unicodeslot=0x2E03,
+ },
+ [0x2E04]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E05,
+ unicodeslot=0x2E04,
+ },
+ [0x2E05]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E04,
+ unicodeslot=0x2E05,
+ },
+ [0x2E06]={
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2E06,
+ },
+ [0x2E07]={
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2E07,
+ },
+ [0x2E08]={
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2E08,
+ },
+ [0x2E09]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E0A,
+ unicodeslot=0x2E09,
+ },
+ [0x2E0A]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E09,
+ unicodeslot=0x2E0A,
+ },
+ [0x2E0B]={
+ category="po",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x2E0B,
+ },
+ [0x2E0C]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E0D,
+ unicodeslot=0x2E0C,
+ },
+ [0x2E0D]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E0C,
+ unicodeslot=0x2E0D,
+ },
+ [0x2E0E]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E0E,
+ },
+ [0x2E0F]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E0F,
+ },
+ [0x2E10]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E10,
+ },
+ [0x2E11]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E11,
+ },
+ [0x2E12]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E12,
+ },
+ [0x2E13]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E13,
+ },
+ [0x2E14]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E14,
+ },
+ [0x2E15]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E15,
+ },
+ [0x2E16]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E16,
+ },
+ [0x2E17]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E17,
+ },
+ [0x2E18]={
+ category="po",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0x2E18,
+ },
+ [0x2E19]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E19,
+ },
+ [0x2E1A]={
+ category="pd",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E1A,
+ },
+ [0x2E1B]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E1B,
+ },
+ [0x2E1C]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E1D,
+ unicodeslot=0x2E1C,
+ },
+ [0x2E1D]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E1C,
+ unicodeslot=0x2E1D,
+ },
+ [0x2E1E]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E1E,
+ },
+ [0x2E1F]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E1F,
+ },
+ [0x2E20]={
+ category="pi",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E21,
+ unicodeslot=0x2E20,
+ },
+ [0x2E21]={
+ category="pf",
+ direction="on",
+ linebreak="qu",
+ mirror=0x2E20,
+ unicodeslot=0x2E21,
+ },
+ [0x2E22]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2E23,
+ unicodeslot=0x2E22,
+ },
+ [0x2E23]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2E22,
+ unicodeslot=0x2E23,
+ },
+ [0x2E24]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2E25,
+ unicodeslot=0x2E24,
+ },
+ [0x2E25]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2E24,
+ unicodeslot=0x2E25,
+ },
+ [0x2E26]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2E27,
+ unicodeslot=0x2E26,
+ },
+ [0x2E27]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2E26,
+ unicodeslot=0x2E27,
+ },
+ [0x2E28]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x2E29,
+ unicodeslot=0x2E28,
+ },
+ [0x2E29]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x2E28,
+ unicodeslot=0x2E29,
+ },
+ [0x2E2A]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E2A,
+ },
+ [0x2E2B]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E2B,
+ },
+ [0x2E2C]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E2C,
+ },
+ [0x2E2D]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E2D,
+ },
+ [0x2E2E]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0x2E2E,
+ },
+ [0x2E2F]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E2F,
+ },
+ [0x2E30]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E30,
+ },
+ [0x2E31]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E31,
+ },
+ [0x2E32]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E32,
+ },
+ [0x2E33]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E33,
+ },
+ [0x2E34]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E34,
+ },
+ [0x2E35]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E35,
+ },
+ [0x2E36]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E36,
+ },
+ [0x2E37]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E37,
+ },
+ [0x2E38]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E38,
+ },
+ [0x2E39]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E39,
+ },
+ [0x2E3A]={
+ category="pd",
+ direction="on",
+ linebreak="b2",
+ unicodeslot=0x2E3A,
+ },
+ [0x2E3B]={
+ category="pd",
+ direction="on",
+ linebreak="b2",
+ unicodeslot=0x2E3B,
+ },
+ [0x2E3C]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E3C,
+ },
+ [0x2E3D]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E3D,
+ },
+ [0x2E3E]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E3E,
+ },
+ [0x2E3F]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E3F,
+ },
+ [0x2E40]={
+ category="pd",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E40,
+ },
+ [0x2E41]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E41,
+ },
+ [0x2E42]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0x2E42,
+ },
+ [0x2E43]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E43,
+ },
+ [0x2E44]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E44,
+ },
+ [0x2E45]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E45,
+ },
+ [0x2E46]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E46,
+ },
+ [0x2E47]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E47,
+ },
+ [0x2E48]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E48,
+ },
+ [0x2E49]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E49,
+ },
+ [0x2E4A]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E4A,
+ },
+ [0x2E4B]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E4B,
+ },
+ [0x2E4C]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E4C,
+ },
+ [0x2E4D]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x2E4D,
+ },
+ [0x2E4E]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E4E,
+ },
+ [0x2E4F]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x2E4F,
+ },
+ [0x2E80]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E80,
+ },
+ [0x2E81]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E81,
+ },
+ [0x2E82]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E82,
+ },
+ [0x2E83]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E83,
+ },
+ [0x2E84]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E84,
+ },
+ [0x2E85]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E85,
+ },
+ [0x2E86]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E86,
+ },
+ [0x2E87]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E87,
+ },
+ [0x2E88]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E88,
+ },
+ [0x2E89]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E89,
+ },
+ [0x2E8A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E8A,
+ },
+ [0x2E8B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E8B,
+ },
+ [0x2E8C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E8C,
+ },
+ [0x2E8D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E8D,
+ },
+ [0x2E8E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E8E,
+ },
+ [0x2E8F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E8F,
+ },
+ [0x2E90]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E90,
+ },
+ [0x2E91]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E91,
+ },
+ [0x2E92]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E92,
+ },
+ [0x2E93]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E93,
+ },
+ [0x2E94]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E94,
+ },
+ [0x2E95]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E95,
+ },
+ [0x2E96]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E96,
+ },
+ [0x2E97]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E97,
+ },
+ [0x2E98]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E98,
+ },
+ [0x2E99]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E99,
+ },
+ [0x2E9B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E9B,
+ },
+ [0x2E9C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E9C,
+ },
+ [0x2E9D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E9D,
+ },
+ [0x2E9E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2E9E,
+ },
+ [0x2E9F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6BCD },
+ unicodeslot=0x2E9F,
+ },
+ [0x2EA0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA0,
+ },
+ [0x2EA1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA1,
+ },
+ [0x2EA2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA2,
+ },
+ [0x2EA3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA3,
+ },
+ [0x2EA4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA4,
+ },
+ [0x2EA5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA5,
+ },
+ [0x2EA6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA6,
+ },
+ [0x2EA7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA7,
+ },
+ [0x2EA8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA8,
+ },
+ [0x2EA9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EA9,
+ },
+ [0x2EAA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EAA,
+ },
+ [0x2EAB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EAB,
+ },
+ [0x2EAC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EAC,
+ },
+ [0x2EAD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EAD,
+ },
+ [0x2EAE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EAE,
+ },
+ [0x2EAF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EAF,
+ },
+ [0x2EB0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB0,
+ },
+ [0x2EB1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB1,
+ },
+ [0x2EB2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB2,
+ },
+ [0x2EB3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB3,
+ },
+ [0x2EB4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB4,
+ },
+ [0x2EB5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB5,
+ },
+ [0x2EB6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB6,
+ },
+ [0x2EB7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB7,
+ },
+ [0x2EB8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB8,
+ },
+ [0x2EB9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EB9,
+ },
+ [0x2EBA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EBA,
+ },
+ [0x2EBB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EBB,
+ },
+ [0x2EBC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EBC,
+ },
+ [0x2EBD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EBD,
+ },
+ [0x2EBE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EBE,
+ },
+ [0x2EBF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EBF,
+ },
+ [0x2EC0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC0,
+ },
+ [0x2EC1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC1,
+ },
+ [0x2EC2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC2,
+ },
+ [0x2EC3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC3,
+ },
+ [0x2EC4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC4,
+ },
+ [0x2EC5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC5,
+ },
+ [0x2EC6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC6,
+ },
+ [0x2EC7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC7,
+ },
+ [0x2EC8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC8,
+ },
+ [0x2EC9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EC9,
+ },
+ [0x2ECA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ECA,
+ },
+ [0x2ECB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ECB,
+ },
+ [0x2ECC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ECC,
+ },
+ [0x2ECD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ECD,
+ },
+ [0x2ECE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ECE,
+ },
+ [0x2ECF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ECF,
+ },
+ [0x2ED0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED0,
+ },
+ [0x2ED1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED1,
+ },
+ [0x2ED2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED2,
+ },
+ [0x2ED3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED3,
+ },
+ [0x2ED4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED4,
+ },
+ [0x2ED5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED5,
+ },
+ [0x2ED6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED6,
+ },
+ [0x2ED7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED7,
+ },
+ [0x2ED8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED8,
+ },
+ [0x2ED9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2ED9,
+ },
+ [0x2EDA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EDA,
+ },
+ [0x2EDB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EDB,
+ },
+ [0x2EDC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EDC,
+ },
+ [0x2EDD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EDD,
+ },
+ [0x2EDE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EDE,
+ },
+ [0x2EDF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EDF,
+ },
+ [0x2EE0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE0,
+ },
+ [0x2EE1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE1,
+ },
+ [0x2EE2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE2,
+ },
+ [0x2EE3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE3,
+ },
+ [0x2EE4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE4,
+ },
+ [0x2EE5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE5,
+ },
+ [0x2EE6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE6,
+ },
+ [0x2EE7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE7,
+ },
+ [0x2EE8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE8,
+ },
+ [0x2EE9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EE9,
+ },
+ [0x2EEA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EEA,
+ },
+ [0x2EEB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EEB,
+ },
+ [0x2EEC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EEC,
+ },
+ [0x2EED]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EED,
+ },
+ [0x2EEE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EEE,
+ },
+ [0x2EEF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EEF,
+ },
+ [0x2EF0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EF0,
+ },
+ [0x2EF1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EF1,
+ },
+ [0x2EF2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2EF2,
+ },
+ [0x2EF3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F9F },
+ unicodeslot=0x2EF3,
+ },
+ [0x2F00]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E00 },
+ unicodeslot=0x2F00,
+ },
+ [0x2F01]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E28 },
+ unicodeslot=0x2F01,
+ },
+ [0x2F02]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E36 },
+ unicodeslot=0x2F02,
+ },
+ [0x2F03]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E3F },
+ unicodeslot=0x2F03,
+ },
+ [0x2F04]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E59 },
+ unicodeslot=0x2F04,
+ },
+ [0x2F05]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E85 },
+ unicodeslot=0x2F05,
+ },
+ [0x2F06]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4E8C },
+ unicodeslot=0x2F06,
+ },
+ [0x2F07]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4EA0 },
+ unicodeslot=0x2F07,
+ },
+ [0x2F08]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x4EBA },
+ unicodeslot=0x2F08,
+ },
+ [0x2F09]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x513F },
+ unicodeslot=0x2F09,
+ },
+ [0x2F0A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5165 },
+ unicodeslot=0x2F0A,
+ },
+ [0x2F0B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x516B },
+ unicodeslot=0x2F0B,
+ },
+ [0x2F0C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5182 },
+ unicodeslot=0x2F0C,
+ },
+ [0x2F0D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5196 },
+ unicodeslot=0x2F0D,
+ },
+ [0x2F0E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x51AB },
+ unicodeslot=0x2F0E,
+ },
+ [0x2F0F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x51E0 },
+ unicodeslot=0x2F0F,
+ },
+ [0x2F10]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x51F5 },
+ unicodeslot=0x2F10,
+ },
+ [0x2F11]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5200 },
+ unicodeslot=0x2F11,
+ },
+ [0x2F12]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x529B },
+ unicodeslot=0x2F12,
+ },
+ [0x2F13]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x52F9 },
+ unicodeslot=0x2F13,
+ },
+ [0x2F14]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5315 },
+ unicodeslot=0x2F14,
+ },
+ [0x2F15]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x531A },
+ unicodeslot=0x2F15,
+ },
+ [0x2F16]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5338 },
+ unicodeslot=0x2F16,
+ },
+ [0x2F17]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5341 },
+ unicodeslot=0x2F17,
+ },
+ [0x2F18]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x535C },
+ unicodeslot=0x2F18,
+ },
+ [0x2F19]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5369 },
+ unicodeslot=0x2F19,
+ },
+ [0x2F1A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5382 },
+ unicodeslot=0x2F1A,
+ },
+ [0x2F1B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x53B6 },
+ unicodeslot=0x2F1B,
+ },
+ [0x2F1C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x53C8 },
+ unicodeslot=0x2F1C,
+ },
+ [0x2F1D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x53E3 },
+ unicodeslot=0x2F1D,
+ },
+ [0x2F1E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x56D7 },
+ unicodeslot=0x2F1E,
+ },
+ [0x2F1F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x571F },
+ unicodeslot=0x2F1F,
+ },
+ [0x2F20]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x58EB },
+ unicodeslot=0x2F20,
+ },
+ [0x2F21]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5902 },
+ unicodeslot=0x2F21,
+ },
+ [0x2F22]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x590A },
+ unicodeslot=0x2F22,
+ },
+ [0x2F23]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5915 },
+ unicodeslot=0x2F23,
+ },
+ [0x2F24]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5927 },
+ unicodeslot=0x2F24,
+ },
+ [0x2F25]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5973 },
+ unicodeslot=0x2F25,
+ },
+ [0x2F26]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5B50 },
+ unicodeslot=0x2F26,
+ },
+ [0x2F27]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5B80 },
+ unicodeslot=0x2F27,
+ },
+ [0x2F28]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5BF8 },
+ unicodeslot=0x2F28,
+ },
+ [0x2F29]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5C0F },
+ unicodeslot=0x2F29,
+ },
+ [0x2F2A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5C22 },
+ unicodeslot=0x2F2A,
+ },
+ [0x2F2B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5C38 },
+ unicodeslot=0x2F2B,
+ },
+ [0x2F2C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5C6E },
+ unicodeslot=0x2F2C,
+ },
+ [0x2F2D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5C71 },
+ unicodeslot=0x2F2D,
+ },
+ [0x2F2E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5DDB },
+ unicodeslot=0x2F2E,
+ },
+ [0x2F2F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5DE5 },
+ unicodeslot=0x2F2F,
+ },
+ [0x2F30]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5DF1 },
+ unicodeslot=0x2F30,
+ },
+ [0x2F31]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5DFE },
+ unicodeslot=0x2F31,
+ },
+ [0x2F32]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5E72 },
+ unicodeslot=0x2F32,
+ },
+ [0x2F33]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5E7A },
+ unicodeslot=0x2F33,
+ },
+ [0x2F34]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5E7F },
+ unicodeslot=0x2F34,
+ },
+ [0x2F35]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5EF4 },
+ unicodeslot=0x2F35,
+ },
+ [0x2F36]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5EFE },
+ unicodeslot=0x2F36,
+ },
+ [0x2F37]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F0B },
+ unicodeslot=0x2F37,
+ },
+ [0x2F38]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F13 },
+ unicodeslot=0x2F38,
+ },
+ [0x2F39]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F50 },
+ unicodeslot=0x2F39,
+ },
+ [0x2F3A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F61 },
+ unicodeslot=0x2F3A,
+ },
+ [0x2F3B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F73 },
+ unicodeslot=0x2F3B,
+ },
+ [0x2F3C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5FC3 },
+ unicodeslot=0x2F3C,
+ },
+ [0x2F3D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6208 },
+ unicodeslot=0x2F3D,
+ },
+ [0x2F3E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6236 },
+ unicodeslot=0x2F3E,
+ },
+ [0x2F3F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x624B },
+ unicodeslot=0x2F3F,
+ },
+ [0x2F40]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x652F },
+ unicodeslot=0x2F40,
+ },
+ [0x2F41]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6534 },
+ unicodeslot=0x2F41,
+ },
+ [0x2F42]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6587 },
+ unicodeslot=0x2F42,
+ },
+ [0x2F43]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6597 },
+ unicodeslot=0x2F43,
+ },
+ [0x2F44]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x65A4 },
+ unicodeslot=0x2F44,
+ },
+ [0x2F45]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x65B9 },
+ unicodeslot=0x2F45,
+ },
+ [0x2F46]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x65E0 },
+ unicodeslot=0x2F46,
+ },
+ [0x2F47]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x65E5 },
+ unicodeslot=0x2F47,
+ },
+ [0x2F48]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x66F0 },
+ unicodeslot=0x2F48,
+ },
+ [0x2F49]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6708 },
+ unicodeslot=0x2F49,
+ },
+ [0x2F4A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6728 },
+ unicodeslot=0x2F4A,
+ },
+ [0x2F4B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6B20 },
+ unicodeslot=0x2F4B,
+ },
+ [0x2F4C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6B62 },
+ unicodeslot=0x2F4C,
+ },
+ [0x2F4D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6B79 },
+ unicodeslot=0x2F4D,
+ },
+ [0x2F4E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6BB3 },
+ unicodeslot=0x2F4E,
+ },
+ [0x2F4F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6BCB },
+ unicodeslot=0x2F4F,
+ },
+ [0x2F50]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6BD4 },
+ unicodeslot=0x2F50,
+ },
+ [0x2F51]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6BDB },
+ unicodeslot=0x2F51,
+ },
+ [0x2F52]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6C0F },
+ unicodeslot=0x2F52,
+ },
+ [0x2F53]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6C14 },
+ unicodeslot=0x2F53,
+ },
+ [0x2F54]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x6C34 },
+ unicodeslot=0x2F54,
+ },
+ [0x2F55]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x706B },
+ unicodeslot=0x2F55,
+ },
+ [0x2F56]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x722A },
+ unicodeslot=0x2F56,
+ },
+ [0x2F57]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7236 },
+ unicodeslot=0x2F57,
+ },
+ [0x2F58]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x723B },
+ unicodeslot=0x2F58,
+ },
+ [0x2F59]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x723F },
+ unicodeslot=0x2F59,
+ },
+ [0x2F5A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7247 },
+ unicodeslot=0x2F5A,
+ },
+ [0x2F5B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7259 },
+ unicodeslot=0x2F5B,
+ },
+ [0x2F5C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x725B },
+ unicodeslot=0x2F5C,
+ },
+ [0x2F5D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x72AC },
+ unicodeslot=0x2F5D,
+ },
+ [0x2F5E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7384 },
+ unicodeslot=0x2F5E,
+ },
+ [0x2F5F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7389 },
+ unicodeslot=0x2F5F,
+ },
+ [0x2F60]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x74DC },
+ unicodeslot=0x2F60,
+ },
+ [0x2F61]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x74E6 },
+ unicodeslot=0x2F61,
+ },
+ [0x2F62]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7518 },
+ unicodeslot=0x2F62,
+ },
+ [0x2F63]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x751F },
+ unicodeslot=0x2F63,
+ },
+ [0x2F64]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7528 },
+ unicodeslot=0x2F64,
+ },
+ [0x2F65]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7530 },
+ unicodeslot=0x2F65,
+ },
+ [0x2F66]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x758B },
+ unicodeslot=0x2F66,
+ },
+ [0x2F67]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7592 },
+ unicodeslot=0x2F67,
+ },
+ [0x2F68]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7676 },
+ unicodeslot=0x2F68,
+ },
+ [0x2F69]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x767D },
+ unicodeslot=0x2F69,
+ },
+ [0x2F6A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x76AE },
+ unicodeslot=0x2F6A,
+ },
+ [0x2F6B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x76BF },
+ unicodeslot=0x2F6B,
+ },
+ [0x2F6C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x76EE },
+ unicodeslot=0x2F6C,
+ },
+ [0x2F6D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x77DB },
+ unicodeslot=0x2F6D,
+ },
+ [0x2F6E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x77E2 },
+ unicodeslot=0x2F6E,
+ },
+ [0x2F6F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x77F3 },
+ unicodeslot=0x2F6F,
+ },
+ [0x2F70]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x793A },
+ unicodeslot=0x2F70,
+ },
+ [0x2F71]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x79B8 },
+ unicodeslot=0x2F71,
+ },
+ [0x2F72]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x79BE },
+ unicodeslot=0x2F72,
+ },
+ [0x2F73]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7A74 },
+ unicodeslot=0x2F73,
+ },
+ [0x2F74]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7ACB },
+ unicodeslot=0x2F74,
+ },
+ [0x2F75]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7AF9 },
+ unicodeslot=0x2F75,
+ },
+ [0x2F76]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7C73 },
+ unicodeslot=0x2F76,
+ },
+ [0x2F77]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7CF8 },
+ unicodeslot=0x2F77,
+ },
+ [0x2F78]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7F36 },
+ unicodeslot=0x2F78,
+ },
+ [0x2F79]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7F51 },
+ unicodeslot=0x2F79,
+ },
+ [0x2F7A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7F8A },
+ unicodeslot=0x2F7A,
+ },
+ [0x2F7B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x7FBD },
+ unicodeslot=0x2F7B,
+ },
+ [0x2F7C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8001 },
+ unicodeslot=0x2F7C,
+ },
+ [0x2F7D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x800C },
+ unicodeslot=0x2F7D,
+ },
+ [0x2F7E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8012 },
+ unicodeslot=0x2F7E,
+ },
+ [0x2F7F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8033 },
+ unicodeslot=0x2F7F,
+ },
+ [0x2F80]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x807F },
+ unicodeslot=0x2F80,
+ },
+ [0x2F81]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8089 },
+ unicodeslot=0x2F81,
+ },
+ [0x2F82]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x81E3 },
+ unicodeslot=0x2F82,
+ },
+ [0x2F83]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x81EA },
+ unicodeslot=0x2F83,
+ },
+ [0x2F84]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x81F3 },
+ unicodeslot=0x2F84,
+ },
+ [0x2F85]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x81FC },
+ unicodeslot=0x2F85,
+ },
+ [0x2F86]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x820C },
+ unicodeslot=0x2F86,
+ },
+ [0x2F87]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x821B },
+ unicodeslot=0x2F87,
+ },
+ [0x2F88]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x821F },
+ unicodeslot=0x2F88,
+ },
+ [0x2F89]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x826E },
+ unicodeslot=0x2F89,
+ },
+ [0x2F8A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8272 },
+ unicodeslot=0x2F8A,
+ },
+ [0x2F8B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8278 },
+ unicodeslot=0x2F8B,
+ },
+ [0x2F8C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x864D },
+ unicodeslot=0x2F8C,
+ },
+ [0x2F8D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x866B },
+ unicodeslot=0x2F8D,
+ },
+ [0x2F8E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8840 },
+ unicodeslot=0x2F8E,
+ },
+ [0x2F8F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x884C },
+ unicodeslot=0x2F8F,
+ },
+ [0x2F90]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8863 },
+ unicodeslot=0x2F90,
+ },
+ [0x2F91]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x897E },
+ unicodeslot=0x2F91,
+ },
+ [0x2F92]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x898B },
+ unicodeslot=0x2F92,
+ },
+ [0x2F93]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x89D2 },
+ unicodeslot=0x2F93,
+ },
+ [0x2F94]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8A00 },
+ unicodeslot=0x2F94,
+ },
+ [0x2F95]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8C37 },
+ unicodeslot=0x2F95,
+ },
+ [0x2F96]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8C46 },
+ unicodeslot=0x2F96,
+ },
+ [0x2F97]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8C55 },
+ unicodeslot=0x2F97,
+ },
+ [0x2F98]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8C78 },
+ unicodeslot=0x2F98,
+ },
+ [0x2F99]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8C9D },
+ unicodeslot=0x2F99,
+ },
+ [0x2F9A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8D64 },
+ unicodeslot=0x2F9A,
+ },
+ [0x2F9B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8D70 },
+ unicodeslot=0x2F9B,
+ },
+ [0x2F9C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8DB3 },
+ unicodeslot=0x2F9C,
+ },
+ [0x2F9D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8EAB },
+ unicodeslot=0x2F9D,
+ },
+ [0x2F9E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8ECA },
+ unicodeslot=0x2F9E,
+ },
+ [0x2F9F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8F9B },
+ unicodeslot=0x2F9F,
+ },
+ [0x2FA0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8FB0 },
+ unicodeslot=0x2FA0,
+ },
+ [0x2FA1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x8FB5 },
+ unicodeslot=0x2FA1,
+ },
+ [0x2FA2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9091 },
+ unicodeslot=0x2FA2,
+ },
+ [0x2FA3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9149 },
+ unicodeslot=0x2FA3,
+ },
+ [0x2FA4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x91C6 },
+ unicodeslot=0x2FA4,
+ },
+ [0x2FA5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x91CC },
+ unicodeslot=0x2FA5,
+ },
+ [0x2FA6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x91D1 },
+ unicodeslot=0x2FA6,
+ },
+ [0x2FA7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9577 },
+ unicodeslot=0x2FA7,
+ },
+ [0x2FA8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9580 },
+ unicodeslot=0x2FA8,
+ },
+ [0x2FA9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x961C },
+ unicodeslot=0x2FA9,
+ },
+ [0x2FAA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x96B6 },
+ unicodeslot=0x2FAA,
+ },
+ [0x2FAB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x96B9 },
+ unicodeslot=0x2FAB,
+ },
+ [0x2FAC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x96E8 },
+ unicodeslot=0x2FAC,
+ },
+ [0x2FAD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9751 },
+ unicodeslot=0x2FAD,
+ },
+ [0x2FAE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x975E },
+ unicodeslot=0x2FAE,
+ },
+ [0x2FAF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9762 },
+ unicodeslot=0x2FAF,
+ },
+ [0x2FB0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9769 },
+ unicodeslot=0x2FB0,
+ },
+ [0x2FB1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x97CB },
+ unicodeslot=0x2FB1,
+ },
+ [0x2FB2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x97ED },
+ unicodeslot=0x2FB2,
+ },
+ [0x2FB3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x97F3 },
+ unicodeslot=0x2FB3,
+ },
+ [0x2FB4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9801 },
+ unicodeslot=0x2FB4,
+ },
+ [0x2FB5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x98A8 },
+ unicodeslot=0x2FB5,
+ },
+ [0x2FB6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x98DB },
+ unicodeslot=0x2FB6,
+ },
+ [0x2FB7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x98DF },
+ unicodeslot=0x2FB7,
+ },
+ [0x2FB8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9996 },
+ unicodeslot=0x2FB8,
+ },
+ [0x2FB9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9999 },
+ unicodeslot=0x2FB9,
+ },
+ [0x2FBA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x99AC },
+ unicodeslot=0x2FBA,
+ },
+ [0x2FBB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9AA8 },
+ unicodeslot=0x2FBB,
+ },
+ [0x2FBC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9AD8 },
+ unicodeslot=0x2FBC,
+ },
+ [0x2FBD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9ADF },
+ unicodeslot=0x2FBD,
+ },
+ [0x2FBE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9B25 },
+ unicodeslot=0x2FBE,
+ },
+ [0x2FBF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9B2F },
+ unicodeslot=0x2FBF,
+ },
+ [0x2FC0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9B32 },
+ unicodeslot=0x2FC0,
+ },
+ [0x2FC1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9B3C },
+ unicodeslot=0x2FC1,
+ },
+ [0x2FC2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9B5A },
+ unicodeslot=0x2FC2,
+ },
+ [0x2FC3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9CE5 },
+ unicodeslot=0x2FC3,
+ },
+ [0x2FC4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9E75 },
+ unicodeslot=0x2FC4,
+ },
+ [0x2FC5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9E7F },
+ unicodeslot=0x2FC5,
+ },
+ [0x2FC6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9EA5 },
+ unicodeslot=0x2FC6,
+ },
+ [0x2FC7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9EBB },
+ unicodeslot=0x2FC7,
+ },
+ [0x2FC8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9EC3 },
+ unicodeslot=0x2FC8,
+ },
+ [0x2FC9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9ECD },
+ unicodeslot=0x2FC9,
+ },
+ [0x2FCA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9ED1 },
+ unicodeslot=0x2FCA,
+ },
+ [0x2FCB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9EF9 },
+ unicodeslot=0x2FCB,
+ },
+ [0x2FCC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9EFD },
+ unicodeslot=0x2FCC,
+ },
+ [0x2FCD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F0E },
+ unicodeslot=0x2FCD,
+ },
+ [0x2FCE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F13 },
+ unicodeslot=0x2FCE,
+ },
+ [0x2FCF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F20 },
+ unicodeslot=0x2FCF,
+ },
+ [0x2FD0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F3B },
+ unicodeslot=0x2FD0,
+ },
+ [0x2FD1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F4A },
+ unicodeslot=0x2FD1,
+ },
+ [0x2FD2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F52 },
+ unicodeslot=0x2FD2,
+ },
+ [0x2FD3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F8D },
+ unicodeslot=0x2FD3,
+ },
+ [0x2FD4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9F9C },
+ unicodeslot=0x2FD4,
+ },
+ [0x2FD5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x9FA0 },
+ unicodeslot=0x2FD5,
+ },
+ [0x2FF0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF0,
+ },
+ [0x2FF1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF1,
+ },
+ [0x2FF2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF2,
+ },
+ [0x2FF3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF3,
+ },
+ [0x2FF4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF4,
+ },
+ [0x2FF5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF5,
+ },
+ [0x2FF6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF6,
+ },
+ [0x2FF7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF7,
+ },
+ [0x2FF8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF8,
+ },
+ [0x2FF9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FF9,
+ },
+ [0x2FFA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FFA,
+ },
+ [0x2FFB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x2FFB,
+ },
+ [0x3000]={
+ category="zs",
+ direction="ws",
+ linebreak="ba",
+ specials={ "wide", 0x20 },
+ unicodeslot=0x3000,
+ },
+ [0x3001]={
+ category="po",
+ direction="on",
+ linebreak="cl",
+ unicodeslot=0x3001,
+ },
+ [0x3002]={
+ category="po",
+ direction="on",
+ linebreak="cl",
+ unicodeslot=0x3002,
+ },
+ [0x3003]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3003,
+ },
+ [0x3004]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3004,
+ },
+ [0x3005]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x3005,
+ },
+ [0x3006]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3006,
+ },
+ [0x3007]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3007,
+ },
+ [0x3008]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x3009,
+ unicodeslot=0x3008,
+ },
+ [0x3009]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x3008,
+ unicodeslot=0x3009,
+ },
+ [0x300A]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x300B,
+ unicodeslot=0x300A,
+ },
+ [0x300B]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x300A,
+ unicodeslot=0x300B,
+ },
+ [0x300C]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x300D,
+ unicodeslot=0x300C,
+ },
+ [0x300D]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x300C,
+ unicodeslot=0x300D,
+ },
+ [0x300E]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x300F,
+ unicodeslot=0x300E,
+ },
+ [0x300F]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x300E,
+ unicodeslot=0x300F,
+ },
+ [0x3010]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x3011,
+ unicodeslot=0x3010,
+ },
+ [0x3011]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x3010,
+ unicodeslot=0x3011,
+ },
+ [0x3012]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3012,
+ },
+ [0x3013]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3013,
+ },
+ [0x3014]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x3015,
+ unicodeslot=0x3014,
+ },
+ [0x3015]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x3014,
+ unicodeslot=0x3015,
+ },
+ [0x3016]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x3017,
+ unicodeslot=0x3016,
+ },
+ [0x3017]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x3016,
+ unicodeslot=0x3017,
+ },
+ [0x3018]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x3019,
+ unicodeslot=0x3018,
+ },
+ [0x3019]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x3018,
+ unicodeslot=0x3019,
+ },
+ [0x301A]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0x301B,
+ unicodeslot=0x301A,
+ },
+ [0x301B]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0x301A,
+ unicodeslot=0x301B,
+ },
+ [0x301C]={
+ category="pd",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x301C,
+ },
+ [0x301D]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0x301D,
+ },
+ [0x301E]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ unicodeslot=0x301E,
+ },
+ [0x301F]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ unicodeslot=0x301F,
+ },
+ [0x3020]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3020,
+ },
+ [0x3021]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3021,
+ },
+ [0x3022]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3022,
+ },
+ [0x3023]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3023,
+ },
+ [0x3024]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3024,
+ },
+ [0x3025]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3025,
+ },
+ [0x3026]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3026,
+ },
+ [0x3027]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3027,
+ },
+ [0x3028]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3028,
+ },
+ [0x3029]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3029,
+ },
+ [0x302A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x302A,
+ },
+ [0x302B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x302B,
+ },
+ [0x302C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x302C,
+ },
+ [0x302D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x302D,
+ },
+ [0x302E]={
+ category="mn",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x302E,
+ },
+ [0x302F]={
+ category="mn",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x302F,
+ },
+ [0x3030]={
+ category="pd",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3030,
+ },
+ [0x3031]={
+ category="lm",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3031,
+ },
+ [0x3032]={
+ category="lm",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3032,
+ },
+ [0x3033]={
+ category="lm",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3033,
+ },
+ [0x3034]={
+ category="lm",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3034,
+ },
+ [0x3035]={
+ category="lm",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x3035,
+ },
+ [0x3036]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x3012 },
+ unicodeslot=0x3036,
+ },
+ [0x3037]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x3037,
+ },
+ [0x3038]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x5341 },
+ unicodeslot=0x3038,
+ },
+ [0x3039]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x5344 },
+ unicodeslot=0x3039,
+ },
+ [0x303A]={
+ category="nl",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x5345 },
+ unicodeslot=0x303A,
+ },
+ [0x303B]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x303B,
+ },
+ [0x303C]={
+ category="lo",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x303C,
+ },
+ [0x303D]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x303D,
+ },
+ [0x303E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x303E,
+ },
+ [0x303F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x303F,
+ },
+ [0x3041]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3041,
+ },
+ [0x3042]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3042,
+ },
+ [0x3043]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3043,
+ },
+ [0x3044]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3044,
+ },
+ [0x3045]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3045,
+ },
+ [0x3046]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3046,
+ },
+ [0x3047]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3047,
+ },
+ [0x3048]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3048,
+ },
+ [0x3049]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3049,
+ },
+ [0x304A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x304A,
+ },
+ [0x304B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x304B,
+ },
+ [0x304C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x304B, 0x3099 },
+ unicodeslot=0x304C,
+ },
+ [0x304D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x304D,
+ },
+ [0x304E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x304D, 0x3099 },
+ unicodeslot=0x304E,
+ },
+ [0x304F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x304F,
+ },
+ [0x3050]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x304F, 0x3099 },
+ unicodeslot=0x3050,
+ },
+ [0x3051]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3051,
+ },
+ [0x3052]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3051, 0x3099 },
+ unicodeslot=0x3052,
+ },
+ [0x3053]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3053,
+ },
+ [0x3054]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3053, 0x3099 },
+ unicodeslot=0x3054,
+ },
+ [0x3055]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3055,
+ },
+ [0x3056]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3055, 0x3099 },
+ unicodeslot=0x3056,
+ },
+ [0x3057]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3057,
+ },
+ [0x3058]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3057, 0x3099 },
+ unicodeslot=0x3058,
+ },
+ [0x3059]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3059,
+ },
+ [0x305A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3059, 0x3099 },
+ unicodeslot=0x305A,
+ },
+ [0x305B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x305B,
+ },
+ [0x305C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x305B, 0x3099 },
+ unicodeslot=0x305C,
+ },
+ [0x305D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x305D,
+ },
+ [0x305E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x305D, 0x3099 },
+ unicodeslot=0x305E,
+ },
+ [0x305F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x305F,
+ },
+ [0x3060]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x305F, 0x3099 },
+ unicodeslot=0x3060,
+ },
+ [0x3061]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3061,
+ },
+ [0x3062]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3061, 0x3099 },
+ unicodeslot=0x3062,
+ },
+ [0x3063]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3063,
+ },
+ [0x3064]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3064,
+ },
+ [0x3065]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3064, 0x3099 },
+ unicodeslot=0x3065,
+ },
+ [0x3066]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3066,
+ },
+ [0x3067]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3066, 0x3099 },
+ unicodeslot=0x3067,
+ },
+ [0x3068]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3068,
+ },
+ [0x3069]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3068, 0x3099 },
+ unicodeslot=0x3069,
+ },
+ [0x306A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x306A,
+ },
+ [0x306B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x306B,
+ },
+ [0x306C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x306C,
+ },
+ [0x306D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x306D,
+ },
+ [0x306E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x306E,
+ },
+ [0x306F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x306F,
+ },
+ [0x3070]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x306F, 0x3099 },
+ unicodeslot=0x3070,
+ },
+ [0x3071]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x306F, 0x309A },
+ unicodeslot=0x3071,
+ },
+ [0x3072]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3072,
+ },
+ [0x3073]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3072, 0x3099 },
+ unicodeslot=0x3073,
+ },
+ [0x3074]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3072, 0x309A },
+ unicodeslot=0x3074,
+ },
+ [0x3075]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3075,
+ },
+ [0x3076]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3075, 0x3099 },
+ unicodeslot=0x3076,
+ },
+ [0x3077]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3075, 0x309A },
+ unicodeslot=0x3077,
+ },
+ [0x3078]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3078,
+ },
+ [0x3079]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3078, 0x3099 },
+ unicodeslot=0x3079,
+ },
+ [0x307A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3078, 0x309A },
+ unicodeslot=0x307A,
+ },
+ [0x307B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x307B,
+ },
+ [0x307C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x307B, 0x3099 },
+ unicodeslot=0x307C,
+ },
+ [0x307D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x307B, 0x309A },
+ unicodeslot=0x307D,
+ },
+ [0x307E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x307E,
+ },
+ [0x307F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x307F,
+ },
+ [0x3080]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3080,
+ },
+ [0x3081]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3081,
+ },
+ [0x3082]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3082,
+ },
+ [0x3083]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3083,
+ },
+ [0x3084]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3084,
+ },
+ [0x3085]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3085,
+ },
+ [0x3086]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3086,
+ },
+ [0x3087]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3087,
+ },
+ [0x3088]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3088,
+ },
+ [0x3089]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3089,
+ },
+ [0x308A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x308A,
+ },
+ [0x308B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x308B,
+ },
+ [0x308C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x308C,
+ },
+ [0x308D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x308D,
+ },
+ [0x308E]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x308E,
+ },
+ [0x308F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x308F,
+ },
+ [0x3090]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3090,
+ },
+ [0x3091]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3091,
+ },
+ [0x3092]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3092,
+ },
+ [0x3093]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3093,
+ },
+ [0x3094]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3046, 0x3099 },
+ unicodeslot=0x3094,
+ },
+ [0x3095]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3095,
+ },
+ [0x3096]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x3096,
+ },
+ [0x3099]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x3099,
+ },
+ [0x309A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x309A,
+ },
+ [0x309B]={
+ category="sk",
+ direction="on",
+ linebreak="ns",
+ specials={ "compat", 0x20, 0x3099 },
+ unicodeslot=0x309B,
+ },
+ [0x309C]={
+ category="sk",
+ direction="on",
+ linebreak="ns",
+ specials={ "compat", 0x20, 0x309A },
+ unicodeslot=0x309C,
+ },
+ [0x309D]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x309D,
+ },
+ [0x309E]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ specials={ "char", 0x309D, 0x3099 },
+ unicodeslot=0x309E,
+ },
+ [0x309F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "vertical", 0x3088, 0x308A },
+ unicodeslot=0x309F,
+ },
+ [0x30A0]={
+ category="pd",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x30A0,
+ },
+ [0x30A1]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30A1,
+ },
+ [0x30A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30A2,
+ },
+ [0x30A3]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30A3,
+ },
+ [0x30A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30A4,
+ },
+ [0x30A5]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30A5,
+ },
+ [0x30A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30A6,
+ },
+ [0x30A7]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30A7,
+ },
+ [0x30A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30A8,
+ },
+ [0x30A9]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30A9,
+ },
+ [0x30AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30AA,
+ },
+ [0x30AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30AB,
+ },
+ [0x30AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30AB, 0x3099 },
+ unicodeslot=0x30AC,
+ },
+ [0x30AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30AD,
+ },
+ [0x30AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30AD, 0x3099 },
+ unicodeslot=0x30AE,
+ },
+ [0x30AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30AF,
+ },
+ [0x30B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30AF, 0x3099 },
+ unicodeslot=0x30B0,
+ },
+ [0x30B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30B1,
+ },
+ [0x30B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30B1, 0x3099 },
+ unicodeslot=0x30B2,
+ },
+ [0x30B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30B3,
+ },
+ [0x30B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30B3, 0x3099 },
+ unicodeslot=0x30B4,
+ },
+ [0x30B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30B5,
+ },
+ [0x30B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30B5, 0x3099 },
+ unicodeslot=0x30B6,
+ },
+ [0x30B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30B7,
+ },
+ [0x30B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30B7, 0x3099 },
+ unicodeslot=0x30B8,
+ },
+ [0x30B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30B9,
+ },
+ [0x30BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30B9, 0x3099 },
+ unicodeslot=0x30BA,
+ },
+ [0x30BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30BB,
+ },
+ [0x30BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30BB, 0x3099 },
+ unicodeslot=0x30BC,
+ },
+ [0x30BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30BD,
+ },
+ [0x30BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30BD, 0x3099 },
+ unicodeslot=0x30BE,
+ },
+ [0x30BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30BF,
+ },
+ [0x30C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30BF, 0x3099 },
+ unicodeslot=0x30C0,
+ },
+ [0x30C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30C1,
+ },
+ [0x30C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30C1, 0x3099 },
+ unicodeslot=0x30C2,
+ },
+ [0x30C3]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30C3,
+ },
+ [0x30C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30C4,
+ },
+ [0x30C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30C4, 0x3099 },
+ unicodeslot=0x30C5,
+ },
+ [0x30C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30C6,
+ },
+ [0x30C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30C6, 0x3099 },
+ unicodeslot=0x30C7,
+ },
+ [0x30C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30C8,
+ },
+ [0x30C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30C8, 0x3099 },
+ unicodeslot=0x30C9,
+ },
+ [0x30CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30CA,
+ },
+ [0x30CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30CB,
+ },
+ [0x30CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30CC,
+ },
+ [0x30CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30CD,
+ },
+ [0x30CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30CE,
+ },
+ [0x30CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30CF,
+ },
+ [0x30D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30CF, 0x3099 },
+ unicodeslot=0x30D0,
+ },
+ [0x30D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30CF, 0x309A },
+ unicodeslot=0x30D1,
+ },
+ [0x30D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30D2,
+ },
+ [0x30D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30D2, 0x3099 },
+ unicodeslot=0x30D3,
+ },
+ [0x30D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30D2, 0x309A },
+ unicodeslot=0x30D4,
+ },
+ [0x30D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30D5,
+ },
+ [0x30D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30D5, 0x3099 },
+ unicodeslot=0x30D6,
+ },
+ [0x30D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30D5, 0x309A },
+ unicodeslot=0x30D7,
+ },
+ [0x30D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30D8,
+ },
+ [0x30D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30D8, 0x3099 },
+ unicodeslot=0x30D9,
+ },
+ [0x30DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30D8, 0x309A },
+ unicodeslot=0x30DA,
+ },
+ [0x30DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30DB,
+ },
+ [0x30DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30DB, 0x3099 },
+ unicodeslot=0x30DC,
+ },
+ [0x30DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30DB, 0x309A },
+ unicodeslot=0x30DD,
+ },
+ [0x30DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30DE,
+ },
+ [0x30DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30DF,
+ },
+ [0x30E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E0,
+ },
+ [0x30E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E1,
+ },
+ [0x30E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E2,
+ },
+ [0x30E3]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30E3,
+ },
+ [0x30E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E4,
+ },
+ [0x30E5]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30E5,
+ },
+ [0x30E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E6,
+ },
+ [0x30E7]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30E7,
+ },
+ [0x30E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E8,
+ },
+ [0x30E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30E9,
+ },
+ [0x30EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30EA,
+ },
+ [0x30EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30EB,
+ },
+ [0x30EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30EC,
+ },
+ [0x30ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30ED,
+ },
+ [0x30EE]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30EE,
+ },
+ [0x30EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30EF,
+ },
+ [0x30F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30F0,
+ },
+ [0x30F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30F1,
+ },
+ [0x30F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30F2,
+ },
+ [0x30F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x30F3,
+ },
+ [0x30F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30A6, 0x3099 },
+ unicodeslot=0x30F4,
+ },
+ [0x30F5]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30F5,
+ },
+ [0x30F6]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30F6,
+ },
+ [0x30F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30EF, 0x3099 },
+ unicodeslot=0x30F7,
+ },
+ [0x30F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30F0, 0x3099 },
+ unicodeslot=0x30F8,
+ },
+ [0x30F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30F1, 0x3099 },
+ unicodeslot=0x30F9,
+ },
+ [0x30FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x30F2, 0x3099 },
+ unicodeslot=0x30FA,
+ },
+ [0x30FB]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x30FB,
+ },
+ [0x30FC]={
+ category="lm",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x30FC,
+ },
+ [0x30FD]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x30FD,
+ },
+ [0x30FE]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ specials={ "char", 0x30FD, 0x3099 },
+ unicodeslot=0x30FE,
+ },
+ [0x30FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "vertical", 0x30B3, 0x30C8 },
+ unicodeslot=0x30FF,
+ },
+ [0x3105]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3105,
+ },
+ [0x3106]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3106,
+ },
+ [0x3107]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3107,
+ },
+ [0x3108]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3108,
+ },
+ [0x3109]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3109,
+ },
+ [0x310A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x310A,
+ },
+ [0x310B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x310B,
+ },
+ [0x310C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x310C,
+ },
+ [0x310D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x310D,
+ },
+ [0x310E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x310E,
+ },
+ [0x310F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x310F,
+ },
+ [0x3110]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3110,
+ },
+ [0x3111]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3111,
+ },
+ [0x3112]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3112,
+ },
+ [0x3113]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3113,
+ },
+ [0x3114]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3114,
+ },
+ [0x3115]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3115,
+ },
+ [0x3116]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3116,
+ },
+ [0x3117]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3117,
+ },
+ [0x3118]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3118,
+ },
+ [0x3119]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3119,
+ },
+ [0x311A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x311A,
+ },
+ [0x311B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x311B,
+ },
+ [0x311C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x311C,
+ },
+ [0x311D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x311D,
+ },
+ [0x311E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x311E,
+ },
+ [0x311F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x311F,
+ },
+ [0x3120]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3120,
+ },
+ [0x3121]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3121,
+ },
+ [0x3122]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3122,
+ },
+ [0x3123]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3123,
+ },
+ [0x3124]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3124,
+ },
+ [0x3125]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3125,
+ },
+ [0x3126]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3126,
+ },
+ [0x3127]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3127,
+ },
+ [0x3128]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3128,
+ },
+ [0x3129]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3129,
+ },
+ [0x312A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x312A,
+ },
+ [0x312B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x312B,
+ },
+ [0x312C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x312C,
+ },
+ [0x312D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x312D,
+ },
+ [0x312E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x312E,
+ },
+ [0x312F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x312F,
+ },
+ [0x3131]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1100 },
+ unicodeslot=0x3131,
+ },
+ [0x3132]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1101 },
+ unicodeslot=0x3132,
+ },
+ [0x3133]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11AA },
+ unicodeslot=0x3133,
+ },
+ [0x3134]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1102 },
+ unicodeslot=0x3134,
+ },
+ [0x3135]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11AC },
+ unicodeslot=0x3135,
+ },
+ [0x3136]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11AD },
+ unicodeslot=0x3136,
+ },
+ [0x3137]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1103 },
+ unicodeslot=0x3137,
+ },
+ [0x3138]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1104 },
+ unicodeslot=0x3138,
+ },
+ [0x3139]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1105 },
+ unicodeslot=0x3139,
+ },
+ [0x313A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11B0 },
+ unicodeslot=0x313A,
+ },
+ [0x313B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11B1 },
+ unicodeslot=0x313B,
+ },
+ [0x313C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11B2 },
+ unicodeslot=0x313C,
+ },
+ [0x313D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11B3 },
+ unicodeslot=0x313D,
+ },
+ [0x313E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11B4 },
+ unicodeslot=0x313E,
+ },
+ [0x313F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11B5 },
+ unicodeslot=0x313F,
+ },
+ [0x3140]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x111A },
+ unicodeslot=0x3140,
+ },
+ [0x3141]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1106 },
+ unicodeslot=0x3141,
+ },
+ [0x3142]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1107 },
+ unicodeslot=0x3142,
+ },
+ [0x3143]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1108 },
+ unicodeslot=0x3143,
+ },
+ [0x3144]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1121 },
+ unicodeslot=0x3144,
+ },
+ [0x3145]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1109 },
+ unicodeslot=0x3145,
+ },
+ [0x3146]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x110A },
+ unicodeslot=0x3146,
+ },
+ [0x3147]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x110B },
+ unicodeslot=0x3147,
+ },
+ [0x3148]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x110C },
+ unicodeslot=0x3148,
+ },
+ [0x3149]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x110D },
+ unicodeslot=0x3149,
+ },
+ [0x314A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x110E },
+ unicodeslot=0x314A,
+ },
+ [0x314B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x110F },
+ unicodeslot=0x314B,
+ },
+ [0x314C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1110 },
+ unicodeslot=0x314C,
+ },
+ [0x314D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1111 },
+ unicodeslot=0x314D,
+ },
+ [0x314E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1112 },
+ unicodeslot=0x314E,
+ },
+ [0x314F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1161 },
+ unicodeslot=0x314F,
+ },
+ [0x3150]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1162 },
+ unicodeslot=0x3150,
+ },
+ [0x3151]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1163 },
+ unicodeslot=0x3151,
+ },
+ [0x3152]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1164 },
+ unicodeslot=0x3152,
+ },
+ [0x3153]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1165 },
+ unicodeslot=0x3153,
+ },
+ [0x3154]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1166 },
+ unicodeslot=0x3154,
+ },
+ [0x3155]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1167 },
+ unicodeslot=0x3155,
+ },
+ [0x3156]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1168 },
+ unicodeslot=0x3156,
+ },
+ [0x3157]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1169 },
+ unicodeslot=0x3157,
+ },
+ [0x3158]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x116A },
+ unicodeslot=0x3158,
+ },
+ [0x3159]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x116B },
+ unicodeslot=0x3159,
+ },
+ [0x315A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x116C },
+ unicodeslot=0x315A,
+ },
+ [0x315B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x116D },
+ unicodeslot=0x315B,
+ },
+ [0x315C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x116E },
+ unicodeslot=0x315C,
+ },
+ [0x315D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x116F },
+ unicodeslot=0x315D,
+ },
+ [0x315E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1170 },
+ unicodeslot=0x315E,
+ },
+ [0x315F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1171 },
+ unicodeslot=0x315F,
+ },
+ [0x3160]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1172 },
+ unicodeslot=0x3160,
+ },
+ [0x3161]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1173 },
+ unicodeslot=0x3161,
+ },
+ [0x3162]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1174 },
+ unicodeslot=0x3162,
+ },
+ [0x3163]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1175 },
+ unicodeslot=0x3163,
+ },
+ [0x3164]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1160 },
+ unicodeslot=0x3164,
+ },
+ [0x3165]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1114 },
+ unicodeslot=0x3165,
+ },
+ [0x3166]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1115 },
+ unicodeslot=0x3166,
+ },
+ [0x3167]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11C7 },
+ unicodeslot=0x3167,
+ },
+ [0x3168]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11C8 },
+ unicodeslot=0x3168,
+ },
+ [0x3169]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11CC },
+ unicodeslot=0x3169,
+ },
+ [0x316A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11CE },
+ unicodeslot=0x316A,
+ },
+ [0x316B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11D3 },
+ unicodeslot=0x316B,
+ },
+ [0x316C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11D7 },
+ unicodeslot=0x316C,
+ },
+ [0x316D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11D9 },
+ unicodeslot=0x316D,
+ },
+ [0x316E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x111C },
+ unicodeslot=0x316E,
+ },
+ [0x316F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11DD },
+ unicodeslot=0x316F,
+ },
+ [0x3170]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11DF },
+ unicodeslot=0x3170,
+ },
+ [0x3171]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x111D },
+ unicodeslot=0x3171,
+ },
+ [0x3172]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x111E },
+ unicodeslot=0x3172,
+ },
+ [0x3173]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1120 },
+ unicodeslot=0x3173,
+ },
+ [0x3174]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1122 },
+ unicodeslot=0x3174,
+ },
+ [0x3175]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1123 },
+ unicodeslot=0x3175,
+ },
+ [0x3176]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1127 },
+ unicodeslot=0x3176,
+ },
+ [0x3177]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1129 },
+ unicodeslot=0x3177,
+ },
+ [0x3178]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x112B },
+ unicodeslot=0x3178,
+ },
+ [0x3179]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x112C },
+ unicodeslot=0x3179,
+ },
+ [0x317A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x112D },
+ unicodeslot=0x317A,
+ },
+ [0x317B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x112E },
+ unicodeslot=0x317B,
+ },
+ [0x317C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x112F },
+ unicodeslot=0x317C,
+ },
+ [0x317D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1132 },
+ unicodeslot=0x317D,
+ },
+ [0x317E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1136 },
+ unicodeslot=0x317E,
+ },
+ [0x317F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1140 },
+ unicodeslot=0x317F,
+ },
+ [0x3180]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1147 },
+ unicodeslot=0x3180,
+ },
+ [0x3181]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x114C },
+ unicodeslot=0x3181,
+ },
+ [0x3182]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11F1 },
+ unicodeslot=0x3182,
+ },
+ [0x3183]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11F2 },
+ unicodeslot=0x3183,
+ },
+ [0x3184]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1157 },
+ unicodeslot=0x3184,
+ },
+ [0x3185]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1158 },
+ unicodeslot=0x3185,
+ },
+ [0x3186]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1159 },
+ unicodeslot=0x3186,
+ },
+ [0x3187]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1184 },
+ unicodeslot=0x3187,
+ },
+ [0x3188]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1185 },
+ unicodeslot=0x3188,
+ },
+ [0x3189]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1188 },
+ unicodeslot=0x3189,
+ },
+ [0x318A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1191 },
+ unicodeslot=0x318A,
+ },
+ [0x318B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1192 },
+ unicodeslot=0x318B,
+ },
+ [0x318C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x1194 },
+ unicodeslot=0x318C,
+ },
+ [0x318D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x119E },
+ unicodeslot=0x318D,
+ },
+ [0x318E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x11A1 },
+ unicodeslot=0x318E,
+ },
+ [0x3190]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3190,
+ },
+ [0x3191]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x3191,
+ },
+ [0x3192]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E00 },
+ unicodeslot=0x3192,
+ },
+ [0x3193]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E8C },
+ unicodeslot=0x3193,
+ },
+ [0x3194]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E09 },
+ unicodeslot=0x3194,
+ },
+ [0x3195]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x56DB },
+ unicodeslot=0x3195,
+ },
+ [0x3196]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E0A },
+ unicodeslot=0x3196,
+ },
+ [0x3197]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E2D },
+ unicodeslot=0x3197,
+ },
+ [0x3198]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E0B },
+ unicodeslot=0x3198,
+ },
+ [0x3199]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x7532 },
+ unicodeslot=0x3199,
+ },
+ [0x319A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E59 },
+ unicodeslot=0x319A,
+ },
+ [0x319B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E19 },
+ unicodeslot=0x319B,
+ },
+ [0x319C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4E01 },
+ unicodeslot=0x319C,
+ },
+ [0x319D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x5929 },
+ unicodeslot=0x319D,
+ },
+ [0x319E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x5730 },
+ unicodeslot=0x319E,
+ },
+ [0x319F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "super", 0x4EBA },
+ unicodeslot=0x319F,
+ },
+ [0x31A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A0,
+ },
+ [0x31A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A1,
+ },
+ [0x31A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A2,
+ },
+ [0x31A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A3,
+ },
+ [0x31A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A4,
+ },
+ [0x31A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A5,
+ },
+ [0x31A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A6,
+ },
+ [0x31A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A7,
+ },
+ [0x31A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A8,
+ },
+ [0x31A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31A9,
+ },
+ [0x31AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31AA,
+ },
+ [0x31AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31AB,
+ },
+ [0x31AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31AC,
+ },
+ [0x31AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31AD,
+ },
+ [0x31AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31AE,
+ },
+ [0x31AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31AF,
+ },
+ [0x31B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B0,
+ },
+ [0x31B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B1,
+ },
+ [0x31B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B2,
+ },
+ [0x31B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B3,
+ },
+ [0x31B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B4,
+ },
+ [0x31B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B5,
+ },
+ [0x31B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B6,
+ },
+ [0x31B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B7,
+ },
+ [0x31B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B8,
+ },
+ [0x31B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31B9,
+ },
+ [0x31BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x31BA,
+ },
+ [0x31C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C0,
+ },
+ [0x31C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C1,
+ },
+ [0x31C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C2,
+ },
+ [0x31C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C3,
+ },
+ [0x31C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C4,
+ },
+ [0x31C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C5,
+ },
+ [0x31C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C6,
+ },
+ [0x31C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C7,
+ },
+ [0x31C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C8,
+ },
+ [0x31C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31C9,
+ },
+ [0x31CA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31CA,
+ },
+ [0x31CB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31CB,
+ },
+ [0x31CC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31CC,
+ },
+ [0x31CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31CD,
+ },
+ [0x31CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31CE,
+ },
+ [0x31CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31CF,
+ },
+ [0x31D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D0,
+ },
+ [0x31D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D1,
+ },
+ [0x31D2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D2,
+ },
+ [0x31D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D3,
+ },
+ [0x31D4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D4,
+ },
+ [0x31D5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D5,
+ },
+ [0x31D6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D6,
+ },
+ [0x31D7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D7,
+ },
+ [0x31D8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D8,
+ },
+ [0x31D9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31D9,
+ },
+ [0x31DA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31DA,
+ },
+ [0x31DB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31DB,
+ },
+ [0x31DC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31DC,
+ },
+ [0x31DD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31DD,
+ },
+ [0x31DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31DE,
+ },
+ [0x31DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31DF,
+ },
+ [0x31E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31E0,
+ },
+ [0x31E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31E1,
+ },
+ [0x31E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31E2,
+ },
+ [0x31E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x31E3,
+ },
+ [0x31F0]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F0,
+ },
+ [0x31F1]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F1,
+ },
+ [0x31F2]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F2,
+ },
+ [0x31F3]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F3,
+ },
+ [0x31F4]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F4,
+ },
+ [0x31F5]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F5,
+ },
+ [0x31F6]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F6,
+ },
+ [0x31F7]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F7,
+ },
+ [0x31F8]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F8,
+ },
+ [0x31F9]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31F9,
+ },
+ [0x31FA]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31FA,
+ },
+ [0x31FB]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31FB,
+ },
+ [0x31FC]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31FC,
+ },
+ [0x31FD]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31FD,
+ },
+ [0x31FE]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31FE,
+ },
+ [0x31FF]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x31FF,
+ },
+ [0x3200]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1100, 0x29 },
+ unicodeslot=0x3200,
+ },
+ [0x3201]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1102, 0x29 },
+ unicodeslot=0x3201,
+ },
+ [0x3202]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1103, 0x29 },
+ unicodeslot=0x3202,
+ },
+ [0x3203]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1105, 0x29 },
+ unicodeslot=0x3203,
+ },
+ [0x3204]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1106, 0x29 },
+ unicodeslot=0x3204,
+ },
+ [0x3205]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1107, 0x29 },
+ unicodeslot=0x3205,
+ },
+ [0x3206]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1109, 0x29 },
+ unicodeslot=0x3206,
+ },
+ [0x3207]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110B, 0x29 },
+ unicodeslot=0x3207,
+ },
+ [0x3208]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110C, 0x29 },
+ unicodeslot=0x3208,
+ },
+ [0x3209]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110E, 0x29 },
+ unicodeslot=0x3209,
+ },
+ [0x320A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110F, 0x29 },
+ unicodeslot=0x320A,
+ },
+ [0x320B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1110, 0x29 },
+ unicodeslot=0x320B,
+ },
+ [0x320C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1111, 0x29 },
+ unicodeslot=0x320C,
+ },
+ [0x320D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1112, 0x29 },
+ unicodeslot=0x320D,
+ },
+ [0x320E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1100, 0x1161, 0x29 },
+ unicodeslot=0x320E,
+ },
+ [0x320F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1102, 0x1161, 0x29 },
+ unicodeslot=0x320F,
+ },
+ [0x3210]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1103, 0x1161, 0x29 },
+ unicodeslot=0x3210,
+ },
+ [0x3211]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1105, 0x1161, 0x29 },
+ unicodeslot=0x3211,
+ },
+ [0x3212]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1106, 0x1161, 0x29 },
+ unicodeslot=0x3212,
+ },
+ [0x3213]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1107, 0x1161, 0x29 },
+ unicodeslot=0x3213,
+ },
+ [0x3214]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1109, 0x1161, 0x29 },
+ unicodeslot=0x3214,
+ },
+ [0x3215]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110B, 0x1161, 0x29 },
+ unicodeslot=0x3215,
+ },
+ [0x3216]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110C, 0x1161, 0x29 },
+ unicodeslot=0x3216,
+ },
+ [0x3217]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110E, 0x1161, 0x29 },
+ unicodeslot=0x3217,
+ },
+ [0x3218]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110F, 0x1161, 0x29 },
+ unicodeslot=0x3218,
+ },
+ [0x3219]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1110, 0x1161, 0x29 },
+ unicodeslot=0x3219,
+ },
+ [0x321A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1111, 0x1161, 0x29 },
+ unicodeslot=0x321A,
+ },
+ [0x321B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x1112, 0x1161, 0x29 },
+ unicodeslot=0x321B,
+ },
+ [0x321C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110C, 0x116E, 0x29 },
+ unicodeslot=0x321C,
+ },
+ [0x321D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110B, 0x1169, 0x110C, 0x1165, 0x11AB, 0x29 },
+ unicodeslot=0x321D,
+ },
+ [0x321E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x110B, 0x1169, 0x1112, 0x116E, 0x29 },
+ unicodeslot=0x321E,
+ },
+ [0x3220]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4E00, 0x29 },
+ unicodeslot=0x3220,
+ },
+ [0x3221]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4E8C, 0x29 },
+ unicodeslot=0x3221,
+ },
+ [0x3222]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4E09, 0x29 },
+ unicodeslot=0x3222,
+ },
+ [0x3223]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x56DB, 0x29 },
+ unicodeslot=0x3223,
+ },
+ [0x3224]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4E94, 0x29 },
+ unicodeslot=0x3224,
+ },
+ [0x3225]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x516D, 0x29 },
+ unicodeslot=0x3225,
+ },
+ [0x3226]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4E03, 0x29 },
+ unicodeslot=0x3226,
+ },
+ [0x3227]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x516B, 0x29 },
+ unicodeslot=0x3227,
+ },
+ [0x3228]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4E5D, 0x29 },
+ unicodeslot=0x3228,
+ },
+ [0x3229]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x5341, 0x29 },
+ unicodeslot=0x3229,
+ },
+ [0x322A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x6708, 0x29 },
+ unicodeslot=0x322A,
+ },
+ [0x322B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x706B, 0x29 },
+ unicodeslot=0x322B,
+ },
+ [0x322C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x6C34, 0x29 },
+ unicodeslot=0x322C,
+ },
+ [0x322D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x6728, 0x29 },
+ unicodeslot=0x322D,
+ },
+ [0x322E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x91D1, 0x29 },
+ unicodeslot=0x322E,
+ },
+ [0x322F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x571F, 0x29 },
+ unicodeslot=0x322F,
+ },
+ [0x3230]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x65E5, 0x29 },
+ unicodeslot=0x3230,
+ },
+ [0x3231]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x682A, 0x29 },
+ unicodeslot=0x3231,
+ },
+ [0x3232]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x6709, 0x29 },
+ unicodeslot=0x3232,
+ },
+ [0x3233]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x793E, 0x29 },
+ unicodeslot=0x3233,
+ },
+ [0x3234]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x540D, 0x29 },
+ unicodeslot=0x3234,
+ },
+ [0x3235]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x7279, 0x29 },
+ unicodeslot=0x3235,
+ },
+ [0x3236]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x8CA1, 0x29 },
+ unicodeslot=0x3236,
+ },
+ [0x3237]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x795D, 0x29 },
+ unicodeslot=0x3237,
+ },
+ [0x3238]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x52B4, 0x29 },
+ unicodeslot=0x3238,
+ },
+ [0x3239]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4EE3, 0x29 },
+ unicodeslot=0x3239,
+ },
+ [0x323A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x547C, 0x29 },
+ unicodeslot=0x323A,
+ },
+ [0x323B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x5B66, 0x29 },
+ unicodeslot=0x323B,
+ },
+ [0x323C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x76E3, 0x29 },
+ unicodeslot=0x323C,
+ },
+ [0x323D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4F01, 0x29 },
+ unicodeslot=0x323D,
+ },
+ [0x323E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x8CC7, 0x29 },
+ unicodeslot=0x323E,
+ },
+ [0x323F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x5354, 0x29 },
+ unicodeslot=0x323F,
+ },
+ [0x3240]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x796D, 0x29 },
+ unicodeslot=0x3240,
+ },
+ [0x3241]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x4F11, 0x29 },
+ unicodeslot=0x3241,
+ },
+ [0x3242]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x81EA, 0x29 },
+ unicodeslot=0x3242,
+ },
+ [0x3243]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x28, 0x81F3, 0x29 },
+ unicodeslot=0x3243,
+ },
+ [0x3244]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x554F },
+ unicodeslot=0x3244,
+ },
+ [0x3245]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5E7C },
+ unicodeslot=0x3245,
+ },
+ [0x3246]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6587 },
+ unicodeslot=0x3246,
+ },
+ [0x3247]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x7B8F },
+ unicodeslot=0x3247,
+ },
+ [0x3248]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x3248,
+ },
+ [0x3249]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x3249,
+ },
+ [0x324A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x324A,
+ },
+ [0x324B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x324B,
+ },
+ [0x324C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x324C,
+ },
+ [0x324D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x324D,
+ },
+ [0x324E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x324E,
+ },
+ [0x324F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x324F,
+ },
+ [0x3250]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x50, 0x54, 0x45 },
+ unicodeslot=0x3250,
+ },
+ [0x3251]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x31 },
+ unicodeslot=0x3251,
+ },
+ [0x3252]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x32 },
+ unicodeslot=0x3252,
+ },
+ [0x3253]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x33 },
+ unicodeslot=0x3253,
+ },
+ [0x3254]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x34 },
+ unicodeslot=0x3254,
+ },
+ [0x3255]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x35 },
+ unicodeslot=0x3255,
+ },
+ [0x3256]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x36 },
+ unicodeslot=0x3256,
+ },
+ [0x3257]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x37 },
+ unicodeslot=0x3257,
+ },
+ [0x3258]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x38 },
+ unicodeslot=0x3258,
+ },
+ [0x3259]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x32, 0x39 },
+ unicodeslot=0x3259,
+ },
+ [0x325A]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x30 },
+ unicodeslot=0x325A,
+ },
+ [0x325B]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x31 },
+ unicodeslot=0x325B,
+ },
+ [0x325C]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x32 },
+ unicodeslot=0x325C,
+ },
+ [0x325D]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x33 },
+ unicodeslot=0x325D,
+ },
+ [0x325E]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x34 },
+ unicodeslot=0x325E,
+ },
+ [0x325F]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x35 },
+ unicodeslot=0x325F,
+ },
+ [0x3260]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1100 },
+ unicodeslot=0x3260,
+ },
+ [0x3261]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1102 },
+ unicodeslot=0x3261,
+ },
+ [0x3262]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1103 },
+ unicodeslot=0x3262,
+ },
+ [0x3263]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1105 },
+ unicodeslot=0x3263,
+ },
+ [0x3264]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1106 },
+ unicodeslot=0x3264,
+ },
+ [0x3265]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1107 },
+ unicodeslot=0x3265,
+ },
+ [0x3266]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1109 },
+ unicodeslot=0x3266,
+ },
+ [0x3267]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110B },
+ unicodeslot=0x3267,
+ },
+ [0x3268]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110C },
+ unicodeslot=0x3268,
+ },
+ [0x3269]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110E },
+ unicodeslot=0x3269,
+ },
+ [0x326A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110F },
+ unicodeslot=0x326A,
+ },
+ [0x326B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1110 },
+ unicodeslot=0x326B,
+ },
+ [0x326C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1111 },
+ unicodeslot=0x326C,
+ },
+ [0x326D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1112 },
+ unicodeslot=0x326D,
+ },
+ [0x326E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1100, 0x1161 },
+ unicodeslot=0x326E,
+ },
+ [0x326F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1102, 0x1161 },
+ unicodeslot=0x326F,
+ },
+ [0x3270]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1103, 0x1161 },
+ unicodeslot=0x3270,
+ },
+ [0x3271]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1105, 0x1161 },
+ unicodeslot=0x3271,
+ },
+ [0x3272]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1106, 0x1161 },
+ unicodeslot=0x3272,
+ },
+ [0x3273]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1107, 0x1161 },
+ unicodeslot=0x3273,
+ },
+ [0x3274]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1109, 0x1161 },
+ unicodeslot=0x3274,
+ },
+ [0x3275]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110B, 0x1161 },
+ unicodeslot=0x3275,
+ },
+ [0x3276]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110C, 0x1161 },
+ unicodeslot=0x3276,
+ },
+ [0x3277]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110E, 0x1161 },
+ unicodeslot=0x3277,
+ },
+ [0x3278]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x110F, 0x1161 },
+ unicodeslot=0x3278,
+ },
+ [0x3279]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1110, 0x1161 },
+ unicodeslot=0x3279,
+ },
+ [0x327A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1111, 0x1161 },
+ unicodeslot=0x327A,
+ },
+ [0x327B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x1112, 0x1161 },
+ unicodeslot=0x327B,
+ },
+ [0x327C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x110E, 0x1161, 0x11B7, 0x1100, 0x1169 },
+ unicodeslot=0x327C,
+ },
+ [0x327D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x110C, 0x116E, 0x110B, 0x1174 },
+ unicodeslot=0x327D,
+ },
+ [0x327E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x110B, 0x116E },
+ unicodeslot=0x327E,
+ },
+ [0x327F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x327F,
+ },
+ [0x3280]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E00 },
+ unicodeslot=0x3280,
+ },
+ [0x3281]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E8C },
+ unicodeslot=0x3281,
+ },
+ [0x3282]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E09 },
+ unicodeslot=0x3282,
+ },
+ [0x3283]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x56DB },
+ unicodeslot=0x3283,
+ },
+ [0x3284]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E94 },
+ unicodeslot=0x3284,
+ },
+ [0x3285]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x516D },
+ unicodeslot=0x3285,
+ },
+ [0x3286]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E03 },
+ unicodeslot=0x3286,
+ },
+ [0x3287]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x516B },
+ unicodeslot=0x3287,
+ },
+ [0x3288]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E5D },
+ unicodeslot=0x3288,
+ },
+ [0x3289]={
+ category="no",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5341 },
+ unicodeslot=0x3289,
+ },
+ [0x328A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6708 },
+ unicodeslot=0x328A,
+ },
+ [0x328B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x706B },
+ unicodeslot=0x328B,
+ },
+ [0x328C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6C34 },
+ unicodeslot=0x328C,
+ },
+ [0x328D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6728 },
+ unicodeslot=0x328D,
+ },
+ [0x328E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x91D1 },
+ unicodeslot=0x328E,
+ },
+ [0x328F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x571F },
+ unicodeslot=0x328F,
+ },
+ [0x3290]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x65E5 },
+ unicodeslot=0x3290,
+ },
+ [0x3291]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x682A },
+ unicodeslot=0x3291,
+ },
+ [0x3292]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6709 },
+ unicodeslot=0x3292,
+ },
+ [0x3293]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x793E },
+ unicodeslot=0x3293,
+ },
+ [0x3294]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x540D },
+ unicodeslot=0x3294,
+ },
+ [0x3295]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x7279 },
+ unicodeslot=0x3295,
+ },
+ [0x3296]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x8CA1 },
+ unicodeslot=0x3296,
+ },
+ [0x3297]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x795D },
+ unicodeslot=0x3297,
+ },
+ [0x3298]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x52B4 },
+ unicodeslot=0x3298,
+ },
+ [0x3299]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x79D8 },
+ unicodeslot=0x3299,
+ },
+ [0x329A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x7537 },
+ unicodeslot=0x329A,
+ },
+ [0x329B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5973 },
+ unicodeslot=0x329B,
+ },
+ [0x329C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x9069 },
+ unicodeslot=0x329C,
+ },
+ [0x329D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x512A },
+ unicodeslot=0x329D,
+ },
+ [0x329E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5370 },
+ unicodeslot=0x329E,
+ },
+ [0x329F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6CE8 },
+ unicodeslot=0x329F,
+ },
+ [0x32A0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x9805 },
+ unicodeslot=0x32A0,
+ },
+ [0x32A1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4F11 },
+ unicodeslot=0x32A1,
+ },
+ [0x32A2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5199 },
+ unicodeslot=0x32A2,
+ },
+ [0x32A3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x6B63 },
+ unicodeslot=0x32A3,
+ },
+ [0x32A4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E0A },
+ unicodeslot=0x32A4,
+ },
+ [0x32A5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E2D },
+ unicodeslot=0x32A5,
+ },
+ [0x32A6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4E0B },
+ unicodeslot=0x32A6,
+ },
+ [0x32A7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5DE6 },
+ unicodeslot=0x32A7,
+ },
+ [0x32A8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x53F3 },
+ unicodeslot=0x32A8,
+ },
+ [0x32A9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x533B },
+ unicodeslot=0x32A9,
+ },
+ [0x32AA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5B97 },
+ unicodeslot=0x32AA,
+ },
+ [0x32AB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5B66 },
+ unicodeslot=0x32AB,
+ },
+ [0x32AC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x76E3 },
+ unicodeslot=0x32AC,
+ },
+ [0x32AD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x4F01 },
+ unicodeslot=0x32AD,
+ },
+ [0x32AE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x8CC7 },
+ unicodeslot=0x32AE,
+ },
+ [0x32AF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5354 },
+ unicodeslot=0x32AF,
+ },
+ [0x32B0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x591C },
+ unicodeslot=0x32B0,
+ },
+ [0x32B1]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x36 },
+ unicodeslot=0x32B1,
+ },
+ [0x32B2]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x37 },
+ unicodeslot=0x32B2,
+ },
+ [0x32B3]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x38 },
+ unicodeslot=0x32B3,
+ },
+ [0x32B4]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x33, 0x39 },
+ unicodeslot=0x32B4,
+ },
+ [0x32B5]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x30 },
+ unicodeslot=0x32B5,
+ },
+ [0x32B6]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x31 },
+ unicodeslot=0x32B6,
+ },
+ [0x32B7]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x32 },
+ unicodeslot=0x32B7,
+ },
+ [0x32B8]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x33 },
+ unicodeslot=0x32B8,
+ },
+ [0x32B9]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x34 },
+ unicodeslot=0x32B9,
+ },
+ [0x32BA]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x35 },
+ unicodeslot=0x32BA,
+ },
+ [0x32BB]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x36 },
+ unicodeslot=0x32BB,
+ },
+ [0x32BC]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x37 },
+ unicodeslot=0x32BC,
+ },
+ [0x32BD]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x38 },
+ unicodeslot=0x32BD,
+ },
+ [0x32BE]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x34, 0x39 },
+ unicodeslot=0x32BE,
+ },
+ [0x32BF]={
+ category="no",
+ direction="on",
+ linebreak="id",
+ specials={ "circle", 0x35, 0x30 },
+ unicodeslot=0x32BF,
+ },
+ [0x32C0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x6708 },
+ unicodeslot=0x32C0,
+ },
+ [0x32C1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x6708 },
+ unicodeslot=0x32C1,
+ },
+ [0x32C2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x33, 0x6708 },
+ unicodeslot=0x32C2,
+ },
+ [0x32C3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x34, 0x6708 },
+ unicodeslot=0x32C3,
+ },
+ [0x32C4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x35, 0x6708 },
+ unicodeslot=0x32C4,
+ },
+ [0x32C5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x36, 0x6708 },
+ unicodeslot=0x32C5,
+ },
+ [0x32C6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x37, 0x6708 },
+ unicodeslot=0x32C6,
+ },
+ [0x32C7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x38, 0x6708 },
+ unicodeslot=0x32C7,
+ },
+ [0x32C8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x39, 0x6708 },
+ unicodeslot=0x32C8,
+ },
+ [0x32C9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x30, 0x6708 },
+ unicodeslot=0x32C9,
+ },
+ [0x32CA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x31, 0x6708 },
+ unicodeslot=0x32CA,
+ },
+ [0x32CB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x32, 0x6708 },
+ unicodeslot=0x32CB,
+ },
+ [0x32CC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x48, 0x67 },
+ unicodeslot=0x32CC,
+ },
+ [0x32CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x65, 0x72, 0x67 },
+ unicodeslot=0x32CD,
+ },
+ [0x32CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x65, 0x56 },
+ unicodeslot=0x32CE,
+ },
+ [0x32CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x4C, 0x54, 0x44 },
+ unicodeslot=0x32CF,
+ },
+ [0x32D0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30A2 },
+ unicodeslot=0x32D0,
+ },
+ [0x32D1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30A4 },
+ unicodeslot=0x32D1,
+ },
+ [0x32D2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30A6 },
+ unicodeslot=0x32D2,
+ },
+ [0x32D3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30A8 },
+ unicodeslot=0x32D3,
+ },
+ [0x32D4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30AA },
+ unicodeslot=0x32D4,
+ },
+ [0x32D5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30AB },
+ unicodeslot=0x32D5,
+ },
+ [0x32D6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30AD },
+ unicodeslot=0x32D6,
+ },
+ [0x32D7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30AF },
+ unicodeslot=0x32D7,
+ },
+ [0x32D8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30B1 },
+ unicodeslot=0x32D8,
+ },
+ [0x32D9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30B3 },
+ unicodeslot=0x32D9,
+ },
+ [0x32DA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30B5 },
+ unicodeslot=0x32DA,
+ },
+ [0x32DB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30B7 },
+ unicodeslot=0x32DB,
+ },
+ [0x32DC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30B9 },
+ unicodeslot=0x32DC,
+ },
+ [0x32DD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30BB },
+ unicodeslot=0x32DD,
+ },
+ [0x32DE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30BD },
+ unicodeslot=0x32DE,
+ },
+ [0x32DF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30BF },
+ unicodeslot=0x32DF,
+ },
+ [0x32E0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30C1 },
+ unicodeslot=0x32E0,
+ },
+ [0x32E1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30C4 },
+ unicodeslot=0x32E1,
+ },
+ [0x32E2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30C6 },
+ unicodeslot=0x32E2,
+ },
+ [0x32E3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30C8 },
+ unicodeslot=0x32E3,
+ },
+ [0x32E4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30CA },
+ unicodeslot=0x32E4,
+ },
+ [0x32E5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30CB },
+ unicodeslot=0x32E5,
+ },
+ [0x32E6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30CC },
+ unicodeslot=0x32E6,
+ },
+ [0x32E7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30CD },
+ unicodeslot=0x32E7,
+ },
+ [0x32E8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30CE },
+ unicodeslot=0x32E8,
+ },
+ [0x32E9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30CF },
+ unicodeslot=0x32E9,
+ },
+ [0x32EA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30D2 },
+ unicodeslot=0x32EA,
+ },
+ [0x32EB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30D5 },
+ unicodeslot=0x32EB,
+ },
+ [0x32EC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30D8 },
+ unicodeslot=0x32EC,
+ },
+ [0x32ED]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30DB },
+ unicodeslot=0x32ED,
+ },
+ [0x32EE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30DE },
+ unicodeslot=0x32EE,
+ },
+ [0x32EF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30DF },
+ unicodeslot=0x32EF,
+ },
+ [0x32F0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E0 },
+ unicodeslot=0x32F0,
+ },
+ [0x32F1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E1 },
+ unicodeslot=0x32F1,
+ },
+ [0x32F2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E2 },
+ unicodeslot=0x32F2,
+ },
+ [0x32F3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E4 },
+ unicodeslot=0x32F3,
+ },
+ [0x32F4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E6 },
+ unicodeslot=0x32F4,
+ },
+ [0x32F5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E8 },
+ unicodeslot=0x32F5,
+ },
+ [0x32F6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30E9 },
+ unicodeslot=0x32F6,
+ },
+ [0x32F7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30EA },
+ unicodeslot=0x32F7,
+ },
+ [0x32F8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30EB },
+ unicodeslot=0x32F8,
+ },
+ [0x32F9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30EC },
+ unicodeslot=0x32F9,
+ },
+ [0x32FA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30ED },
+ unicodeslot=0x32FA,
+ },
+ [0x32FB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30EF },
+ unicodeslot=0x32FB,
+ },
+ [0x32FC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30F0 },
+ unicodeslot=0x32FC,
+ },
+ [0x32FD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30F1 },
+ unicodeslot=0x32FD,
+ },
+ [0x32FE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x30F2 },
+ unicodeslot=0x32FE,
+ },
+ [0x32FF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4EE4, 0x548C },
+ unicodeslot=0x32FF,
+ },
+ [0x3300]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A2, 0x30D1, 0x30FC, 0x30C8 },
+ unicodeslot=0x3300,
+ },
+ [0x3301]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A2, 0x30EB, 0x30D5, 0x30A1 },
+ unicodeslot=0x3301,
+ },
+ [0x3302]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A2, 0x30F3, 0x30DA, 0x30A2 },
+ unicodeslot=0x3302,
+ },
+ [0x3303]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A2, 0x30FC, 0x30EB },
+ unicodeslot=0x3303,
+ },
+ [0x3304]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A4, 0x30CB, 0x30F3, 0x30B0 },
+ unicodeslot=0x3304,
+ },
+ [0x3305]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A4, 0x30F3, 0x30C1 },
+ unicodeslot=0x3305,
+ },
+ [0x3306]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A6, 0x30A9, 0x30F3 },
+ unicodeslot=0x3306,
+ },
+ [0x3307]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A8, 0x30B9, 0x30AF, 0x30FC, 0x30C9 },
+ unicodeslot=0x3307,
+ },
+ [0x3308]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30A8, 0x30FC, 0x30AB, 0x30FC },
+ unicodeslot=0x3308,
+ },
+ [0x3309]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AA, 0x30F3, 0x30B9 },
+ unicodeslot=0x3309,
+ },
+ [0x330A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AA, 0x30FC, 0x30E0 },
+ unicodeslot=0x330A,
+ },
+ [0x330B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AB, 0x30A4, 0x30EA },
+ unicodeslot=0x330B,
+ },
+ [0x330C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AB, 0x30E9, 0x30C3, 0x30C8 },
+ unicodeslot=0x330C,
+ },
+ [0x330D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AB, 0x30ED, 0x30EA, 0x30FC },
+ unicodeslot=0x330D,
+ },
+ [0x330E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AC, 0x30ED, 0x30F3 },
+ unicodeslot=0x330E,
+ },
+ [0x330F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AC, 0x30F3, 0x30DE },
+ unicodeslot=0x330F,
+ },
+ [0x3310]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AE, 0x30AC },
+ unicodeslot=0x3310,
+ },
+ [0x3311]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AE, 0x30CB, 0x30FC },
+ unicodeslot=0x3311,
+ },
+ [0x3312]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AD, 0x30E5, 0x30EA, 0x30FC },
+ unicodeslot=0x3312,
+ },
+ [0x3313]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AE, 0x30EB, 0x30C0, 0x30FC },
+ unicodeslot=0x3313,
+ },
+ [0x3314]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AD, 0x30ED },
+ unicodeslot=0x3314,
+ },
+ [0x3315]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AD, 0x30ED, 0x30B0, 0x30E9, 0x30E0 },
+ unicodeslot=0x3315,
+ },
+ [0x3316]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AD, 0x30ED, 0x30E1, 0x30FC, 0x30C8, 0x30EB },
+ unicodeslot=0x3316,
+ },
+ [0x3317]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AD, 0x30ED, 0x30EF, 0x30C3, 0x30C8 },
+ unicodeslot=0x3317,
+ },
+ [0x3318]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B0, 0x30E9, 0x30E0 },
+ unicodeslot=0x3318,
+ },
+ [0x3319]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B0, 0x30E9, 0x30E0, 0x30C8, 0x30F3 },
+ unicodeslot=0x3319,
+ },
+ [0x331A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AF, 0x30EB, 0x30BC, 0x30A4, 0x30ED },
+ unicodeslot=0x331A,
+ },
+ [0x331B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30AF, 0x30ED, 0x30FC, 0x30CD },
+ unicodeslot=0x331B,
+ },
+ [0x331C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B1, 0x30FC, 0x30B9 },
+ unicodeslot=0x331C,
+ },
+ [0x331D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B3, 0x30EB, 0x30CA },
+ unicodeslot=0x331D,
+ },
+ [0x331E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B3, 0x30FC, 0x30DD },
+ unicodeslot=0x331E,
+ },
+ [0x331F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B5, 0x30A4, 0x30AF, 0x30EB },
+ unicodeslot=0x331F,
+ },
+ [0x3320]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B5, 0x30F3, 0x30C1, 0x30FC, 0x30E0 },
+ unicodeslot=0x3320,
+ },
+ [0x3321]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B7, 0x30EA, 0x30F3, 0x30B0 },
+ unicodeslot=0x3321,
+ },
+ [0x3322]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30BB, 0x30F3, 0x30C1 },
+ unicodeslot=0x3322,
+ },
+ [0x3323]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30BB, 0x30F3, 0x30C8 },
+ unicodeslot=0x3323,
+ },
+ [0x3324]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30C0, 0x30FC, 0x30B9 },
+ unicodeslot=0x3324,
+ },
+ [0x3325]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30C7, 0x30B7 },
+ unicodeslot=0x3325,
+ },
+ [0x3326]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30C9, 0x30EB },
+ unicodeslot=0x3326,
+ },
+ [0x3327]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30C8, 0x30F3 },
+ unicodeslot=0x3327,
+ },
+ [0x3328]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30CA, 0x30CE },
+ unicodeslot=0x3328,
+ },
+ [0x3329]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30CE, 0x30C3, 0x30C8 },
+ unicodeslot=0x3329,
+ },
+ [0x332A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30CF, 0x30A4, 0x30C4 },
+ unicodeslot=0x332A,
+ },
+ [0x332B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D1, 0x30FC, 0x30BB, 0x30F3, 0x30C8 },
+ unicodeslot=0x332B,
+ },
+ [0x332C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D1, 0x30FC, 0x30C4 },
+ unicodeslot=0x332C,
+ },
+ [0x332D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D0, 0x30FC, 0x30EC, 0x30EB },
+ unicodeslot=0x332D,
+ },
+ [0x332E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D4, 0x30A2, 0x30B9, 0x30C8, 0x30EB },
+ unicodeslot=0x332E,
+ },
+ [0x332F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D4, 0x30AF, 0x30EB },
+ unicodeslot=0x332F,
+ },
+ [0x3330]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D4, 0x30B3 },
+ unicodeslot=0x3330,
+ },
+ [0x3331]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D3, 0x30EB },
+ unicodeslot=0x3331,
+ },
+ [0x3332]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D5, 0x30A1, 0x30E9, 0x30C3, 0x30C9 },
+ unicodeslot=0x3332,
+ },
+ [0x3333]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D5, 0x30A3, 0x30FC, 0x30C8 },
+ unicodeslot=0x3333,
+ },
+ [0x3334]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D6, 0x30C3, 0x30B7, 0x30A7, 0x30EB },
+ unicodeslot=0x3334,
+ },
+ [0x3335]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D5, 0x30E9, 0x30F3 },
+ unicodeslot=0x3335,
+ },
+ [0x3336]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D8, 0x30AF, 0x30BF, 0x30FC, 0x30EB },
+ unicodeslot=0x3336,
+ },
+ [0x3337]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DA, 0x30BD },
+ unicodeslot=0x3337,
+ },
+ [0x3338]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DA, 0x30CB, 0x30D2 },
+ unicodeslot=0x3338,
+ },
+ [0x3339]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D8, 0x30EB, 0x30C4 },
+ unicodeslot=0x3339,
+ },
+ [0x333A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DA, 0x30F3, 0x30B9 },
+ unicodeslot=0x333A,
+ },
+ [0x333B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DA, 0x30FC, 0x30B8 },
+ unicodeslot=0x333B,
+ },
+ [0x333C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30D9, 0x30FC, 0x30BF },
+ unicodeslot=0x333C,
+ },
+ [0x333D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DD, 0x30A4, 0x30F3, 0x30C8 },
+ unicodeslot=0x333D,
+ },
+ [0x333E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DC, 0x30EB, 0x30C8 },
+ unicodeslot=0x333E,
+ },
+ [0x333F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DB, 0x30F3 },
+ unicodeslot=0x333F,
+ },
+ [0x3340]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DD, 0x30F3, 0x30C9 },
+ unicodeslot=0x3340,
+ },
+ [0x3341]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DB, 0x30FC, 0x30EB },
+ unicodeslot=0x3341,
+ },
+ [0x3342]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DB, 0x30FC, 0x30F3 },
+ unicodeslot=0x3342,
+ },
+ [0x3343]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DE, 0x30A4, 0x30AF, 0x30ED },
+ unicodeslot=0x3343,
+ },
+ [0x3344]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DE, 0x30A4, 0x30EB },
+ unicodeslot=0x3344,
+ },
+ [0x3345]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DE, 0x30C3, 0x30CF },
+ unicodeslot=0x3345,
+ },
+ [0x3346]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DE, 0x30EB, 0x30AF },
+ unicodeslot=0x3346,
+ },
+ [0x3347]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DE, 0x30F3, 0x30B7, 0x30E7, 0x30F3 },
+ unicodeslot=0x3347,
+ },
+ [0x3348]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DF, 0x30AF, 0x30ED, 0x30F3 },
+ unicodeslot=0x3348,
+ },
+ [0x3349]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DF, 0x30EA },
+ unicodeslot=0x3349,
+ },
+ [0x334A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30DF, 0x30EA, 0x30D0, 0x30FC, 0x30EB },
+ unicodeslot=0x334A,
+ },
+ [0x334B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30E1, 0x30AC },
+ unicodeslot=0x334B,
+ },
+ [0x334C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30E1, 0x30AC, 0x30C8, 0x30F3 },
+ unicodeslot=0x334C,
+ },
+ [0x334D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30E1, 0x30FC, 0x30C8, 0x30EB },
+ unicodeslot=0x334D,
+ },
+ [0x334E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30E4, 0x30FC, 0x30C9 },
+ unicodeslot=0x334E,
+ },
+ [0x334F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30E4, 0x30FC, 0x30EB },
+ unicodeslot=0x334F,
+ },
+ [0x3350]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30E6, 0x30A2, 0x30F3 },
+ unicodeslot=0x3350,
+ },
+ [0x3351]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EA, 0x30C3, 0x30C8, 0x30EB },
+ unicodeslot=0x3351,
+ },
+ [0x3352]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EA, 0x30E9 },
+ unicodeslot=0x3352,
+ },
+ [0x3353]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EB, 0x30D4, 0x30FC },
+ unicodeslot=0x3353,
+ },
+ [0x3354]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EB, 0x30FC, 0x30D6, 0x30EB },
+ unicodeslot=0x3354,
+ },
+ [0x3355]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EC, 0x30E0 },
+ unicodeslot=0x3355,
+ },
+ [0x3356]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EC, 0x30F3, 0x30C8, 0x30B2, 0x30F3 },
+ unicodeslot=0x3356,
+ },
+ [0x3357]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30EF, 0x30C3, 0x30C8 },
+ unicodeslot=0x3357,
+ },
+ [0x3358]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x30, 0x70B9 },
+ unicodeslot=0x3358,
+ },
+ [0x3359]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x70B9 },
+ unicodeslot=0x3359,
+ },
+ [0x335A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x70B9 },
+ unicodeslot=0x335A,
+ },
+ [0x335B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x33, 0x70B9 },
+ unicodeslot=0x335B,
+ },
+ [0x335C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x34, 0x70B9 },
+ unicodeslot=0x335C,
+ },
+ [0x335D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x35, 0x70B9 },
+ unicodeslot=0x335D,
+ },
+ [0x335E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x36, 0x70B9 },
+ unicodeslot=0x335E,
+ },
+ [0x335F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x37, 0x70B9 },
+ unicodeslot=0x335F,
+ },
+ [0x3360]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x38, 0x70B9 },
+ unicodeslot=0x3360,
+ },
+ [0x3361]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x39, 0x70B9 },
+ unicodeslot=0x3361,
+ },
+ [0x3362]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x30, 0x70B9 },
+ unicodeslot=0x3362,
+ },
+ [0x3363]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x31, 0x70B9 },
+ unicodeslot=0x3363,
+ },
+ [0x3364]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x32, 0x70B9 },
+ unicodeslot=0x3364,
+ },
+ [0x3365]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x33, 0x70B9 },
+ unicodeslot=0x3365,
+ },
+ [0x3366]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x34, 0x70B9 },
+ unicodeslot=0x3366,
+ },
+ [0x3367]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x35, 0x70B9 },
+ unicodeslot=0x3367,
+ },
+ [0x3368]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x36, 0x70B9 },
+ unicodeslot=0x3368,
+ },
+ [0x3369]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x37, 0x70B9 },
+ unicodeslot=0x3369,
+ },
+ [0x336A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x38, 0x70B9 },
+ unicodeslot=0x336A,
+ },
+ [0x336B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x39, 0x70B9 },
+ unicodeslot=0x336B,
+ },
+ [0x336C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x30, 0x70B9 },
+ unicodeslot=0x336C,
+ },
+ [0x336D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x31, 0x70B9 },
+ unicodeslot=0x336D,
+ },
+ [0x336E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x32, 0x70B9 },
+ unicodeslot=0x336E,
+ },
+ [0x336F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x33, 0x70B9 },
+ unicodeslot=0x336F,
+ },
+ [0x3370]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x34, 0x70B9 },
+ unicodeslot=0x3370,
+ },
+ [0x3371]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x68, 0x50, 0x61 },
+ unicodeslot=0x3371,
+ },
+ [0x3372]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x64, 0x61 },
+ unicodeslot=0x3372,
+ },
+ [0x3373]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x41, 0x55 },
+ unicodeslot=0x3373,
+ },
+ [0x3374]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x62, 0x61, 0x72 },
+ unicodeslot=0x3374,
+ },
+ [0x3375]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6F, 0x56 },
+ unicodeslot=0x3375,
+ },
+ [0x3376]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x63 },
+ unicodeslot=0x3376,
+ },
+ [0x3377]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x64, 0x6D },
+ unicodeslot=0x3377,
+ },
+ [0x3378]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x64, 0x6D, 0xB2 },
+ unicodeslot=0x3378,
+ },
+ [0x3379]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x64, 0x6D, 0xB3 },
+ unicodeslot=0x3379,
+ },
+ [0x337A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x49, 0x55 },
+ unicodeslot=0x337A,
+ },
+ [0x337B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5E73, 0x6210 },
+ unicodeslot=0x337B,
+ },
+ [0x337C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x662D, 0x548C },
+ unicodeslot=0x337C,
+ },
+ [0x337D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5927, 0x6B63 },
+ unicodeslot=0x337D,
+ },
+ [0x337E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x660E, 0x6CBB },
+ unicodeslot=0x337E,
+ },
+ [0x337F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x682A, 0x5F0F, 0x4F1A, 0x793E },
+ unicodeslot=0x337F,
+ },
+ [0x3380]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x41 },
+ unicodeslot=0x3380,
+ },
+ [0x3381]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E, 0x41 },
+ unicodeslot=0x3381,
+ },
+ [0x3382]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x41 },
+ unicodeslot=0x3382,
+ },
+ [0x3383]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x41 },
+ unicodeslot=0x3383,
+ },
+ [0x3384]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x41 },
+ unicodeslot=0x3384,
+ },
+ [0x3385]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4B, 0x42 },
+ unicodeslot=0x3385,
+ },
+ [0x3386]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4D, 0x42 },
+ unicodeslot=0x3386,
+ },
+ [0x3387]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x47, 0x42 },
+ unicodeslot=0x3387,
+ },
+ [0x3388]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x63, 0x61, 0x6C },
+ unicodeslot=0x3388,
+ },
+ [0x3389]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x63, 0x61, 0x6C },
+ unicodeslot=0x3389,
+ },
+ [0x338A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x46 },
+ unicodeslot=0x338A,
+ },
+ [0x338B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E, 0x46 },
+ unicodeslot=0x338B,
+ },
+ [0x338C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x46 },
+ unicodeslot=0x338C,
+ },
+ [0x338D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x67 },
+ unicodeslot=0x338D,
+ },
+ [0x338E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x67 },
+ unicodeslot=0x338E,
+ },
+ [0x338F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x67 },
+ unicodeslot=0x338F,
+ },
+ [0x3390]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x48, 0x7A },
+ unicodeslot=0x3390,
+ },
+ [0x3391]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x48, 0x7A },
+ unicodeslot=0x3391,
+ },
+ [0x3392]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4D, 0x48, 0x7A },
+ unicodeslot=0x3392,
+ },
+ [0x3393]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x47, 0x48, 0x7A },
+ unicodeslot=0x3393,
+ },
+ [0x3394]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x54, 0x48, 0x7A },
+ unicodeslot=0x3394,
+ },
+ [0x3395]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x2113 },
+ unicodeslot=0x3395,
+ },
+ [0x3396]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x2113 },
+ unicodeslot=0x3396,
+ },
+ [0x3397]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x64, 0x2113 },
+ unicodeslot=0x3397,
+ },
+ [0x3398]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x2113 },
+ unicodeslot=0x3398,
+ },
+ [0x3399]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x66, 0x6D },
+ unicodeslot=0x3399,
+ },
+ [0x339A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E, 0x6D },
+ unicodeslot=0x339A,
+ },
+ [0x339B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x6D },
+ unicodeslot=0x339B,
+ },
+ [0x339C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x6D },
+ unicodeslot=0x339C,
+ },
+ [0x339D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x63, 0x6D },
+ unicodeslot=0x339D,
+ },
+ [0x339E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x6D },
+ unicodeslot=0x339E,
+ },
+ [0x339F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x6D, 0xB2 },
+ unicodeslot=0x339F,
+ },
+ [0x33A0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x63, 0x6D, 0xB2 },
+ unicodeslot=0x33A0,
+ },
+ [0x33A1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0xB2 },
+ unicodeslot=0x33A1,
+ },
+ [0x33A2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x6D, 0xB2 },
+ unicodeslot=0x33A2,
+ },
+ [0x33A3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x6D, 0xB3 },
+ unicodeslot=0x33A3,
+ },
+ [0x33A4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x63, 0x6D, 0xB3 },
+ unicodeslot=0x33A4,
+ },
+ [0x33A5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0xB3 },
+ unicodeslot=0x33A5,
+ },
+ [0x33A6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x6D, 0xB3 },
+ unicodeslot=0x33A6,
+ },
+ [0x33A7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x2215, 0x73 },
+ unicodeslot=0x33A7,
+ },
+ [0x33A8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x2215, 0x73, 0xB2 },
+ unicodeslot=0x33A8,
+ },
+ [0x33A9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x50, 0x61 },
+ unicodeslot=0x33A9,
+ },
+ [0x33AA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x50, 0x61 },
+ unicodeslot=0x33AA,
+ },
+ [0x33AB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4D, 0x50, 0x61 },
+ unicodeslot=0x33AB,
+ },
+ [0x33AC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x47, 0x50, 0x61 },
+ unicodeslot=0x33AC,
+ },
+ [0x33AD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x72, 0x61, 0x64 },
+ unicodeslot=0x33AD,
+ },
+ [0x33AE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x72, 0x61, 0x64, 0x2215, 0x73 },
+ unicodeslot=0x33AE,
+ },
+ [0x33AF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x72, 0x61, 0x64, 0x2215, 0x73, 0xB2 },
+ unicodeslot=0x33AF,
+ },
+ [0x33B0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x73 },
+ unicodeslot=0x33B0,
+ },
+ [0x33B1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E, 0x73 },
+ unicodeslot=0x33B1,
+ },
+ [0x33B2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x73 },
+ unicodeslot=0x33B2,
+ },
+ [0x33B3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x73 },
+ unicodeslot=0x33B3,
+ },
+ [0x33B4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x56 },
+ unicodeslot=0x33B4,
+ },
+ [0x33B5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E, 0x56 },
+ unicodeslot=0x33B5,
+ },
+ [0x33B6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x56 },
+ unicodeslot=0x33B6,
+ },
+ [0x33B7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x56 },
+ unicodeslot=0x33B7,
+ },
+ [0x33B8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x56 },
+ unicodeslot=0x33B8,
+ },
+ [0x33B9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4D, 0x56 },
+ unicodeslot=0x33B9,
+ },
+ [0x33BA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x57 },
+ unicodeslot=0x33BA,
+ },
+ [0x33BB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E, 0x57 },
+ unicodeslot=0x33BB,
+ },
+ [0x33BC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x3BC, 0x57 },
+ unicodeslot=0x33BC,
+ },
+ [0x33BD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x57 },
+ unicodeslot=0x33BD,
+ },
+ [0x33BE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x57 },
+ unicodeslot=0x33BE,
+ },
+ [0x33BF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4D, 0x57 },
+ unicodeslot=0x33BF,
+ },
+ [0x33C0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x3A9 },
+ unicodeslot=0x33C0,
+ },
+ [0x33C1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4D, 0x3A9 },
+ unicodeslot=0x33C1,
+ },
+ [0x33C2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x61, 0x2E, 0x6D, 0x2E },
+ unicodeslot=0x33C2,
+ },
+ [0x33C3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x42, 0x71 },
+ unicodeslot=0x33C3,
+ },
+ [0x33C4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x63, 0x63 },
+ unicodeslot=0x33C4,
+ },
+ [0x33C5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x63, 0x64 },
+ unicodeslot=0x33C5,
+ },
+ [0x33C6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x43, 0x2215, 0x6B, 0x67 },
+ unicodeslot=0x33C6,
+ },
+ [0x33C7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x43, 0x6F, 0x2E },
+ unicodeslot=0x33C7,
+ },
+ [0x33C8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x64, 0x42 },
+ unicodeslot=0x33C8,
+ },
+ [0x33C9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x47, 0x79 },
+ unicodeslot=0x33C9,
+ },
+ [0x33CA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x68, 0x61 },
+ unicodeslot=0x33CA,
+ },
+ [0x33CB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x48, 0x50 },
+ unicodeslot=0x33CB,
+ },
+ [0x33CC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x69, 0x6E },
+ unicodeslot=0x33CC,
+ },
+ [0x33CD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4B, 0x4B },
+ unicodeslot=0x33CD,
+ },
+ [0x33CE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4B, 0x4D },
+ unicodeslot=0x33CE,
+ },
+ [0x33CF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6B, 0x74 },
+ unicodeslot=0x33CF,
+ },
+ [0x33D0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6C, 0x6D },
+ unicodeslot=0x33D0,
+ },
+ [0x33D1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6C, 0x6E },
+ unicodeslot=0x33D1,
+ },
+ [0x33D2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6C, 0x6F, 0x67 },
+ unicodeslot=0x33D2,
+ },
+ [0x33D3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6C, 0x78 },
+ unicodeslot=0x33D3,
+ },
+ [0x33D4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x62 },
+ unicodeslot=0x33D4,
+ },
+ [0x33D5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x69, 0x6C },
+ unicodeslot=0x33D5,
+ },
+ [0x33D6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6D, 0x6F, 0x6C },
+ unicodeslot=0x33D6,
+ },
+ [0x33D7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x50, 0x48 },
+ unicodeslot=0x33D7,
+ },
+ [0x33D8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x70, 0x2E, 0x6D, 0x2E },
+ unicodeslot=0x33D8,
+ },
+ [0x33D9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x50, 0x50, 0x4D },
+ unicodeslot=0x33D9,
+ },
+ [0x33DA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x50, 0x52 },
+ unicodeslot=0x33DA,
+ },
+ [0x33DB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x73, 0x72 },
+ unicodeslot=0x33DB,
+ },
+ [0x33DC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x53, 0x76 },
+ unicodeslot=0x33DC,
+ },
+ [0x33DD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x57, 0x62 },
+ unicodeslot=0x33DD,
+ },
+ [0x33DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x56, 0x2215, 0x6D },
+ unicodeslot=0x33DE,
+ },
+ [0x33DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x41, 0x2215, 0x6D },
+ unicodeslot=0x33DF,
+ },
+ [0x33E0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x65E5 },
+ unicodeslot=0x33E0,
+ },
+ [0x33E1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x65E5 },
+ unicodeslot=0x33E1,
+ },
+ [0x33E2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x33, 0x65E5 },
+ unicodeslot=0x33E2,
+ },
+ [0x33E3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x34, 0x65E5 },
+ unicodeslot=0x33E3,
+ },
+ [0x33E4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x35, 0x65E5 },
+ unicodeslot=0x33E4,
+ },
+ [0x33E5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x36, 0x65E5 },
+ unicodeslot=0x33E5,
+ },
+ [0x33E6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x37, 0x65E5 },
+ unicodeslot=0x33E6,
+ },
+ [0x33E7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x38, 0x65E5 },
+ unicodeslot=0x33E7,
+ },
+ [0x33E8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x39, 0x65E5 },
+ unicodeslot=0x33E8,
+ },
+ [0x33E9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x30, 0x65E5 },
+ unicodeslot=0x33E9,
+ },
+ [0x33EA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x31, 0x65E5 },
+ unicodeslot=0x33EA,
+ },
+ [0x33EB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x32, 0x65E5 },
+ unicodeslot=0x33EB,
+ },
+ [0x33EC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x33, 0x65E5 },
+ unicodeslot=0x33EC,
+ },
+ [0x33ED]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x34, 0x65E5 },
+ unicodeslot=0x33ED,
+ },
+ [0x33EE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x35, 0x65E5 },
+ unicodeslot=0x33EE,
+ },
+ [0x33EF]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x36, 0x65E5 },
+ unicodeslot=0x33EF,
+ },
+ [0x33F0]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x37, 0x65E5 },
+ unicodeslot=0x33F0,
+ },
+ [0x33F1]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x38, 0x65E5 },
+ unicodeslot=0x33F1,
+ },
+ [0x33F2]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x31, 0x39, 0x65E5 },
+ unicodeslot=0x33F2,
+ },
+ [0x33F3]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x30, 0x65E5 },
+ unicodeslot=0x33F3,
+ },
+ [0x33F4]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x31, 0x65E5 },
+ unicodeslot=0x33F4,
+ },
+ [0x33F5]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x32, 0x65E5 },
+ unicodeslot=0x33F5,
+ },
+ [0x33F6]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x33, 0x65E5 },
+ unicodeslot=0x33F6,
+ },
+ [0x33F7]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x34, 0x65E5 },
+ unicodeslot=0x33F7,
+ },
+ [0x33F8]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x35, 0x65E5 },
+ unicodeslot=0x33F8,
+ },
+ [0x33F9]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x36, 0x65E5 },
+ unicodeslot=0x33F9,
+ },
+ [0x33FA]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x37, 0x65E5 },
+ unicodeslot=0x33FA,
+ },
+ [0x33FB]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x38, 0x65E5 },
+ unicodeslot=0x33FB,
+ },
+ [0x33FC]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x32, 0x39, 0x65E5 },
+ unicodeslot=0x33FC,
+ },
+ [0x33FD]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x33, 0x30, 0x65E5 },
+ unicodeslot=0x33FD,
+ },
+ [0x33FE]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x33, 0x31, 0x65E5 },
+ unicodeslot=0x33FE,
+ },
+ [0x33FF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "square", 0x67, 0x61, 0x6C },
+ unicodeslot=0x33FF,
+ },
+ [0x4DC0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC0,
+ },
+ [0x4DC1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC1,
+ },
+ [0x4DC2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC2,
+ },
+ [0x4DC3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC3,
+ },
+ [0x4DC4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC4,
+ },
+ [0x4DC5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC5,
+ },
+ [0x4DC6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC6,
+ },
+ [0x4DC7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC7,
+ },
+ [0x4DC8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC8,
+ },
+ [0x4DC9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DC9,
+ },
+ [0x4DCA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DCA,
+ },
+ [0x4DCB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DCB,
+ },
+ [0x4DCC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DCC,
+ },
+ [0x4DCD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DCD,
+ },
+ [0x4DCE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DCE,
+ },
+ [0x4DCF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DCF,
+ },
+ [0x4DD0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD0,
+ },
+ [0x4DD1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD1,
+ },
+ [0x4DD2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD2,
+ },
+ [0x4DD3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD3,
+ },
+ [0x4DD4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD4,
+ },
+ [0x4DD5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD5,
+ },
+ [0x4DD6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD6,
+ },
+ [0x4DD7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD7,
+ },
+ [0x4DD8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD8,
+ },
+ [0x4DD9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DD9,
+ },
+ [0x4DDA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DDA,
+ },
+ [0x4DDB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DDB,
+ },
+ [0x4DDC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DDC,
+ },
+ [0x4DDD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DDD,
+ },
+ [0x4DDE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DDE,
+ },
+ [0x4DDF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DDF,
+ },
+ [0x4DE0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE0,
+ },
+ [0x4DE1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE1,
+ },
+ [0x4DE2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE2,
+ },
+ [0x4DE3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE3,
+ },
+ [0x4DE4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE4,
+ },
+ [0x4DE5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE5,
+ },
+ [0x4DE6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE6,
+ },
+ [0x4DE7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE7,
+ },
+ [0x4DE8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE8,
+ },
+ [0x4DE9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DE9,
+ },
+ [0x4DEA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DEA,
+ },
+ [0x4DEB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DEB,
+ },
+ [0x4DEC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DEC,
+ },
+ [0x4DED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DED,
+ },
+ [0x4DEE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DEE,
+ },
+ [0x4DEF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DEF,
+ },
+ [0x4DF0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF0,
+ },
+ [0x4DF1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF1,
+ },
+ [0x4DF2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF2,
+ },
+ [0x4DF3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF3,
+ },
+ [0x4DF4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF4,
+ },
+ [0x4DF5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF5,
+ },
+ [0x4DF6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF6,
+ },
+ [0x4DF7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF7,
+ },
+ [0x4DF8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF8,
+ },
+ [0x4DF9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DF9,
+ },
+ [0x4DFA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DFA,
+ },
+ [0x4DFB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DFB,
+ },
+ [0x4DFC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DFC,
+ },
+ [0x4DFD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DFD,
+ },
+ [0x4DFE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DFE,
+ },
+ [0x4DFF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x4DFF,
+ },
+ [0xA000]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA000,
+ },
+ [0xA001]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA001,
+ },
+ [0xA002]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA002,
+ },
+ [0xA003]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA003,
+ },
+ [0xA004]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA004,
+ },
+ [0xA005]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA005,
+ },
+ [0xA006]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA006,
+ },
+ [0xA007]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA007,
+ },
+ [0xA008]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA008,
+ },
+ [0xA009]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA009,
+ },
+ [0xA00A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA00A,
+ },
+ [0xA00B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA00B,
+ },
+ [0xA00C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA00C,
+ },
+ [0xA00D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA00D,
+ },
+ [0xA00E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA00E,
+ },
+ [0xA00F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA00F,
+ },
+ [0xA010]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA010,
+ },
+ [0xA011]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA011,
+ },
+ [0xA012]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA012,
+ },
+ [0xA013]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA013,
+ },
+ [0xA014]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA014,
+ },
+ [0xA015]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0xA015,
+ },
+ [0xA016]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA016,
+ },
+ [0xA017]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA017,
+ },
+ [0xA018]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA018,
+ },
+ [0xA019]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA019,
+ },
+ [0xA01A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA01A,
+ },
+ [0xA01B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA01B,
+ },
+ [0xA01C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA01C,
+ },
+ [0xA01D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA01D,
+ },
+ [0xA01E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA01E,
+ },
+ [0xA01F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA01F,
+ },
+ [0xA020]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA020,
+ },
+ [0xA021]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA021,
+ },
+ [0xA022]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA022,
+ },
+ [0xA023]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA023,
+ },
+ [0xA024]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA024,
+ },
+ [0xA025]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA025,
+ },
+ [0xA026]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA026,
+ },
+ [0xA027]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA027,
+ },
+ [0xA028]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA028,
+ },
+ [0xA029]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA029,
+ },
+ [0xA02A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA02A,
+ },
+ [0xA02B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA02B,
+ },
+ [0xA02C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA02C,
+ },
+ [0xA02D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA02D,
+ },
+ [0xA02E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA02E,
+ },
+ [0xA02F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA02F,
+ },
+ [0xA030]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA030,
+ },
+ [0xA031]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA031,
+ },
+ [0xA032]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA032,
+ },
+ [0xA033]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA033,
+ },
+ [0xA034]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA034,
+ },
+ [0xA035]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA035,
+ },
+ [0xA036]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA036,
+ },
+ [0xA037]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA037,
+ },
+ [0xA038]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA038,
+ },
+ [0xA039]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA039,
+ },
+ [0xA03A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA03A,
+ },
+ [0xA03B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA03B,
+ },
+ [0xA03C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA03C,
+ },
+ [0xA03D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA03D,
+ },
+ [0xA03E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA03E,
+ },
+ [0xA03F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA03F,
+ },
+ [0xA040]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA040,
+ },
+ [0xA041]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA041,
+ },
+ [0xA042]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA042,
+ },
+ [0xA043]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA043,
+ },
+ [0xA044]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA044,
+ },
+ [0xA045]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA045,
+ },
+ [0xA046]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA046,
+ },
+ [0xA047]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA047,
+ },
+ [0xA048]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA048,
+ },
+ [0xA049]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA049,
+ },
+ [0xA04A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA04A,
+ },
+ [0xA04B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA04B,
+ },
+ [0xA04C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA04C,
+ },
+ [0xA04D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA04D,
+ },
+ [0xA04E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA04E,
+ },
+ [0xA04F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA04F,
+ },
+ [0xA050]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA050,
+ },
+ [0xA051]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA051,
+ },
+ [0xA052]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA052,
+ },
+ [0xA053]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA053,
+ },
+ [0xA054]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA054,
+ },
+ [0xA055]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA055,
+ },
+ [0xA056]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA056,
+ },
+ [0xA057]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA057,
+ },
+ [0xA058]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA058,
+ },
+ [0xA059]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA059,
+ },
+ [0xA05A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA05A,
+ },
+ [0xA05B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA05B,
+ },
+ [0xA05C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA05C,
+ },
+ [0xA05D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA05D,
+ },
+ [0xA05E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA05E,
+ },
+ [0xA05F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA05F,
+ },
+ [0xA060]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA060,
+ },
+ [0xA061]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA061,
+ },
+ [0xA062]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA062,
+ },
+ [0xA063]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA063,
+ },
+ [0xA064]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA064,
+ },
+ [0xA065]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA065,
+ },
+ [0xA066]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA066,
+ },
+ [0xA067]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA067,
+ },
+ [0xA068]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA068,
+ },
+ [0xA069]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA069,
+ },
+ [0xA06A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA06A,
+ },
+ [0xA06B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA06B,
+ },
+ [0xA06C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA06C,
+ },
+ [0xA06D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA06D,
+ },
+ [0xA06E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA06E,
+ },
+ [0xA06F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA06F,
+ },
+ [0xA070]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA070,
+ },
+ [0xA071]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA071,
+ },
+ [0xA072]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA072,
+ },
+ [0xA073]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA073,
+ },
+ [0xA074]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA074,
+ },
+ [0xA075]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA075,
+ },
+ [0xA076]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA076,
+ },
+ [0xA077]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA077,
+ },
+ [0xA078]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA078,
+ },
+ [0xA079]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA079,
+ },
+ [0xA07A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA07A,
+ },
+ [0xA07B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA07B,
+ },
+ [0xA07C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA07C,
+ },
+ [0xA07D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA07D,
+ },
+ [0xA07E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA07E,
+ },
+ [0xA07F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA07F,
+ },
+ [0xA080]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA080,
+ },
+ [0xA081]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA081,
+ },
+ [0xA082]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA082,
+ },
+ [0xA083]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA083,
+ },
+ [0xA084]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA084,
+ },
+ [0xA085]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA085,
+ },
+ [0xA086]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA086,
+ },
+ [0xA087]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA087,
+ },
+ [0xA088]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA088,
+ },
+ [0xA089]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA089,
+ },
+ [0xA08A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA08A,
+ },
+ [0xA08B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA08B,
+ },
+ [0xA08C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA08C,
+ },
+ [0xA08D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA08D,
+ },
+ [0xA08E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA08E,
+ },
+ [0xA08F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA08F,
+ },
+ [0xA090]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA090,
+ },
+ [0xA091]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA091,
+ },
+ [0xA092]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA092,
+ },
+ [0xA093]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA093,
+ },
+ [0xA094]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA094,
+ },
+ [0xA095]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA095,
+ },
+ [0xA096]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA096,
+ },
+ [0xA097]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA097,
+ },
+ [0xA098]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA098,
+ },
+ [0xA099]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA099,
+ },
+ [0xA09A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA09A,
+ },
+ [0xA09B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA09B,
+ },
+ [0xA09C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA09C,
+ },
+ [0xA09D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA09D,
+ },
+ [0xA09E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA09E,
+ },
+ [0xA09F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA09F,
+ },
+ [0xA0A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A0,
+ },
+ [0xA0A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A1,
+ },
+ [0xA0A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A2,
+ },
+ [0xA0A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A3,
+ },
+ [0xA0A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A4,
+ },
+ [0xA0A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A5,
+ },
+ [0xA0A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A6,
+ },
+ [0xA0A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A7,
+ },
+ [0xA0A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A8,
+ },
+ [0xA0A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0A9,
+ },
+ [0xA0AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0AA,
+ },
+ [0xA0AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0AB,
+ },
+ [0xA0AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0AC,
+ },
+ [0xA0AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0AD,
+ },
+ [0xA0AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0AE,
+ },
+ [0xA0AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0AF,
+ },
+ [0xA0B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B0,
+ },
+ [0xA0B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B1,
+ },
+ [0xA0B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B2,
+ },
+ [0xA0B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B3,
+ },
+ [0xA0B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B4,
+ },
+ [0xA0B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B5,
+ },
+ [0xA0B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B6,
+ },
+ [0xA0B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B7,
+ },
+ [0xA0B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B8,
+ },
+ [0xA0B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0B9,
+ },
+ [0xA0BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0BA,
+ },
+ [0xA0BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0BB,
+ },
+ [0xA0BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0BC,
+ },
+ [0xA0BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0BD,
+ },
+ [0xA0BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0BE,
+ },
+ [0xA0BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0BF,
+ },
+ [0xA0C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C0,
+ },
+ [0xA0C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C1,
+ },
+ [0xA0C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C2,
+ },
+ [0xA0C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C3,
+ },
+ [0xA0C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C4,
+ },
+ [0xA0C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C5,
+ },
+ [0xA0C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C6,
+ },
+ [0xA0C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C7,
+ },
+ [0xA0C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C8,
+ },
+ [0xA0C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0C9,
+ },
+ [0xA0CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0CA,
+ },
+ [0xA0CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0CB,
+ },
+ [0xA0CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0CC,
+ },
+ [0xA0CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0CD,
+ },
+ [0xA0CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0CE,
+ },
+ [0xA0CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0CF,
+ },
+ [0xA0D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D0,
+ },
+ [0xA0D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D1,
+ },
+ [0xA0D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D2,
+ },
+ [0xA0D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D3,
+ },
+ [0xA0D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D4,
+ },
+ [0xA0D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D5,
+ },
+ [0xA0D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D6,
+ },
+ [0xA0D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D7,
+ },
+ [0xA0D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D8,
+ },
+ [0xA0D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0D9,
+ },
+ [0xA0DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0DA,
+ },
+ [0xA0DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0DB,
+ },
+ [0xA0DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0DC,
+ },
+ [0xA0DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0DD,
+ },
+ [0xA0DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0DE,
+ },
+ [0xA0DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0DF,
+ },
+ [0xA0E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E0,
+ },
+ [0xA0E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E1,
+ },
+ [0xA0E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E2,
+ },
+ [0xA0E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E3,
+ },
+ [0xA0E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E4,
+ },
+ [0xA0E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E5,
+ },
+ [0xA0E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E6,
+ },
+ [0xA0E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E7,
+ },
+ [0xA0E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E8,
+ },
+ [0xA0E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0E9,
+ },
+ [0xA0EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0EA,
+ },
+ [0xA0EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0EB,
+ },
+ [0xA0EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0EC,
+ },
+ [0xA0ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0ED,
+ },
+ [0xA0EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0EE,
+ },
+ [0xA0EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0EF,
+ },
+ [0xA0F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F0,
+ },
+ [0xA0F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F1,
+ },
+ [0xA0F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F2,
+ },
+ [0xA0F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F3,
+ },
+ [0xA0F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F4,
+ },
+ [0xA0F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F5,
+ },
+ [0xA0F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F6,
+ },
+ [0xA0F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F7,
+ },
+ [0xA0F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F8,
+ },
+ [0xA0F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0F9,
+ },
+ [0xA0FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0FA,
+ },
+ [0xA0FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0FB,
+ },
+ [0xA0FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0FC,
+ },
+ [0xA0FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0FD,
+ },
+ [0xA0FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0FE,
+ },
+ [0xA0FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA0FF,
+ },
+ [0xA100]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA100,
+ },
+ [0xA101]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA101,
+ },
+ [0xA102]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA102,
+ },
+ [0xA103]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA103,
+ },
+ [0xA104]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA104,
+ },
+ [0xA105]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA105,
+ },
+ [0xA106]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA106,
+ },
+ [0xA107]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA107,
+ },
+ [0xA108]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA108,
+ },
+ [0xA109]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA109,
+ },
+ [0xA10A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA10A,
+ },
+ [0xA10B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA10B,
+ },
+ [0xA10C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA10C,
+ },
+ [0xA10D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA10D,
+ },
+ [0xA10E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA10E,
+ },
+ [0xA10F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA10F,
+ },
+ [0xA110]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA110,
+ },
+ [0xA111]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA111,
+ },
+ [0xA112]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA112,
+ },
+ [0xA113]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA113,
+ },
+ [0xA114]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA114,
+ },
+ [0xA115]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA115,
+ },
+ [0xA116]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA116,
+ },
+ [0xA117]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA117,
+ },
+ [0xA118]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA118,
+ },
+ [0xA119]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA119,
+ },
+ [0xA11A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA11A,
+ },
+ [0xA11B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA11B,
+ },
+ [0xA11C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA11C,
+ },
+ [0xA11D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA11D,
+ },
+ [0xA11E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA11E,
+ },
+ [0xA11F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA11F,
+ },
+ [0xA120]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA120,
+ },
+ [0xA121]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA121,
+ },
+ [0xA122]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA122,
+ },
+ [0xA123]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA123,
+ },
+ [0xA124]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA124,
+ },
+ [0xA125]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA125,
+ },
+ [0xA126]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA126,
+ },
+ [0xA127]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA127,
+ },
+ [0xA128]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA128,
+ },
+ [0xA129]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA129,
+ },
+ [0xA12A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA12A,
+ },
+ [0xA12B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA12B,
+ },
+ [0xA12C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA12C,
+ },
+ [0xA12D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA12D,
+ },
+ [0xA12E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA12E,
+ },
+ [0xA12F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA12F,
+ },
+ [0xA130]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA130,
+ },
+ [0xA131]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA131,
+ },
+ [0xA132]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA132,
+ },
+ [0xA133]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA133,
+ },
+ [0xA134]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA134,
+ },
+ [0xA135]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA135,
+ },
+ [0xA136]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA136,
+ },
+ [0xA137]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA137,
+ },
+ [0xA138]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA138,
+ },
+ [0xA139]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA139,
+ },
+ [0xA13A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA13A,
+ },
+ [0xA13B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA13B,
+ },
+ [0xA13C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA13C,
+ },
+ [0xA13D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA13D,
+ },
+ [0xA13E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA13E,
+ },
+ [0xA13F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA13F,
+ },
+ [0xA140]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA140,
+ },
+ [0xA141]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA141,
+ },
+ [0xA142]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA142,
+ },
+ [0xA143]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA143,
+ },
+ [0xA144]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA144,
+ },
+ [0xA145]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA145,
+ },
+ [0xA146]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA146,
+ },
+ [0xA147]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA147,
+ },
+ [0xA148]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA148,
+ },
+ [0xA149]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA149,
+ },
+ [0xA14A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA14A,
+ },
+ [0xA14B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA14B,
+ },
+ [0xA14C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA14C,
+ },
+ [0xA14D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA14D,
+ },
+ [0xA14E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA14E,
+ },
+ [0xA14F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA14F,
+ },
+ [0xA150]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA150,
+ },
+ [0xA151]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA151,
+ },
+ [0xA152]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA152,
+ },
+ [0xA153]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA153,
+ },
+ [0xA154]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA154,
+ },
+ [0xA155]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA155,
+ },
+ [0xA156]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA156,
+ },
+ [0xA157]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA157,
+ },
+ [0xA158]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA158,
+ },
+ [0xA159]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA159,
+ },
+ [0xA15A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA15A,
+ },
+ [0xA15B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA15B,
+ },
+ [0xA15C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA15C,
+ },
+ [0xA15D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA15D,
+ },
+ [0xA15E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA15E,
+ },
+ [0xA15F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA15F,
+ },
+ [0xA160]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA160,
+ },
+ [0xA161]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA161,
+ },
+ [0xA162]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA162,
+ },
+ [0xA163]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA163,
+ },
+ [0xA164]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA164,
+ },
+ [0xA165]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA165,
+ },
+ [0xA166]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA166,
+ },
+ [0xA167]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA167,
+ },
+ [0xA168]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA168,
+ },
+ [0xA169]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA169,
+ },
+ [0xA16A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA16A,
+ },
+ [0xA16B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA16B,
+ },
+ [0xA16C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA16C,
+ },
+ [0xA16D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA16D,
+ },
+ [0xA16E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA16E,
+ },
+ [0xA16F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA16F,
+ },
+ [0xA170]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA170,
+ },
+ [0xA171]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA171,
+ },
+ [0xA172]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA172,
+ },
+ [0xA173]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA173,
+ },
+ [0xA174]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA174,
+ },
+ [0xA175]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA175,
+ },
+ [0xA176]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA176,
+ },
+ [0xA177]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA177,
+ },
+ [0xA178]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA178,
+ },
+ [0xA179]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA179,
+ },
+ [0xA17A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA17A,
+ },
+ [0xA17B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA17B,
+ },
+ [0xA17C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA17C,
+ },
+ [0xA17D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA17D,
+ },
+ [0xA17E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA17E,
+ },
+ [0xA17F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA17F,
+ },
+ [0xA180]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA180,
+ },
+ [0xA181]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA181,
+ },
+ [0xA182]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA182,
+ },
+ [0xA183]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA183,
+ },
+ [0xA184]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA184,
+ },
+ [0xA185]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA185,
+ },
+ [0xA186]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA186,
+ },
+ [0xA187]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA187,
+ },
+ [0xA188]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA188,
+ },
+ [0xA189]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA189,
+ },
+ [0xA18A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA18A,
+ },
+ [0xA18B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA18B,
+ },
+ [0xA18C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA18C,
+ },
+ [0xA18D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA18D,
+ },
+ [0xA18E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA18E,
+ },
+ [0xA18F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA18F,
+ },
+ [0xA190]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA190,
+ },
+ [0xA191]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA191,
+ },
+ [0xA192]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA192,
+ },
+ [0xA193]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA193,
+ },
+ [0xA194]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA194,
+ },
+ [0xA195]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA195,
+ },
+ [0xA196]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA196,
+ },
+ [0xA197]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA197,
+ },
+ [0xA198]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA198,
+ },
+ [0xA199]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA199,
+ },
+ [0xA19A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA19A,
+ },
+ [0xA19B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA19B,
+ },
+ [0xA19C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA19C,
+ },
+ [0xA19D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA19D,
+ },
+ [0xA19E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA19E,
+ },
+ [0xA19F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA19F,
+ },
+ [0xA1A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A0,
+ },
+ [0xA1A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A1,
+ },
+ [0xA1A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A2,
+ },
+ [0xA1A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A3,
+ },
+ [0xA1A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A4,
+ },
+ [0xA1A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A5,
+ },
+ [0xA1A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A6,
+ },
+ [0xA1A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A7,
+ },
+ [0xA1A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A8,
+ },
+ [0xA1A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1A9,
+ },
+ [0xA1AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1AA,
+ },
+ [0xA1AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1AB,
+ },
+ [0xA1AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1AC,
+ },
+ [0xA1AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1AD,
+ },
+ [0xA1AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1AE,
+ },
+ [0xA1AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1AF,
+ },
+ [0xA1B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B0,
+ },
+ [0xA1B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B1,
+ },
+ [0xA1B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B2,
+ },
+ [0xA1B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B3,
+ },
+ [0xA1B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B4,
+ },
+ [0xA1B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B5,
+ },
+ [0xA1B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B6,
+ },
+ [0xA1B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B7,
+ },
+ [0xA1B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B8,
+ },
+ [0xA1B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1B9,
+ },
+ [0xA1BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1BA,
+ },
+ [0xA1BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1BB,
+ },
+ [0xA1BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1BC,
+ },
+ [0xA1BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1BD,
+ },
+ [0xA1BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1BE,
+ },
+ [0xA1BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1BF,
+ },
+ [0xA1C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C0,
+ },
+ [0xA1C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C1,
+ },
+ [0xA1C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C2,
+ },
+ [0xA1C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C3,
+ },
+ [0xA1C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C4,
+ },
+ [0xA1C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C5,
+ },
+ [0xA1C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C6,
+ },
+ [0xA1C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C7,
+ },
+ [0xA1C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C8,
+ },
+ [0xA1C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1C9,
+ },
+ [0xA1CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1CA,
+ },
+ [0xA1CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1CB,
+ },
+ [0xA1CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1CC,
+ },
+ [0xA1CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1CD,
+ },
+ [0xA1CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1CE,
+ },
+ [0xA1CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1CF,
+ },
+ [0xA1D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D0,
+ },
+ [0xA1D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D1,
+ },
+ [0xA1D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D2,
+ },
+ [0xA1D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D3,
+ },
+ [0xA1D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D4,
+ },
+ [0xA1D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D5,
+ },
+ [0xA1D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D6,
+ },
+ [0xA1D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D7,
+ },
+ [0xA1D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D8,
+ },
+ [0xA1D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1D9,
+ },
+ [0xA1DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1DA,
+ },
+ [0xA1DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1DB,
+ },
+ [0xA1DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1DC,
+ },
+ [0xA1DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1DD,
+ },
+ [0xA1DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1DE,
+ },
+ [0xA1DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1DF,
+ },
+ [0xA1E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E0,
+ },
+ [0xA1E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E1,
+ },
+ [0xA1E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E2,
+ },
+ [0xA1E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E3,
+ },
+ [0xA1E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E4,
+ },
+ [0xA1E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E5,
+ },
+ [0xA1E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E6,
+ },
+ [0xA1E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E7,
+ },
+ [0xA1E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E8,
+ },
+ [0xA1E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1E9,
+ },
+ [0xA1EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1EA,
+ },
+ [0xA1EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1EB,
+ },
+ [0xA1EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1EC,
+ },
+ [0xA1ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1ED,
+ },
+ [0xA1EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1EE,
+ },
+ [0xA1EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1EF,
+ },
+ [0xA1F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F0,
+ },
+ [0xA1F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F1,
+ },
+ [0xA1F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F2,
+ },
+ [0xA1F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F3,
+ },
+ [0xA1F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F4,
+ },
+ [0xA1F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F5,
+ },
+ [0xA1F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F6,
+ },
+ [0xA1F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F7,
+ },
+ [0xA1F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F8,
+ },
+ [0xA1F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1F9,
+ },
+ [0xA1FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1FA,
+ },
+ [0xA1FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1FB,
+ },
+ [0xA1FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1FC,
+ },
+ [0xA1FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1FD,
+ },
+ [0xA1FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1FE,
+ },
+ [0xA1FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA1FF,
+ },
+ [0xA200]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA200,
+ },
+ [0xA201]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA201,
+ },
+ [0xA202]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA202,
+ },
+ [0xA203]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA203,
+ },
+ [0xA204]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA204,
+ },
+ [0xA205]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA205,
+ },
+ [0xA206]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA206,
+ },
+ [0xA207]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA207,
+ },
+ [0xA208]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA208,
+ },
+ [0xA209]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA209,
+ },
+ [0xA20A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA20A,
+ },
+ [0xA20B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA20B,
+ },
+ [0xA20C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA20C,
+ },
+ [0xA20D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA20D,
+ },
+ [0xA20E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA20E,
+ },
+ [0xA20F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA20F,
+ },
+ [0xA210]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA210,
+ },
+ [0xA211]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA211,
+ },
+ [0xA212]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA212,
+ },
+ [0xA213]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA213,
+ },
+ [0xA214]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA214,
+ },
+ [0xA215]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA215,
+ },
+ [0xA216]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA216,
+ },
+ [0xA217]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA217,
+ },
+ [0xA218]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA218,
+ },
+ [0xA219]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA219,
+ },
+ [0xA21A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA21A,
+ },
+ [0xA21B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA21B,
+ },
+ [0xA21C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA21C,
+ },
+ [0xA21D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA21D,
+ },
+ [0xA21E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA21E,
+ },
+ [0xA21F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA21F,
+ },
+ [0xA220]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA220,
+ },
+ [0xA221]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA221,
+ },
+ [0xA222]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA222,
+ },
+ [0xA223]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA223,
+ },
+ [0xA224]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA224,
+ },
+ [0xA225]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA225,
+ },
+ [0xA226]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA226,
+ },
+ [0xA227]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA227,
+ },
+ [0xA228]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA228,
+ },
+ [0xA229]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA229,
+ },
+ [0xA22A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA22A,
+ },
+ [0xA22B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA22B,
+ },
+ [0xA22C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA22C,
+ },
+ [0xA22D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA22D,
+ },
+ [0xA22E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA22E,
+ },
+ [0xA22F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA22F,
+ },
+ [0xA230]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA230,
+ },
+ [0xA231]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA231,
+ },
+ [0xA232]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA232,
+ },
+ [0xA233]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA233,
+ },
+ [0xA234]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA234,
+ },
+ [0xA235]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA235,
+ },
+ [0xA236]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA236,
+ },
+ [0xA237]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA237,
+ },
+ [0xA238]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA238,
+ },
+ [0xA239]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA239,
+ },
+ [0xA23A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA23A,
+ },
+ [0xA23B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA23B,
+ },
+ [0xA23C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA23C,
+ },
+ [0xA23D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA23D,
+ },
+ [0xA23E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA23E,
+ },
+ [0xA23F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA23F,
+ },
+ [0xA240]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA240,
+ },
+ [0xA241]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA241,
+ },
+ [0xA242]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA242,
+ },
+ [0xA243]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA243,
+ },
+ [0xA244]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA244,
+ },
+ [0xA245]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA245,
+ },
+ [0xA246]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA246,
+ },
+ [0xA247]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA247,
+ },
+ [0xA248]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA248,
+ },
+ [0xA249]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA249,
+ },
+ [0xA24A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA24A,
+ },
+ [0xA24B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA24B,
+ },
+ [0xA24C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA24C,
+ },
+ [0xA24D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA24D,
+ },
+ [0xA24E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA24E,
+ },
+ [0xA24F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA24F,
+ },
+ [0xA250]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA250,
+ },
+ [0xA251]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA251,
+ },
+ [0xA252]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA252,
+ },
+ [0xA253]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA253,
+ },
+ [0xA254]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA254,
+ },
+ [0xA255]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA255,
+ },
+ [0xA256]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA256,
+ },
+ [0xA257]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA257,
+ },
+ [0xA258]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA258,
+ },
+ [0xA259]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA259,
+ },
+ [0xA25A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA25A,
+ },
+ [0xA25B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA25B,
+ },
+ [0xA25C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA25C,
+ },
+ [0xA25D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA25D,
+ },
+ [0xA25E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA25E,
+ },
+ [0xA25F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA25F,
+ },
+ [0xA260]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA260,
+ },
+ [0xA261]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA261,
+ },
+ [0xA262]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA262,
+ },
+ [0xA263]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA263,
+ },
+ [0xA264]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA264,
+ },
+ [0xA265]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA265,
+ },
+ [0xA266]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA266,
+ },
+ [0xA267]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA267,
+ },
+ [0xA268]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA268,
+ },
+ [0xA269]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA269,
+ },
+ [0xA26A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA26A,
+ },
+ [0xA26B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA26B,
+ },
+ [0xA26C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA26C,
+ },
+ [0xA26D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA26D,
+ },
+ [0xA26E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA26E,
+ },
+ [0xA26F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA26F,
+ },
+ [0xA270]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA270,
+ },
+ [0xA271]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA271,
+ },
+ [0xA272]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA272,
+ },
+ [0xA273]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA273,
+ },
+ [0xA274]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA274,
+ },
+ [0xA275]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA275,
+ },
+ [0xA276]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA276,
+ },
+ [0xA277]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA277,
+ },
+ [0xA278]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA278,
+ },
+ [0xA279]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA279,
+ },
+ [0xA27A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA27A,
+ },
+ [0xA27B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA27B,
+ },
+ [0xA27C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA27C,
+ },
+ [0xA27D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA27D,
+ },
+ [0xA27E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA27E,
+ },
+ [0xA27F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA27F,
+ },
+ [0xA280]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA280,
+ },
+ [0xA281]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA281,
+ },
+ [0xA282]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA282,
+ },
+ [0xA283]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA283,
+ },
+ [0xA284]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA284,
+ },
+ [0xA285]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA285,
+ },
+ [0xA286]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA286,
+ },
+ [0xA287]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA287,
+ },
+ [0xA288]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA288,
+ },
+ [0xA289]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA289,
+ },
+ [0xA28A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA28A,
+ },
+ [0xA28B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA28B,
+ },
+ [0xA28C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA28C,
+ },
+ [0xA28D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA28D,
+ },
+ [0xA28E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA28E,
+ },
+ [0xA28F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA28F,
+ },
+ [0xA290]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA290,
+ },
+ [0xA291]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA291,
+ },
+ [0xA292]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA292,
+ },
+ [0xA293]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA293,
+ },
+ [0xA294]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA294,
+ },
+ [0xA295]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA295,
+ },
+ [0xA296]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA296,
+ },
+ [0xA297]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA297,
+ },
+ [0xA298]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA298,
+ },
+ [0xA299]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA299,
+ },
+ [0xA29A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA29A,
+ },
+ [0xA29B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA29B,
+ },
+ [0xA29C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA29C,
+ },
+ [0xA29D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA29D,
+ },
+ [0xA29E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA29E,
+ },
+ [0xA29F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA29F,
+ },
+ [0xA2A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A0,
+ },
+ [0xA2A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A1,
+ },
+ [0xA2A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A2,
+ },
+ [0xA2A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A3,
+ },
+ [0xA2A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A4,
+ },
+ [0xA2A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A5,
+ },
+ [0xA2A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A6,
+ },
+ [0xA2A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A7,
+ },
+ [0xA2A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A8,
+ },
+ [0xA2A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2A9,
+ },
+ [0xA2AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2AA,
+ },
+ [0xA2AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2AB,
+ },
+ [0xA2AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2AC,
+ },
+ [0xA2AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2AD,
+ },
+ [0xA2AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2AE,
+ },
+ [0xA2AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2AF,
+ },
+ [0xA2B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B0,
+ },
+ [0xA2B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B1,
+ },
+ [0xA2B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B2,
+ },
+ [0xA2B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B3,
+ },
+ [0xA2B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B4,
+ },
+ [0xA2B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B5,
+ },
+ [0xA2B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B6,
+ },
+ [0xA2B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B7,
+ },
+ [0xA2B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B8,
+ },
+ [0xA2B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2B9,
+ },
+ [0xA2BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2BA,
+ },
+ [0xA2BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2BB,
+ },
+ [0xA2BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2BC,
+ },
+ [0xA2BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2BD,
+ },
+ [0xA2BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2BE,
+ },
+ [0xA2BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2BF,
+ },
+ [0xA2C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C0,
+ },
+ [0xA2C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C1,
+ },
+ [0xA2C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C2,
+ },
+ [0xA2C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C3,
+ },
+ [0xA2C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C4,
+ },
+ [0xA2C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C5,
+ },
+ [0xA2C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C6,
+ },
+ [0xA2C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C7,
+ },
+ [0xA2C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C8,
+ },
+ [0xA2C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2C9,
+ },
+ [0xA2CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2CA,
+ },
+ [0xA2CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2CB,
+ },
+ [0xA2CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2CC,
+ },
+ [0xA2CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2CD,
+ },
+ [0xA2CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2CE,
+ },
+ [0xA2CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2CF,
+ },
+ [0xA2D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D0,
+ },
+ [0xA2D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D1,
+ },
+ [0xA2D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D2,
+ },
+ [0xA2D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D3,
+ },
+ [0xA2D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D4,
+ },
+ [0xA2D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D5,
+ },
+ [0xA2D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D6,
+ },
+ [0xA2D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D7,
+ },
+ [0xA2D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D8,
+ },
+ [0xA2D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2D9,
+ },
+ [0xA2DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2DA,
+ },
+ [0xA2DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2DB,
+ },
+ [0xA2DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2DC,
+ },
+ [0xA2DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2DD,
+ },
+ [0xA2DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2DE,
+ },
+ [0xA2DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2DF,
+ },
+ [0xA2E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E0,
+ },
+ [0xA2E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E1,
+ },
+ [0xA2E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E2,
+ },
+ [0xA2E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E3,
+ },
+ [0xA2E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E4,
+ },
+ [0xA2E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E5,
+ },
+ [0xA2E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E6,
+ },
+ [0xA2E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E7,
+ },
+ [0xA2E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E8,
+ },
+ [0xA2E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2E9,
+ },
+ [0xA2EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2EA,
+ },
+ [0xA2EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2EB,
+ },
+ [0xA2EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2EC,
+ },
+ [0xA2ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2ED,
+ },
+ [0xA2EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2EE,
+ },
+ [0xA2EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2EF,
+ },
+ [0xA2F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F0,
+ },
+ [0xA2F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F1,
+ },
+ [0xA2F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F2,
+ },
+ [0xA2F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F3,
+ },
+ [0xA2F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F4,
+ },
+ [0xA2F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F5,
+ },
+ [0xA2F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F6,
+ },
+ [0xA2F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F7,
+ },
+ [0xA2F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F8,
+ },
+ [0xA2F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2F9,
+ },
+ [0xA2FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2FA,
+ },
+ [0xA2FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2FB,
+ },
+ [0xA2FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2FC,
+ },
+ [0xA2FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2FD,
+ },
+ [0xA2FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2FE,
+ },
+ [0xA2FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA2FF,
+ },
+ [0xA300]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA300,
+ },
+ [0xA301]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA301,
+ },
+ [0xA302]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA302,
+ },
+ [0xA303]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA303,
+ },
+ [0xA304]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA304,
+ },
+ [0xA305]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA305,
+ },
+ [0xA306]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA306,
+ },
+ [0xA307]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA307,
+ },
+ [0xA308]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA308,
+ },
+ [0xA309]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA309,
+ },
+ [0xA30A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA30A,
+ },
+ [0xA30B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA30B,
+ },
+ [0xA30C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA30C,
+ },
+ [0xA30D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA30D,
+ },
+ [0xA30E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA30E,
+ },
+ [0xA30F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA30F,
+ },
+ [0xA310]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA310,
+ },
+ [0xA311]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA311,
+ },
+ [0xA312]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA312,
+ },
+ [0xA313]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA313,
+ },
+ [0xA314]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA314,
+ },
+ [0xA315]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA315,
+ },
+ [0xA316]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA316,
+ },
+ [0xA317]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA317,
+ },
+ [0xA318]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA318,
+ },
+ [0xA319]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA319,
+ },
+ [0xA31A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA31A,
+ },
+ [0xA31B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA31B,
+ },
+ [0xA31C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA31C,
+ },
+ [0xA31D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA31D,
+ },
+ [0xA31E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA31E,
+ },
+ [0xA31F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA31F,
+ },
+ [0xA320]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA320,
+ },
+ [0xA321]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA321,
+ },
+ [0xA322]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA322,
+ },
+ [0xA323]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA323,
+ },
+ [0xA324]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA324,
+ },
+ [0xA325]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA325,
+ },
+ [0xA326]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA326,
+ },
+ [0xA327]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA327,
+ },
+ [0xA328]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA328,
+ },
+ [0xA329]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA329,
+ },
+ [0xA32A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA32A,
+ },
+ [0xA32B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA32B,
+ },
+ [0xA32C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA32C,
+ },
+ [0xA32D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA32D,
+ },
+ [0xA32E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA32E,
+ },
+ [0xA32F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA32F,
+ },
+ [0xA330]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA330,
+ },
+ [0xA331]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA331,
+ },
+ [0xA332]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA332,
+ },
+ [0xA333]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA333,
+ },
+ [0xA334]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA334,
+ },
+ [0xA335]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA335,
+ },
+ [0xA336]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA336,
+ },
+ [0xA337]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA337,
+ },
+ [0xA338]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA338,
+ },
+ [0xA339]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA339,
+ },
+ [0xA33A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA33A,
+ },
+ [0xA33B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA33B,
+ },
+ [0xA33C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA33C,
+ },
+ [0xA33D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA33D,
+ },
+ [0xA33E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA33E,
+ },
+ [0xA33F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA33F,
+ },
+ [0xA340]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA340,
+ },
+ [0xA341]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA341,
+ },
+ [0xA342]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA342,
+ },
+ [0xA343]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA343,
+ },
+ [0xA344]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA344,
+ },
+ [0xA345]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA345,
+ },
+ [0xA346]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA346,
+ },
+ [0xA347]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA347,
+ },
+ [0xA348]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA348,
+ },
+ [0xA349]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA349,
+ },
+ [0xA34A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA34A,
+ },
+ [0xA34B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA34B,
+ },
+ [0xA34C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA34C,
+ },
+ [0xA34D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA34D,
+ },
+ [0xA34E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA34E,
+ },
+ [0xA34F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA34F,
+ },
+ [0xA350]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA350,
+ },
+ [0xA351]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA351,
+ },
+ [0xA352]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA352,
+ },
+ [0xA353]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA353,
+ },
+ [0xA354]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA354,
+ },
+ [0xA355]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA355,
+ },
+ [0xA356]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA356,
+ },
+ [0xA357]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA357,
+ },
+ [0xA358]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA358,
+ },
+ [0xA359]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA359,
+ },
+ [0xA35A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA35A,
+ },
+ [0xA35B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA35B,
+ },
+ [0xA35C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA35C,
+ },
+ [0xA35D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA35D,
+ },
+ [0xA35E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA35E,
+ },
+ [0xA35F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA35F,
+ },
+ [0xA360]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA360,
+ },
+ [0xA361]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA361,
+ },
+ [0xA362]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA362,
+ },
+ [0xA363]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA363,
+ },
+ [0xA364]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA364,
+ },
+ [0xA365]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA365,
+ },
+ [0xA366]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA366,
+ },
+ [0xA367]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA367,
+ },
+ [0xA368]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA368,
+ },
+ [0xA369]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA369,
+ },
+ [0xA36A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA36A,
+ },
+ [0xA36B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA36B,
+ },
+ [0xA36C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA36C,
+ },
+ [0xA36D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA36D,
+ },
+ [0xA36E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA36E,
+ },
+ [0xA36F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA36F,
+ },
+ [0xA370]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA370,
+ },
+ [0xA371]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA371,
+ },
+ [0xA372]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA372,
+ },
+ [0xA373]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA373,
+ },
+ [0xA374]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA374,
+ },
+ [0xA375]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA375,
+ },
+ [0xA376]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA376,
+ },
+ [0xA377]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA377,
+ },
+ [0xA378]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA378,
+ },
+ [0xA379]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA379,
+ },
+ [0xA37A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA37A,
+ },
+ [0xA37B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA37B,
+ },
+ [0xA37C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA37C,
+ },
+ [0xA37D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA37D,
+ },
+ [0xA37E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA37E,
+ },
+ [0xA37F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA37F,
+ },
+ [0xA380]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA380,
+ },
+ [0xA381]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA381,
+ },
+ [0xA382]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA382,
+ },
+ [0xA383]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA383,
+ },
+ [0xA384]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA384,
+ },
+ [0xA385]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA385,
+ },
+ [0xA386]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA386,
+ },
+ [0xA387]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA387,
+ },
+ [0xA388]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA388,
+ },
+ [0xA389]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA389,
+ },
+ [0xA38A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA38A,
+ },
+ [0xA38B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA38B,
+ },
+ [0xA38C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA38C,
+ },
+ [0xA38D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA38D,
+ },
+ [0xA38E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA38E,
+ },
+ [0xA38F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA38F,
+ },
+ [0xA390]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA390,
+ },
+ [0xA391]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA391,
+ },
+ [0xA392]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA392,
+ },
+ [0xA393]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA393,
+ },
+ [0xA394]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA394,
+ },
+ [0xA395]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA395,
+ },
+ [0xA396]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA396,
+ },
+ [0xA397]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA397,
+ },
+ [0xA398]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA398,
+ },
+ [0xA399]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA399,
+ },
+ [0xA39A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA39A,
+ },
+ [0xA39B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA39B,
+ },
+ [0xA39C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA39C,
+ },
+ [0xA39D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA39D,
+ },
+ [0xA39E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA39E,
+ },
+ [0xA39F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA39F,
+ },
+ [0xA3A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A0,
+ },
+ [0xA3A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A1,
+ },
+ [0xA3A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A2,
+ },
+ [0xA3A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A3,
+ },
+ [0xA3A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A4,
+ },
+ [0xA3A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A5,
+ },
+ [0xA3A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A6,
+ },
+ [0xA3A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A7,
+ },
+ [0xA3A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A8,
+ },
+ [0xA3A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3A9,
+ },
+ [0xA3AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3AA,
+ },
+ [0xA3AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3AB,
+ },
+ [0xA3AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3AC,
+ },
+ [0xA3AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3AD,
+ },
+ [0xA3AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3AE,
+ },
+ [0xA3AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3AF,
+ },
+ [0xA3B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B0,
+ },
+ [0xA3B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B1,
+ },
+ [0xA3B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B2,
+ },
+ [0xA3B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B3,
+ },
+ [0xA3B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B4,
+ },
+ [0xA3B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B5,
+ },
+ [0xA3B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B6,
+ },
+ [0xA3B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B7,
+ },
+ [0xA3B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B8,
+ },
+ [0xA3B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3B9,
+ },
+ [0xA3BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3BA,
+ },
+ [0xA3BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3BB,
+ },
+ [0xA3BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3BC,
+ },
+ [0xA3BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3BD,
+ },
+ [0xA3BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3BE,
+ },
+ [0xA3BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3BF,
+ },
+ [0xA3C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C0,
+ },
+ [0xA3C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C1,
+ },
+ [0xA3C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C2,
+ },
+ [0xA3C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C3,
+ },
+ [0xA3C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C4,
+ },
+ [0xA3C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C5,
+ },
+ [0xA3C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C6,
+ },
+ [0xA3C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C7,
+ },
+ [0xA3C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C8,
+ },
+ [0xA3C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3C9,
+ },
+ [0xA3CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3CA,
+ },
+ [0xA3CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3CB,
+ },
+ [0xA3CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3CC,
+ },
+ [0xA3CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3CD,
+ },
+ [0xA3CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3CE,
+ },
+ [0xA3CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3CF,
+ },
+ [0xA3D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D0,
+ },
+ [0xA3D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D1,
+ },
+ [0xA3D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D2,
+ },
+ [0xA3D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D3,
+ },
+ [0xA3D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D4,
+ },
+ [0xA3D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D5,
+ },
+ [0xA3D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D6,
+ },
+ [0xA3D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D7,
+ },
+ [0xA3D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D8,
+ },
+ [0xA3D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3D9,
+ },
+ [0xA3DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3DA,
+ },
+ [0xA3DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3DB,
+ },
+ [0xA3DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3DC,
+ },
+ [0xA3DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3DD,
+ },
+ [0xA3DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3DE,
+ },
+ [0xA3DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3DF,
+ },
+ [0xA3E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E0,
+ },
+ [0xA3E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E1,
+ },
+ [0xA3E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E2,
+ },
+ [0xA3E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E3,
+ },
+ [0xA3E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E4,
+ },
+ [0xA3E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E5,
+ },
+ [0xA3E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E6,
+ },
+ [0xA3E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E7,
+ },
+ [0xA3E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E8,
+ },
+ [0xA3E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3E9,
+ },
+ [0xA3EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3EA,
+ },
+ [0xA3EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3EB,
+ },
+ [0xA3EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3EC,
+ },
+ [0xA3ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3ED,
+ },
+ [0xA3EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3EE,
+ },
+ [0xA3EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3EF,
+ },
+ [0xA3F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F0,
+ },
+ [0xA3F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F1,
+ },
+ [0xA3F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F2,
+ },
+ [0xA3F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F3,
+ },
+ [0xA3F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F4,
+ },
+ [0xA3F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F5,
+ },
+ [0xA3F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F6,
+ },
+ [0xA3F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F7,
+ },
+ [0xA3F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F8,
+ },
+ [0xA3F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3F9,
+ },
+ [0xA3FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3FA,
+ },
+ [0xA3FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3FB,
+ },
+ [0xA3FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3FC,
+ },
+ [0xA3FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3FD,
+ },
+ [0xA3FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3FE,
+ },
+ [0xA3FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA3FF,
+ },
+ [0xA400]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA400,
+ },
+ [0xA401]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA401,
+ },
+ [0xA402]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA402,
+ },
+ [0xA403]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA403,
+ },
+ [0xA404]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA404,
+ },
+ [0xA405]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA405,
+ },
+ [0xA406]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA406,
+ },
+ [0xA407]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA407,
+ },
+ [0xA408]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA408,
+ },
+ [0xA409]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA409,
+ },
+ [0xA40A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA40A,
+ },
+ [0xA40B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA40B,
+ },
+ [0xA40C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA40C,
+ },
+ [0xA40D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA40D,
+ },
+ [0xA40E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA40E,
+ },
+ [0xA40F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA40F,
+ },
+ [0xA410]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA410,
+ },
+ [0xA411]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA411,
+ },
+ [0xA412]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA412,
+ },
+ [0xA413]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA413,
+ },
+ [0xA414]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA414,
+ },
+ [0xA415]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA415,
+ },
+ [0xA416]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA416,
+ },
+ [0xA417]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA417,
+ },
+ [0xA418]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA418,
+ },
+ [0xA419]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA419,
+ },
+ [0xA41A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA41A,
+ },
+ [0xA41B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA41B,
+ },
+ [0xA41C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA41C,
+ },
+ [0xA41D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA41D,
+ },
+ [0xA41E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA41E,
+ },
+ [0xA41F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA41F,
+ },
+ [0xA420]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA420,
+ },
+ [0xA421]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA421,
+ },
+ [0xA422]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA422,
+ },
+ [0xA423]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA423,
+ },
+ [0xA424]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA424,
+ },
+ [0xA425]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA425,
+ },
+ [0xA426]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA426,
+ },
+ [0xA427]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA427,
+ },
+ [0xA428]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA428,
+ },
+ [0xA429]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA429,
+ },
+ [0xA42A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA42A,
+ },
+ [0xA42B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA42B,
+ },
+ [0xA42C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA42C,
+ },
+ [0xA42D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA42D,
+ },
+ [0xA42E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA42E,
+ },
+ [0xA42F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA42F,
+ },
+ [0xA430]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA430,
+ },
+ [0xA431]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA431,
+ },
+ [0xA432]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA432,
+ },
+ [0xA433]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA433,
+ },
+ [0xA434]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA434,
+ },
+ [0xA435]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA435,
+ },
+ [0xA436]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA436,
+ },
+ [0xA437]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA437,
+ },
+ [0xA438]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA438,
+ },
+ [0xA439]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA439,
+ },
+ [0xA43A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA43A,
+ },
+ [0xA43B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA43B,
+ },
+ [0xA43C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA43C,
+ },
+ [0xA43D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA43D,
+ },
+ [0xA43E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA43E,
+ },
+ [0xA43F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA43F,
+ },
+ [0xA440]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA440,
+ },
+ [0xA441]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA441,
+ },
+ [0xA442]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA442,
+ },
+ [0xA443]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA443,
+ },
+ [0xA444]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA444,
+ },
+ [0xA445]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA445,
+ },
+ [0xA446]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA446,
+ },
+ [0xA447]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA447,
+ },
+ [0xA448]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA448,
+ },
+ [0xA449]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA449,
+ },
+ [0xA44A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA44A,
+ },
+ [0xA44B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA44B,
+ },
+ [0xA44C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA44C,
+ },
+ [0xA44D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA44D,
+ },
+ [0xA44E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA44E,
+ },
+ [0xA44F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA44F,
+ },
+ [0xA450]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA450,
+ },
+ [0xA451]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA451,
+ },
+ [0xA452]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA452,
+ },
+ [0xA453]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA453,
+ },
+ [0xA454]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA454,
+ },
+ [0xA455]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA455,
+ },
+ [0xA456]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA456,
+ },
+ [0xA457]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA457,
+ },
+ [0xA458]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA458,
+ },
+ [0xA459]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA459,
+ },
+ [0xA45A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA45A,
+ },
+ [0xA45B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA45B,
+ },
+ [0xA45C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA45C,
+ },
+ [0xA45D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA45D,
+ },
+ [0xA45E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA45E,
+ },
+ [0xA45F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA45F,
+ },
+ [0xA460]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA460,
+ },
+ [0xA461]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA461,
+ },
+ [0xA462]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA462,
+ },
+ [0xA463]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA463,
+ },
+ [0xA464]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA464,
+ },
+ [0xA465]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA465,
+ },
+ [0xA466]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA466,
+ },
+ [0xA467]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA467,
+ },
+ [0xA468]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA468,
+ },
+ [0xA469]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA469,
+ },
+ [0xA46A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA46A,
+ },
+ [0xA46B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA46B,
+ },
+ [0xA46C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA46C,
+ },
+ [0xA46D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA46D,
+ },
+ [0xA46E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA46E,
+ },
+ [0xA46F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA46F,
+ },
+ [0xA470]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA470,
+ },
+ [0xA471]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA471,
+ },
+ [0xA472]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA472,
+ },
+ [0xA473]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA473,
+ },
+ [0xA474]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA474,
+ },
+ [0xA475]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA475,
+ },
+ [0xA476]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA476,
+ },
+ [0xA477]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA477,
+ },
+ [0xA478]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA478,
+ },
+ [0xA479]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA479,
+ },
+ [0xA47A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA47A,
+ },
+ [0xA47B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA47B,
+ },
+ [0xA47C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA47C,
+ },
+ [0xA47D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA47D,
+ },
+ [0xA47E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA47E,
+ },
+ [0xA47F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA47F,
+ },
+ [0xA480]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA480,
+ },
+ [0xA481]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA481,
+ },
+ [0xA482]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA482,
+ },
+ [0xA483]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA483,
+ },
+ [0xA484]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA484,
+ },
+ [0xA485]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA485,
+ },
+ [0xA486]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA486,
+ },
+ [0xA487]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA487,
+ },
+ [0xA488]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA488,
+ },
+ [0xA489]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA489,
+ },
+ [0xA48A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA48A,
+ },
+ [0xA48B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA48B,
+ },
+ [0xA48C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xA48C,
+ },
+ [0xA490]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA490,
+ },
+ [0xA491]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA491,
+ },
+ [0xA492]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA492,
+ },
+ [0xA493]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA493,
+ },
+ [0xA494]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA494,
+ },
+ [0xA495]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA495,
+ },
+ [0xA496]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA496,
+ },
+ [0xA497]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA497,
+ },
+ [0xA498]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA498,
+ },
+ [0xA499]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA499,
+ },
+ [0xA49A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA49A,
+ },
+ [0xA49B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA49B,
+ },
+ [0xA49C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA49C,
+ },
+ [0xA49D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA49D,
+ },
+ [0xA49E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA49E,
+ },
+ [0xA49F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA49F,
+ },
+ [0xA4A0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A0,
+ },
+ [0xA4A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A1,
+ },
+ [0xA4A2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A2,
+ },
+ [0xA4A3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A3,
+ },
+ [0xA4A4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A4,
+ },
+ [0xA4A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A5,
+ },
+ [0xA4A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A6,
+ },
+ [0xA4A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A7,
+ },
+ [0xA4A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A8,
+ },
+ [0xA4A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4A9,
+ },
+ [0xA4AA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4AA,
+ },
+ [0xA4AB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4AB,
+ },
+ [0xA4AC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4AC,
+ },
+ [0xA4AD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4AD,
+ },
+ [0xA4AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4AE,
+ },
+ [0xA4AF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4AF,
+ },
+ [0xA4B0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B0,
+ },
+ [0xA4B1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B1,
+ },
+ [0xA4B2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B2,
+ },
+ [0xA4B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B3,
+ },
+ [0xA4B4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B4,
+ },
+ [0xA4B5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B5,
+ },
+ [0xA4B6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B6,
+ },
+ [0xA4B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B7,
+ },
+ [0xA4B8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B8,
+ },
+ [0xA4B9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4B9,
+ },
+ [0xA4BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4BA,
+ },
+ [0xA4BB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4BB,
+ },
+ [0xA4BC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4BC,
+ },
+ [0xA4BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4BD,
+ },
+ [0xA4BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4BE,
+ },
+ [0xA4BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4BF,
+ },
+ [0xA4C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C0,
+ },
+ [0xA4C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C1,
+ },
+ [0xA4C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C2,
+ },
+ [0xA4C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C3,
+ },
+ [0xA4C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C4,
+ },
+ [0xA4C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C5,
+ },
+ [0xA4C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xA4C6,
+ },
+ [0xA4D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D0,
+ },
+ [0xA4D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D1,
+ },
+ [0xA4D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D2,
+ },
+ [0xA4D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D3,
+ },
+ [0xA4D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D4,
+ },
+ [0xA4D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D5,
+ },
+ [0xA4D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D6,
+ },
+ [0xA4D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D7,
+ },
+ [0xA4D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D8,
+ },
+ [0xA4D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4D9,
+ },
+ [0xA4DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4DA,
+ },
+ [0xA4DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4DB,
+ },
+ [0xA4DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4DC,
+ },
+ [0xA4DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4DD,
+ },
+ [0xA4DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4DE,
+ },
+ [0xA4DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4DF,
+ },
+ [0xA4E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E0,
+ },
+ [0xA4E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E1,
+ },
+ [0xA4E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E2,
+ },
+ [0xA4E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E3,
+ },
+ [0xA4E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E4,
+ },
+ [0xA4E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E5,
+ },
+ [0xA4E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E6,
+ },
+ [0xA4E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E7,
+ },
+ [0xA4E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E8,
+ },
+ [0xA4E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4E9,
+ },
+ [0xA4EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4EA,
+ },
+ [0xA4EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4EB,
+ },
+ [0xA4EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4EC,
+ },
+ [0xA4ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4ED,
+ },
+ [0xA4EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4EE,
+ },
+ [0xA4EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4EF,
+ },
+ [0xA4F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F0,
+ },
+ [0xA4F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F1,
+ },
+ [0xA4F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F2,
+ },
+ [0xA4F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F3,
+ },
+ [0xA4F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F4,
+ },
+ [0xA4F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F5,
+ },
+ [0xA4F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F6,
+ },
+ [0xA4F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F7,
+ },
+ [0xA4F8]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F8,
+ },
+ [0xA4F9]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4F9,
+ },
+ [0xA4FA]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4FA,
+ },
+ [0xA4FB]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4FB,
+ },
+ [0xA4FC]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4FC,
+ },
+ [0xA4FD]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA4FD,
+ },
+ [0xA4FE]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA4FE,
+ },
+ [0xA4FF]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA4FF,
+ },
+ [0xA500]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA500,
+ },
+ [0xA501]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA501,
+ },
+ [0xA502]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA502,
+ },
+ [0xA503]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA503,
+ },
+ [0xA504]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA504,
+ },
+ [0xA505]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA505,
+ },
+ [0xA506]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA506,
+ },
+ [0xA507]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA507,
+ },
+ [0xA508]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA508,
+ },
+ [0xA509]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA509,
+ },
+ [0xA50A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA50A,
+ },
+ [0xA50B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA50B,
+ },
+ [0xA50C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA50C,
+ },
+ [0xA50D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA50D,
+ },
+ [0xA50E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA50E,
+ },
+ [0xA50F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA50F,
+ },
+ [0xA510]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA510,
+ },
+ [0xA511]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA511,
+ },
+ [0xA512]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA512,
+ },
+ [0xA513]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA513,
+ },
+ [0xA514]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA514,
+ },
+ [0xA515]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA515,
+ },
+ [0xA516]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA516,
+ },
+ [0xA517]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA517,
+ },
+ [0xA518]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA518,
+ },
+ [0xA519]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA519,
+ },
+ [0xA51A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA51A,
+ },
+ [0xA51B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA51B,
+ },
+ [0xA51C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA51C,
+ },
+ [0xA51D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA51D,
+ },
+ [0xA51E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA51E,
+ },
+ [0xA51F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA51F,
+ },
+ [0xA520]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA520,
+ },
+ [0xA521]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA521,
+ },
+ [0xA522]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA522,
+ },
+ [0xA523]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA523,
+ },
+ [0xA524]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA524,
+ },
+ [0xA525]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA525,
+ },
+ [0xA526]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA526,
+ },
+ [0xA527]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA527,
+ },
+ [0xA528]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA528,
+ },
+ [0xA529]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA529,
+ },
+ [0xA52A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA52A,
+ },
+ [0xA52B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA52B,
+ },
+ [0xA52C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA52C,
+ },
+ [0xA52D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA52D,
+ },
+ [0xA52E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA52E,
+ },
+ [0xA52F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA52F,
+ },
+ [0xA530]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA530,
+ },
+ [0xA531]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA531,
+ },
+ [0xA532]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA532,
+ },
+ [0xA533]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA533,
+ },
+ [0xA534]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA534,
+ },
+ [0xA535]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA535,
+ },
+ [0xA536]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA536,
+ },
+ [0xA537]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA537,
+ },
+ [0xA538]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA538,
+ },
+ [0xA539]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA539,
+ },
+ [0xA53A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA53A,
+ },
+ [0xA53B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA53B,
+ },
+ [0xA53C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA53C,
+ },
+ [0xA53D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA53D,
+ },
+ [0xA53E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA53E,
+ },
+ [0xA53F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA53F,
+ },
+ [0xA540]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA540,
+ },
+ [0xA541]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA541,
+ },
+ [0xA542]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA542,
+ },
+ [0xA543]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA543,
+ },
+ [0xA544]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA544,
+ },
+ [0xA545]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA545,
+ },
+ [0xA546]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA546,
+ },
+ [0xA547]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA547,
+ },
+ [0xA548]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA548,
+ },
+ [0xA549]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA549,
+ },
+ [0xA54A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA54A,
+ },
+ [0xA54B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA54B,
+ },
+ [0xA54C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA54C,
+ },
+ [0xA54D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA54D,
+ },
+ [0xA54E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA54E,
+ },
+ [0xA54F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA54F,
+ },
+ [0xA550]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA550,
+ },
+ [0xA551]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA551,
+ },
+ [0xA552]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA552,
+ },
+ [0xA553]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA553,
+ },
+ [0xA554]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA554,
+ },
+ [0xA555]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA555,
+ },
+ [0xA556]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA556,
+ },
+ [0xA557]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA557,
+ },
+ [0xA558]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA558,
+ },
+ [0xA559]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA559,
+ },
+ [0xA55A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA55A,
+ },
+ [0xA55B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA55B,
+ },
+ [0xA55C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA55C,
+ },
+ [0xA55D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA55D,
+ },
+ [0xA55E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA55E,
+ },
+ [0xA55F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA55F,
+ },
+ [0xA560]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA560,
+ },
+ [0xA561]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA561,
+ },
+ [0xA562]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA562,
+ },
+ [0xA563]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA563,
+ },
+ [0xA564]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA564,
+ },
+ [0xA565]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA565,
+ },
+ [0xA566]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA566,
+ },
+ [0xA567]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA567,
+ },
+ [0xA568]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA568,
+ },
+ [0xA569]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA569,
+ },
+ [0xA56A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA56A,
+ },
+ [0xA56B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA56B,
+ },
+ [0xA56C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA56C,
+ },
+ [0xA56D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA56D,
+ },
+ [0xA56E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA56E,
+ },
+ [0xA56F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA56F,
+ },
+ [0xA570]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA570,
+ },
+ [0xA571]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA571,
+ },
+ [0xA572]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA572,
+ },
+ [0xA573]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA573,
+ },
+ [0xA574]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA574,
+ },
+ [0xA575]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA575,
+ },
+ [0xA576]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA576,
+ },
+ [0xA577]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA577,
+ },
+ [0xA578]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA578,
+ },
+ [0xA579]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA579,
+ },
+ [0xA57A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA57A,
+ },
+ [0xA57B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA57B,
+ },
+ [0xA57C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA57C,
+ },
+ [0xA57D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA57D,
+ },
+ [0xA57E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA57E,
+ },
+ [0xA57F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA57F,
+ },
+ [0xA580]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA580,
+ },
+ [0xA581]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA581,
+ },
+ [0xA582]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA582,
+ },
+ [0xA583]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA583,
+ },
+ [0xA584]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA584,
+ },
+ [0xA585]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA585,
+ },
+ [0xA586]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA586,
+ },
+ [0xA587]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA587,
+ },
+ [0xA588]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA588,
+ },
+ [0xA589]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA589,
+ },
+ [0xA58A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA58A,
+ },
+ [0xA58B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA58B,
+ },
+ [0xA58C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA58C,
+ },
+ [0xA58D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA58D,
+ },
+ [0xA58E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA58E,
+ },
+ [0xA58F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA58F,
+ },
+ [0xA590]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA590,
+ },
+ [0xA591]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA591,
+ },
+ [0xA592]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA592,
+ },
+ [0xA593]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA593,
+ },
+ [0xA594]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA594,
+ },
+ [0xA595]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA595,
+ },
+ [0xA596]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA596,
+ },
+ [0xA597]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA597,
+ },
+ [0xA598]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA598,
+ },
+ [0xA599]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA599,
+ },
+ [0xA59A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA59A,
+ },
+ [0xA59B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA59B,
+ },
+ [0xA59C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA59C,
+ },
+ [0xA59D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA59D,
+ },
+ [0xA59E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA59E,
+ },
+ [0xA59F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA59F,
+ },
+ [0xA5A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A0,
+ },
+ [0xA5A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A1,
+ },
+ [0xA5A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A2,
+ },
+ [0xA5A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A3,
+ },
+ [0xA5A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A4,
+ },
+ [0xA5A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A5,
+ },
+ [0xA5A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A6,
+ },
+ [0xA5A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A7,
+ },
+ [0xA5A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A8,
+ },
+ [0xA5A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5A9,
+ },
+ [0xA5AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5AA,
+ },
+ [0xA5AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5AB,
+ },
+ [0xA5AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5AC,
+ },
+ [0xA5AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5AD,
+ },
+ [0xA5AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5AE,
+ },
+ [0xA5AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5AF,
+ },
+ [0xA5B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B0,
+ },
+ [0xA5B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B1,
+ },
+ [0xA5B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B2,
+ },
+ [0xA5B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B3,
+ },
+ [0xA5B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B4,
+ },
+ [0xA5B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B5,
+ },
+ [0xA5B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B6,
+ },
+ [0xA5B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B7,
+ },
+ [0xA5B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B8,
+ },
+ [0xA5B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5B9,
+ },
+ [0xA5BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5BA,
+ },
+ [0xA5BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5BB,
+ },
+ [0xA5BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5BC,
+ },
+ [0xA5BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5BD,
+ },
+ [0xA5BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5BE,
+ },
+ [0xA5BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5BF,
+ },
+ [0xA5C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C0,
+ },
+ [0xA5C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C1,
+ },
+ [0xA5C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C2,
+ },
+ [0xA5C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C3,
+ },
+ [0xA5C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C4,
+ },
+ [0xA5C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C5,
+ },
+ [0xA5C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C6,
+ },
+ [0xA5C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C7,
+ },
+ [0xA5C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C8,
+ },
+ [0xA5C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5C9,
+ },
+ [0xA5CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5CA,
+ },
+ [0xA5CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5CB,
+ },
+ [0xA5CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5CC,
+ },
+ [0xA5CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5CD,
+ },
+ [0xA5CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5CE,
+ },
+ [0xA5CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5CF,
+ },
+ [0xA5D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D0,
+ },
+ [0xA5D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D1,
+ },
+ [0xA5D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D2,
+ },
+ [0xA5D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D3,
+ },
+ [0xA5D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D4,
+ },
+ [0xA5D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D5,
+ },
+ [0xA5D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D6,
+ },
+ [0xA5D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D7,
+ },
+ [0xA5D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D8,
+ },
+ [0xA5D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5D9,
+ },
+ [0xA5DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5DA,
+ },
+ [0xA5DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5DB,
+ },
+ [0xA5DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5DC,
+ },
+ [0xA5DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5DD,
+ },
+ [0xA5DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5DE,
+ },
+ [0xA5DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5DF,
+ },
+ [0xA5E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E0,
+ },
+ [0xA5E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E1,
+ },
+ [0xA5E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E2,
+ },
+ [0xA5E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E3,
+ },
+ [0xA5E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E4,
+ },
+ [0xA5E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E5,
+ },
+ [0xA5E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E6,
+ },
+ [0xA5E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E7,
+ },
+ [0xA5E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E8,
+ },
+ [0xA5E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5E9,
+ },
+ [0xA5EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5EA,
+ },
+ [0xA5EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5EB,
+ },
+ [0xA5EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5EC,
+ },
+ [0xA5ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5ED,
+ },
+ [0xA5EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5EE,
+ },
+ [0xA5EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5EF,
+ },
+ [0xA5F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F0,
+ },
+ [0xA5F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F1,
+ },
+ [0xA5F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F2,
+ },
+ [0xA5F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F3,
+ },
+ [0xA5F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F4,
+ },
+ [0xA5F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F5,
+ },
+ [0xA5F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F6,
+ },
+ [0xA5F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F7,
+ },
+ [0xA5F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F8,
+ },
+ [0xA5F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5F9,
+ },
+ [0xA5FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5FA,
+ },
+ [0xA5FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5FB,
+ },
+ [0xA5FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5FC,
+ },
+ [0xA5FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5FD,
+ },
+ [0xA5FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5FE,
+ },
+ [0xA5FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA5FF,
+ },
+ [0xA600]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA600,
+ },
+ [0xA601]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA601,
+ },
+ [0xA602]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA602,
+ },
+ [0xA603]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA603,
+ },
+ [0xA604]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA604,
+ },
+ [0xA605]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA605,
+ },
+ [0xA606]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA606,
+ },
+ [0xA607]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA607,
+ },
+ [0xA608]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA608,
+ },
+ [0xA609]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA609,
+ },
+ [0xA60A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA60A,
+ },
+ [0xA60B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA60B,
+ },
+ [0xA60C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA60C,
+ },
+ [0xA60D]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0xA60D,
+ },
+ [0xA60E]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0xA60E,
+ },
+ [0xA60F]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0xA60F,
+ },
+ [0xA610]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA610,
+ },
+ [0xA611]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA611,
+ },
+ [0xA612]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA612,
+ },
+ [0xA613]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA613,
+ },
+ [0xA614]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA614,
+ },
+ [0xA615]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA615,
+ },
+ [0xA616]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA616,
+ },
+ [0xA617]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA617,
+ },
+ [0xA618]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA618,
+ },
+ [0xA619]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA619,
+ },
+ [0xA61A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA61A,
+ },
+ [0xA61B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA61B,
+ },
+ [0xA61C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA61C,
+ },
+ [0xA61D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA61D,
+ },
+ [0xA61E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA61E,
+ },
+ [0xA61F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA61F,
+ },
+ [0xA620]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA620,
+ },
+ [0xA621]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA621,
+ },
+ [0xA622]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA622,
+ },
+ [0xA623]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA623,
+ },
+ [0xA624]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA624,
+ },
+ [0xA625]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA625,
+ },
+ [0xA626]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA626,
+ },
+ [0xA627]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA627,
+ },
+ [0xA628]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA628,
+ },
+ [0xA629]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA629,
+ },
+ [0xA62A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA62A,
+ },
+ [0xA62B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA62B,
+ },
+ [0xA640]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA640,
+ },
+ [0xA641]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA641,
+ },
+ [0xA642]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA642,
+ },
+ [0xA643]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA643,
+ },
+ [0xA644]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA644,
+ },
+ [0xA645]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA645,
+ },
+ [0xA646]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA646,
+ },
+ [0xA647]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA647,
+ },
+ [0xA648]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA648,
+ },
+ [0xA649]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA649,
+ },
+ [0xA64A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA64A,
+ },
+ [0xA64B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA64B,
+ },
+ [0xA64C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA64C,
+ },
+ [0xA64D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA64D,
+ },
+ [0xA64E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA64E,
+ },
+ [0xA64F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA64F,
+ },
+ [0xA650]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA650,
+ },
+ [0xA651]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA651,
+ },
+ [0xA652]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA652,
+ },
+ [0xA653]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA653,
+ },
+ [0xA654]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA654,
+ },
+ [0xA655]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA655,
+ },
+ [0xA656]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA656,
+ },
+ [0xA657]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA657,
+ },
+ [0xA658]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA658,
+ },
+ [0xA659]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA659,
+ },
+ [0xA65A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA65A,
+ },
+ [0xA65B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA65B,
+ },
+ [0xA65C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA65C,
+ },
+ [0xA65D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA65D,
+ },
+ [0xA65E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA65E,
+ },
+ [0xA65F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA65F,
+ },
+ [0xA660]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA660,
+ },
+ [0xA661]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA661,
+ },
+ [0xA662]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA662,
+ },
+ [0xA663]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA663,
+ },
+ [0xA664]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA664,
+ },
+ [0xA665]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA665,
+ },
+ [0xA666]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA666,
+ },
+ [0xA667]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA667,
+ },
+ [0xA668]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA668,
+ },
+ [0xA669]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA669,
+ },
+ [0xA66A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA66A,
+ },
+ [0xA66B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA66B,
+ },
+ [0xA66C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA66C,
+ },
+ [0xA66D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA66D,
+ },
+ [0xA66E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA66E,
+ },
+ [0xA66F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA66F,
+ },
+ [0xA670]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA670,
+ },
+ [0xA671]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA671,
+ },
+ [0xA672]={
+ category="me",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA672,
+ },
+ [0xA673]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA673,
+ },
+ [0xA674]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA674,
+ },
+ [0xA675]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA675,
+ },
+ [0xA676]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA676,
+ },
+ [0xA677]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA677,
+ },
+ [0xA678]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA678,
+ },
+ [0xA679]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA679,
+ },
+ [0xA67A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA67A,
+ },
+ [0xA67B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA67B,
+ },
+ [0xA67C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA67C,
+ },
+ [0xA67D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA67D,
+ },
+ [0xA67E]={
+ category="po",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA67E,
+ },
+ [0xA67F]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA67F,
+ },
+ [0xA680]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA680,
+ },
+ [0xA681]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA681,
+ },
+ [0xA682]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA682,
+ },
+ [0xA683]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA683,
+ },
+ [0xA684]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA684,
+ },
+ [0xA685]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA685,
+ },
+ [0xA686]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA686,
+ },
+ [0xA687]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA687,
+ },
+ [0xA688]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA688,
+ },
+ [0xA689]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA689,
+ },
+ [0xA68A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA68A,
+ },
+ [0xA68B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA68B,
+ },
+ [0xA68C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA68C,
+ },
+ [0xA68D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA68D,
+ },
+ [0xA68E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA68E,
+ },
+ [0xA68F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA68F,
+ },
+ [0xA690]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA690,
+ },
+ [0xA691]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA691,
+ },
+ [0xA692]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA692,
+ },
+ [0xA693]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA693,
+ },
+ [0xA694]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA694,
+ },
+ [0xA695]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA695,
+ },
+ [0xA696]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA696,
+ },
+ [0xA697]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA697,
+ },
+ [0xA698]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA698,
+ },
+ [0xA699]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA699,
+ },
+ [0xA69A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA69A,
+ },
+ [0xA69B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA69B,
+ },
+ [0xA69C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x44A },
+ unicodeslot=0xA69C,
+ },
+ [0xA69D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x44C },
+ unicodeslot=0xA69D,
+ },
+ [0xA69E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA69E,
+ },
+ [0xA69F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA69F,
+ },
+ [0xA6A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A0,
+ },
+ [0xA6A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A1,
+ },
+ [0xA6A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A2,
+ },
+ [0xA6A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A3,
+ },
+ [0xA6A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A4,
+ },
+ [0xA6A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A5,
+ },
+ [0xA6A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A6,
+ },
+ [0xA6A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A7,
+ },
+ [0xA6A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A8,
+ },
+ [0xA6A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6A9,
+ },
+ [0xA6AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6AA,
+ },
+ [0xA6AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6AB,
+ },
+ [0xA6AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6AC,
+ },
+ [0xA6AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6AD,
+ },
+ [0xA6AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6AE,
+ },
+ [0xA6AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6AF,
+ },
+ [0xA6B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B0,
+ },
+ [0xA6B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B1,
+ },
+ [0xA6B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B2,
+ },
+ [0xA6B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B3,
+ },
+ [0xA6B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B4,
+ },
+ [0xA6B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B5,
+ },
+ [0xA6B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B6,
+ },
+ [0xA6B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B7,
+ },
+ [0xA6B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B8,
+ },
+ [0xA6B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6B9,
+ },
+ [0xA6BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6BA,
+ },
+ [0xA6BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6BB,
+ },
+ [0xA6BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6BC,
+ },
+ [0xA6BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6BD,
+ },
+ [0xA6BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6BE,
+ },
+ [0xA6BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6BF,
+ },
+ [0xA6C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C0,
+ },
+ [0xA6C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C1,
+ },
+ [0xA6C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C2,
+ },
+ [0xA6C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C3,
+ },
+ [0xA6C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C4,
+ },
+ [0xA6C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C5,
+ },
+ [0xA6C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C6,
+ },
+ [0xA6C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C7,
+ },
+ [0xA6C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C8,
+ },
+ [0xA6C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6C9,
+ },
+ [0xA6CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6CA,
+ },
+ [0xA6CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6CB,
+ },
+ [0xA6CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6CC,
+ },
+ [0xA6CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6CD,
+ },
+ [0xA6CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6CE,
+ },
+ [0xA6CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6CF,
+ },
+ [0xA6D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D0,
+ },
+ [0xA6D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D1,
+ },
+ [0xA6D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D2,
+ },
+ [0xA6D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D3,
+ },
+ [0xA6D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D4,
+ },
+ [0xA6D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D5,
+ },
+ [0xA6D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D6,
+ },
+ [0xA6D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D7,
+ },
+ [0xA6D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D8,
+ },
+ [0xA6D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6D9,
+ },
+ [0xA6DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6DA,
+ },
+ [0xA6DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6DB,
+ },
+ [0xA6DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6DC,
+ },
+ [0xA6DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6DD,
+ },
+ [0xA6DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6DE,
+ },
+ [0xA6DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6DF,
+ },
+ [0xA6E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E0,
+ },
+ [0xA6E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E1,
+ },
+ [0xA6E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E2,
+ },
+ [0xA6E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E3,
+ },
+ [0xA6E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E4,
+ },
+ [0xA6E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E5,
+ },
+ [0xA6E6]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E6,
+ },
+ [0xA6E7]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E7,
+ },
+ [0xA6E8]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E8,
+ },
+ [0xA6E9]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6E9,
+ },
+ [0xA6EA]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6EA,
+ },
+ [0xA6EB]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6EB,
+ },
+ [0xA6EC]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6EC,
+ },
+ [0xA6ED]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6ED,
+ },
+ [0xA6EE]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6EE,
+ },
+ [0xA6EF]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6EF,
+ },
+ [0xA6F0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA6F0,
+ },
+ [0xA6F1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA6F1,
+ },
+ [0xA6F2]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA6F2,
+ },
+ [0xA6F3]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA6F3,
+ },
+ [0xA6F4]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA6F4,
+ },
+ [0xA6F5]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA6F5,
+ },
+ [0xA6F6]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA6F6,
+ },
+ [0xA6F7]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA6F7,
+ },
+ [0xA700]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA700,
+ },
+ [0xA701]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA701,
+ },
+ [0xA702]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA702,
+ },
+ [0xA703]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA703,
+ },
+ [0xA704]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA704,
+ },
+ [0xA705]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA705,
+ },
+ [0xA706]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA706,
+ },
+ [0xA707]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA707,
+ },
+ [0xA708]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA708,
+ },
+ [0xA709]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA709,
+ },
+ [0xA70A]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA70A,
+ },
+ [0xA70B]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA70B,
+ },
+ [0xA70C]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA70C,
+ },
+ [0xA70D]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA70D,
+ },
+ [0xA70E]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA70E,
+ },
+ [0xA70F]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA70F,
+ },
+ [0xA710]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA710,
+ },
+ [0xA711]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA711,
+ },
+ [0xA712]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA712,
+ },
+ [0xA713]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA713,
+ },
+ [0xA714]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA714,
+ },
+ [0xA715]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA715,
+ },
+ [0xA716]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA716,
+ },
+ [0xA717]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA717,
+ },
+ [0xA718]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA718,
+ },
+ [0xA719]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA719,
+ },
+ [0xA71A]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA71A,
+ },
+ [0xA71B]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA71B,
+ },
+ [0xA71C]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA71C,
+ },
+ [0xA71D]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA71D,
+ },
+ [0xA71E]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA71E,
+ },
+ [0xA71F]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA71F,
+ },
+ [0xA720]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA720,
+ },
+ [0xA721]={
+ category="sk",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA721,
+ },
+ [0xA722]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA722,
+ },
+ [0xA723]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA723,
+ },
+ [0xA724]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA724,
+ },
+ [0xA725]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA725,
+ },
+ [0xA726]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA726,
+ },
+ [0xA727]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA727,
+ },
+ [0xA728]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA728,
+ },
+ [0xA729]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA729,
+ },
+ [0xA72A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA72A,
+ },
+ [0xA72B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA72B,
+ },
+ [0xA72C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA72C,
+ },
+ [0xA72D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA72D,
+ },
+ [0xA72E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA72E,
+ },
+ [0xA72F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA72F,
+ },
+ [0xA730]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA730,
+ },
+ [0xA731]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA731,
+ },
+ [0xA732]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA732,
+ },
+ [0xA733]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA733,
+ },
+ [0xA734]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA734,
+ },
+ [0xA735]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA735,
+ },
+ [0xA736]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA736,
+ },
+ [0xA737]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA737,
+ },
+ [0xA738]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA738,
+ },
+ [0xA739]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA739,
+ },
+ [0xA73A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA73A,
+ },
+ [0xA73B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA73B,
+ },
+ [0xA73C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA73C,
+ },
+ [0xA73D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA73D,
+ },
+ [0xA73E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA73E,
+ },
+ [0xA73F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA73F,
+ },
+ [0xA740]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA740,
+ },
+ [0xA741]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA741,
+ },
+ [0xA742]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA742,
+ },
+ [0xA743]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA743,
+ },
+ [0xA744]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA744,
+ },
+ [0xA745]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA745,
+ },
+ [0xA746]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA746,
+ },
+ [0xA747]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA747,
+ },
+ [0xA748]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA748,
+ },
+ [0xA749]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA749,
+ },
+ [0xA74A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA74A,
+ },
+ [0xA74B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA74B,
+ },
+ [0xA74C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA74C,
+ },
+ [0xA74D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA74D,
+ },
+ [0xA74E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA74E,
+ },
+ [0xA74F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA74F,
+ },
+ [0xA750]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA750,
+ },
+ [0xA751]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA751,
+ },
+ [0xA752]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA752,
+ },
+ [0xA753]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA753,
+ },
+ [0xA754]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA754,
+ },
+ [0xA755]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA755,
+ },
+ [0xA756]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA756,
+ },
+ [0xA757]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA757,
+ },
+ [0xA758]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA758,
+ },
+ [0xA759]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA759,
+ },
+ [0xA75A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA75A,
+ },
+ [0xA75B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA75B,
+ },
+ [0xA75C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA75C,
+ },
+ [0xA75D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA75D,
+ },
+ [0xA75E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA75E,
+ },
+ [0xA75F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA75F,
+ },
+ [0xA760]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA760,
+ },
+ [0xA761]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA761,
+ },
+ [0xA762]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA762,
+ },
+ [0xA763]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA763,
+ },
+ [0xA764]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA764,
+ },
+ [0xA765]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA765,
+ },
+ [0xA766]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA766,
+ },
+ [0xA767]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA767,
+ },
+ [0xA768]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA768,
+ },
+ [0xA769]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA769,
+ },
+ [0xA76A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76A,
+ },
+ [0xA76B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76B,
+ },
+ [0xA76C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76C,
+ },
+ [0xA76D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76D,
+ },
+ [0xA76E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76E,
+ },
+ [0xA76F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA76F,
+ },
+ [0xA770]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0xA76F },
+ unicodeslot=0xA770,
+ },
+ [0xA771]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA771,
+ },
+ [0xA772]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA772,
+ },
+ [0xA773]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA773,
+ },
+ [0xA774]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA774,
+ },
+ [0xA775]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA775,
+ },
+ [0xA776]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA776,
+ },
+ [0xA777]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA777,
+ },
+ [0xA778]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA778,
+ },
+ [0xA779]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA779,
+ },
+ [0xA77A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA77A,
+ },
+ [0xA77B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA77B,
+ },
+ [0xA77C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA77C,
+ },
+ [0xA77D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA77D,
+ },
+ [0xA77E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA77E,
+ },
+ [0xA77F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA77F,
+ },
+ [0xA780]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA780,
+ },
+ [0xA781]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA781,
+ },
+ [0xA782]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA782,
+ },
+ [0xA783]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA783,
+ },
+ [0xA784]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA784,
+ },
+ [0xA785]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA785,
+ },
+ [0xA786]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA786,
+ },
+ [0xA787]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA787,
+ },
+ [0xA788]={
+ category="lm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA788,
+ },
+ [0xA789]={
+ category="sk",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA789,
+ },
+ [0xA78A]={
+ category="sk",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA78A,
+ },
+ [0xA78B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA78B,
+ },
+ [0xA78C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA78C,
+ },
+ [0xA78D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA78D,
+ },
+ [0xA78E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA78E,
+ },
+ [0xA78F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA78F,
+ },
+ [0xA790]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA790,
+ },
+ [0xA791]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA791,
+ },
+ [0xA792]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA792,
+ },
+ [0xA793]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA793,
+ },
+ [0xA794]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA794,
+ },
+ [0xA795]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA795,
+ },
+ [0xA796]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA796,
+ },
+ [0xA797]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA797,
+ },
+ [0xA798]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA798,
+ },
+ [0xA799]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA799,
+ },
+ [0xA79A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA79A,
+ },
+ [0xA79B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA79B,
+ },
+ [0xA79C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA79C,
+ },
+ [0xA79D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA79D,
+ },
+ [0xA79E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA79E,
+ },
+ [0xA79F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA79F,
+ },
+ [0xA7A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A0,
+ },
+ [0xA7A1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A1,
+ },
+ [0xA7A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A2,
+ },
+ [0xA7A3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A3,
+ },
+ [0xA7A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A4,
+ },
+ [0xA7A5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A5,
+ },
+ [0xA7A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A6,
+ },
+ [0xA7A7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A7,
+ },
+ [0xA7A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A8,
+ },
+ [0xA7A9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7A9,
+ },
+ [0xA7AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7AA,
+ },
+ [0xA7AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7AB,
+ },
+ [0xA7AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7AC,
+ },
+ [0xA7AD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7AD,
+ },
+ [0xA7AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7AE,
+ },
+ [0xA7AF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7AF,
+ },
+ [0xA7B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B0,
+ },
+ [0xA7B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B1,
+ },
+ [0xA7B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B2,
+ },
+ [0xA7B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B3,
+ },
+ [0xA7B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B4,
+ },
+ [0xA7B5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B5,
+ },
+ [0xA7B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B6,
+ },
+ [0xA7B7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B7,
+ },
+ [0xA7B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B8,
+ },
+ [0xA7B9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7B9,
+ },
+ [0xA7BA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7BA,
+ },
+ [0xA7BB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7BB,
+ },
+ [0xA7BC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7BC,
+ },
+ [0xA7BD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7BD,
+ },
+ [0xA7BE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7BE,
+ },
+ [0xA7BF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7BF,
+ },
+ [0xA7C2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7C2,
+ },
+ [0xA7C3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7C3,
+ },
+ [0xA7C4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7C4,
+ },
+ [0xA7C5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7C5,
+ },
+ [0xA7C6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7C6,
+ },
+ [0xA7F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7F7,
+ },
+ [0xA7F8]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x126 },
+ unicodeslot=0xA7F8,
+ },
+ [0xA7F9]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x153 },
+ unicodeslot=0xA7F9,
+ },
+ [0xA7FA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7FA,
+ },
+ [0xA7FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7FB,
+ },
+ [0xA7FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7FC,
+ },
+ [0xA7FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7FD,
+ },
+ [0xA7FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7FE,
+ },
+ [0xA7FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA7FF,
+ },
+ [0xA800]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA800,
+ },
+ [0xA801]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA801,
+ },
+ [0xA802]={
+ category="mc",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA802,
+ },
+ [0xA803]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA803,
+ },
+ [0xA804]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA804,
+ },
+ [0xA805]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA805,
+ },
+ [0xA806]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA806,
+ },
+ [0xA807]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA807,
+ },
+ [0xA808]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA808,
+ },
+ [0xA809]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA809,
+ },
+ [0xA80A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA80A,
+ },
+ [0xA80B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA80B,
+ },
+ [0xA80C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA80C,
+ },
+ [0xA80D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA80D,
+ },
+ [0xA80E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA80E,
+ },
+ [0xA80F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA80F,
+ },
+ [0xA810]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA810,
+ },
+ [0xA811]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA811,
+ },
+ [0xA812]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA812,
+ },
+ [0xA813]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA813,
+ },
+ [0xA814]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA814,
+ },
+ [0xA815]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA815,
+ },
+ [0xA816]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA816,
+ },
+ [0xA817]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA817,
+ },
+ [0xA818]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA818,
+ },
+ [0xA819]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA819,
+ },
+ [0xA81A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA81A,
+ },
+ [0xA81B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA81B,
+ },
+ [0xA81C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA81C,
+ },
+ [0xA81D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA81D,
+ },
+ [0xA81E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA81E,
+ },
+ [0xA81F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA81F,
+ },
+ [0xA820]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA820,
+ },
+ [0xA821]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA821,
+ },
+ [0xA822]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA822,
+ },
+ [0xA823]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA823,
+ },
+ [0xA824]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA824,
+ },
+ [0xA825]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA825,
+ },
+ [0xA826]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA826,
+ },
+ [0xA827]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA827,
+ },
+ [0xA828]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA828,
+ },
+ [0xA829]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA829,
+ },
+ [0xA82A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA82A,
+ },
+ [0xA82B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xA82B,
+ },
+ [0xA830]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA830,
+ },
+ [0xA831]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA831,
+ },
+ [0xA832]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA832,
+ },
+ [0xA833]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA833,
+ },
+ [0xA834]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA834,
+ },
+ [0xA835]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA835,
+ },
+ [0xA836]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA836,
+ },
+ [0xA837]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA837,
+ },
+ [0xA838]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0xA838,
+ },
+ [0xA839]={
+ category="so",
+ direction="et",
+ linebreak="al",
+ unicodeslot=0xA839,
+ },
+ [0xA840]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA840,
+ },
+ [0xA841]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA841,
+ },
+ [0xA842]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA842,
+ },
+ [0xA843]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA843,
+ },
+ [0xA844]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA844,
+ },
+ [0xA845]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA845,
+ },
+ [0xA846]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA846,
+ },
+ [0xA847]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA847,
+ },
+ [0xA848]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA848,
+ },
+ [0xA849]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA849,
+ },
+ [0xA84A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA84A,
+ },
+ [0xA84B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA84B,
+ },
+ [0xA84C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA84C,
+ },
+ [0xA84D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA84D,
+ },
+ [0xA84E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA84E,
+ },
+ [0xA84F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA84F,
+ },
+ [0xA850]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA850,
+ },
+ [0xA851]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA851,
+ },
+ [0xA852]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA852,
+ },
+ [0xA853]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA853,
+ },
+ [0xA854]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA854,
+ },
+ [0xA855]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA855,
+ },
+ [0xA856]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA856,
+ },
+ [0xA857]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA857,
+ },
+ [0xA858]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA858,
+ },
+ [0xA859]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA859,
+ },
+ [0xA85A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA85A,
+ },
+ [0xA85B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA85B,
+ },
+ [0xA85C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA85C,
+ },
+ [0xA85D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA85D,
+ },
+ [0xA85E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA85E,
+ },
+ [0xA85F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA85F,
+ },
+ [0xA860]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA860,
+ },
+ [0xA861]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA861,
+ },
+ [0xA862]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA862,
+ },
+ [0xA863]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA863,
+ },
+ [0xA864]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA864,
+ },
+ [0xA865]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA865,
+ },
+ [0xA866]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA866,
+ },
+ [0xA867]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA867,
+ },
+ [0xA868]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA868,
+ },
+ [0xA869]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA869,
+ },
+ [0xA86A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA86A,
+ },
+ [0xA86B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA86B,
+ },
+ [0xA86C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA86C,
+ },
+ [0xA86D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA86D,
+ },
+ [0xA86E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA86E,
+ },
+ [0xA86F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA86F,
+ },
+ [0xA870]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA870,
+ },
+ [0xA871]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA871,
+ },
+ [0xA872]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA872,
+ },
+ [0xA873]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA873,
+ },
+ [0xA874]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0xA874,
+ },
+ [0xA875]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0xA875,
+ },
+ [0xA876]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0xA876,
+ },
+ [0xA877]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ unicodeslot=0xA877,
+ },
+ [0xA880]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA880,
+ },
+ [0xA881]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA881,
+ },
+ [0xA882]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA882,
+ },
+ [0xA883]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA883,
+ },
+ [0xA884]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA884,
+ },
+ [0xA885]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA885,
+ },
+ [0xA886]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA886,
+ },
+ [0xA887]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA887,
+ },
+ [0xA888]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA888,
+ },
+ [0xA889]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA889,
+ },
+ [0xA88A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA88A,
+ },
+ [0xA88B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA88B,
+ },
+ [0xA88C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA88C,
+ },
+ [0xA88D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA88D,
+ },
+ [0xA88E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA88E,
+ },
+ [0xA88F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA88F,
+ },
+ [0xA890]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA890,
+ },
+ [0xA891]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA891,
+ },
+ [0xA892]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA892,
+ },
+ [0xA893]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA893,
+ },
+ [0xA894]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA894,
+ },
+ [0xA895]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA895,
+ },
+ [0xA896]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA896,
+ },
+ [0xA897]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA897,
+ },
+ [0xA898]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA898,
+ },
+ [0xA899]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA899,
+ },
+ [0xA89A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA89A,
+ },
+ [0xA89B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA89B,
+ },
+ [0xA89C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA89C,
+ },
+ [0xA89D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA89D,
+ },
+ [0xA89E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA89E,
+ },
+ [0xA89F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA89F,
+ },
+ [0xA8A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A0,
+ },
+ [0xA8A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A1,
+ },
+ [0xA8A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A2,
+ },
+ [0xA8A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A3,
+ },
+ [0xA8A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A4,
+ },
+ [0xA8A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A5,
+ },
+ [0xA8A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A6,
+ },
+ [0xA8A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A7,
+ },
+ [0xA8A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A8,
+ },
+ [0xA8A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8A9,
+ },
+ [0xA8AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8AA,
+ },
+ [0xA8AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8AB,
+ },
+ [0xA8AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8AC,
+ },
+ [0xA8AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8AD,
+ },
+ [0xA8AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8AE,
+ },
+ [0xA8AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8AF,
+ },
+ [0xA8B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8B0,
+ },
+ [0xA8B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8B1,
+ },
+ [0xA8B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8B2,
+ },
+ [0xA8B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8B3,
+ },
+ [0xA8B4]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8B4,
+ },
+ [0xA8B5]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8B5,
+ },
+ [0xA8B6]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8B6,
+ },
+ [0xA8B7]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8B7,
+ },
+ [0xA8B8]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8B8,
+ },
+ [0xA8B9]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8B9,
+ },
+ [0xA8BA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8BA,
+ },
+ [0xA8BB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8BB,
+ },
+ [0xA8BC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8BC,
+ },
+ [0xA8BD]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8BD,
+ },
+ [0xA8BE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8BE,
+ },
+ [0xA8BF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8BF,
+ },
+ [0xA8C0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8C0,
+ },
+ [0xA8C1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8C1,
+ },
+ [0xA8C2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8C2,
+ },
+ [0xA8C3]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA8C3,
+ },
+ [0xA8C4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA8C4,
+ },
+ [0xA8C5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA8C5,
+ },
+ [0xA8CE]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA8CE,
+ },
+ [0xA8CF]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA8CF,
+ },
+ [0xA8D0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D0,
+ },
+ [0xA8D1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D1,
+ },
+ [0xA8D2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D2,
+ },
+ [0xA8D3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D3,
+ },
+ [0xA8D4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D4,
+ },
+ [0xA8D5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D5,
+ },
+ [0xA8D6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D6,
+ },
+ [0xA8D7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D7,
+ },
+ [0xA8D8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D8,
+ },
+ [0xA8D9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA8D9,
+ },
+ [0xA8E0]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E0,
+ },
+ [0xA8E1]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E1,
+ },
+ [0xA8E2]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E2,
+ },
+ [0xA8E3]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E3,
+ },
+ [0xA8E4]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E4,
+ },
+ [0xA8E5]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E5,
+ },
+ [0xA8E6]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E6,
+ },
+ [0xA8E7]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E7,
+ },
+ [0xA8E8]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E8,
+ },
+ [0xA8E9]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8E9,
+ },
+ [0xA8EA]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8EA,
+ },
+ [0xA8EB]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8EB,
+ },
+ [0xA8EC]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8EC,
+ },
+ [0xA8ED]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8ED,
+ },
+ [0xA8EE]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8EE,
+ },
+ [0xA8EF]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8EF,
+ },
+ [0xA8F0]={
+ category="mn",
+ direction="nsm",
+ indic="o",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8F0,
+ },
+ [0xA8F1]={
+ category="mn",
+ direction="nsm",
+ indic="m",
+ indicmark="t",
+ linebreak="cm",
+ unicodeslot=0xA8F1,
+ },
+ [0xA8F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F2,
+ },
+ [0xA8F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F3,
+ },
+ [0xA8F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F4,
+ },
+ [0xA8F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F5,
+ },
+ [0xA8F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F6,
+ },
+ [0xA8F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F7,
+ },
+ [0xA8F8]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F8,
+ },
+ [0xA8F9]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8F9,
+ },
+ [0xA8FA]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8FA,
+ },
+ [0xA8FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8FB,
+ },
+ [0xA8FC]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0xA8FC,
+ },
+ [0xA8FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8FD,
+ },
+ [0xA8FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA8FE,
+ },
+ [0xA8FF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA8FF,
+ },
+ [0xA900]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA900,
+ },
+ [0xA901]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA901,
+ },
+ [0xA902]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA902,
+ },
+ [0xA903]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA903,
+ },
+ [0xA904]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA904,
+ },
+ [0xA905]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA905,
+ },
+ [0xA906]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA906,
+ },
+ [0xA907]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA907,
+ },
+ [0xA908]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA908,
+ },
+ [0xA909]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA909,
+ },
+ [0xA90A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA90A,
+ },
+ [0xA90B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA90B,
+ },
+ [0xA90C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA90C,
+ },
+ [0xA90D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA90D,
+ },
+ [0xA90E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA90E,
+ },
+ [0xA90F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA90F,
+ },
+ [0xA910]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA910,
+ },
+ [0xA911]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA911,
+ },
+ [0xA912]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA912,
+ },
+ [0xA913]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA913,
+ },
+ [0xA914]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA914,
+ },
+ [0xA915]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA915,
+ },
+ [0xA916]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA916,
+ },
+ [0xA917]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA917,
+ },
+ [0xA918]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA918,
+ },
+ [0xA919]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA919,
+ },
+ [0xA91A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA91A,
+ },
+ [0xA91B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA91B,
+ },
+ [0xA91C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA91C,
+ },
+ [0xA91D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA91D,
+ },
+ [0xA91E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA91E,
+ },
+ [0xA91F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA91F,
+ },
+ [0xA920]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA920,
+ },
+ [0xA921]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA921,
+ },
+ [0xA922]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA922,
+ },
+ [0xA923]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA923,
+ },
+ [0xA924]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA924,
+ },
+ [0xA925]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA925,
+ },
+ [0xA926]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA926,
+ },
+ [0xA927]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA927,
+ },
+ [0xA928]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA928,
+ },
+ [0xA929]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA929,
+ },
+ [0xA92A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA92A,
+ },
+ [0xA92B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA92B,
+ },
+ [0xA92C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA92C,
+ },
+ [0xA92D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA92D,
+ },
+ [0xA92E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA92E,
+ },
+ [0xA92F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA92F,
+ },
+ [0xA930]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA930,
+ },
+ [0xA931]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA931,
+ },
+ [0xA932]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA932,
+ },
+ [0xA933]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA933,
+ },
+ [0xA934]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA934,
+ },
+ [0xA935]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA935,
+ },
+ [0xA936]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA936,
+ },
+ [0xA937]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA937,
+ },
+ [0xA938]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA938,
+ },
+ [0xA939]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA939,
+ },
+ [0xA93A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA93A,
+ },
+ [0xA93B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA93B,
+ },
+ [0xA93C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA93C,
+ },
+ [0xA93D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA93D,
+ },
+ [0xA93E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA93E,
+ },
+ [0xA93F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA93F,
+ },
+ [0xA940]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA940,
+ },
+ [0xA941]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA941,
+ },
+ [0xA942]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA942,
+ },
+ [0xA943]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA943,
+ },
+ [0xA944]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA944,
+ },
+ [0xA945]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA945,
+ },
+ [0xA946]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA946,
+ },
+ [0xA947]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA947,
+ },
+ [0xA948]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA948,
+ },
+ [0xA949]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA949,
+ },
+ [0xA94A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA94A,
+ },
+ [0xA94B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA94B,
+ },
+ [0xA94C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA94C,
+ },
+ [0xA94D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA94D,
+ },
+ [0xA94E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA94E,
+ },
+ [0xA94F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA94F,
+ },
+ [0xA950]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA950,
+ },
+ [0xA951]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA951,
+ },
+ [0xA952]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA952,
+ },
+ [0xA953]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA953,
+ },
+ [0xA95F]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA95F,
+ },
+ [0xA960]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA960,
+ },
+ [0xA961]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA961,
+ },
+ [0xA962]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA962,
+ },
+ [0xA963]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA963,
+ },
+ [0xA964]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA964,
+ },
+ [0xA965]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA965,
+ },
+ [0xA966]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA966,
+ },
+ [0xA967]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA967,
+ },
+ [0xA968]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA968,
+ },
+ [0xA969]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA969,
+ },
+ [0xA96A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA96A,
+ },
+ [0xA96B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA96B,
+ },
+ [0xA96C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA96C,
+ },
+ [0xA96D]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA96D,
+ },
+ [0xA96E]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA96E,
+ },
+ [0xA96F]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA96F,
+ },
+ [0xA970]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA970,
+ },
+ [0xA971]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA971,
+ },
+ [0xA972]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA972,
+ },
+ [0xA973]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA973,
+ },
+ [0xA974]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA974,
+ },
+ [0xA975]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA975,
+ },
+ [0xA976]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA976,
+ },
+ [0xA977]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA977,
+ },
+ [0xA978]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA978,
+ },
+ [0xA979]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA979,
+ },
+ [0xA97A]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA97A,
+ },
+ [0xA97B]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA97B,
+ },
+ [0xA97C]={
+ category="lo",
+ direction="l",
+ linebreak="jl",
+ unicodeslot=0xA97C,
+ },
+ [0xA980]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA980,
+ },
+ [0xA981]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA981,
+ },
+ [0xA982]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA982,
+ },
+ [0xA983]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA983,
+ },
+ [0xA984]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA984,
+ },
+ [0xA985]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA985,
+ },
+ [0xA986]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA986,
+ },
+ [0xA987]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA987,
+ },
+ [0xA988]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA988,
+ },
+ [0xA989]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA989,
+ },
+ [0xA98A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA98A,
+ },
+ [0xA98B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA98B,
+ },
+ [0xA98C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA98C,
+ },
+ [0xA98D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA98D,
+ },
+ [0xA98E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA98E,
+ },
+ [0xA98F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA98F,
+ },
+ [0xA990]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA990,
+ },
+ [0xA991]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA991,
+ },
+ [0xA992]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA992,
+ },
+ [0xA993]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA993,
+ },
+ [0xA994]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA994,
+ },
+ [0xA995]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA995,
+ },
+ [0xA996]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA996,
+ },
+ [0xA997]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA997,
+ },
+ [0xA998]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA998,
+ },
+ [0xA999]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA999,
+ },
+ [0xA99A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA99A,
+ },
+ [0xA99B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA99B,
+ },
+ [0xA99C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA99C,
+ },
+ [0xA99D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA99D,
+ },
+ [0xA99E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA99E,
+ },
+ [0xA99F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA99F,
+ },
+ [0xA9A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A0,
+ },
+ [0xA9A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A1,
+ },
+ [0xA9A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A2,
+ },
+ [0xA9A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A3,
+ },
+ [0xA9A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A4,
+ },
+ [0xA9A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A5,
+ },
+ [0xA9A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A6,
+ },
+ [0xA9A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A7,
+ },
+ [0xA9A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A8,
+ },
+ [0xA9A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9A9,
+ },
+ [0xA9AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9AA,
+ },
+ [0xA9AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9AB,
+ },
+ [0xA9AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9AC,
+ },
+ [0xA9AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9AD,
+ },
+ [0xA9AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9AE,
+ },
+ [0xA9AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9AF,
+ },
+ [0xA9B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9B0,
+ },
+ [0xA9B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9B1,
+ },
+ [0xA9B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9B2,
+ },
+ [0xA9B3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9B3,
+ },
+ [0xA9B4]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9B4,
+ },
+ [0xA9B5]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9B5,
+ },
+ [0xA9B6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9B6,
+ },
+ [0xA9B7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9B7,
+ },
+ [0xA9B8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9B8,
+ },
+ [0xA9B9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9B9,
+ },
+ [0xA9BA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9BA,
+ },
+ [0xA9BB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9BB,
+ },
+ [0xA9BC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9BC,
+ },
+ [0xA9BD]={
+ category="mc",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xA9BD,
+ },
+ [0xA9BE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9BE,
+ },
+ [0xA9BF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9BF,
+ },
+ [0xA9C0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xA9C0,
+ },
+ [0xA9C1]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9C1,
+ },
+ [0xA9C2]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9C2,
+ },
+ [0xA9C3]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9C3,
+ },
+ [0xA9C4]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9C4,
+ },
+ [0xA9C5]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9C5,
+ },
+ [0xA9C6]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9C6,
+ },
+ [0xA9C7]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA9C7,
+ },
+ [0xA9C8]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA9C8,
+ },
+ [0xA9C9]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xA9C9,
+ },
+ [0xA9CA]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9CA,
+ },
+ [0xA9CB]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9CB,
+ },
+ [0xA9CC]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9CC,
+ },
+ [0xA9CD]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9CD,
+ },
+ [0xA9CF]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9CF,
+ },
+ [0xA9D0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D0,
+ },
+ [0xA9D1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D1,
+ },
+ [0xA9D2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D2,
+ },
+ [0xA9D3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D3,
+ },
+ [0xA9D4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D4,
+ },
+ [0xA9D5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D5,
+ },
+ [0xA9D6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D6,
+ },
+ [0xA9D7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D7,
+ },
+ [0xA9D8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D8,
+ },
+ [0xA9D9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xA9D9,
+ },
+ [0xA9DE]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9DE,
+ },
+ [0xA9DF]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xA9DF,
+ },
+ [0xA9E0]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E0,
+ },
+ [0xA9E1]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E1,
+ },
+ [0xA9E2]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E2,
+ },
+ [0xA9E3]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E3,
+ },
+ [0xA9E4]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E4,
+ },
+ [0xA9E5]={
+ category="mn",
+ direction="nsm",
+ indic="d",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0xA9E5,
+ },
+ [0xA9E6]={
+ category="lm",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0xA9E6,
+ },
+ [0xA9E7]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E7,
+ },
+ [0xA9E8]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E8,
+ },
+ [0xA9E9]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9E9,
+ },
+ [0xA9EA]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9EA,
+ },
+ [0xA9EB]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9EB,
+ },
+ [0xA9EC]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9EC,
+ },
+ [0xA9ED]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9ED,
+ },
+ [0xA9EE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9EE,
+ },
+ [0xA9EF]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9EF,
+ },
+ [0xA9F0]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F0,
+ },
+ [0xA9F1]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F1,
+ },
+ [0xA9F2]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F2,
+ },
+ [0xA9F3]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F3,
+ },
+ [0xA9F4]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F4,
+ },
+ [0xA9F5]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F5,
+ },
+ [0xA9F6]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F6,
+ },
+ [0xA9F7]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F7,
+ },
+ [0xA9F8]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F8,
+ },
+ [0xA9F9]={
+ category="nd",
+ direction="l",
+ indic="o",
+ linebreak="nu",
+ unicodeslot=0xA9F9,
+ },
+ [0xA9FA]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9FA,
+ },
+ [0xA9FB]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9FB,
+ },
+ [0xA9FC]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9FC,
+ },
+ [0xA9FD]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9FD,
+ },
+ [0xA9FE]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xA9FE,
+ },
+ [0xAA00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA00,
+ },
+ [0xAA01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA01,
+ },
+ [0xAA02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA02,
+ },
+ [0xAA03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA03,
+ },
+ [0xAA04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA04,
+ },
+ [0xAA05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA05,
+ },
+ [0xAA06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA06,
+ },
+ [0xAA07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA07,
+ },
+ [0xAA08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA08,
+ },
+ [0xAA09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA09,
+ },
+ [0xAA0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA0A,
+ },
+ [0xAA0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA0B,
+ },
+ [0xAA0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA0C,
+ },
+ [0xAA0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA0D,
+ },
+ [0xAA0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA0E,
+ },
+ [0xAA0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA0F,
+ },
+ [0xAA10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA10,
+ },
+ [0xAA11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA11,
+ },
+ [0xAA12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA12,
+ },
+ [0xAA13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA13,
+ },
+ [0xAA14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA14,
+ },
+ [0xAA15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA15,
+ },
+ [0xAA16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA16,
+ },
+ [0xAA17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA17,
+ },
+ [0xAA18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA18,
+ },
+ [0xAA19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA19,
+ },
+ [0xAA1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA1A,
+ },
+ [0xAA1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA1B,
+ },
+ [0xAA1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA1C,
+ },
+ [0xAA1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA1D,
+ },
+ [0xAA1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA1E,
+ },
+ [0xAA1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA1F,
+ },
+ [0xAA20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA20,
+ },
+ [0xAA21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA21,
+ },
+ [0xAA22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA22,
+ },
+ [0xAA23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA23,
+ },
+ [0xAA24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA24,
+ },
+ [0xAA25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA25,
+ },
+ [0xAA26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA26,
+ },
+ [0xAA27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA27,
+ },
+ [0xAA28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA28,
+ },
+ [0xAA29]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA29,
+ },
+ [0xAA2A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA2A,
+ },
+ [0xAA2B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA2B,
+ },
+ [0xAA2C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA2C,
+ },
+ [0xAA2D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA2D,
+ },
+ [0xAA2E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA2E,
+ },
+ [0xAA2F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAA2F,
+ },
+ [0xAA30]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAA30,
+ },
+ [0xAA31]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA31,
+ },
+ [0xAA32]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA32,
+ },
+ [0xAA33]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAA33,
+ },
+ [0xAA34]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAA34,
+ },
+ [0xAA35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA35,
+ },
+ [0xAA36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA36,
+ },
+ [0xAA40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA40,
+ },
+ [0xAA41]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA41,
+ },
+ [0xAA42]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA42,
+ },
+ [0xAA43]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA43,
+ },
+ [0xAA44]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA44,
+ },
+ [0xAA45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA45,
+ },
+ [0xAA46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA46,
+ },
+ [0xAA47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA47,
+ },
+ [0xAA48]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA48,
+ },
+ [0xAA49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA49,
+ },
+ [0xAA4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA4A,
+ },
+ [0xAA4B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA4B,
+ },
+ [0xAA4C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAA4C,
+ },
+ [0xAA4D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAA4D,
+ },
+ [0xAA50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA50,
+ },
+ [0xAA51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA51,
+ },
+ [0xAA52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA52,
+ },
+ [0xAA53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA53,
+ },
+ [0xAA54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA54,
+ },
+ [0xAA55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA55,
+ },
+ [0xAA56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA56,
+ },
+ [0xAA57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA57,
+ },
+ [0xAA58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA58,
+ },
+ [0xAA59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xAA59,
+ },
+ [0xAA5C]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAA5C,
+ },
+ [0xAA5D]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xAA5D,
+ },
+ [0xAA5E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xAA5E,
+ },
+ [0xAA5F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xAA5F,
+ },
+ [0xAA60]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA60,
+ },
+ [0xAA61]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA61,
+ },
+ [0xAA62]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA62,
+ },
+ [0xAA63]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA63,
+ },
+ [0xAA64]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA64,
+ },
+ [0xAA65]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA65,
+ },
+ [0xAA66]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA66,
+ },
+ [0xAA67]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA67,
+ },
+ [0xAA68]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA68,
+ },
+ [0xAA69]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA69,
+ },
+ [0xAA6A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA6A,
+ },
+ [0xAA6B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA6B,
+ },
+ [0xAA6C]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA6C,
+ },
+ [0xAA6D]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA6D,
+ },
+ [0xAA6E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA6E,
+ },
+ [0xAA6F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA6F,
+ },
+ [0xAA70]={
+ category="lm",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0xAA70,
+ },
+ [0xAA71]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA71,
+ },
+ [0xAA72]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA72,
+ },
+ [0xAA73]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA73,
+ },
+ [0xAA74]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA74,
+ },
+ [0xAA75]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA75,
+ },
+ [0xAA76]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA76,
+ },
+ [0xAA77]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0xAA77,
+ },
+ [0xAA78]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0xAA78,
+ },
+ [0xAA79]={
+ category="so",
+ direction="l",
+ indic="o",
+ linebreak="sa",
+ unicodeslot=0xAA79,
+ },
+ [0xAA7A]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA7A,
+ },
+ [0xAA7B]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0xAA7B,
+ },
+ [0xAA7C]={
+ category="mn",
+ direction="nsm",
+ indic="s",
+ indicmark="t",
+ linebreak="sa",
+ unicodeslot=0xAA7C,
+ },
+ [0xAA7D]={
+ category="mc",
+ direction="l",
+ indic="s",
+ indicmark="r",
+ linebreak="sa",
+ unicodeslot=0xAA7D,
+ },
+ [0xAA7E]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA7E,
+ },
+ [0xAA7F]={
+ category="lo",
+ direction="l",
+ indic="c",
+ linebreak="sa",
+ unicodeslot=0xAA7F,
+ },
+ [0xAA80]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA80,
+ },
+ [0xAA81]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA81,
+ },
+ [0xAA82]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA82,
+ },
+ [0xAA83]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA83,
+ },
+ [0xAA84]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA84,
+ },
+ [0xAA85]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA85,
+ },
+ [0xAA86]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA86,
+ },
+ [0xAA87]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA87,
+ },
+ [0xAA88]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA88,
+ },
+ [0xAA89]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA89,
+ },
+ [0xAA8A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA8A,
+ },
+ [0xAA8B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA8B,
+ },
+ [0xAA8C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA8C,
+ },
+ [0xAA8D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA8D,
+ },
+ [0xAA8E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA8E,
+ },
+ [0xAA8F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA8F,
+ },
+ [0xAA90]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA90,
+ },
+ [0xAA91]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA91,
+ },
+ [0xAA92]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA92,
+ },
+ [0xAA93]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA93,
+ },
+ [0xAA94]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA94,
+ },
+ [0xAA95]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA95,
+ },
+ [0xAA96]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA96,
+ },
+ [0xAA97]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA97,
+ },
+ [0xAA98]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA98,
+ },
+ [0xAA99]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA99,
+ },
+ [0xAA9A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA9A,
+ },
+ [0xAA9B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA9B,
+ },
+ [0xAA9C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA9C,
+ },
+ [0xAA9D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA9D,
+ },
+ [0xAA9E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA9E,
+ },
+ [0xAA9F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAA9F,
+ },
+ [0xAAA0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA0,
+ },
+ [0xAAA1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA1,
+ },
+ [0xAAA2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA2,
+ },
+ [0xAAA3]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA3,
+ },
+ [0xAAA4]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA4,
+ },
+ [0xAAA5]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA5,
+ },
+ [0xAAA6]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA6,
+ },
+ [0xAAA7]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA7,
+ },
+ [0xAAA8]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA8,
+ },
+ [0xAAA9]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAA9,
+ },
+ [0xAAAA]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAAA,
+ },
+ [0xAAAB]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAAB,
+ },
+ [0xAAAC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAAC,
+ },
+ [0xAAAD]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAAD,
+ },
+ [0xAAAE]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAAE,
+ },
+ [0xAAAF]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAAF,
+ },
+ [0xAAB0]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAB0,
+ },
+ [0xAAB1]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAB1,
+ },
+ [0xAAB2]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAB2,
+ },
+ [0xAAB3]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAB3,
+ },
+ [0xAAB4]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAB4,
+ },
+ [0xAAB5]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAB5,
+ },
+ [0xAAB6]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAB6,
+ },
+ [0xAAB7]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAB7,
+ },
+ [0xAAB8]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAB8,
+ },
+ [0xAAB9]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAB9,
+ },
+ [0xAABA]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAABA,
+ },
+ [0xAABB]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAABB,
+ },
+ [0xAABC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAABC,
+ },
+ [0xAABD]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAABD,
+ },
+ [0xAABE]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAABE,
+ },
+ [0xAABF]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAABF,
+ },
+ [0xAAC0]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAC0,
+ },
+ [0xAAC1]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0xAAC1,
+ },
+ [0xAAC2]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAAC2,
+ },
+ [0xAADB]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAADB,
+ },
+ [0xAADC]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAADC,
+ },
+ [0xAADD]={
+ category="lm",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAADD,
+ },
+ [0xAADE]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAADE,
+ },
+ [0xAADF]={
+ category="po",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0xAADF,
+ },
+ [0xAAE0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE0,
+ },
+ [0xAAE1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE1,
+ },
+ [0xAAE2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE2,
+ },
+ [0xAAE3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE3,
+ },
+ [0xAAE4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE4,
+ },
+ [0xAAE5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE5,
+ },
+ [0xAAE6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE6,
+ },
+ [0xAAE7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE7,
+ },
+ [0xAAE8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE8,
+ },
+ [0xAAE9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAE9,
+ },
+ [0xAAEA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAEA,
+ },
+ [0xAAEB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAAEB,
+ },
+ [0xAAEC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAAEC,
+ },
+ [0xAAED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAAED,
+ },
+ [0xAAEE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAAEE,
+ },
+ [0xAAEF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAAEF,
+ },
+ [0xAAF0]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xAAF0,
+ },
+ [0xAAF1]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xAAF1,
+ },
+ [0xAAF2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAF2,
+ },
+ [0xAAF3]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAF3,
+ },
+ [0xAAF4]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAAF4,
+ },
+ [0xAAF5]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xAAF5,
+ },
+ [0xAAF6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xAAF6,
+ },
+ [0xAB01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB01,
+ },
+ [0xAB02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB02,
+ },
+ [0xAB03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB03,
+ },
+ [0xAB04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB04,
+ },
+ [0xAB05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB05,
+ },
+ [0xAB06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB06,
+ },
+ [0xAB09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB09,
+ },
+ [0xAB0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB0A,
+ },
+ [0xAB0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB0B,
+ },
+ [0xAB0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB0C,
+ },
+ [0xAB0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB0D,
+ },
+ [0xAB0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB0E,
+ },
+ [0xAB11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB11,
+ },
+ [0xAB12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB12,
+ },
+ [0xAB13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB13,
+ },
+ [0xAB14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB14,
+ },
+ [0xAB15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB15,
+ },
+ [0xAB16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB16,
+ },
+ [0xAB20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB20,
+ },
+ [0xAB21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB21,
+ },
+ [0xAB22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB22,
+ },
+ [0xAB23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB23,
+ },
+ [0xAB24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB24,
+ },
+ [0xAB25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB25,
+ },
+ [0xAB26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB26,
+ },
+ [0xAB28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB28,
+ },
+ [0xAB29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB29,
+ },
+ [0xAB2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB2A,
+ },
+ [0xAB2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB2B,
+ },
+ [0xAB2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB2C,
+ },
+ [0xAB2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB2D,
+ },
+ [0xAB2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB2E,
+ },
+ [0xAB30]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB30,
+ },
+ [0xAB31]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB31,
+ },
+ [0xAB32]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB32,
+ },
+ [0xAB33]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB33,
+ },
+ [0xAB34]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB34,
+ },
+ [0xAB35]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB35,
+ },
+ [0xAB36]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB36,
+ },
+ [0xAB37]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB37,
+ },
+ [0xAB38]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB38,
+ },
+ [0xAB39]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB39,
+ },
+ [0xAB3A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB3A,
+ },
+ [0xAB3B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB3B,
+ },
+ [0xAB3C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB3C,
+ },
+ [0xAB3D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB3D,
+ },
+ [0xAB3E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB3E,
+ },
+ [0xAB3F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB3F,
+ },
+ [0xAB40]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB40,
+ },
+ [0xAB41]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB41,
+ },
+ [0xAB42]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB42,
+ },
+ [0xAB43]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB43,
+ },
+ [0xAB44]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB44,
+ },
+ [0xAB45]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB45,
+ },
+ [0xAB46]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB46,
+ },
+ [0xAB47]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB47,
+ },
+ [0xAB48]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB48,
+ },
+ [0xAB49]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB49,
+ },
+ [0xAB4A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB4A,
+ },
+ [0xAB4B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB4B,
+ },
+ [0xAB4C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB4C,
+ },
+ [0xAB4D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB4D,
+ },
+ [0xAB4E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB4E,
+ },
+ [0xAB4F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB4F,
+ },
+ [0xAB50]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB50,
+ },
+ [0xAB51]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB51,
+ },
+ [0xAB52]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB52,
+ },
+ [0xAB53]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB53,
+ },
+ [0xAB54]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB54,
+ },
+ [0xAB55]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB55,
+ },
+ [0xAB56]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB56,
+ },
+ [0xAB57]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB57,
+ },
+ [0xAB58]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB58,
+ },
+ [0xAB59]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB59,
+ },
+ [0xAB5A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB5A,
+ },
+ [0xAB5B]={
+ category="sk",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB5B,
+ },
+ [0xAB5C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0xA727 },
+ unicodeslot=0xAB5C,
+ },
+ [0xAB5D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0xAB37 },
+ unicodeslot=0xAB5D,
+ },
+ [0xAB5E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0x26B },
+ unicodeslot=0xAB5E,
+ },
+ [0xAB5F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ specials={ "super", 0xAB52 },
+ unicodeslot=0xAB5F,
+ },
+ [0xAB60]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB60,
+ },
+ [0xAB61]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB61,
+ },
+ [0xAB62]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB62,
+ },
+ [0xAB63]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB63,
+ },
+ [0xAB64]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB64,
+ },
+ [0xAB65]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB65,
+ },
+ [0xAB66]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB66,
+ },
+ [0xAB67]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB67,
+ },
+ [0xAB70]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB70,
+ },
+ [0xAB71]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB71,
+ },
+ [0xAB72]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB72,
+ },
+ [0xAB73]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB73,
+ },
+ [0xAB74]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB74,
+ },
+ [0xAB75]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB75,
+ },
+ [0xAB76]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB76,
+ },
+ [0xAB77]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB77,
+ },
+ [0xAB78]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB78,
+ },
+ [0xAB79]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB79,
+ },
+ [0xAB7A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB7A,
+ },
+ [0xAB7B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB7B,
+ },
+ [0xAB7C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB7C,
+ },
+ [0xAB7D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB7D,
+ },
+ [0xAB7E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB7E,
+ },
+ [0xAB7F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB7F,
+ },
+ [0xAB80]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB80,
+ },
+ [0xAB81]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB81,
+ },
+ [0xAB82]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB82,
+ },
+ [0xAB83]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB83,
+ },
+ [0xAB84]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB84,
+ },
+ [0xAB85]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB85,
+ },
+ [0xAB86]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB86,
+ },
+ [0xAB87]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB87,
+ },
+ [0xAB88]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB88,
+ },
+ [0xAB89]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB89,
+ },
+ [0xAB8A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB8A,
+ },
+ [0xAB8B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB8B,
+ },
+ [0xAB8C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB8C,
+ },
+ [0xAB8D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB8D,
+ },
+ [0xAB8E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB8E,
+ },
+ [0xAB8F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB8F,
+ },
+ [0xAB90]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB90,
+ },
+ [0xAB91]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB91,
+ },
+ [0xAB92]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB92,
+ },
+ [0xAB93]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB93,
+ },
+ [0xAB94]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB94,
+ },
+ [0xAB95]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB95,
+ },
+ [0xAB96]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB96,
+ },
+ [0xAB97]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB97,
+ },
+ [0xAB98]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB98,
+ },
+ [0xAB99]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB99,
+ },
+ [0xAB9A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB9A,
+ },
+ [0xAB9B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB9B,
+ },
+ [0xAB9C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB9C,
+ },
+ [0xAB9D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB9D,
+ },
+ [0xAB9E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB9E,
+ },
+ [0xAB9F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xAB9F,
+ },
+ [0xABA0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA0,
+ },
+ [0xABA1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA1,
+ },
+ [0xABA2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA2,
+ },
+ [0xABA3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA3,
+ },
+ [0xABA4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA4,
+ },
+ [0xABA5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA5,
+ },
+ [0xABA6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA6,
+ },
+ [0xABA7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA7,
+ },
+ [0xABA8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA8,
+ },
+ [0xABA9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABA9,
+ },
+ [0xABAA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABAA,
+ },
+ [0xABAB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABAB,
+ },
+ [0xABAC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABAC,
+ },
+ [0xABAD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABAD,
+ },
+ [0xABAE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABAE,
+ },
+ [0xABAF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABAF,
+ },
+ [0xABB0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB0,
+ },
+ [0xABB1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB1,
+ },
+ [0xABB2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB2,
+ },
+ [0xABB3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB3,
+ },
+ [0xABB4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB4,
+ },
+ [0xABB5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB5,
+ },
+ [0xABB6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB6,
+ },
+ [0xABB7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB7,
+ },
+ [0xABB8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB8,
+ },
+ [0xABB9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABB9,
+ },
+ [0xABBA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABBA,
+ },
+ [0xABBB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABBB,
+ },
+ [0xABBC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABBC,
+ },
+ [0xABBD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABBD,
+ },
+ [0xABBE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABBE,
+ },
+ [0xABBF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABBF,
+ },
+ [0xABC0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC0,
+ },
+ [0xABC1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC1,
+ },
+ [0xABC2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC2,
+ },
+ [0xABC3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC3,
+ },
+ [0xABC4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC4,
+ },
+ [0xABC5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC5,
+ },
+ [0xABC6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC6,
+ },
+ [0xABC7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC7,
+ },
+ [0xABC8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC8,
+ },
+ [0xABC9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABC9,
+ },
+ [0xABCA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABCA,
+ },
+ [0xABCB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABCB,
+ },
+ [0xABCC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABCC,
+ },
+ [0xABCD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABCD,
+ },
+ [0xABCE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABCE,
+ },
+ [0xABCF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABCF,
+ },
+ [0xABD0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD0,
+ },
+ [0xABD1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD1,
+ },
+ [0xABD2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD2,
+ },
+ [0xABD3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD3,
+ },
+ [0xABD4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD4,
+ },
+ [0xABD5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD5,
+ },
+ [0xABD6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD6,
+ },
+ [0xABD7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD7,
+ },
+ [0xABD8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD8,
+ },
+ [0xABD9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABD9,
+ },
+ [0xABDA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABDA,
+ },
+ [0xABDB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABDB,
+ },
+ [0xABDC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABDC,
+ },
+ [0xABDD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABDD,
+ },
+ [0xABDE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABDE,
+ },
+ [0xABDF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABDF,
+ },
+ [0xABE0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABE0,
+ },
+ [0xABE1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABE1,
+ },
+ [0xABE2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0xABE2,
+ },
+ [0xABE3]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABE3,
+ },
+ [0xABE4]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABE4,
+ },
+ [0xABE5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xABE5,
+ },
+ [0xABE6]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABE6,
+ },
+ [0xABE7]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABE7,
+ },
+ [0xABE8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xABE8,
+ },
+ [0xABE9]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABE9,
+ },
+ [0xABEA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABEA,
+ },
+ [0xABEB]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0xABEB,
+ },
+ [0xABEC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0xABEC,
+ },
+ [0xABED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xABED,
+ },
+ [0xABF0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF0,
+ },
+ [0xABF1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF1,
+ },
+ [0xABF2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF2,
+ },
+ [0xABF3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF3,
+ },
+ [0xABF4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF4,
+ },
+ [0xABF5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF5,
+ },
+ [0xABF6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF6,
+ },
+ [0xABF7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF7,
+ },
+ [0xABF8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF8,
+ },
+ [0xABF9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0xABF9,
+ },
+ [0xD7B0]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B0,
+ },
+ [0xD7B1]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B1,
+ },
+ [0xD7B2]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B2,
+ },
+ [0xD7B3]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B3,
+ },
+ [0xD7B4]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B4,
+ },
+ [0xD7B5]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B5,
+ },
+ [0xD7B6]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B6,
+ },
+ [0xD7B7]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B7,
+ },
+ [0xD7B8]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B8,
+ },
+ [0xD7B9]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7B9,
+ },
+ [0xD7BA]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7BA,
+ },
+ [0xD7BB]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7BB,
+ },
+ [0xD7BC]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7BC,
+ },
+ [0xD7BD]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7BD,
+ },
+ [0xD7BE]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7BE,
+ },
+ [0xD7BF]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7BF,
+ },
+ [0xD7C0]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C0,
+ },
+ [0xD7C1]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C1,
+ },
+ [0xD7C2]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C2,
+ },
+ [0xD7C3]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C3,
+ },
+ [0xD7C4]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C4,
+ },
+ [0xD7C5]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C5,
+ },
+ [0xD7C6]={
+ category="lo",
+ direction="l",
+ linebreak="jv",
+ unicodeslot=0xD7C6,
+ },
+ [0xD7CB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7CB,
+ },
+ [0xD7CC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7CC,
+ },
+ [0xD7CD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7CD,
+ },
+ [0xD7CE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7CE,
+ },
+ [0xD7CF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7CF,
+ },
+ [0xD7D0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D0,
+ },
+ [0xD7D1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D1,
+ },
+ [0xD7D2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D2,
+ },
+ [0xD7D3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D3,
+ },
+ [0xD7D4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D4,
+ },
+ [0xD7D5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D5,
+ },
+ [0xD7D6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D6,
+ },
+ [0xD7D7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D7,
+ },
+ [0xD7D8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D8,
+ },
+ [0xD7D9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7D9,
+ },
+ [0xD7DA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7DA,
+ },
+ [0xD7DB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7DB,
+ },
+ [0xD7DC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7DC,
+ },
+ [0xD7DD]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7DD,
+ },
+ [0xD7DE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7DE,
+ },
+ [0xD7DF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7DF,
+ },
+ [0xD7E0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E0,
+ },
+ [0xD7E1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E1,
+ },
+ [0xD7E2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E2,
+ },
+ [0xD7E3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E3,
+ },
+ [0xD7E4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E4,
+ },
+ [0xD7E5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E5,
+ },
+ [0xD7E6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E6,
+ },
+ [0xD7E7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E7,
+ },
+ [0xD7E8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E8,
+ },
+ [0xD7E9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7E9,
+ },
+ [0xD7EA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7EA,
+ },
+ [0xD7EB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7EB,
+ },
+ [0xD7EC]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7EC,
+ },
+ [0xD7ED]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7ED,
+ },
+ [0xD7EE]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7EE,
+ },
+ [0xD7EF]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7EF,
+ },
+ [0xD7F0]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F0,
+ },
+ [0xD7F1]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F1,
+ },
+ [0xD7F2]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F2,
+ },
+ [0xD7F3]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F3,
+ },
+ [0xD7F4]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F4,
+ },
+ [0xD7F5]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F5,
+ },
+ [0xD7F6]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F6,
+ },
+ [0xD7F7]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F7,
+ },
+ [0xD7F8]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F8,
+ },
+ [0xD7F9]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7F9,
+ },
+ [0xD7FA]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7FA,
+ },
+ [0xD7FB]={
+ category="lo",
+ direction="l",
+ linebreak="jt",
+ unicodeslot=0xD7FB,
+ },
+ [0xD800]={
+ category="cs",
+ direction="l",
+ linebreak="sg",
+ unicodeslot=0xD800,
+ },
+ [0xDB7F]={
+ category="cs",
+ direction="l",
+ linebreak="sg",
+ unicodeslot=0xDB7F,
+ },
+ [0xDB80]={
+ category="cs",
+ direction="l",
+ linebreak="sg",
+ unicodeslot=0xDB80,
+ },
+ [0xDBFF]={
+ category="cs",
+ direction="l",
+ linebreak="sg",
+ unicodeslot=0xDBFF,
+ },
+ [0xDC00]={
+ category="cs",
+ direction="l",
+ linebreak="sg",
+ unicodeslot=0xDC00,
+ },
+ [0xDFFF]={
+ category="cs",
+ direction="l",
+ linebreak="sg",
+ unicodeslot=0xDFFF,
+ },
+ [0xE000]={
+ category="co",
+ direction="l",
+ unicodeslot=0xE000,
+ },
+ [0xF8FF]={
+ category="co",
+ direction="l",
+ unicodeslot=0xF8FF,
+ },
+ [0xF900]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8C48 },
+ unicodeslot=0xF900,
+ },
+ [0xF901]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x66F4 },
+ unicodeslot=0xF901,
+ },
+ [0xF902]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8ECA },
+ unicodeslot=0xF902,
+ },
+ [0xF903]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8CC8 },
+ unicodeslot=0xF903,
+ },
+ [0xF904]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6ED1 },
+ unicodeslot=0xF904,
+ },
+ [0xF905]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E32 },
+ unicodeslot=0xF905,
+ },
+ [0xF906]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x53E5 },
+ unicodeslot=0xF906,
+ },
+ [0xF907]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F9C },
+ unicodeslot=0xF907,
+ },
+ [0xF908]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F9C },
+ unicodeslot=0xF908,
+ },
+ [0xF909]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5951 },
+ unicodeslot=0xF909,
+ },
+ [0xF90A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x91D1 },
+ unicodeslot=0xF90A,
+ },
+ [0xF90B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5587 },
+ unicodeslot=0xF90B,
+ },
+ [0xF90C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5948 },
+ unicodeslot=0xF90C,
+ },
+ [0xF90D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61F6 },
+ unicodeslot=0xF90D,
+ },
+ [0xF90E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7669 },
+ unicodeslot=0xF90E,
+ },
+ [0xF90F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F85 },
+ unicodeslot=0xF90F,
+ },
+ [0xF910]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x863F },
+ unicodeslot=0xF910,
+ },
+ [0xF911]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x87BA },
+ unicodeslot=0xF911,
+ },
+ [0xF912]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88F8 },
+ unicodeslot=0xF912,
+ },
+ [0xF913]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x908F },
+ unicodeslot=0xF913,
+ },
+ [0xF914]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6A02 },
+ unicodeslot=0xF914,
+ },
+ [0xF915]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D1B },
+ unicodeslot=0xF915,
+ },
+ [0xF916]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x70D9 },
+ unicodeslot=0xF916,
+ },
+ [0xF917]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x73DE },
+ unicodeslot=0xF917,
+ },
+ [0xF918]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x843D },
+ unicodeslot=0xF918,
+ },
+ [0xF919]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x916A },
+ unicodeslot=0xF919,
+ },
+ [0xF91A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x99F1 },
+ unicodeslot=0xF91A,
+ },
+ [0xF91B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E82 },
+ unicodeslot=0xF91B,
+ },
+ [0xF91C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5375 },
+ unicodeslot=0xF91C,
+ },
+ [0xF91D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B04 },
+ unicodeslot=0xF91D,
+ },
+ [0xF91E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x721B },
+ unicodeslot=0xF91E,
+ },
+ [0xF91F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x862D },
+ unicodeslot=0xF91F,
+ },
+ [0xF920]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9E1E },
+ unicodeslot=0xF920,
+ },
+ [0xF921]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5D50 },
+ unicodeslot=0xF921,
+ },
+ [0xF922]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6FEB },
+ unicodeslot=0xF922,
+ },
+ [0xF923]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x85CD },
+ unicodeslot=0xF923,
+ },
+ [0xF924]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8964 },
+ unicodeslot=0xF924,
+ },
+ [0xF925]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62C9 },
+ unicodeslot=0xF925,
+ },
+ [0xF926]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x81D8 },
+ unicodeslot=0xF926,
+ },
+ [0xF927]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x881F },
+ unicodeslot=0xF927,
+ },
+ [0xF928]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5ECA },
+ unicodeslot=0xF928,
+ },
+ [0xF929]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6717 },
+ unicodeslot=0xF929,
+ },
+ [0xF92A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D6A },
+ unicodeslot=0xF92A,
+ },
+ [0xF92B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x72FC },
+ unicodeslot=0xF92B,
+ },
+ [0xF92C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x90CE },
+ unicodeslot=0xF92C,
+ },
+ [0xF92D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4F86 },
+ unicodeslot=0xF92D,
+ },
+ [0xF92E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51B7 },
+ unicodeslot=0xF92E,
+ },
+ [0xF92F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52DE },
+ unicodeslot=0xF92F,
+ },
+ [0xF930]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x64C4 },
+ unicodeslot=0xF930,
+ },
+ [0xF931]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6AD3 },
+ unicodeslot=0xF931,
+ },
+ [0xF932]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7210 },
+ unicodeslot=0xF932,
+ },
+ [0xF933]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x76E7 },
+ unicodeslot=0xF933,
+ },
+ [0xF934]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8001 },
+ unicodeslot=0xF934,
+ },
+ [0xF935]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8606 },
+ unicodeslot=0xF935,
+ },
+ [0xF936]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x865C },
+ unicodeslot=0xF936,
+ },
+ [0xF937]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8DEF },
+ unicodeslot=0xF937,
+ },
+ [0xF938]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9732 },
+ unicodeslot=0xF938,
+ },
+ [0xF939]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9B6F },
+ unicodeslot=0xF939,
+ },
+ [0xF93A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9DFA },
+ unicodeslot=0xF93A,
+ },
+ [0xF93B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x788C },
+ unicodeslot=0xF93B,
+ },
+ [0xF93C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x797F },
+ unicodeslot=0xF93C,
+ },
+ [0xF93D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7DA0 },
+ unicodeslot=0xF93D,
+ },
+ [0xF93E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83C9 },
+ unicodeslot=0xF93E,
+ },
+ [0xF93F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9304 },
+ unicodeslot=0xF93F,
+ },
+ [0xF940]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9E7F },
+ unicodeslot=0xF940,
+ },
+ [0xF941]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AD6 },
+ unicodeslot=0xF941,
+ },
+ [0xF942]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58DF },
+ unicodeslot=0xF942,
+ },
+ [0xF943]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F04 },
+ unicodeslot=0xF943,
+ },
+ [0xF944]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7C60 },
+ unicodeslot=0xF944,
+ },
+ [0xF945]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x807E },
+ unicodeslot=0xF945,
+ },
+ [0xF946]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7262 },
+ unicodeslot=0xF946,
+ },
+ [0xF947]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x78CA },
+ unicodeslot=0xF947,
+ },
+ [0xF948]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8CC2 },
+ unicodeslot=0xF948,
+ },
+ [0xF949]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96F7 },
+ unicodeslot=0xF949,
+ },
+ [0xF94A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58D8 },
+ unicodeslot=0xF94A,
+ },
+ [0xF94B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C62 },
+ unicodeslot=0xF94B,
+ },
+ [0xF94C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6A13 },
+ unicodeslot=0xF94C,
+ },
+ [0xF94D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6DDA },
+ unicodeslot=0xF94D,
+ },
+ [0xF94E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6F0F },
+ unicodeslot=0xF94E,
+ },
+ [0xF94F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7D2F },
+ unicodeslot=0xF94F,
+ },
+ [0xF950]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7E37 },
+ unicodeslot=0xF950,
+ },
+ [0xF951]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x964B },
+ unicodeslot=0xF951,
+ },
+ [0xF952]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52D2 },
+ unicodeslot=0xF952,
+ },
+ [0xF953]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x808B },
+ unicodeslot=0xF953,
+ },
+ [0xF954]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51DC },
+ unicodeslot=0xF954,
+ },
+ [0xF955]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51CC },
+ unicodeslot=0xF955,
+ },
+ [0xF956]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7A1C },
+ unicodeslot=0xF956,
+ },
+ [0xF957]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7DBE },
+ unicodeslot=0xF957,
+ },
+ [0xF958]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83F1 },
+ unicodeslot=0xF958,
+ },
+ [0xF959]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9675 },
+ unicodeslot=0xF959,
+ },
+ [0xF95A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B80 },
+ unicodeslot=0xF95A,
+ },
+ [0xF95B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62CF },
+ unicodeslot=0xF95B,
+ },
+ [0xF95C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6A02 },
+ unicodeslot=0xF95C,
+ },
+ [0xF95D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AFE },
+ unicodeslot=0xF95D,
+ },
+ [0xF95E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E39 },
+ unicodeslot=0xF95E,
+ },
+ [0xF95F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BE7 },
+ unicodeslot=0xF95F,
+ },
+ [0xF960]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6012 },
+ unicodeslot=0xF960,
+ },
+ [0xF961]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7387 },
+ unicodeslot=0xF961,
+ },
+ [0xF962]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7570 },
+ unicodeslot=0xF962,
+ },
+ [0xF963]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5317 },
+ unicodeslot=0xF963,
+ },
+ [0xF964]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x78FB },
+ unicodeslot=0xF964,
+ },
+ [0xF965]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4FBF },
+ unicodeslot=0xF965,
+ },
+ [0xF966]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5FA9 },
+ unicodeslot=0xF966,
+ },
+ [0xF967]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E0D },
+ unicodeslot=0xF967,
+ },
+ [0xF968]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6CCC },
+ unicodeslot=0xF968,
+ },
+ [0xF969]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6578 },
+ unicodeslot=0xF969,
+ },
+ [0xF96A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7D22 },
+ unicodeslot=0xF96A,
+ },
+ [0xF96B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x53C3 },
+ unicodeslot=0xF96B,
+ },
+ [0xF96C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x585E },
+ unicodeslot=0xF96C,
+ },
+ [0xF96D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7701 },
+ unicodeslot=0xF96D,
+ },
+ [0xF96E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8449 },
+ unicodeslot=0xF96E,
+ },
+ [0xF96F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AAA },
+ unicodeslot=0xF96F,
+ },
+ [0xF970]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6BBA },
+ unicodeslot=0xF970,
+ },
+ [0xF971]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8FB0 },
+ unicodeslot=0xF971,
+ },
+ [0xF972]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6C88 },
+ unicodeslot=0xF972,
+ },
+ [0xF973]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62FE },
+ unicodeslot=0xF973,
+ },
+ [0xF974]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x82E5 },
+ unicodeslot=0xF974,
+ },
+ [0xF975]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x63A0 },
+ unicodeslot=0xF975,
+ },
+ [0xF976]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7565 },
+ unicodeslot=0xF976,
+ },
+ [0xF977]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4EAE },
+ unicodeslot=0xF977,
+ },
+ [0xF978]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5169 },
+ unicodeslot=0xF978,
+ },
+ [0xF979]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51C9 },
+ unicodeslot=0xF979,
+ },
+ [0xF97A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6881 },
+ unicodeslot=0xF97A,
+ },
+ [0xF97B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7CE7 },
+ unicodeslot=0xF97B,
+ },
+ [0xF97C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x826F },
+ unicodeslot=0xF97C,
+ },
+ [0xF97D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AD2 },
+ unicodeslot=0xF97D,
+ },
+ [0xF97E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x91CF },
+ unicodeslot=0xF97E,
+ },
+ [0xF97F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52F5 },
+ unicodeslot=0xF97F,
+ },
+ [0xF980]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5442 },
+ unicodeslot=0xF980,
+ },
+ [0xF981]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5973 },
+ unicodeslot=0xF981,
+ },
+ [0xF982]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EEC },
+ unicodeslot=0xF982,
+ },
+ [0xF983]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x65C5 },
+ unicodeslot=0xF983,
+ },
+ [0xF984]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6FFE },
+ unicodeslot=0xF984,
+ },
+ [0xF985]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x792A },
+ unicodeslot=0xF985,
+ },
+ [0xF986]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x95AD },
+ unicodeslot=0xF986,
+ },
+ [0xF987]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9A6A },
+ unicodeslot=0xF987,
+ },
+ [0xF988]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9E97 },
+ unicodeslot=0xF988,
+ },
+ [0xF989]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9ECE },
+ unicodeslot=0xF989,
+ },
+ [0xF98A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x529B },
+ unicodeslot=0xF98A,
+ },
+ [0xF98B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x66C6 },
+ unicodeslot=0xF98B,
+ },
+ [0xF98C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B77 },
+ unicodeslot=0xF98C,
+ },
+ [0xF98D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F62 },
+ unicodeslot=0xF98D,
+ },
+ [0xF98E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5E74 },
+ unicodeslot=0xF98E,
+ },
+ [0xF98F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6190 },
+ unicodeslot=0xF98F,
+ },
+ [0xF990]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6200 },
+ unicodeslot=0xF990,
+ },
+ [0xF991]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x649A },
+ unicodeslot=0xF991,
+ },
+ [0xF992]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6F23 },
+ unicodeslot=0xF992,
+ },
+ [0xF993]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7149 },
+ unicodeslot=0xF993,
+ },
+ [0xF994]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7489 },
+ unicodeslot=0xF994,
+ },
+ [0xF995]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x79CA },
+ unicodeslot=0xF995,
+ },
+ [0xF996]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7DF4 },
+ unicodeslot=0xF996,
+ },
+ [0xF997]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x806F },
+ unicodeslot=0xF997,
+ },
+ [0xF998]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F26 },
+ unicodeslot=0xF998,
+ },
+ [0xF999]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x84EE },
+ unicodeslot=0xF999,
+ },
+ [0xF99A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9023 },
+ unicodeslot=0xF99A,
+ },
+ [0xF99B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x934A },
+ unicodeslot=0xF99B,
+ },
+ [0xF99C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5217 },
+ unicodeslot=0xF99C,
+ },
+ [0xF99D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52A3 },
+ unicodeslot=0xF99D,
+ },
+ [0xF99E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x54BD },
+ unicodeslot=0xF99E,
+ },
+ [0xF99F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x70C8 },
+ unicodeslot=0xF99F,
+ },
+ [0xF9A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88C2 },
+ unicodeslot=0xF9A0,
+ },
+ [0xF9A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AAA },
+ unicodeslot=0xF9A1,
+ },
+ [0xF9A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EC9 },
+ unicodeslot=0xF9A2,
+ },
+ [0xF9A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5FF5 },
+ unicodeslot=0xF9A3,
+ },
+ [0xF9A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x637B },
+ unicodeslot=0xF9A4,
+ },
+ [0xF9A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6BAE },
+ unicodeslot=0xF9A5,
+ },
+ [0xF9A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7C3E },
+ unicodeslot=0xF9A6,
+ },
+ [0xF9A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7375 },
+ unicodeslot=0xF9A7,
+ },
+ [0xF9A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4EE4 },
+ unicodeslot=0xF9A8,
+ },
+ [0xF9A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x56F9 },
+ unicodeslot=0xF9A9,
+ },
+ [0xF9AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BE7 },
+ unicodeslot=0xF9AA,
+ },
+ [0xF9AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5DBA },
+ unicodeslot=0xF9AB,
+ },
+ [0xF9AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x601C },
+ unicodeslot=0xF9AC,
+ },
+ [0xF9AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x73B2 },
+ unicodeslot=0xF9AD,
+ },
+ [0xF9AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7469 },
+ unicodeslot=0xF9AE,
+ },
+ [0xF9AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F9A },
+ unicodeslot=0xF9AF,
+ },
+ [0xF9B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8046 },
+ unicodeslot=0xF9B0,
+ },
+ [0xF9B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9234 },
+ unicodeslot=0xF9B1,
+ },
+ [0xF9B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96F6 },
+ unicodeslot=0xF9B2,
+ },
+ [0xF9B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9748 },
+ unicodeslot=0xF9B3,
+ },
+ [0xF9B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9818 },
+ unicodeslot=0xF9B4,
+ },
+ [0xF9B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4F8B },
+ unicodeslot=0xF9B5,
+ },
+ [0xF9B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x79AE },
+ unicodeslot=0xF9B6,
+ },
+ [0xF9B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x91B4 },
+ unicodeslot=0xF9B7,
+ },
+ [0xF9B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96B8 },
+ unicodeslot=0xF9B8,
+ },
+ [0xF9B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x60E1 },
+ unicodeslot=0xF9B9,
+ },
+ [0xF9BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E86 },
+ unicodeslot=0xF9BA,
+ },
+ [0xF9BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x50DA },
+ unicodeslot=0xF9BB,
+ },
+ [0xF9BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BEE },
+ unicodeslot=0xF9BC,
+ },
+ [0xF9BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C3F },
+ unicodeslot=0xF9BD,
+ },
+ [0xF9BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6599 },
+ unicodeslot=0xF9BE,
+ },
+ [0xF9BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6A02 },
+ unicodeslot=0xF9BF,
+ },
+ [0xF9C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x71CE },
+ unicodeslot=0xF9C0,
+ },
+ [0xF9C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7642 },
+ unicodeslot=0xF9C1,
+ },
+ [0xF9C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x84FC },
+ unicodeslot=0xF9C2,
+ },
+ [0xF9C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x907C },
+ unicodeslot=0xF9C3,
+ },
+ [0xF9C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F8D },
+ unicodeslot=0xF9C4,
+ },
+ [0xF9C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6688 },
+ unicodeslot=0xF9C5,
+ },
+ [0xF9C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x962E },
+ unicodeslot=0xF9C6,
+ },
+ [0xF9C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5289 },
+ unicodeslot=0xF9C7,
+ },
+ [0xF9C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x677B },
+ unicodeslot=0xF9C8,
+ },
+ [0xF9C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x67F3 },
+ unicodeslot=0xF9C9,
+ },
+ [0xF9CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D41 },
+ unicodeslot=0xF9CA,
+ },
+ [0xF9CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6E9C },
+ unicodeslot=0xF9CB,
+ },
+ [0xF9CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7409 },
+ unicodeslot=0xF9CC,
+ },
+ [0xF9CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7559 },
+ unicodeslot=0xF9CD,
+ },
+ [0xF9CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x786B },
+ unicodeslot=0xF9CE,
+ },
+ [0xF9CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7D10 },
+ unicodeslot=0xF9CF,
+ },
+ [0xF9D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x985E },
+ unicodeslot=0xF9D0,
+ },
+ [0xF9D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x516D },
+ unicodeslot=0xF9D1,
+ },
+ [0xF9D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x622E },
+ unicodeslot=0xF9D2,
+ },
+ [0xF9D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9678 },
+ unicodeslot=0xF9D3,
+ },
+ [0xF9D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x502B },
+ unicodeslot=0xF9D4,
+ },
+ [0xF9D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5D19 },
+ unicodeslot=0xF9D5,
+ },
+ [0xF9D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6DEA },
+ unicodeslot=0xF9D6,
+ },
+ [0xF9D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F2A },
+ unicodeslot=0xF9D7,
+ },
+ [0xF9D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F8B },
+ unicodeslot=0xF9D8,
+ },
+ [0xF9D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6144 },
+ unicodeslot=0xF9D9,
+ },
+ [0xF9DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6817 },
+ unicodeslot=0xF9DA,
+ },
+ [0xF9DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7387 },
+ unicodeslot=0xF9DB,
+ },
+ [0xF9DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9686 },
+ unicodeslot=0xF9DC,
+ },
+ [0xF9DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5229 },
+ unicodeslot=0xF9DD,
+ },
+ [0xF9DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x540F },
+ unicodeslot=0xF9DE,
+ },
+ [0xF9DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C65 },
+ unicodeslot=0xF9DF,
+ },
+ [0xF9E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6613 },
+ unicodeslot=0xF9E0,
+ },
+ [0xF9E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x674E },
+ unicodeslot=0xF9E1,
+ },
+ [0xF9E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x68A8 },
+ unicodeslot=0xF9E2,
+ },
+ [0xF9E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6CE5 },
+ unicodeslot=0xF9E3,
+ },
+ [0xF9E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7406 },
+ unicodeslot=0xF9E4,
+ },
+ [0xF9E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x75E2 },
+ unicodeslot=0xF9E5,
+ },
+ [0xF9E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F79 },
+ unicodeslot=0xF9E6,
+ },
+ [0xF9E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88CF },
+ unicodeslot=0xF9E7,
+ },
+ [0xF9E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88E1 },
+ unicodeslot=0xF9E8,
+ },
+ [0xF9E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x91CC },
+ unicodeslot=0xF9E9,
+ },
+ [0xF9EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96E2 },
+ unicodeslot=0xF9EA,
+ },
+ [0xF9EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x533F },
+ unicodeslot=0xF9EB,
+ },
+ [0xF9EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6EBA },
+ unicodeslot=0xF9EC,
+ },
+ [0xF9ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x541D },
+ unicodeslot=0xF9ED,
+ },
+ [0xF9EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x71D0 },
+ unicodeslot=0xF9EE,
+ },
+ [0xF9EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7498 },
+ unicodeslot=0xF9EF,
+ },
+ [0xF9F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x85FA },
+ unicodeslot=0xF9F0,
+ },
+ [0xF9F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96A3 },
+ unicodeslot=0xF9F1,
+ },
+ [0xF9F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9C57 },
+ unicodeslot=0xF9F2,
+ },
+ [0xF9F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9E9F },
+ unicodeslot=0xF9F3,
+ },
+ [0xF9F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6797 },
+ unicodeslot=0xF9F4,
+ },
+ [0xF9F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6DCB },
+ unicodeslot=0xF9F5,
+ },
+ [0xF9F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x81E8 },
+ unicodeslot=0xF9F6,
+ },
+ [0xF9F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7ACB },
+ unicodeslot=0xF9F7,
+ },
+ [0xF9F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7B20 },
+ unicodeslot=0xF9F8,
+ },
+ [0xF9F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7C92 },
+ unicodeslot=0xF9F9,
+ },
+ [0xF9FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x72C0 },
+ unicodeslot=0xF9FA,
+ },
+ [0xF9FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7099 },
+ unicodeslot=0xF9FB,
+ },
+ [0xF9FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B58 },
+ unicodeslot=0xF9FC,
+ },
+ [0xF9FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4EC0 },
+ unicodeslot=0xF9FD,
+ },
+ [0xF9FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8336 },
+ unicodeslot=0xF9FE,
+ },
+ [0xF9FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x523A },
+ unicodeslot=0xF9FF,
+ },
+ [0xFA00]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5207 },
+ unicodeslot=0xFA00,
+ },
+ [0xFA01]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EA6 },
+ unicodeslot=0xFA01,
+ },
+ [0xFA02]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62D3 },
+ unicodeslot=0xFA02,
+ },
+ [0xFA03]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7CD6 },
+ unicodeslot=0xFA03,
+ },
+ [0xFA04]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5B85 },
+ unicodeslot=0xFA04,
+ },
+ [0xFA05]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D1E },
+ unicodeslot=0xFA05,
+ },
+ [0xFA06]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x66B4 },
+ unicodeslot=0xFA06,
+ },
+ [0xFA07]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F3B },
+ unicodeslot=0xFA07,
+ },
+ [0xFA08]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x884C },
+ unicodeslot=0xFA08,
+ },
+ [0xFA09]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x964D },
+ unicodeslot=0xFA09,
+ },
+ [0xFA0A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x898B },
+ unicodeslot=0xFA0A,
+ },
+ [0xFA0B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5ED3 },
+ unicodeslot=0xFA0B,
+ },
+ [0xFA0C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5140 },
+ unicodeslot=0xFA0C,
+ },
+ [0xFA0D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x55C0 },
+ unicodeslot=0xFA0D,
+ },
+ [0xFA0E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA0E,
+ },
+ [0xFA0F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA0F,
+ },
+ [0xFA10]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x585A },
+ unicodeslot=0xFA10,
+ },
+ [0xFA11]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA11,
+ },
+ [0xFA12]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6674 },
+ unicodeslot=0xFA12,
+ },
+ [0xFA13]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA13,
+ },
+ [0xFA14]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA14,
+ },
+ [0xFA15]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51DE },
+ unicodeslot=0xFA15,
+ },
+ [0xFA16]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x732A },
+ unicodeslot=0xFA16,
+ },
+ [0xFA17]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x76CA },
+ unicodeslot=0xFA17,
+ },
+ [0xFA18]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x793C },
+ unicodeslot=0xFA18,
+ },
+ [0xFA19]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x795E },
+ unicodeslot=0xFA19,
+ },
+ [0xFA1A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7965 },
+ unicodeslot=0xFA1A,
+ },
+ [0xFA1B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x798F },
+ unicodeslot=0xFA1B,
+ },
+ [0xFA1C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9756 },
+ unicodeslot=0xFA1C,
+ },
+ [0xFA1D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7CBE },
+ unicodeslot=0xFA1D,
+ },
+ [0xFA1E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7FBD },
+ unicodeslot=0xFA1E,
+ },
+ [0xFA1F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA1F,
+ },
+ [0xFA20]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8612 },
+ unicodeslot=0xFA20,
+ },
+ [0xFA21]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA21,
+ },
+ [0xFA22]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AF8 },
+ unicodeslot=0xFA22,
+ },
+ [0xFA23]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA23,
+ },
+ [0xFA24]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA24,
+ },
+ [0xFA25]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9038 },
+ unicodeslot=0xFA25,
+ },
+ [0xFA26]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x90FD },
+ unicodeslot=0xFA26,
+ },
+ [0xFA27]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA27,
+ },
+ [0xFA28]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA28,
+ },
+ [0xFA29]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0xFA29,
+ },
+ [0xFA2A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x98EF },
+ unicodeslot=0xFA2A,
+ },
+ [0xFA2B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x98FC },
+ unicodeslot=0xFA2B,
+ },
+ [0xFA2C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9928 },
+ unicodeslot=0xFA2C,
+ },
+ [0xFA2D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9DB4 },
+ unicodeslot=0xFA2D,
+ },
+ [0xFA2E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x90DE },
+ unicodeslot=0xFA2E,
+ },
+ [0xFA2F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96B7 },
+ unicodeslot=0xFA2F,
+ },
+ [0xFA30]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4FAE },
+ unicodeslot=0xFA30,
+ },
+ [0xFA31]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x50E7 },
+ unicodeslot=0xFA31,
+ },
+ [0xFA32]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x514D },
+ unicodeslot=0xFA32,
+ },
+ [0xFA33]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52C9 },
+ unicodeslot=0xFA33,
+ },
+ [0xFA34]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52E4 },
+ unicodeslot=0xFA34,
+ },
+ [0xFA35]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5351 },
+ unicodeslot=0xFA35,
+ },
+ [0xFA36]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x559D },
+ unicodeslot=0xFA36,
+ },
+ [0xFA37]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5606 },
+ unicodeslot=0xFA37,
+ },
+ [0xFA38]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5668 },
+ unicodeslot=0xFA38,
+ },
+ [0xFA39]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5840 },
+ unicodeslot=0xFA39,
+ },
+ [0xFA3A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58A8 },
+ unicodeslot=0xFA3A,
+ },
+ [0xFA3B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C64 },
+ unicodeslot=0xFA3B,
+ },
+ [0xFA3C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C6E },
+ unicodeslot=0xFA3C,
+ },
+ [0xFA3D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6094 },
+ unicodeslot=0xFA3D,
+ },
+ [0xFA3E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6168 },
+ unicodeslot=0xFA3E,
+ },
+ [0xFA3F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x618E },
+ unicodeslot=0xFA3F,
+ },
+ [0xFA40]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61F2 },
+ unicodeslot=0xFA40,
+ },
+ [0xFA41]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x654F },
+ unicodeslot=0xFA41,
+ },
+ [0xFA42]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x65E2 },
+ unicodeslot=0xFA42,
+ },
+ [0xFA43]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6691 },
+ unicodeslot=0xFA43,
+ },
+ [0xFA44]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6885 },
+ unicodeslot=0xFA44,
+ },
+ [0xFA45]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D77 },
+ unicodeslot=0xFA45,
+ },
+ [0xFA46]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6E1A },
+ unicodeslot=0xFA46,
+ },
+ [0xFA47]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6F22 },
+ unicodeslot=0xFA47,
+ },
+ [0xFA48]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x716E },
+ unicodeslot=0xFA48,
+ },
+ [0xFA49]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x722B },
+ unicodeslot=0xFA49,
+ },
+ [0xFA4A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7422 },
+ unicodeslot=0xFA4A,
+ },
+ [0xFA4B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7891 },
+ unicodeslot=0xFA4B,
+ },
+ [0xFA4C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x793E },
+ unicodeslot=0xFA4C,
+ },
+ [0xFA4D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7949 },
+ unicodeslot=0xFA4D,
+ },
+ [0xFA4E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7948 },
+ unicodeslot=0xFA4E,
+ },
+ [0xFA4F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7950 },
+ unicodeslot=0xFA4F,
+ },
+ [0xFA50]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7956 },
+ unicodeslot=0xFA50,
+ },
+ [0xFA51]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x795D },
+ unicodeslot=0xFA51,
+ },
+ [0xFA52]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x798D },
+ unicodeslot=0xFA52,
+ },
+ [0xFA53]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x798E },
+ unicodeslot=0xFA53,
+ },
+ [0xFA54]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7A40 },
+ unicodeslot=0xFA54,
+ },
+ [0xFA55]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7A81 },
+ unicodeslot=0xFA55,
+ },
+ [0xFA56]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7BC0 },
+ unicodeslot=0xFA56,
+ },
+ [0xFA57]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7DF4 },
+ unicodeslot=0xFA57,
+ },
+ [0xFA58]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7E09 },
+ unicodeslot=0xFA58,
+ },
+ [0xFA59]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7E41 },
+ unicodeslot=0xFA59,
+ },
+ [0xFA5A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F72 },
+ unicodeslot=0xFA5A,
+ },
+ [0xFA5B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8005 },
+ unicodeslot=0xFA5B,
+ },
+ [0xFA5C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x81ED },
+ unicodeslot=0xFA5C,
+ },
+ [0xFA5D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8279 },
+ unicodeslot=0xFA5D,
+ },
+ [0xFA5E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8279 },
+ unicodeslot=0xFA5E,
+ },
+ [0xFA5F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8457 },
+ unicodeslot=0xFA5F,
+ },
+ [0xFA60]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8910 },
+ unicodeslot=0xFA60,
+ },
+ [0xFA61]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8996 },
+ unicodeslot=0xFA61,
+ },
+ [0xFA62]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B01 },
+ unicodeslot=0xFA62,
+ },
+ [0xFA63]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B39 },
+ unicodeslot=0xFA63,
+ },
+ [0xFA64]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8CD3 },
+ unicodeslot=0xFA64,
+ },
+ [0xFA65]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8D08 },
+ unicodeslot=0xFA65,
+ },
+ [0xFA66]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8FB6 },
+ unicodeslot=0xFA66,
+ },
+ [0xFA67]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9038 },
+ unicodeslot=0xFA67,
+ },
+ [0xFA68]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96E3 },
+ unicodeslot=0xFA68,
+ },
+ [0xFA69]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x97FF },
+ unicodeslot=0xFA69,
+ },
+ [0xFA6A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x983B },
+ unicodeslot=0xFA6A,
+ },
+ [0xFA6B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6075 },
+ unicodeslot=0xFA6B,
+ },
+ [0xFA6C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x242EE },
+ unicodeslot=0xFA6C,
+ },
+ [0xFA6D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8218 },
+ unicodeslot=0xFA6D,
+ },
+ [0xFA70]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E26 },
+ unicodeslot=0xFA70,
+ },
+ [0xFA71]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51B5 },
+ unicodeslot=0xFA71,
+ },
+ [0xFA72]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5168 },
+ unicodeslot=0xFA72,
+ },
+ [0xFA73]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4F80 },
+ unicodeslot=0xFA73,
+ },
+ [0xFA74]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5145 },
+ unicodeslot=0xFA74,
+ },
+ [0xFA75]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5180 },
+ unicodeslot=0xFA75,
+ },
+ [0xFA76]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52C7 },
+ unicodeslot=0xFA76,
+ },
+ [0xFA77]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52FA },
+ unicodeslot=0xFA77,
+ },
+ [0xFA78]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x559D },
+ unicodeslot=0xFA78,
+ },
+ [0xFA79]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5555 },
+ unicodeslot=0xFA79,
+ },
+ [0xFA7A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5599 },
+ unicodeslot=0xFA7A,
+ },
+ [0xFA7B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x55E2 },
+ unicodeslot=0xFA7B,
+ },
+ [0xFA7C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x585A },
+ unicodeslot=0xFA7C,
+ },
+ [0xFA7D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58B3 },
+ unicodeslot=0xFA7D,
+ },
+ [0xFA7E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5944 },
+ unicodeslot=0xFA7E,
+ },
+ [0xFA7F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5954 },
+ unicodeslot=0xFA7F,
+ },
+ [0xFA80]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5A62 },
+ unicodeslot=0xFA80,
+ },
+ [0xFA81]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5B28 },
+ unicodeslot=0xFA81,
+ },
+ [0xFA82]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5ED2 },
+ unicodeslot=0xFA82,
+ },
+ [0xFA83]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5ED9 },
+ unicodeslot=0xFA83,
+ },
+ [0xFA84]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F69 },
+ unicodeslot=0xFA84,
+ },
+ [0xFA85]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5FAD },
+ unicodeslot=0xFA85,
+ },
+ [0xFA86]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x60D8 },
+ unicodeslot=0xFA86,
+ },
+ [0xFA87]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x614E },
+ unicodeslot=0xFA87,
+ },
+ [0xFA88]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6108 },
+ unicodeslot=0xFA88,
+ },
+ [0xFA89]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x618E },
+ unicodeslot=0xFA89,
+ },
+ [0xFA8A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6160 },
+ unicodeslot=0xFA8A,
+ },
+ [0xFA8B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61F2 },
+ unicodeslot=0xFA8B,
+ },
+ [0xFA8C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6234 },
+ unicodeslot=0xFA8C,
+ },
+ [0xFA8D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x63C4 },
+ unicodeslot=0xFA8D,
+ },
+ [0xFA8E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x641C },
+ unicodeslot=0xFA8E,
+ },
+ [0xFA8F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6452 },
+ unicodeslot=0xFA8F,
+ },
+ [0xFA90]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6556 },
+ unicodeslot=0xFA90,
+ },
+ [0xFA91]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6674 },
+ unicodeslot=0xFA91,
+ },
+ [0xFA92]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6717 },
+ unicodeslot=0xFA92,
+ },
+ [0xFA93]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x671B },
+ unicodeslot=0xFA93,
+ },
+ [0xFA94]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6756 },
+ unicodeslot=0xFA94,
+ },
+ [0xFA95]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B79 },
+ unicodeslot=0xFA95,
+ },
+ [0xFA96]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6BBA },
+ unicodeslot=0xFA96,
+ },
+ [0xFA97]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D41 },
+ unicodeslot=0xFA97,
+ },
+ [0xFA98]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6EDB },
+ unicodeslot=0xFA98,
+ },
+ [0xFA99]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6ECB },
+ unicodeslot=0xFA99,
+ },
+ [0xFA9A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6F22 },
+ unicodeslot=0xFA9A,
+ },
+ [0xFA9B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x701E },
+ unicodeslot=0xFA9B,
+ },
+ [0xFA9C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x716E },
+ unicodeslot=0xFA9C,
+ },
+ [0xFA9D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x77A7 },
+ unicodeslot=0xFA9D,
+ },
+ [0xFA9E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7235 },
+ unicodeslot=0xFA9E,
+ },
+ [0xFA9F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x72AF },
+ unicodeslot=0xFA9F,
+ },
+ [0xFAA0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x732A },
+ unicodeslot=0xFAA0,
+ },
+ [0xFAA1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7471 },
+ unicodeslot=0xFAA1,
+ },
+ [0xFAA2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7506 },
+ unicodeslot=0xFAA2,
+ },
+ [0xFAA3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x753B },
+ unicodeslot=0xFAA3,
+ },
+ [0xFAA4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x761D },
+ unicodeslot=0xFAA4,
+ },
+ [0xFAA5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x761F },
+ unicodeslot=0xFAA5,
+ },
+ [0xFAA6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x76CA },
+ unicodeslot=0xFAA6,
+ },
+ [0xFAA7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x76DB },
+ unicodeslot=0xFAA7,
+ },
+ [0xFAA8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x76F4 },
+ unicodeslot=0xFAA8,
+ },
+ [0xFAA9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x774A },
+ unicodeslot=0xFAA9,
+ },
+ [0xFAAA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7740 },
+ unicodeslot=0xFAAA,
+ },
+ [0xFAAB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x78CC },
+ unicodeslot=0xFAAB,
+ },
+ [0xFAAC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7AB1 },
+ unicodeslot=0xFAAC,
+ },
+ [0xFAAD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7BC0 },
+ unicodeslot=0xFAAD,
+ },
+ [0xFAAE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7C7B },
+ unicodeslot=0xFAAE,
+ },
+ [0xFAAF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7D5B },
+ unicodeslot=0xFAAF,
+ },
+ [0xFAB0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7DF4 },
+ unicodeslot=0xFAB0,
+ },
+ [0xFAB1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F3E },
+ unicodeslot=0xFAB1,
+ },
+ [0xFAB2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8005 },
+ unicodeslot=0xFAB2,
+ },
+ [0xFAB3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8352 },
+ unicodeslot=0xFAB3,
+ },
+ [0xFAB4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83EF },
+ unicodeslot=0xFAB4,
+ },
+ [0xFAB5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8779 },
+ unicodeslot=0xFAB5,
+ },
+ [0xFAB6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8941 },
+ unicodeslot=0xFAB6,
+ },
+ [0xFAB7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8986 },
+ unicodeslot=0xFAB7,
+ },
+ [0xFAB8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8996 },
+ unicodeslot=0xFAB8,
+ },
+ [0xFAB9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8ABF },
+ unicodeslot=0xFAB9,
+ },
+ [0xFABA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AF8 },
+ unicodeslot=0xFABA,
+ },
+ [0xFABB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8ACB },
+ unicodeslot=0xFABB,
+ },
+ [0xFABC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B01 },
+ unicodeslot=0xFABC,
+ },
+ [0xFABD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AFE },
+ unicodeslot=0xFABD,
+ },
+ [0xFABE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AED },
+ unicodeslot=0xFABE,
+ },
+ [0xFABF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B39 },
+ unicodeslot=0xFABF,
+ },
+ [0xFAC0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B8A },
+ unicodeslot=0xFAC0,
+ },
+ [0xFAC1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8D08 },
+ unicodeslot=0xFAC1,
+ },
+ [0xFAC2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F38 },
+ unicodeslot=0xFAC2,
+ },
+ [0xFAC3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9072 },
+ unicodeslot=0xFAC3,
+ },
+ [0xFAC4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9199 },
+ unicodeslot=0xFAC4,
+ },
+ [0xFAC5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9276 },
+ unicodeslot=0xFAC5,
+ },
+ [0xFAC6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x967C },
+ unicodeslot=0xFAC6,
+ },
+ [0xFAC7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96E3 },
+ unicodeslot=0xFAC7,
+ },
+ [0xFAC8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9756 },
+ unicodeslot=0xFAC8,
+ },
+ [0xFAC9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x97DB },
+ unicodeslot=0xFAC9,
+ },
+ [0xFACA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x97FF },
+ unicodeslot=0xFACA,
+ },
+ [0xFACB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x980B },
+ unicodeslot=0xFACB,
+ },
+ [0xFACC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x983B },
+ unicodeslot=0xFACC,
+ },
+ [0xFACD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9B12 },
+ unicodeslot=0xFACD,
+ },
+ [0xFACE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F9C },
+ unicodeslot=0xFACE,
+ },
+ [0xFACF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2284A },
+ unicodeslot=0xFACF,
+ },
+ [0xFAD0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x22844 },
+ unicodeslot=0xFAD0,
+ },
+ [0xFAD1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x233D5 },
+ unicodeslot=0xFAD1,
+ },
+ [0xFAD2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3B9D },
+ unicodeslot=0xFAD2,
+ },
+ [0xFAD3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4018 },
+ unicodeslot=0xFAD3,
+ },
+ [0xFAD4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4039 },
+ unicodeslot=0xFAD4,
+ },
+ [0xFAD5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25249 },
+ unicodeslot=0xFAD5,
+ },
+ [0xFAD6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25CD0 },
+ unicodeslot=0xFAD6,
+ },
+ [0xFAD7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x27ED3 },
+ unicodeslot=0xFAD7,
+ },
+ [0xFAD8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F43 },
+ unicodeslot=0xFAD8,
+ },
+ [0xFAD9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F8E },
+ unicodeslot=0xFAD9,
+ },
+ [0xFB00]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x66, 0x66 },
+ unicodeslot=0xFB00,
+ },
+ [0xFB01]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x66, 0x69 },
+ unicodeslot=0xFB01,
+ },
+ [0xFB02]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x66, 0x6C },
+ unicodeslot=0xFB02,
+ },
+ [0xFB03]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x66, 0x66, 0x69 },
+ unicodeslot=0xFB03,
+ },
+ [0xFB04]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x66, 0x66, 0x6C },
+ unicodeslot=0xFB04,
+ },
+ [0xFB05]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x17F, 0x74 },
+ unicodeslot=0xFB05,
+ },
+ [0xFB06]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x73, 0x74 },
+ unicodeslot=0xFB06,
+ },
+ [0xFB13]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x574, 0x576 },
+ unicodeslot=0xFB13,
+ },
+ [0xFB14]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x574, 0x565 },
+ unicodeslot=0xFB14,
+ },
+ [0xFB15]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x574, 0x56B },
+ unicodeslot=0xFB15,
+ },
+ [0xFB16]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x57E, 0x576 },
+ unicodeslot=0xFB16,
+ },
+ [0xFB17]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "compat", 0x574, 0x56D },
+ unicodeslot=0xFB17,
+ },
+ [0xFB1D]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D9, 0x5B4 },
+ unicodeslot=0xFB1D,
+ },
+ [0xFB1E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFB1E,
+ },
+ [0xFB1F]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5F2, 0x5B7 },
+ unicodeslot=0xFB1F,
+ },
+ [0xFB20]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5E2 },
+ unicodeslot=0xFB20,
+ },
+ [0xFB21]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5D0 },
+ unicodeslot=0xFB21,
+ },
+ [0xFB22]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5D3 },
+ unicodeslot=0xFB22,
+ },
+ [0xFB23]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5D4 },
+ unicodeslot=0xFB23,
+ },
+ [0xFB24]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5DB },
+ unicodeslot=0xFB24,
+ },
+ [0xFB25]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5DC },
+ unicodeslot=0xFB25,
+ },
+ [0xFB26]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5DD },
+ unicodeslot=0xFB26,
+ },
+ [0xFB27]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5E8 },
+ unicodeslot=0xFB27,
+ },
+ [0xFB28]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "font", 0x5EA },
+ unicodeslot=0xFB28,
+ },
+ [0xFB29]={
+ category="sm",
+ direction="es",
+ linebreak="al",
+ specials={ "font", 0x2B },
+ unicodeslot=0xFB29,
+ },
+ [0xFB2A]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E9, 0x5C1 },
+ unicodeslot=0xFB2A,
+ },
+ [0xFB2B]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E9, 0x5C2 },
+ unicodeslot=0xFB2B,
+ },
+ [0xFB2C]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0xFB49, 0x5C1 },
+ unicodeslot=0xFB2C,
+ },
+ [0xFB2D]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0xFB49, 0x5C2 },
+ unicodeslot=0xFB2D,
+ },
+ [0xFB2E]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D0, 0x5B7 },
+ unicodeslot=0xFB2E,
+ },
+ [0xFB2F]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D0, 0x5B8 },
+ unicodeslot=0xFB2F,
+ },
+ [0xFB30]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D0, 0x5BC },
+ unicodeslot=0xFB30,
+ },
+ [0xFB31]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D1, 0x5BC },
+ unicodeslot=0xFB31,
+ },
+ [0xFB32]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D2, 0x5BC },
+ unicodeslot=0xFB32,
+ },
+ [0xFB33]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D3, 0x5BC },
+ unicodeslot=0xFB33,
+ },
+ [0xFB34]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D4, 0x5BC },
+ unicodeslot=0xFB34,
+ },
+ [0xFB35]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D5, 0x5BC },
+ unicodeslot=0xFB35,
+ },
+ [0xFB36]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D6, 0x5BC },
+ unicodeslot=0xFB36,
+ },
+ [0xFB38]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D8, 0x5BC },
+ unicodeslot=0xFB38,
+ },
+ [0xFB39]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D9, 0x5BC },
+ unicodeslot=0xFB39,
+ },
+ [0xFB3A]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5DA, 0x5BC },
+ unicodeslot=0xFB3A,
+ },
+ [0xFB3B]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5DB, 0x5BC },
+ unicodeslot=0xFB3B,
+ },
+ [0xFB3C]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5DC, 0x5BC },
+ unicodeslot=0xFB3C,
+ },
+ [0xFB3E]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5DE, 0x5BC },
+ unicodeslot=0xFB3E,
+ },
+ [0xFB40]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E0, 0x5BC },
+ unicodeslot=0xFB40,
+ },
+ [0xFB41]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E1, 0x5BC },
+ unicodeslot=0xFB41,
+ },
+ [0xFB43]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E3, 0x5BC },
+ unicodeslot=0xFB43,
+ },
+ [0xFB44]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E4, 0x5BC },
+ unicodeslot=0xFB44,
+ },
+ [0xFB46]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E6, 0x5BC },
+ unicodeslot=0xFB46,
+ },
+ [0xFB47]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E7, 0x5BC },
+ unicodeslot=0xFB47,
+ },
+ [0xFB48]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E8, 0x5BC },
+ unicodeslot=0xFB48,
+ },
+ [0xFB49]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E9, 0x5BC },
+ unicodeslot=0xFB49,
+ },
+ [0xFB4A]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5EA, 0x5BC },
+ unicodeslot=0xFB4A,
+ },
+ [0xFB4B]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D5, 0x5B9 },
+ unicodeslot=0xFB4B,
+ },
+ [0xFB4C]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5D1, 0x5BF },
+ unicodeslot=0xFB4C,
+ },
+ [0xFB4D]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5DB, 0x5BF },
+ unicodeslot=0xFB4D,
+ },
+ [0xFB4E]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "char", 0x5E4, 0x5BF },
+ unicodeslot=0xFB4E,
+ },
+ [0xFB4F]={
+ category="lo",
+ direction="r",
+ linebreak="hl",
+ specials={ "compat", 0x5D0, 0x5DC },
+ unicodeslot=0xFB4F,
+ },
+ [0xFB50]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x671 },
+ unicodeslot=0xFB50,
+ },
+ [0xFB51]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x671 },
+ unicodeslot=0xFB51,
+ },
+ [0xFB52]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x67B },
+ unicodeslot=0xFB52,
+ },
+ [0xFB53]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x67B },
+ unicodeslot=0xFB53,
+ },
+ [0xFB54]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x67B },
+ unicodeslot=0xFB54,
+ },
+ [0xFB55]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x67B },
+ unicodeslot=0xFB55,
+ },
+ [0xFB56]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x67E },
+ unicodeslot=0xFB56,
+ },
+ [0xFB57]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x67E },
+ unicodeslot=0xFB57,
+ },
+ [0xFB58]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x67E },
+ unicodeslot=0xFB58,
+ },
+ [0xFB59]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x67E },
+ unicodeslot=0xFB59,
+ },
+ [0xFB5A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x680 },
+ unicodeslot=0xFB5A,
+ },
+ [0xFB5B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x680 },
+ unicodeslot=0xFB5B,
+ },
+ [0xFB5C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x680 },
+ unicodeslot=0xFB5C,
+ },
+ [0xFB5D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x680 },
+ unicodeslot=0xFB5D,
+ },
+ [0xFB5E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x67A },
+ unicodeslot=0xFB5E,
+ },
+ [0xFB5F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x67A },
+ unicodeslot=0xFB5F,
+ },
+ [0xFB60]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x67A },
+ unicodeslot=0xFB60,
+ },
+ [0xFB61]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x67A },
+ unicodeslot=0xFB61,
+ },
+ [0xFB62]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x67F },
+ unicodeslot=0xFB62,
+ },
+ [0xFB63]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x67F },
+ unicodeslot=0xFB63,
+ },
+ [0xFB64]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x67F },
+ unicodeslot=0xFB64,
+ },
+ [0xFB65]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x67F },
+ unicodeslot=0xFB65,
+ },
+ [0xFB66]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x679 },
+ unicodeslot=0xFB66,
+ },
+ [0xFB67]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x679 },
+ unicodeslot=0xFB67,
+ },
+ [0xFB68]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x679 },
+ unicodeslot=0xFB68,
+ },
+ [0xFB69]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x679 },
+ unicodeslot=0xFB69,
+ },
+ [0xFB6A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6A4 },
+ unicodeslot=0xFB6A,
+ },
+ [0xFB6B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6A4 },
+ unicodeslot=0xFB6B,
+ },
+ [0xFB6C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6A4 },
+ unicodeslot=0xFB6C,
+ },
+ [0xFB6D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6A4 },
+ unicodeslot=0xFB6D,
+ },
+ [0xFB6E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6A6 },
+ unicodeslot=0xFB6E,
+ },
+ [0xFB6F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6A6 },
+ unicodeslot=0xFB6F,
+ },
+ [0xFB70]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6A6 },
+ unicodeslot=0xFB70,
+ },
+ [0xFB71]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6A6 },
+ unicodeslot=0xFB71,
+ },
+ [0xFB72]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x684 },
+ unicodeslot=0xFB72,
+ },
+ [0xFB73]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x684 },
+ unicodeslot=0xFB73,
+ },
+ [0xFB74]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x684 },
+ unicodeslot=0xFB74,
+ },
+ [0xFB75]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x684 },
+ unicodeslot=0xFB75,
+ },
+ [0xFB76]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x683 },
+ unicodeslot=0xFB76,
+ },
+ [0xFB77]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x683 },
+ unicodeslot=0xFB77,
+ },
+ [0xFB78]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x683 },
+ unicodeslot=0xFB78,
+ },
+ [0xFB79]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x683 },
+ unicodeslot=0xFB79,
+ },
+ [0xFB7A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x686 },
+ unicodeslot=0xFB7A,
+ },
+ [0xFB7B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x686 },
+ unicodeslot=0xFB7B,
+ },
+ [0xFB7C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x686 },
+ unicodeslot=0xFB7C,
+ },
+ [0xFB7D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x686 },
+ unicodeslot=0xFB7D,
+ },
+ [0xFB7E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x687 },
+ unicodeslot=0xFB7E,
+ },
+ [0xFB7F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x687 },
+ unicodeslot=0xFB7F,
+ },
+ [0xFB80]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x687 },
+ unicodeslot=0xFB80,
+ },
+ [0xFB81]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x687 },
+ unicodeslot=0xFB81,
+ },
+ [0xFB82]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x68D },
+ unicodeslot=0xFB82,
+ },
+ [0xFB83]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x68D },
+ unicodeslot=0xFB83,
+ },
+ [0xFB84]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x68C },
+ unicodeslot=0xFB84,
+ },
+ [0xFB85]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x68C },
+ unicodeslot=0xFB85,
+ },
+ [0xFB86]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x68E },
+ unicodeslot=0xFB86,
+ },
+ [0xFB87]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x68E },
+ unicodeslot=0xFB87,
+ },
+ [0xFB88]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x688 },
+ unicodeslot=0xFB88,
+ },
+ [0xFB89]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x688 },
+ unicodeslot=0xFB89,
+ },
+ [0xFB8A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x698 },
+ unicodeslot=0xFB8A,
+ },
+ [0xFB8B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x698 },
+ unicodeslot=0xFB8B,
+ },
+ [0xFB8C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x691 },
+ unicodeslot=0xFB8C,
+ },
+ [0xFB8D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x691 },
+ unicodeslot=0xFB8D,
+ },
+ [0xFB8E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6A9 },
+ unicodeslot=0xFB8E,
+ },
+ [0xFB8F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6A9 },
+ unicodeslot=0xFB8F,
+ },
+ [0xFB90]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6A9 },
+ unicodeslot=0xFB90,
+ },
+ [0xFB91]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6A9 },
+ unicodeslot=0xFB91,
+ },
+ [0xFB92]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6AF },
+ unicodeslot=0xFB92,
+ },
+ [0xFB93]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6AF },
+ unicodeslot=0xFB93,
+ },
+ [0xFB94]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6AF },
+ unicodeslot=0xFB94,
+ },
+ [0xFB95]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6AF },
+ unicodeslot=0xFB95,
+ },
+ [0xFB96]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6B3 },
+ unicodeslot=0xFB96,
+ },
+ [0xFB97]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6B3 },
+ unicodeslot=0xFB97,
+ },
+ [0xFB98]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6B3 },
+ unicodeslot=0xFB98,
+ },
+ [0xFB99]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6B3 },
+ unicodeslot=0xFB99,
+ },
+ [0xFB9A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6B1 },
+ unicodeslot=0xFB9A,
+ },
+ [0xFB9B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6B1 },
+ unicodeslot=0xFB9B,
+ },
+ [0xFB9C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6B1 },
+ unicodeslot=0xFB9C,
+ },
+ [0xFB9D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6B1 },
+ unicodeslot=0xFB9D,
+ },
+ [0xFB9E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6BA },
+ unicodeslot=0xFB9E,
+ },
+ [0xFB9F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6BA },
+ unicodeslot=0xFB9F,
+ },
+ [0xFBA0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6BB },
+ unicodeslot=0xFBA0,
+ },
+ [0xFBA1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6BB },
+ unicodeslot=0xFBA1,
+ },
+ [0xFBA2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6BB },
+ unicodeslot=0xFBA2,
+ },
+ [0xFBA3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6BB },
+ unicodeslot=0xFBA3,
+ },
+ [0xFBA4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C0 },
+ unicodeslot=0xFBA4,
+ },
+ [0xFBA5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C0 },
+ unicodeslot=0xFBA5,
+ },
+ [0xFBA6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C1 },
+ unicodeslot=0xFBA6,
+ },
+ [0xFBA7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C1 },
+ unicodeslot=0xFBA7,
+ },
+ [0xFBA8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6C1 },
+ unicodeslot=0xFBA8,
+ },
+ [0xFBA9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6C1 },
+ unicodeslot=0xFBA9,
+ },
+ [0xFBAA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6BE },
+ unicodeslot=0xFBAA,
+ },
+ [0xFBAB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6BE },
+ unicodeslot=0xFBAB,
+ },
+ [0xFBAC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6BE },
+ unicodeslot=0xFBAC,
+ },
+ [0xFBAD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6BE },
+ unicodeslot=0xFBAD,
+ },
+ [0xFBAE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6D2 },
+ unicodeslot=0xFBAE,
+ },
+ [0xFBAF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6D2 },
+ unicodeslot=0xFBAF,
+ },
+ [0xFBB0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6D3 },
+ unicodeslot=0xFBB0,
+ },
+ [0xFBB1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6D3 },
+ unicodeslot=0xFBB1,
+ },
+ [0xFBB2]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB2,
+ },
+ [0xFBB3]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB3,
+ },
+ [0xFBB4]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB4,
+ },
+ [0xFBB5]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB5,
+ },
+ [0xFBB6]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB6,
+ },
+ [0xFBB7]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB7,
+ },
+ [0xFBB8]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB8,
+ },
+ [0xFBB9]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBB9,
+ },
+ [0xFBBA]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBBA,
+ },
+ [0xFBBB]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBBB,
+ },
+ [0xFBBC]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBBC,
+ },
+ [0xFBBD]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBBD,
+ },
+ [0xFBBE]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBBE,
+ },
+ [0xFBBF]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBBF,
+ },
+ [0xFBC0]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBC0,
+ },
+ [0xFBC1]={
+ category="sk",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFBC1,
+ },
+ [0xFBD3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6AD },
+ unicodeslot=0xFBD3,
+ },
+ [0xFBD4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6AD },
+ unicodeslot=0xFBD4,
+ },
+ [0xFBD5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6AD },
+ unicodeslot=0xFBD5,
+ },
+ [0xFBD6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6AD },
+ unicodeslot=0xFBD6,
+ },
+ [0xFBD7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C7 },
+ unicodeslot=0xFBD7,
+ },
+ [0xFBD8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C7 },
+ unicodeslot=0xFBD8,
+ },
+ [0xFBD9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C6 },
+ unicodeslot=0xFBD9,
+ },
+ [0xFBDA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C6 },
+ unicodeslot=0xFBDA,
+ },
+ [0xFBDB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C8 },
+ unicodeslot=0xFBDB,
+ },
+ [0xFBDC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C8 },
+ unicodeslot=0xFBDC,
+ },
+ [0xFBDD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x677 },
+ unicodeslot=0xFBDD,
+ },
+ [0xFBDE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6CB },
+ unicodeslot=0xFBDE,
+ },
+ [0xFBDF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6CB },
+ unicodeslot=0xFBDF,
+ },
+ [0xFBE0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C5 },
+ unicodeslot=0xFBE0,
+ },
+ [0xFBE1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C5 },
+ unicodeslot=0xFBE1,
+ },
+ [0xFBE2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6C9 },
+ unicodeslot=0xFBE2,
+ },
+ [0xFBE3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6C9 },
+ unicodeslot=0xFBE3,
+ },
+ [0xFBE4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6D0 },
+ unicodeslot=0xFBE4,
+ },
+ [0xFBE5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6D0 },
+ unicodeslot=0xFBE5,
+ },
+ [0xFBE6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6D0 },
+ unicodeslot=0xFBE6,
+ },
+ [0xFBE7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6D0 },
+ unicodeslot=0xFBE7,
+ },
+ [0xFBE8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x649 },
+ unicodeslot=0xFBE8,
+ },
+ [0xFBE9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x649 },
+ unicodeslot=0xFBE9,
+ },
+ [0xFBEA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x627 },
+ unicodeslot=0xFBEA,
+ },
+ [0xFBEB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x627 },
+ unicodeslot=0xFBEB,
+ },
+ [0xFBEC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x6D5 },
+ unicodeslot=0xFBEC,
+ },
+ [0xFBED]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x6D5 },
+ unicodeslot=0xFBED,
+ },
+ [0xFBEE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x648 },
+ unicodeslot=0xFBEE,
+ },
+ [0xFBEF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x648 },
+ unicodeslot=0xFBEF,
+ },
+ [0xFBF0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x6C7 },
+ unicodeslot=0xFBF0,
+ },
+ [0xFBF1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x6C7 },
+ unicodeslot=0xFBF1,
+ },
+ [0xFBF2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x6C6 },
+ unicodeslot=0xFBF2,
+ },
+ [0xFBF3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x6C6 },
+ unicodeslot=0xFBF3,
+ },
+ [0xFBF4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x6C8 },
+ unicodeslot=0xFBF4,
+ },
+ [0xFBF5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x6C8 },
+ unicodeslot=0xFBF5,
+ },
+ [0xFBF6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x6D0 },
+ unicodeslot=0xFBF6,
+ },
+ [0xFBF7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x6D0 },
+ unicodeslot=0xFBF7,
+ },
+ [0xFBF8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x6D0 },
+ unicodeslot=0xFBF8,
+ },
+ [0xFBF9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x649 },
+ unicodeslot=0xFBF9,
+ },
+ [0xFBFA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x649 },
+ unicodeslot=0xFBFA,
+ },
+ [0xFBFB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x649 },
+ unicodeslot=0xFBFB,
+ },
+ [0xFBFC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x6CC },
+ unicodeslot=0xFBFC,
+ },
+ [0xFBFD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x6CC },
+ unicodeslot=0xFBFD,
+ },
+ [0xFBFE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x6CC },
+ unicodeslot=0xFBFE,
+ },
+ [0xFBFF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x6CC },
+ unicodeslot=0xFBFF,
+ },
+ [0xFC00]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x62C },
+ unicodeslot=0xFC00,
+ },
+ [0xFC01]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x62D },
+ unicodeslot=0xFC01,
+ },
+ [0xFC02]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x645 },
+ unicodeslot=0xFC02,
+ },
+ [0xFC03]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x649 },
+ unicodeslot=0xFC03,
+ },
+ [0xFC04]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626, 0x64A },
+ unicodeslot=0xFC04,
+ },
+ [0xFC05]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628, 0x62C },
+ unicodeslot=0xFC05,
+ },
+ [0xFC06]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628, 0x62D },
+ unicodeslot=0xFC06,
+ },
+ [0xFC07]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628, 0x62E },
+ unicodeslot=0xFC07,
+ },
+ [0xFC08]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628, 0x645 },
+ unicodeslot=0xFC08,
+ },
+ [0xFC09]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628, 0x649 },
+ unicodeslot=0xFC09,
+ },
+ [0xFC0A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628, 0x64A },
+ unicodeslot=0xFC0A,
+ },
+ [0xFC0B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A, 0x62C },
+ unicodeslot=0xFC0B,
+ },
+ [0xFC0C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A, 0x62D },
+ unicodeslot=0xFC0C,
+ },
+ [0xFC0D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A, 0x62E },
+ unicodeslot=0xFC0D,
+ },
+ [0xFC0E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A, 0x645 },
+ unicodeslot=0xFC0E,
+ },
+ [0xFC0F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A, 0x649 },
+ unicodeslot=0xFC0F,
+ },
+ [0xFC10]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A, 0x64A },
+ unicodeslot=0xFC10,
+ },
+ [0xFC11]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62B, 0x62C },
+ unicodeslot=0xFC11,
+ },
+ [0xFC12]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62B, 0x645 },
+ unicodeslot=0xFC12,
+ },
+ [0xFC13]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62B, 0x649 },
+ unicodeslot=0xFC13,
+ },
+ [0xFC14]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62B, 0x64A },
+ unicodeslot=0xFC14,
+ },
+ [0xFC15]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62C, 0x62D },
+ unicodeslot=0xFC15,
+ },
+ [0xFC16]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62C, 0x645 },
+ unicodeslot=0xFC16,
+ },
+ [0xFC17]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62D, 0x62C },
+ unicodeslot=0xFC17,
+ },
+ [0xFC18]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62D, 0x645 },
+ unicodeslot=0xFC18,
+ },
+ [0xFC19]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62E, 0x62C },
+ unicodeslot=0xFC19,
+ },
+ [0xFC1A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62E, 0x62D },
+ unicodeslot=0xFC1A,
+ },
+ [0xFC1B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62E, 0x645 },
+ unicodeslot=0xFC1B,
+ },
+ [0xFC1C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x62C },
+ unicodeslot=0xFC1C,
+ },
+ [0xFC1D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x62D },
+ unicodeslot=0xFC1D,
+ },
+ [0xFC1E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x62E },
+ unicodeslot=0xFC1E,
+ },
+ [0xFC1F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x645 },
+ unicodeslot=0xFC1F,
+ },
+ [0xFC20]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x62D },
+ unicodeslot=0xFC20,
+ },
+ [0xFC21]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x645 },
+ unicodeslot=0xFC21,
+ },
+ [0xFC22]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x62C },
+ unicodeslot=0xFC22,
+ },
+ [0xFC23]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x62D },
+ unicodeslot=0xFC23,
+ },
+ [0xFC24]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x62E },
+ unicodeslot=0xFC24,
+ },
+ [0xFC25]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x645 },
+ unicodeslot=0xFC25,
+ },
+ [0xFC26]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x637, 0x62D },
+ unicodeslot=0xFC26,
+ },
+ [0xFC27]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x637, 0x645 },
+ unicodeslot=0xFC27,
+ },
+ [0xFC28]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x638, 0x645 },
+ unicodeslot=0xFC28,
+ },
+ [0xFC29]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x639, 0x62C },
+ unicodeslot=0xFC29,
+ },
+ [0xFC2A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x639, 0x645 },
+ unicodeslot=0xFC2A,
+ },
+ [0xFC2B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x63A, 0x62C },
+ unicodeslot=0xFC2B,
+ },
+ [0xFC2C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x63A, 0x645 },
+ unicodeslot=0xFC2C,
+ },
+ [0xFC2D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641, 0x62C },
+ unicodeslot=0xFC2D,
+ },
+ [0xFC2E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641, 0x62D },
+ unicodeslot=0xFC2E,
+ },
+ [0xFC2F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641, 0x62E },
+ unicodeslot=0xFC2F,
+ },
+ [0xFC30]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641, 0x645 },
+ unicodeslot=0xFC30,
+ },
+ [0xFC31]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641, 0x649 },
+ unicodeslot=0xFC31,
+ },
+ [0xFC32]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641, 0x64A },
+ unicodeslot=0xFC32,
+ },
+ [0xFC33]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x642, 0x62D },
+ unicodeslot=0xFC33,
+ },
+ [0xFC34]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x642, 0x645 },
+ unicodeslot=0xFC34,
+ },
+ [0xFC35]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x642, 0x649 },
+ unicodeslot=0xFC35,
+ },
+ [0xFC36]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x642, 0x64A },
+ unicodeslot=0xFC36,
+ },
+ [0xFC37]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x627 },
+ unicodeslot=0xFC37,
+ },
+ [0xFC38]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x62C },
+ unicodeslot=0xFC38,
+ },
+ [0xFC39]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x62D },
+ unicodeslot=0xFC39,
+ },
+ [0xFC3A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x62E },
+ unicodeslot=0xFC3A,
+ },
+ [0xFC3B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x644 },
+ unicodeslot=0xFC3B,
+ },
+ [0xFC3C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x645 },
+ unicodeslot=0xFC3C,
+ },
+ [0xFC3D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x649 },
+ unicodeslot=0xFC3D,
+ },
+ [0xFC3E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643, 0x64A },
+ unicodeslot=0xFC3E,
+ },
+ [0xFC3F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x62C },
+ unicodeslot=0xFC3F,
+ },
+ [0xFC40]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x62D },
+ unicodeslot=0xFC40,
+ },
+ [0xFC41]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x62E },
+ unicodeslot=0xFC41,
+ },
+ [0xFC42]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x645 },
+ unicodeslot=0xFC42,
+ },
+ [0xFC43]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x649 },
+ unicodeslot=0xFC43,
+ },
+ [0xFC44]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x64A },
+ unicodeslot=0xFC44,
+ },
+ [0xFC45]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x62C },
+ unicodeslot=0xFC45,
+ },
+ [0xFC46]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x62D },
+ unicodeslot=0xFC46,
+ },
+ [0xFC47]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x62E },
+ unicodeslot=0xFC47,
+ },
+ [0xFC48]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x645 },
+ unicodeslot=0xFC48,
+ },
+ [0xFC49]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x649 },
+ unicodeslot=0xFC49,
+ },
+ [0xFC4A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x64A },
+ unicodeslot=0xFC4A,
+ },
+ [0xFC4B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646, 0x62C },
+ unicodeslot=0xFC4B,
+ },
+ [0xFC4C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646, 0x62D },
+ unicodeslot=0xFC4C,
+ },
+ [0xFC4D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646, 0x62E },
+ unicodeslot=0xFC4D,
+ },
+ [0xFC4E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646, 0x645 },
+ unicodeslot=0xFC4E,
+ },
+ [0xFC4F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646, 0x649 },
+ unicodeslot=0xFC4F,
+ },
+ [0xFC50]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646, 0x64A },
+ unicodeslot=0xFC50,
+ },
+ [0xFC51]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x647, 0x62C },
+ unicodeslot=0xFC51,
+ },
+ [0xFC52]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x647, 0x645 },
+ unicodeslot=0xFC52,
+ },
+ [0xFC53]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x647, 0x649 },
+ unicodeslot=0xFC53,
+ },
+ [0xFC54]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x647, 0x64A },
+ unicodeslot=0xFC54,
+ },
+ [0xFC55]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A, 0x62C },
+ unicodeslot=0xFC55,
+ },
+ [0xFC56]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A, 0x62D },
+ unicodeslot=0xFC56,
+ },
+ [0xFC57]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A, 0x62E },
+ unicodeslot=0xFC57,
+ },
+ [0xFC58]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A, 0x645 },
+ unicodeslot=0xFC58,
+ },
+ [0xFC59]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A, 0x649 },
+ unicodeslot=0xFC59,
+ },
+ [0xFC5A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A, 0x64A },
+ unicodeslot=0xFC5A,
+ },
+ [0xFC5B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x630, 0x670 },
+ unicodeslot=0xFC5B,
+ },
+ [0xFC5C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x631, 0x670 },
+ unicodeslot=0xFC5C,
+ },
+ [0xFC5D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x649, 0x670 },
+ unicodeslot=0xFC5D,
+ },
+ [0xFC5E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64C, 0x651 },
+ unicodeslot=0xFC5E,
+ },
+ [0xFC5F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64D, 0x651 },
+ unicodeslot=0xFC5F,
+ },
+ [0xFC60]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64E, 0x651 },
+ unicodeslot=0xFC60,
+ },
+ [0xFC61]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64F, 0x651 },
+ unicodeslot=0xFC61,
+ },
+ [0xFC62]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x650, 0x651 },
+ unicodeslot=0xFC62,
+ },
+ [0xFC63]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x651, 0x670 },
+ unicodeslot=0xFC63,
+ },
+ [0xFC64]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x631 },
+ unicodeslot=0xFC64,
+ },
+ [0xFC65]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x632 },
+ unicodeslot=0xFC65,
+ },
+ [0xFC66]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x645 },
+ unicodeslot=0xFC66,
+ },
+ [0xFC67]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x646 },
+ unicodeslot=0xFC67,
+ },
+ [0xFC68]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x649 },
+ unicodeslot=0xFC68,
+ },
+ [0xFC69]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626, 0x64A },
+ unicodeslot=0xFC69,
+ },
+ [0xFC6A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x631 },
+ unicodeslot=0xFC6A,
+ },
+ [0xFC6B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x632 },
+ unicodeslot=0xFC6B,
+ },
+ [0xFC6C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x645 },
+ unicodeslot=0xFC6C,
+ },
+ [0xFC6D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x646 },
+ unicodeslot=0xFC6D,
+ },
+ [0xFC6E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x649 },
+ unicodeslot=0xFC6E,
+ },
+ [0xFC6F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x64A },
+ unicodeslot=0xFC6F,
+ },
+ [0xFC70]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x631 },
+ unicodeslot=0xFC70,
+ },
+ [0xFC71]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x632 },
+ unicodeslot=0xFC71,
+ },
+ [0xFC72]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x645 },
+ unicodeslot=0xFC72,
+ },
+ [0xFC73]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x646 },
+ unicodeslot=0xFC73,
+ },
+ [0xFC74]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x649 },
+ unicodeslot=0xFC74,
+ },
+ [0xFC75]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x64A },
+ unicodeslot=0xFC75,
+ },
+ [0xFC76]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B, 0x631 },
+ unicodeslot=0xFC76,
+ },
+ [0xFC77]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B, 0x632 },
+ unicodeslot=0xFC77,
+ },
+ [0xFC78]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B, 0x645 },
+ unicodeslot=0xFC78,
+ },
+ [0xFC79]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B, 0x646 },
+ unicodeslot=0xFC79,
+ },
+ [0xFC7A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B, 0x649 },
+ unicodeslot=0xFC7A,
+ },
+ [0xFC7B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B, 0x64A },
+ unicodeslot=0xFC7B,
+ },
+ [0xFC7C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x641, 0x649 },
+ unicodeslot=0xFC7C,
+ },
+ [0xFC7D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x641, 0x64A },
+ unicodeslot=0xFC7D,
+ },
+ [0xFC7E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x642, 0x649 },
+ unicodeslot=0xFC7E,
+ },
+ [0xFC7F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x642, 0x64A },
+ unicodeslot=0xFC7F,
+ },
+ [0xFC80]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x627 },
+ unicodeslot=0xFC80,
+ },
+ [0xFC81]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x644 },
+ unicodeslot=0xFC81,
+ },
+ [0xFC82]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x645 },
+ unicodeslot=0xFC82,
+ },
+ [0xFC83]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x649 },
+ unicodeslot=0xFC83,
+ },
+ [0xFC84]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x64A },
+ unicodeslot=0xFC84,
+ },
+ [0xFC85]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x645 },
+ unicodeslot=0xFC85,
+ },
+ [0xFC86]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x649 },
+ unicodeslot=0xFC86,
+ },
+ [0xFC87]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x64A },
+ unicodeslot=0xFC87,
+ },
+ [0xFC88]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645, 0x627 },
+ unicodeslot=0xFC88,
+ },
+ [0xFC89]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645, 0x645 },
+ unicodeslot=0xFC89,
+ },
+ [0xFC8A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x631 },
+ unicodeslot=0xFC8A,
+ },
+ [0xFC8B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x632 },
+ unicodeslot=0xFC8B,
+ },
+ [0xFC8C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x645 },
+ unicodeslot=0xFC8C,
+ },
+ [0xFC8D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x646 },
+ unicodeslot=0xFC8D,
+ },
+ [0xFC8E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x649 },
+ unicodeslot=0xFC8E,
+ },
+ [0xFC8F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x64A },
+ unicodeslot=0xFC8F,
+ },
+ [0xFC90]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x649, 0x670 },
+ unicodeslot=0xFC90,
+ },
+ [0xFC91]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x631 },
+ unicodeslot=0xFC91,
+ },
+ [0xFC92]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x632 },
+ unicodeslot=0xFC92,
+ },
+ [0xFC93]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x645 },
+ unicodeslot=0xFC93,
+ },
+ [0xFC94]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x646 },
+ unicodeslot=0xFC94,
+ },
+ [0xFC95]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x649 },
+ unicodeslot=0xFC95,
+ },
+ [0xFC96]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x64A },
+ unicodeslot=0xFC96,
+ },
+ [0xFC97]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x62C },
+ unicodeslot=0xFC97,
+ },
+ [0xFC98]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x62D },
+ unicodeslot=0xFC98,
+ },
+ [0xFC99]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x62E },
+ unicodeslot=0xFC99,
+ },
+ [0xFC9A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x645 },
+ unicodeslot=0xFC9A,
+ },
+ [0xFC9B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626, 0x647 },
+ unicodeslot=0xFC9B,
+ },
+ [0xFC9C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x628, 0x62C },
+ unicodeslot=0xFC9C,
+ },
+ [0xFC9D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x628, 0x62D },
+ unicodeslot=0xFC9D,
+ },
+ [0xFC9E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x628, 0x62E },
+ unicodeslot=0xFC9E,
+ },
+ [0xFC9F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x628, 0x645 },
+ unicodeslot=0xFC9F,
+ },
+ [0xFCA0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x628, 0x647 },
+ unicodeslot=0xFCA0,
+ },
+ [0xFCA1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62C },
+ unicodeslot=0xFCA1,
+ },
+ [0xFCA2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62D },
+ unicodeslot=0xFCA2,
+ },
+ [0xFCA3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62E },
+ unicodeslot=0xFCA3,
+ },
+ [0xFCA4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x645 },
+ unicodeslot=0xFCA4,
+ },
+ [0xFCA5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x647 },
+ unicodeslot=0xFCA5,
+ },
+ [0xFCA6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62B, 0x645 },
+ unicodeslot=0xFCA6,
+ },
+ [0xFCA7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62C, 0x62D },
+ unicodeslot=0xFCA7,
+ },
+ [0xFCA8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62C, 0x645 },
+ unicodeslot=0xFCA8,
+ },
+ [0xFCA9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62D, 0x62C },
+ unicodeslot=0xFCA9,
+ },
+ [0xFCAA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62D, 0x645 },
+ unicodeslot=0xFCAA,
+ },
+ [0xFCAB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62E, 0x62C },
+ unicodeslot=0xFCAB,
+ },
+ [0xFCAC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62E, 0x645 },
+ unicodeslot=0xFCAC,
+ },
+ [0xFCAD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x62C },
+ unicodeslot=0xFCAD,
+ },
+ [0xFCAE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x62D },
+ unicodeslot=0xFCAE,
+ },
+ [0xFCAF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x62E },
+ unicodeslot=0xFCAF,
+ },
+ [0xFCB0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x645 },
+ unicodeslot=0xFCB0,
+ },
+ [0xFCB1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x635, 0x62D },
+ unicodeslot=0xFCB1,
+ },
+ [0xFCB2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x635, 0x62E },
+ unicodeslot=0xFCB2,
+ },
+ [0xFCB3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x635, 0x645 },
+ unicodeslot=0xFCB3,
+ },
+ [0xFCB4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x636, 0x62C },
+ unicodeslot=0xFCB4,
+ },
+ [0xFCB5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x636, 0x62D },
+ unicodeslot=0xFCB5,
+ },
+ [0xFCB6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x636, 0x62E },
+ unicodeslot=0xFCB6,
+ },
+ [0xFCB7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x636, 0x645 },
+ unicodeslot=0xFCB7,
+ },
+ [0xFCB8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x637, 0x62D },
+ unicodeslot=0xFCB8,
+ },
+ [0xFCB9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x638, 0x645 },
+ unicodeslot=0xFCB9,
+ },
+ [0xFCBA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x639, 0x62C },
+ unicodeslot=0xFCBA,
+ },
+ [0xFCBB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x639, 0x645 },
+ unicodeslot=0xFCBB,
+ },
+ [0xFCBC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x63A, 0x62C },
+ unicodeslot=0xFCBC,
+ },
+ [0xFCBD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x63A, 0x645 },
+ unicodeslot=0xFCBD,
+ },
+ [0xFCBE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x641, 0x62C },
+ unicodeslot=0xFCBE,
+ },
+ [0xFCBF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x641, 0x62D },
+ unicodeslot=0xFCBF,
+ },
+ [0xFCC0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x641, 0x62E },
+ unicodeslot=0xFCC0,
+ },
+ [0xFCC1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x641, 0x645 },
+ unicodeslot=0xFCC1,
+ },
+ [0xFCC2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x642, 0x62D },
+ unicodeslot=0xFCC2,
+ },
+ [0xFCC3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x642, 0x645 },
+ unicodeslot=0xFCC3,
+ },
+ [0xFCC4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643, 0x62C },
+ unicodeslot=0xFCC4,
+ },
+ [0xFCC5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643, 0x62D },
+ unicodeslot=0xFCC5,
+ },
+ [0xFCC6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643, 0x62E },
+ unicodeslot=0xFCC6,
+ },
+ [0xFCC7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643, 0x644 },
+ unicodeslot=0xFCC7,
+ },
+ [0xFCC8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643, 0x645 },
+ unicodeslot=0xFCC8,
+ },
+ [0xFCC9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62C },
+ unicodeslot=0xFCC9,
+ },
+ [0xFCCA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62D },
+ unicodeslot=0xFCCA,
+ },
+ [0xFCCB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62E },
+ unicodeslot=0xFCCB,
+ },
+ [0xFCCC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x645 },
+ unicodeslot=0xFCCC,
+ },
+ [0xFCCD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x647 },
+ unicodeslot=0xFCCD,
+ },
+ [0xFCCE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62C },
+ unicodeslot=0xFCCE,
+ },
+ [0xFCCF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62D },
+ unicodeslot=0xFCCF,
+ },
+ [0xFCD0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62E },
+ unicodeslot=0xFCD0,
+ },
+ [0xFCD1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x645 },
+ unicodeslot=0xFCD1,
+ },
+ [0xFCD2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x62C },
+ unicodeslot=0xFCD2,
+ },
+ [0xFCD3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x62D },
+ unicodeslot=0xFCD3,
+ },
+ [0xFCD4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x62E },
+ unicodeslot=0xFCD4,
+ },
+ [0xFCD5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x645 },
+ unicodeslot=0xFCD5,
+ },
+ [0xFCD6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x647 },
+ unicodeslot=0xFCD6,
+ },
+ [0xFCD7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x647, 0x62C },
+ unicodeslot=0xFCD7,
+ },
+ [0xFCD8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x647, 0x645 },
+ unicodeslot=0xFCD8,
+ },
+ [0xFCD9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x647, 0x670 },
+ unicodeslot=0xFCD9,
+ },
+ [0xFCDA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A, 0x62C },
+ unicodeslot=0xFCDA,
+ },
+ [0xFCDB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A, 0x62D },
+ unicodeslot=0xFCDB,
+ },
+ [0xFCDC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A, 0x62E },
+ unicodeslot=0xFCDC,
+ },
+ [0xFCDD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A, 0x645 },
+ unicodeslot=0xFCDD,
+ },
+ [0xFCDE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A, 0x647 },
+ unicodeslot=0xFCDE,
+ },
+ [0xFCDF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x626, 0x645 },
+ unicodeslot=0xFCDF,
+ },
+ [0xFCE0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x626, 0x647 },
+ unicodeslot=0xFCE0,
+ },
+ [0xFCE1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x628, 0x645 },
+ unicodeslot=0xFCE1,
+ },
+ [0xFCE2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x628, 0x647 },
+ unicodeslot=0xFCE2,
+ },
+ [0xFCE3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62A, 0x645 },
+ unicodeslot=0xFCE3,
+ },
+ [0xFCE4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62A, 0x647 },
+ unicodeslot=0xFCE4,
+ },
+ [0xFCE5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62B, 0x645 },
+ unicodeslot=0xFCE5,
+ },
+ [0xFCE6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62B, 0x647 },
+ unicodeslot=0xFCE6,
+ },
+ [0xFCE7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x633, 0x645 },
+ unicodeslot=0xFCE7,
+ },
+ [0xFCE8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x633, 0x647 },
+ unicodeslot=0xFCE8,
+ },
+ [0xFCE9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x634, 0x645 },
+ unicodeslot=0xFCE9,
+ },
+ [0xFCEA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x634, 0x647 },
+ unicodeslot=0xFCEA,
+ },
+ [0xFCEB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x643, 0x644 },
+ unicodeslot=0xFCEB,
+ },
+ [0xFCEC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x643, 0x645 },
+ unicodeslot=0xFCEC,
+ },
+ [0xFCED]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x644, 0x645 },
+ unicodeslot=0xFCED,
+ },
+ [0xFCEE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x646, 0x645 },
+ unicodeslot=0xFCEE,
+ },
+ [0xFCEF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x646, 0x647 },
+ unicodeslot=0xFCEF,
+ },
+ [0xFCF0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x64A, 0x645 },
+ unicodeslot=0xFCF0,
+ },
+ [0xFCF1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x64A, 0x647 },
+ unicodeslot=0xFCF1,
+ },
+ [0xFCF2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x64E, 0x651 },
+ unicodeslot=0xFCF2,
+ },
+ [0xFCF3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x64F, 0x651 },
+ unicodeslot=0xFCF3,
+ },
+ [0xFCF4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x650, 0x651 },
+ unicodeslot=0xFCF4,
+ },
+ [0xFCF5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x637, 0x649 },
+ unicodeslot=0xFCF5,
+ },
+ [0xFCF6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x637, 0x64A },
+ unicodeslot=0xFCF6,
+ },
+ [0xFCF7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x639, 0x649 },
+ unicodeslot=0xFCF7,
+ },
+ [0xFCF8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x639, 0x64A },
+ unicodeslot=0xFCF8,
+ },
+ [0xFCF9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x63A, 0x649 },
+ unicodeslot=0xFCF9,
+ },
+ [0xFCFA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x63A, 0x64A },
+ unicodeslot=0xFCFA,
+ },
+ [0xFCFB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x649 },
+ unicodeslot=0xFCFB,
+ },
+ [0xFCFC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x64A },
+ unicodeslot=0xFCFC,
+ },
+ [0xFCFD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x649 },
+ unicodeslot=0xFCFD,
+ },
+ [0xFCFE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x64A },
+ unicodeslot=0xFCFE,
+ },
+ [0xFCFF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62D, 0x649 },
+ unicodeslot=0xFCFF,
+ },
+ [0xFD00]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62D, 0x64A },
+ unicodeslot=0xFD00,
+ },
+ [0xFD01]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62C, 0x649 },
+ unicodeslot=0xFD01,
+ },
+ [0xFD02]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62C, 0x64A },
+ unicodeslot=0xFD02,
+ },
+ [0xFD03]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62E, 0x649 },
+ unicodeslot=0xFD03,
+ },
+ [0xFD04]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62E, 0x64A },
+ unicodeslot=0xFD04,
+ },
+ [0xFD05]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x649 },
+ unicodeslot=0xFD05,
+ },
+ [0xFD06]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x64A },
+ unicodeslot=0xFD06,
+ },
+ [0xFD07]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x649 },
+ unicodeslot=0xFD07,
+ },
+ [0xFD08]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x64A },
+ unicodeslot=0xFD08,
+ },
+ [0xFD09]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x62C },
+ unicodeslot=0xFD09,
+ },
+ [0xFD0A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x62D },
+ unicodeslot=0xFD0A,
+ },
+ [0xFD0B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x62E },
+ unicodeslot=0xFD0B,
+ },
+ [0xFD0C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x645 },
+ unicodeslot=0xFD0C,
+ },
+ [0xFD0D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634, 0x631 },
+ unicodeslot=0xFD0D,
+ },
+ [0xFD0E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633, 0x631 },
+ unicodeslot=0xFD0E,
+ },
+ [0xFD0F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x631 },
+ unicodeslot=0xFD0F,
+ },
+ [0xFD10]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636, 0x631 },
+ unicodeslot=0xFD10,
+ },
+ [0xFD11]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x637, 0x649 },
+ unicodeslot=0xFD11,
+ },
+ [0xFD12]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x637, 0x64A },
+ unicodeslot=0xFD12,
+ },
+ [0xFD13]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639, 0x649 },
+ unicodeslot=0xFD13,
+ },
+ [0xFD14]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639, 0x64A },
+ unicodeslot=0xFD14,
+ },
+ [0xFD15]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x63A, 0x649 },
+ unicodeslot=0xFD15,
+ },
+ [0xFD16]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x63A, 0x64A },
+ unicodeslot=0xFD16,
+ },
+ [0xFD17]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x649 },
+ unicodeslot=0xFD17,
+ },
+ [0xFD18]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x64A },
+ unicodeslot=0xFD18,
+ },
+ [0xFD19]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x649 },
+ unicodeslot=0xFD19,
+ },
+ [0xFD1A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x64A },
+ unicodeslot=0xFD1A,
+ },
+ [0xFD1B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62D, 0x649 },
+ unicodeslot=0xFD1B,
+ },
+ [0xFD1C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62D, 0x64A },
+ unicodeslot=0xFD1C,
+ },
+ [0xFD1D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x649 },
+ unicodeslot=0xFD1D,
+ },
+ [0xFD1E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x64A },
+ unicodeslot=0xFD1E,
+ },
+ [0xFD1F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62E, 0x649 },
+ unicodeslot=0xFD1F,
+ },
+ [0xFD20]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62E, 0x64A },
+ unicodeslot=0xFD20,
+ },
+ [0xFD21]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635, 0x649 },
+ unicodeslot=0xFD21,
+ },
+ [0xFD22]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635, 0x64A },
+ unicodeslot=0xFD22,
+ },
+ [0xFD23]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636, 0x649 },
+ unicodeslot=0xFD23,
+ },
+ [0xFD24]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636, 0x64A },
+ unicodeslot=0xFD24,
+ },
+ [0xFD25]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x62C },
+ unicodeslot=0xFD25,
+ },
+ [0xFD26]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x62D },
+ unicodeslot=0xFD26,
+ },
+ [0xFD27]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x62E },
+ unicodeslot=0xFD27,
+ },
+ [0xFD28]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x645 },
+ unicodeslot=0xFD28,
+ },
+ [0xFD29]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x631 },
+ unicodeslot=0xFD29,
+ },
+ [0xFD2A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x631 },
+ unicodeslot=0xFD2A,
+ },
+ [0xFD2B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635, 0x631 },
+ unicodeslot=0xFD2B,
+ },
+ [0xFD2C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636, 0x631 },
+ unicodeslot=0xFD2C,
+ },
+ [0xFD2D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x62C },
+ unicodeslot=0xFD2D,
+ },
+ [0xFD2E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x62D },
+ unicodeslot=0xFD2E,
+ },
+ [0xFD2F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x62E },
+ unicodeslot=0xFD2F,
+ },
+ [0xFD30]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x645 },
+ unicodeslot=0xFD30,
+ },
+ [0xFD31]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x647 },
+ unicodeslot=0xFD31,
+ },
+ [0xFD32]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x647 },
+ unicodeslot=0xFD32,
+ },
+ [0xFD33]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x637, 0x645 },
+ unicodeslot=0xFD33,
+ },
+ [0xFD34]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x633, 0x62C },
+ unicodeslot=0xFD34,
+ },
+ [0xFD35]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x633, 0x62D },
+ unicodeslot=0xFD35,
+ },
+ [0xFD36]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x633, 0x62E },
+ unicodeslot=0xFD36,
+ },
+ [0xFD37]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x634, 0x62C },
+ unicodeslot=0xFD37,
+ },
+ [0xFD38]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x634, 0x62D },
+ unicodeslot=0xFD38,
+ },
+ [0xFD39]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x634, 0x62E },
+ unicodeslot=0xFD39,
+ },
+ [0xFD3A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x637, 0x645 },
+ unicodeslot=0xFD3A,
+ },
+ [0xFD3B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x638, 0x645 },
+ unicodeslot=0xFD3B,
+ },
+ [0xFD3C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x627, 0x64B },
+ unicodeslot=0xFD3C,
+ },
+ [0xFD3D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x627, 0x64B },
+ unicodeslot=0xFD3D,
+ },
+ [0xFD3E]={
+ category="ps",
+ direction="on",
+ linebreak="cl",
+ unicodeslot=0xFD3E,
+ },
+ [0xFD3F]={
+ category="pe",
+ direction="on",
+ linebreak="op",
+ unicodeslot=0xFD3F,
+ },
+ [0xFD50]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62C, 0x645 },
+ unicodeslot=0xFD50,
+ },
+ [0xFD51]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x62D, 0x62C },
+ unicodeslot=0xFD51,
+ },
+ [0xFD52]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62D, 0x62C },
+ unicodeslot=0xFD52,
+ },
+ [0xFD53]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62D, 0x645 },
+ unicodeslot=0xFD53,
+ },
+ [0xFD54]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x62E, 0x645 },
+ unicodeslot=0xFD54,
+ },
+ [0xFD55]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x645, 0x62C },
+ unicodeslot=0xFD55,
+ },
+ [0xFD56]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x645, 0x62D },
+ unicodeslot=0xFD56,
+ },
+ [0xFD57]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A, 0x645, 0x62E },
+ unicodeslot=0xFD57,
+ },
+ [0xFD58]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x645, 0x62D },
+ unicodeslot=0xFD58,
+ },
+ [0xFD59]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62C, 0x645, 0x62D },
+ unicodeslot=0xFD59,
+ },
+ [0xFD5A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62D, 0x645, 0x64A },
+ unicodeslot=0xFD5A,
+ },
+ [0xFD5B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62D, 0x645, 0x649 },
+ unicodeslot=0xFD5B,
+ },
+ [0xFD5C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x62D, 0x62C },
+ unicodeslot=0xFD5C,
+ },
+ [0xFD5D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x62C, 0x62D },
+ unicodeslot=0xFD5D,
+ },
+ [0xFD5E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x62C, 0x649 },
+ unicodeslot=0xFD5E,
+ },
+ [0xFD5F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x645, 0x62D },
+ unicodeslot=0xFD5F,
+ },
+ [0xFD60]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x645, 0x62D },
+ unicodeslot=0xFD60,
+ },
+ [0xFD61]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x645, 0x62C },
+ unicodeslot=0xFD61,
+ },
+ [0xFD62]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x645, 0x645 },
+ unicodeslot=0xFD62,
+ },
+ [0xFD63]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633, 0x645, 0x645 },
+ unicodeslot=0xFD63,
+ },
+ [0xFD64]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635, 0x62D, 0x62D },
+ unicodeslot=0xFD64,
+ },
+ [0xFD65]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x635, 0x62D, 0x62D },
+ unicodeslot=0xFD65,
+ },
+ [0xFD66]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635, 0x645, 0x645 },
+ unicodeslot=0xFD66,
+ },
+ [0xFD67]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x62D, 0x645 },
+ unicodeslot=0xFD67,
+ },
+ [0xFD68]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x62D, 0x645 },
+ unicodeslot=0xFD68,
+ },
+ [0xFD69]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x62C, 0x64A },
+ unicodeslot=0xFD69,
+ },
+ [0xFD6A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x645, 0x62E },
+ unicodeslot=0xFD6A,
+ },
+ [0xFD6B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x645, 0x62E },
+ unicodeslot=0xFD6B,
+ },
+ [0xFD6C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x645, 0x645 },
+ unicodeslot=0xFD6C,
+ },
+ [0xFD6D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634, 0x645, 0x645 },
+ unicodeslot=0xFD6D,
+ },
+ [0xFD6E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636, 0x62D, 0x649 },
+ unicodeslot=0xFD6E,
+ },
+ [0xFD6F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636, 0x62E, 0x645 },
+ unicodeslot=0xFD6F,
+ },
+ [0xFD70]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x636, 0x62E, 0x645 },
+ unicodeslot=0xFD70,
+ },
+ [0xFD71]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x637, 0x645, 0x62D },
+ unicodeslot=0xFD71,
+ },
+ [0xFD72]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x637, 0x645, 0x62D },
+ unicodeslot=0xFD72,
+ },
+ [0xFD73]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x637, 0x645, 0x645 },
+ unicodeslot=0xFD73,
+ },
+ [0xFD74]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x637, 0x645, 0x64A },
+ unicodeslot=0xFD74,
+ },
+ [0xFD75]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639, 0x62C, 0x645 },
+ unicodeslot=0xFD75,
+ },
+ [0xFD76]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639, 0x645, 0x645 },
+ unicodeslot=0xFD76,
+ },
+ [0xFD77]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x639, 0x645, 0x645 },
+ unicodeslot=0xFD77,
+ },
+ [0xFD78]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639, 0x645, 0x649 },
+ unicodeslot=0xFD78,
+ },
+ [0xFD79]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x63A, 0x645, 0x645 },
+ unicodeslot=0xFD79,
+ },
+ [0xFD7A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x63A, 0x645, 0x64A },
+ unicodeslot=0xFD7A,
+ },
+ [0xFD7B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x63A, 0x645, 0x649 },
+ unicodeslot=0xFD7B,
+ },
+ [0xFD7C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x641, 0x62E, 0x645 },
+ unicodeslot=0xFD7C,
+ },
+ [0xFD7D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x641, 0x62E, 0x645 },
+ unicodeslot=0xFD7D,
+ },
+ [0xFD7E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x642, 0x645, 0x62D },
+ unicodeslot=0xFD7E,
+ },
+ [0xFD7F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x642, 0x645, 0x645 },
+ unicodeslot=0xFD7F,
+ },
+ [0xFD80]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62D, 0x645 },
+ unicodeslot=0xFD80,
+ },
+ [0xFD81]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62D, 0x64A },
+ unicodeslot=0xFD81,
+ },
+ [0xFD82]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62D, 0x649 },
+ unicodeslot=0xFD82,
+ },
+ [0xFD83]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62C, 0x62C },
+ unicodeslot=0xFD83,
+ },
+ [0xFD84]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62C, 0x62C },
+ unicodeslot=0xFD84,
+ },
+ [0xFD85]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62E, 0x645 },
+ unicodeslot=0xFD85,
+ },
+ [0xFD86]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62E, 0x645 },
+ unicodeslot=0xFD86,
+ },
+ [0xFD87]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x645, 0x62D },
+ unicodeslot=0xFD87,
+ },
+ [0xFD88]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x645, 0x62D },
+ unicodeslot=0xFD88,
+ },
+ [0xFD89]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62D, 0x62C },
+ unicodeslot=0xFD89,
+ },
+ [0xFD8A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62D, 0x645 },
+ unicodeslot=0xFD8A,
+ },
+ [0xFD8B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645, 0x62D, 0x64A },
+ unicodeslot=0xFD8B,
+ },
+ [0xFD8C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62C, 0x62D },
+ unicodeslot=0xFD8C,
+ },
+ [0xFD8D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62C, 0x645 },
+ unicodeslot=0xFD8D,
+ },
+ [0xFD8E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62E, 0x62C },
+ unicodeslot=0xFD8E,
+ },
+ [0xFD8F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62E, 0x645 },
+ unicodeslot=0xFD8F,
+ },
+ [0xFD92]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645, 0x62C, 0x62E },
+ unicodeslot=0xFD92,
+ },
+ [0xFD93]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x647, 0x645, 0x62C },
+ unicodeslot=0xFD93,
+ },
+ [0xFD94]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x647, 0x645, 0x645 },
+ unicodeslot=0xFD94,
+ },
+ [0xFD95]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x62D, 0x645 },
+ unicodeslot=0xFD95,
+ },
+ [0xFD96]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x62D, 0x649 },
+ unicodeslot=0xFD96,
+ },
+ [0xFD97]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x62C, 0x645 },
+ unicodeslot=0xFD97,
+ },
+ [0xFD98]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x62C, 0x645 },
+ unicodeslot=0xFD98,
+ },
+ [0xFD99]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x62C, 0x649 },
+ unicodeslot=0xFD99,
+ },
+ [0xFD9A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x645, 0x64A },
+ unicodeslot=0xFD9A,
+ },
+ [0xFD9B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x645, 0x649 },
+ unicodeslot=0xFD9B,
+ },
+ [0xFD9C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x645, 0x645 },
+ unicodeslot=0xFD9C,
+ },
+ [0xFD9D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A, 0x645, 0x645 },
+ unicodeslot=0xFD9D,
+ },
+ [0xFD9E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x62E, 0x64A },
+ unicodeslot=0xFD9E,
+ },
+ [0xFD9F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x62C, 0x64A },
+ unicodeslot=0xFD9F,
+ },
+ [0xFDA0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x62C, 0x649 },
+ unicodeslot=0xFDA0,
+ },
+ [0xFDA1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x62E, 0x64A },
+ unicodeslot=0xFDA1,
+ },
+ [0xFDA2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x62E, 0x649 },
+ unicodeslot=0xFDA2,
+ },
+ [0xFDA3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x645, 0x64A },
+ unicodeslot=0xFDA3,
+ },
+ [0xFDA4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A, 0x645, 0x649 },
+ unicodeslot=0xFDA4,
+ },
+ [0xFDA5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x645, 0x64A },
+ unicodeslot=0xFDA5,
+ },
+ [0xFDA6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x62D, 0x649 },
+ unicodeslot=0xFDA6,
+ },
+ [0xFDA7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x645, 0x649 },
+ unicodeslot=0xFDA7,
+ },
+ [0xFDA8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x62E, 0x649 },
+ unicodeslot=0xFDA8,
+ },
+ [0xFDA9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635, 0x62D, 0x64A },
+ unicodeslot=0xFDA9,
+ },
+ [0xFDAA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634, 0x62D, 0x64A },
+ unicodeslot=0xFDAA,
+ },
+ [0xFDAB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636, 0x62D, 0x64A },
+ unicodeslot=0xFDAB,
+ },
+ [0xFDAC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62C, 0x64A },
+ unicodeslot=0xFDAC,
+ },
+ [0xFDAD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x645, 0x64A },
+ unicodeslot=0xFDAD,
+ },
+ [0xFDAE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x62D, 0x64A },
+ unicodeslot=0xFDAE,
+ },
+ [0xFDAF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x62C, 0x64A },
+ unicodeslot=0xFDAF,
+ },
+ [0xFDB0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A, 0x645, 0x64A },
+ unicodeslot=0xFDB0,
+ },
+ [0xFDB1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645, 0x645, 0x64A },
+ unicodeslot=0xFDB1,
+ },
+ [0xFDB2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x642, 0x645, 0x64A },
+ unicodeslot=0xFDB2,
+ },
+ [0xFDB3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x62D, 0x64A },
+ unicodeslot=0xFDB3,
+ },
+ [0xFDB4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x642, 0x645, 0x62D },
+ unicodeslot=0xFDB4,
+ },
+ [0xFDB5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62D, 0x645 },
+ unicodeslot=0xFDB5,
+ },
+ [0xFDB6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639, 0x645, 0x64A },
+ unicodeslot=0xFDB6,
+ },
+ [0xFDB7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x645, 0x64A },
+ unicodeslot=0xFDB7,
+ },
+ [0xFDB8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646, 0x62C, 0x62D },
+ unicodeslot=0xFDB8,
+ },
+ [0xFDB9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645, 0x62E, 0x64A },
+ unicodeslot=0xFDB9,
+ },
+ [0xFDBA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644, 0x62C, 0x645 },
+ unicodeslot=0xFDBA,
+ },
+ [0xFDBB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643, 0x645, 0x645 },
+ unicodeslot=0xFDBB,
+ },
+ [0xFDBC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x62C, 0x645 },
+ unicodeslot=0xFDBC,
+ },
+ [0xFDBD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x62C, 0x62D },
+ unicodeslot=0xFDBD,
+ },
+ [0xFDBE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C, 0x62D, 0x64A },
+ unicodeslot=0xFDBE,
+ },
+ [0xFDBF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62D, 0x62C, 0x64A },
+ unicodeslot=0xFDBF,
+ },
+ [0xFDC0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645, 0x62C, 0x64A },
+ unicodeslot=0xFDC0,
+ },
+ [0xFDC1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x641, 0x645, 0x64A },
+ unicodeslot=0xFDC1,
+ },
+ [0xFDC2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628, 0x62D, 0x64A },
+ unicodeslot=0xFDC2,
+ },
+ [0xFDC3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643, 0x645, 0x645 },
+ unicodeslot=0xFDC3,
+ },
+ [0xFDC4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x639, 0x62C, 0x645 },
+ unicodeslot=0xFDC4,
+ },
+ [0xFDC5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x635, 0x645, 0x645 },
+ unicodeslot=0xFDC5,
+ },
+ [0xFDC6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633, 0x62E, 0x64A },
+ unicodeslot=0xFDC6,
+ },
+ [0xFDC7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646, 0x62C, 0x64A },
+ unicodeslot=0xFDC7,
+ },
+ [0xFDF0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x644, 0x6D2 },
+ unicodeslot=0xFDF0,
+ },
+ [0xFDF1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x642, 0x644, 0x6D2 },
+ unicodeslot=0xFDF1,
+ },
+ [0xFDF2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x627, 0x644, 0x644, 0x647 },
+ unicodeslot=0xFDF2,
+ },
+ [0xFDF3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x627, 0x643, 0x628, 0x631 },
+ unicodeslot=0xFDF3,
+ },
+ [0xFDF4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645, 0x62D, 0x645, 0x62F },
+ unicodeslot=0xFDF4,
+ },
+ [0xFDF5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x644, 0x639, 0x645 },
+ unicodeslot=0xFDF5,
+ },
+ [0xFDF6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x631, 0x633, 0x648, 0x644 },
+ unicodeslot=0xFDF6,
+ },
+ [0xFDF7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x639, 0x644, 0x64A, 0x647 },
+ unicodeslot=0xFDF7,
+ },
+ [0xFDF8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x648, 0x633, 0x644, 0x645 },
+ unicodeslot=0xFDF8,
+ },
+ [0xFDF9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x644, 0x649 },
+ unicodeslot=0xFDF9,
+ },
+ [0xFDFA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635, 0x644, 0x649, 0x20, 0x627, 0x644, 0x644, 0x647, 0x20, 0x639, 0x644, 0x64A, 0x647, 0x20, 0x648, 0x633, 0x644, 0x645 },
+ unicodeslot=0xFDFA,
+ },
+ [0xFDFB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62C, 0x644, 0x20, 0x62C, 0x644, 0x627, 0x644, 0x647 },
+ unicodeslot=0xFDFB,
+ },
+ [0xFDFC]={
+ category="sc",
+ direction="al",
+ linebreak="po",
+ specials={ "isolated", 0x631, 0x6CC, 0x627, 0x644 },
+ unicodeslot=0xFDFC,
+ },
+ [0xFDFD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0xFDFD,
+ },
+ [0xFE00]={
+ unicodeslot=0xFE00,
+ },
+ [0xFE10]={
+ category="po",
+ direction="on",
+ linebreak="is",
+ specials={ "vertical", 0x2C },
+ unicodeslot=0xFE10,
+ },
+ [0xFE11]={
+ category="po",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x3001 },
+ unicodeslot=0xFE11,
+ },
+ [0xFE12]={
+ category="po",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x3002 },
+ unicodeslot=0xFE12,
+ },
+ [0xFE13]={
+ category="po",
+ direction="on",
+ linebreak="is",
+ specials={ "vertical", 0x3A },
+ unicodeslot=0xFE13,
+ },
+ [0xFE14]={
+ category="po",
+ direction="on",
+ linebreak="is",
+ specials={ "vertical", 0x3B },
+ unicodeslot=0xFE14,
+ },
+ [0xFE15]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ specials={ "vertical", 0x21 },
+ unicodeslot=0xFE15,
+ },
+ [0xFE16]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ specials={ "vertical", 0x3F },
+ unicodeslot=0xFE16,
+ },
+ [0xFE17]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x3016 },
+ unicodeslot=0xFE17,
+ },
+ [0xFE18]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x3017 },
+ unicodeslot=0xFE18,
+ },
+ [0xFE19]={
+ category="po",
+ direction="on",
+ linebreak="in",
+ specials={ "vertical", 0x2026 },
+ unicodeslot=0xFE19,
+ },
+ [0xFE20]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE20,
+ },
+ [0xFE21]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE21,
+ },
+ [0xFE22]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE22,
+ },
+ [0xFE23]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE23,
+ },
+ [0xFE24]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE24,
+ },
+ [0xFE25]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE25,
+ },
+ [0xFE26]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE26,
+ },
+ [0xFE27]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE27,
+ },
+ [0xFE28]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE28,
+ },
+ [0xFE29]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE29,
+ },
+ [0xFE2A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE2A,
+ },
+ [0xFE2B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE2B,
+ },
+ [0xFE2C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE2C,
+ },
+ [0xFE2D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE2D,
+ },
+ [0xFE2E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE2E,
+ },
+ [0xFE2F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0xFE2F,
+ },
+ [0xFE30]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "vertical", 0x2025 },
+ unicodeslot=0xFE30,
+ },
+ [0xFE31]={
+ category="pd",
+ direction="on",
+ linebreak="id",
+ specials={ "vertical", 0x2014 },
+ unicodeslot=0xFE31,
+ },
+ [0xFE32]={
+ category="pd",
+ direction="on",
+ linebreak="id",
+ specials={ "vertical", 0x2013 },
+ unicodeslot=0xFE32,
+ },
+ [0xFE33]={
+ category="pc",
+ direction="on",
+ linebreak="id",
+ specials={ "vertical", 0x5F },
+ unicodeslot=0xFE33,
+ },
+ [0xFE34]={
+ category="pc",
+ direction="on",
+ linebreak="id",
+ specials={ "vertical", 0x5F },
+ unicodeslot=0xFE34,
+ },
+ [0xFE35]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x28 },
+ unicodeslot=0xFE35,
+ },
+ [0xFE36]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x29 },
+ unicodeslot=0xFE36,
+ },
+ [0xFE37]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x7B },
+ unicodeslot=0xFE37,
+ },
+ [0xFE38]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x7D },
+ unicodeslot=0xFE38,
+ },
+ [0xFE39]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x3014 },
+ unicodeslot=0xFE39,
+ },
+ [0xFE3A]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x3015 },
+ unicodeslot=0xFE3A,
+ },
+ [0xFE3B]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x3010 },
+ unicodeslot=0xFE3B,
+ },
+ [0xFE3C]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x3011 },
+ unicodeslot=0xFE3C,
+ },
+ [0xFE3D]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x300A },
+ unicodeslot=0xFE3D,
+ },
+ [0xFE3E]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x300B },
+ unicodeslot=0xFE3E,
+ },
+ [0xFE3F]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x3008 },
+ unicodeslot=0xFE3F,
+ },
+ [0xFE40]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x3009 },
+ unicodeslot=0xFE40,
+ },
+ [0xFE41]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x300C },
+ unicodeslot=0xFE41,
+ },
+ [0xFE42]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x300D },
+ unicodeslot=0xFE42,
+ },
+ [0xFE43]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x300E },
+ unicodeslot=0xFE43,
+ },
+ [0xFE44]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x300F },
+ unicodeslot=0xFE44,
+ },
+ [0xFE45]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xFE45,
+ },
+ [0xFE46]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0xFE46,
+ },
+ [0xFE47]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ specials={ "vertical", 0x5B },
+ unicodeslot=0xFE47,
+ },
+ [0xFE48]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ specials={ "vertical", 0x5D },
+ unicodeslot=0xFE48,
+ },
+ [0xFE49]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x203E },
+ unicodeslot=0xFE49,
+ },
+ [0xFE4A]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x203E },
+ unicodeslot=0xFE4A,
+ },
+ [0xFE4B]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x203E },
+ unicodeslot=0xFE4B,
+ },
+ [0xFE4C]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x203E },
+ unicodeslot=0xFE4C,
+ },
+ [0xFE4D]={
+ category="pc",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F },
+ unicodeslot=0xFE4D,
+ },
+ [0xFE4E]={
+ category="pc",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F },
+ unicodeslot=0xFE4E,
+ },
+ [0xFE4F]={
+ category="pc",
+ direction="on",
+ linebreak="id",
+ specials={ "compat", 0x5F },
+ unicodeslot=0xFE4F,
+ },
+ [0xFE50]={
+ category="po",
+ direction="cs",
+ linebreak="cl",
+ specials={ "small", 0x2C },
+ unicodeslot=0xFE50,
+ },
+ [0xFE51]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x3001 },
+ unicodeslot=0xFE51,
+ },
+ [0xFE52]={
+ category="po",
+ direction="cs",
+ linebreak="cl",
+ specials={ "small", 0x2E },
+ unicodeslot=0xFE52,
+ },
+ [0xFE54]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "small", 0x3B },
+ unicodeslot=0xFE54,
+ },
+ [0xFE55]={
+ category="po",
+ direction="cs",
+ linebreak="ns",
+ specials={ "small", 0x3A },
+ unicodeslot=0xFE55,
+ },
+ [0xFE56]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ specials={ "small", 0x3F },
+ unicodeslot=0xFE56,
+ },
+ [0xFE57]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ specials={ "small", 0x21 },
+ unicodeslot=0xFE57,
+ },
+ [0xFE58]={
+ category="pd",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x2014 },
+ unicodeslot=0xFE58,
+ },
+ [0xFE59]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFE5A,
+ specials={ "small", 0x28 },
+ textclass="open",
+ unicodeslot=0xFE59,
+ },
+ [0xFE5A]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFE59,
+ specials={ "small", 0x29 },
+ textclass="close",
+ unicodeslot=0xFE5A,
+ },
+ [0xFE5B]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFE5C,
+ specials={ "small", 0x7B },
+ textclass="open",
+ unicodeslot=0xFE5B,
+ },
+ [0xFE5C]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFE5B,
+ specials={ "small", 0x7D },
+ textclass="close",
+ unicodeslot=0xFE5C,
+ },
+ [0xFE5D]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFE5E,
+ specials={ "small", 0x3014 },
+ textclass="open",
+ unicodeslot=0xFE5D,
+ },
+ [0xFE5E]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFE5D,
+ specials={ "small", 0x3015 },
+ textclass="close",
+ unicodeslot=0xFE5E,
+ },
+ [0xFE5F]={
+ category="po",
+ direction="et",
+ linebreak="id",
+ specials={ "small", 0x23 },
+ unicodeslot=0xFE5F,
+ },
+ [0xFE60]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x26 },
+ unicodeslot=0xFE60,
+ },
+ [0xFE61]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x2A },
+ unicodeslot=0xFE61,
+ },
+ [0xFE62]={
+ category="sm",
+ direction="es",
+ linebreak="id",
+ specials={ "small", 0x2B },
+ unicodeslot=0xFE62,
+ },
+ [0xFE63]={
+ category="pd",
+ direction="es",
+ linebreak="id",
+ specials={ "small", 0x2D },
+ unicodeslot=0xFE63,
+ },
+ [0xFE64]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ mirror=0xFE65,
+ specials={ "small", 0x3C },
+ textclass="open",
+ unicodeslot=0xFE64,
+ },
+ [0xFE65]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ mirror=0xFE64,
+ specials={ "small", 0x3E },
+ textclass="close",
+ unicodeslot=0xFE65,
+ },
+ [0xFE66]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x3D },
+ unicodeslot=0xFE66,
+ },
+ [0xFE68]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x5C },
+ unicodeslot=0xFE68,
+ },
+ [0xFE69]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ specials={ "small", 0x24 },
+ unicodeslot=0xFE69,
+ },
+ [0xFE6A]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ specials={ "small", 0x25 },
+ unicodeslot=0xFE6A,
+ },
+ [0xFE6B]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "small", 0x40 },
+ unicodeslot=0xFE6B,
+ },
+ [0xFE70]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64B },
+ unicodeslot=0xFE70,
+ },
+ [0xFE71]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x64B },
+ unicodeslot=0xFE71,
+ },
+ [0xFE72]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64C },
+ unicodeslot=0xFE72,
+ },
+ [0xFE73]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0xFE73,
+ },
+ [0xFE74]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64D },
+ unicodeslot=0xFE74,
+ },
+ [0xFE76]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64E },
+ unicodeslot=0xFE76,
+ },
+ [0xFE77]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x64E },
+ unicodeslot=0xFE77,
+ },
+ [0xFE78]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x64F },
+ unicodeslot=0xFE78,
+ },
+ [0xFE79]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x64F },
+ unicodeslot=0xFE79,
+ },
+ [0xFE7A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x650 },
+ unicodeslot=0xFE7A,
+ },
+ [0xFE7B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x650 },
+ unicodeslot=0xFE7B,
+ },
+ [0xFE7C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x651 },
+ unicodeslot=0xFE7C,
+ },
+ [0xFE7D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x651 },
+ unicodeslot=0xFE7D,
+ },
+ [0xFE7E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x20, 0x652 },
+ unicodeslot=0xFE7E,
+ },
+ [0xFE7F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x640, 0x652 },
+ unicodeslot=0xFE7F,
+ },
+ [0xFE80]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x621 },
+ unicodeslot=0xFE80,
+ },
+ [0xFE81]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x622 },
+ unicodeslot=0xFE81,
+ },
+ [0xFE82]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x622 },
+ unicodeslot=0xFE82,
+ },
+ [0xFE83]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x623 },
+ unicodeslot=0xFE83,
+ },
+ [0xFE84]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x623 },
+ unicodeslot=0xFE84,
+ },
+ [0xFE85]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x624 },
+ unicodeslot=0xFE85,
+ },
+ [0xFE86]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x624 },
+ unicodeslot=0xFE86,
+ },
+ [0xFE87]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x625 },
+ unicodeslot=0xFE87,
+ },
+ [0xFE88]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x625 },
+ unicodeslot=0xFE88,
+ },
+ [0xFE89]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x626 },
+ unicodeslot=0xFE89,
+ },
+ [0xFE8A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x626 },
+ unicodeslot=0xFE8A,
+ },
+ [0xFE8B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x626 },
+ unicodeslot=0xFE8B,
+ },
+ [0xFE8C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x626 },
+ unicodeslot=0xFE8C,
+ },
+ [0xFE8D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x627 },
+ unicodeslot=0xFE8D,
+ },
+ [0xFE8E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x627 },
+ unicodeslot=0xFE8E,
+ },
+ [0xFE8F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x628 },
+ unicodeslot=0xFE8F,
+ },
+ [0xFE90]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x628 },
+ unicodeslot=0xFE90,
+ },
+ [0xFE91]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x628 },
+ unicodeslot=0xFE91,
+ },
+ [0xFE92]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x628 },
+ unicodeslot=0xFE92,
+ },
+ [0xFE93]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x629 },
+ unicodeslot=0xFE93,
+ },
+ [0xFE94]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x629 },
+ unicodeslot=0xFE94,
+ },
+ [0xFE95]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62A },
+ unicodeslot=0xFE95,
+ },
+ [0xFE96]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62A },
+ unicodeslot=0xFE96,
+ },
+ [0xFE97]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62A },
+ unicodeslot=0xFE97,
+ },
+ [0xFE98]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62A },
+ unicodeslot=0xFE98,
+ },
+ [0xFE99]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62B },
+ unicodeslot=0xFE99,
+ },
+ [0xFE9A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62B },
+ unicodeslot=0xFE9A,
+ },
+ [0xFE9B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62B },
+ unicodeslot=0xFE9B,
+ },
+ [0xFE9C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62B },
+ unicodeslot=0xFE9C,
+ },
+ [0xFE9D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62C },
+ unicodeslot=0xFE9D,
+ },
+ [0xFE9E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62C },
+ unicodeslot=0xFE9E,
+ },
+ [0xFE9F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62C },
+ unicodeslot=0xFE9F,
+ },
+ [0xFEA0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62C },
+ unicodeslot=0xFEA0,
+ },
+ [0xFEA1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62D },
+ unicodeslot=0xFEA1,
+ },
+ [0xFEA2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62D },
+ unicodeslot=0xFEA2,
+ },
+ [0xFEA3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62D },
+ unicodeslot=0xFEA3,
+ },
+ [0xFEA4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62D },
+ unicodeslot=0xFEA4,
+ },
+ [0xFEA5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62E },
+ unicodeslot=0xFEA5,
+ },
+ [0xFEA6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62E },
+ unicodeslot=0xFEA6,
+ },
+ [0xFEA7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x62E },
+ unicodeslot=0xFEA7,
+ },
+ [0xFEA8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x62E },
+ unicodeslot=0xFEA8,
+ },
+ [0xFEA9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x62F },
+ unicodeslot=0xFEA9,
+ },
+ [0xFEAA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x62F },
+ unicodeslot=0xFEAA,
+ },
+ [0xFEAB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x630 },
+ unicodeslot=0xFEAB,
+ },
+ [0xFEAC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x630 },
+ unicodeslot=0xFEAC,
+ },
+ [0xFEAD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x631 },
+ unicodeslot=0xFEAD,
+ },
+ [0xFEAE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x631 },
+ unicodeslot=0xFEAE,
+ },
+ [0xFEAF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x632 },
+ unicodeslot=0xFEAF,
+ },
+ [0xFEB0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x632 },
+ unicodeslot=0xFEB0,
+ },
+ [0xFEB1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x633 },
+ unicodeslot=0xFEB1,
+ },
+ [0xFEB2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x633 },
+ unicodeslot=0xFEB2,
+ },
+ [0xFEB3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x633 },
+ unicodeslot=0xFEB3,
+ },
+ [0xFEB4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x633 },
+ unicodeslot=0xFEB4,
+ },
+ [0xFEB5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x634 },
+ unicodeslot=0xFEB5,
+ },
+ [0xFEB6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x634 },
+ unicodeslot=0xFEB6,
+ },
+ [0xFEB7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x634 },
+ unicodeslot=0xFEB7,
+ },
+ [0xFEB8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x634 },
+ unicodeslot=0xFEB8,
+ },
+ [0xFEB9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x635 },
+ unicodeslot=0xFEB9,
+ },
+ [0xFEBA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x635 },
+ unicodeslot=0xFEBA,
+ },
+ [0xFEBB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x635 },
+ unicodeslot=0xFEBB,
+ },
+ [0xFEBC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x635 },
+ unicodeslot=0xFEBC,
+ },
+ [0xFEBD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x636 },
+ unicodeslot=0xFEBD,
+ },
+ [0xFEBE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x636 },
+ unicodeslot=0xFEBE,
+ },
+ [0xFEBF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x636 },
+ unicodeslot=0xFEBF,
+ },
+ [0xFEC0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x636 },
+ unicodeslot=0xFEC0,
+ },
+ [0xFEC1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x637 },
+ unicodeslot=0xFEC1,
+ },
+ [0xFEC2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x637 },
+ unicodeslot=0xFEC2,
+ },
+ [0xFEC3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x637 },
+ unicodeslot=0xFEC3,
+ },
+ [0xFEC4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x637 },
+ unicodeslot=0xFEC4,
+ },
+ [0xFEC5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x638 },
+ unicodeslot=0xFEC5,
+ },
+ [0xFEC6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x638 },
+ unicodeslot=0xFEC6,
+ },
+ [0xFEC7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x638 },
+ unicodeslot=0xFEC7,
+ },
+ [0xFEC8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x638 },
+ unicodeslot=0xFEC8,
+ },
+ [0xFEC9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x639 },
+ unicodeslot=0xFEC9,
+ },
+ [0xFECA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x639 },
+ unicodeslot=0xFECA,
+ },
+ [0xFECB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x639 },
+ unicodeslot=0xFECB,
+ },
+ [0xFECC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x639 },
+ unicodeslot=0xFECC,
+ },
+ [0xFECD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x63A },
+ unicodeslot=0xFECD,
+ },
+ [0xFECE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x63A },
+ unicodeslot=0xFECE,
+ },
+ [0xFECF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x63A },
+ unicodeslot=0xFECF,
+ },
+ [0xFED0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x63A },
+ unicodeslot=0xFED0,
+ },
+ [0xFED1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x641 },
+ unicodeslot=0xFED1,
+ },
+ [0xFED2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x641 },
+ unicodeslot=0xFED2,
+ },
+ [0xFED3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x641 },
+ unicodeslot=0xFED3,
+ },
+ [0xFED4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x641 },
+ unicodeslot=0xFED4,
+ },
+ [0xFED5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x642 },
+ unicodeslot=0xFED5,
+ },
+ [0xFED6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x642 },
+ unicodeslot=0xFED6,
+ },
+ [0xFED7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x642 },
+ unicodeslot=0xFED7,
+ },
+ [0xFED8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x642 },
+ unicodeslot=0xFED8,
+ },
+ [0xFED9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x643 },
+ unicodeslot=0xFED9,
+ },
+ [0xFEDA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x643 },
+ unicodeslot=0xFEDA,
+ },
+ [0xFEDB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x643 },
+ unicodeslot=0xFEDB,
+ },
+ [0xFEDC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x643 },
+ unicodeslot=0xFEDC,
+ },
+ [0xFEDD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644 },
+ unicodeslot=0xFEDD,
+ },
+ [0xFEDE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644 },
+ unicodeslot=0xFEDE,
+ },
+ [0xFEDF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x644 },
+ unicodeslot=0xFEDF,
+ },
+ [0xFEE0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x644 },
+ unicodeslot=0xFEE0,
+ },
+ [0xFEE1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x645 },
+ unicodeslot=0xFEE1,
+ },
+ [0xFEE2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x645 },
+ unicodeslot=0xFEE2,
+ },
+ [0xFEE3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x645 },
+ unicodeslot=0xFEE3,
+ },
+ [0xFEE4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x645 },
+ unicodeslot=0xFEE4,
+ },
+ [0xFEE5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x646 },
+ unicodeslot=0xFEE5,
+ },
+ [0xFEE6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x646 },
+ unicodeslot=0xFEE6,
+ },
+ [0xFEE7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x646 },
+ unicodeslot=0xFEE7,
+ },
+ [0xFEE8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x646 },
+ unicodeslot=0xFEE8,
+ },
+ [0xFEE9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x647 },
+ unicodeslot=0xFEE9,
+ },
+ [0xFEEA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x647 },
+ unicodeslot=0xFEEA,
+ },
+ [0xFEEB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x647 },
+ unicodeslot=0xFEEB,
+ },
+ [0xFEEC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x647 },
+ unicodeslot=0xFEEC,
+ },
+ [0xFEED]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x648 },
+ unicodeslot=0xFEED,
+ },
+ [0xFEEE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x648 },
+ unicodeslot=0xFEEE,
+ },
+ [0xFEEF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x649 },
+ unicodeslot=0xFEEF,
+ },
+ [0xFEF0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x649 },
+ unicodeslot=0xFEF0,
+ },
+ [0xFEF1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x64A },
+ unicodeslot=0xFEF1,
+ },
+ [0xFEF2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x64A },
+ unicodeslot=0xFEF2,
+ },
+ [0xFEF3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "initial", 0x64A },
+ unicodeslot=0xFEF3,
+ },
+ [0xFEF4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "medial", 0x64A },
+ unicodeslot=0xFEF4,
+ },
+ [0xFEF5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x622 },
+ unicodeslot=0xFEF5,
+ },
+ [0xFEF6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x622 },
+ unicodeslot=0xFEF6,
+ },
+ [0xFEF7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x623 },
+ unicodeslot=0xFEF7,
+ },
+ [0xFEF8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x623 },
+ unicodeslot=0xFEF8,
+ },
+ [0xFEF9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x625 },
+ unicodeslot=0xFEF9,
+ },
+ [0xFEFA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x625 },
+ unicodeslot=0xFEFA,
+ },
+ [0xFEFB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "isolated", 0x644, 0x627 },
+ unicodeslot=0xFEFB,
+ },
+ [0xFEFC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "final", 0x644, 0x627 },
+ unicodeslot=0xFEFC,
+ },
+ [0xFEFF]={
+ category="cf",
+ direction="bn",
+ linebreak="wj",
+ unicodeslot=0xFEFF,
+ },
+ [0xFF01]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ specials={ "wide", 0x21 },
+ unicodeslot=0xFF01,
+ },
+ [0xFF02]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x22 },
+ unicodeslot=0xFF02,
+ },
+ [0xFF03]={
+ category="po",
+ direction="et",
+ linebreak="id",
+ specials={ "wide", 0x23 },
+ unicodeslot=0xFF03,
+ },
+ [0xFF04]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ specials={ "wide", 0x24 },
+ unicodeslot=0xFF04,
+ },
+ [0xFF05]={
+ category="po",
+ direction="et",
+ linebreak="po",
+ specials={ "wide", 0x25 },
+ unicodeslot=0xFF05,
+ },
+ [0xFF06]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x26 },
+ unicodeslot=0xFF06,
+ },
+ [0xFF07]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x27 },
+ unicodeslot=0xFF07,
+ },
+ [0xFF08]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFF09,
+ specials={ "wide", 0x28 },
+ textclass="open",
+ unicodeslot=0xFF08,
+ },
+ [0xFF09]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFF08,
+ specials={ "wide", 0x29 },
+ textclass="close",
+ unicodeslot=0xFF09,
+ },
+ [0xFF0A]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x2A },
+ unicodeslot=0xFF0A,
+ },
+ [0xFF0B]={
+ category="sm",
+ direction="es",
+ linebreak="id",
+ specials={ "wide", 0x2B },
+ unicodeslot=0xFF0B,
+ },
+ [0xFF0C]={
+ category="po",
+ direction="cs",
+ linebreak="cl",
+ specials={ "wide", 0x2C },
+ unicodeslot=0xFF0C,
+ },
+ [0xFF0D]={
+ category="pd",
+ direction="es",
+ linebreak="id",
+ specials={ "wide", 0x2D },
+ unicodeslot=0xFF0D,
+ },
+ [0xFF0E]={
+ category="po",
+ direction="cs",
+ linebreak="cl",
+ specials={ "wide", 0x2E },
+ unicodeslot=0xFF0E,
+ },
+ [0xFF0F]={
+ category="po",
+ direction="cs",
+ linebreak="id",
+ specials={ "wide", 0x2F },
+ unicodeslot=0xFF0F,
+ },
+ [0xFF10]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x30 },
+ unicodeslot=0xFF10,
+ },
+ [0xFF11]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x31 },
+ unicodeslot=0xFF11,
+ },
+ [0xFF12]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x32 },
+ unicodeslot=0xFF12,
+ },
+ [0xFF13]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x33 },
+ unicodeslot=0xFF13,
+ },
+ [0xFF14]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x34 },
+ unicodeslot=0xFF14,
+ },
+ [0xFF15]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x35 },
+ unicodeslot=0xFF15,
+ },
+ [0xFF16]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x36 },
+ unicodeslot=0xFF16,
+ },
+ [0xFF17]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x37 },
+ unicodeslot=0xFF17,
+ },
+ [0xFF18]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x38 },
+ unicodeslot=0xFF18,
+ },
+ [0xFF19]={
+ category="nd",
+ direction="en",
+ linebreak="id",
+ specials={ "wide", 0x39 },
+ unicodeslot=0xFF19,
+ },
+ [0xFF1A]={
+ category="po",
+ direction="cs",
+ linebreak="ns",
+ specials={ "wide", 0x3A },
+ unicodeslot=0xFF1A,
+ },
+ [0xFF1B]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "wide", 0x3B },
+ unicodeslot=0xFF1B,
+ },
+ [0xFF1C]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ mirror=0xFF1E,
+ specials={ "wide", 0x3C },
+ textclass="open",
+ unicodeslot=0xFF1C,
+ },
+ [0xFF1D]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x3D },
+ unicodeslot=0xFF1D,
+ },
+ [0xFF1E]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ mirror=0xFF1C,
+ specials={ "wide", 0x3E },
+ textclass="close",
+ unicodeslot=0xFF1E,
+ },
+ [0xFF1F]={
+ category="po",
+ direction="on",
+ linebreak="ex",
+ specials={ "wide", 0x3F },
+ unicodeslot=0xFF1F,
+ },
+ [0xFF20]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x40 },
+ unicodeslot=0xFF20,
+ },
+ [0xFF21]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x41 },
+ unicodeslot=0xFF21,
+ },
+ [0xFF22]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x42 },
+ unicodeslot=0xFF22,
+ },
+ [0xFF23]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x43 },
+ unicodeslot=0xFF23,
+ },
+ [0xFF24]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x44 },
+ unicodeslot=0xFF24,
+ },
+ [0xFF25]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x45 },
+ unicodeslot=0xFF25,
+ },
+ [0xFF26]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x46 },
+ unicodeslot=0xFF26,
+ },
+ [0xFF27]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x47 },
+ unicodeslot=0xFF27,
+ },
+ [0xFF28]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x48 },
+ unicodeslot=0xFF28,
+ },
+ [0xFF29]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x49 },
+ unicodeslot=0xFF29,
+ },
+ [0xFF2A]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x4A },
+ unicodeslot=0xFF2A,
+ },
+ [0xFF2B]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x4B },
+ unicodeslot=0xFF2B,
+ },
+ [0xFF2C]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x4C },
+ unicodeslot=0xFF2C,
+ },
+ [0xFF2D]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x4D },
+ unicodeslot=0xFF2D,
+ },
+ [0xFF2E]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x4E },
+ unicodeslot=0xFF2E,
+ },
+ [0xFF2F]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x4F },
+ unicodeslot=0xFF2F,
+ },
+ [0xFF30]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x50 },
+ unicodeslot=0xFF30,
+ },
+ [0xFF31]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x51 },
+ unicodeslot=0xFF31,
+ },
+ [0xFF32]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x52 },
+ unicodeslot=0xFF32,
+ },
+ [0xFF33]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x53 },
+ unicodeslot=0xFF33,
+ },
+ [0xFF34]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x54 },
+ unicodeslot=0xFF34,
+ },
+ [0xFF35]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x55 },
+ unicodeslot=0xFF35,
+ },
+ [0xFF36]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x56 },
+ unicodeslot=0xFF36,
+ },
+ [0xFF37]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x57 },
+ unicodeslot=0xFF37,
+ },
+ [0xFF38]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x58 },
+ unicodeslot=0xFF38,
+ },
+ [0xFF39]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x59 },
+ unicodeslot=0xFF39,
+ },
+ [0xFF3A]={
+ category="lu",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x5A },
+ unicodeslot=0xFF3A,
+ },
+ [0xFF3B]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFF3D,
+ specials={ "wide", 0x5B },
+ textclass="open",
+ unicodeslot=0xFF3B,
+ },
+ [0xFF3C]={
+ category="po",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x5C },
+ unicodeslot=0xFF3C,
+ },
+ [0xFF3D]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFF3B,
+ specials={ "wide", 0x5D },
+ textclass="close",
+ unicodeslot=0xFF3D,
+ },
+ [0xFF3E]={
+ category="sk",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x5E },
+ unicodeslot=0xFF3E,
+ },
+ [0xFF3F]={
+ category="pc",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x5F },
+ unicodeslot=0xFF3F,
+ },
+ [0xFF40]={
+ category="sk",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x60 },
+ unicodeslot=0xFF40,
+ },
+ [0xFF41]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x61 },
+ unicodeslot=0xFF41,
+ },
+ [0xFF42]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x62 },
+ unicodeslot=0xFF42,
+ },
+ [0xFF43]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x63 },
+ unicodeslot=0xFF43,
+ },
+ [0xFF44]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x64 },
+ unicodeslot=0xFF44,
+ },
+ [0xFF45]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x65 },
+ unicodeslot=0xFF45,
+ },
+ [0xFF46]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x66 },
+ unicodeslot=0xFF46,
+ },
+ [0xFF47]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x67 },
+ unicodeslot=0xFF47,
+ },
+ [0xFF48]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x68 },
+ unicodeslot=0xFF48,
+ },
+ [0xFF49]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x69 },
+ unicodeslot=0xFF49,
+ },
+ [0xFF4A]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x6A },
+ unicodeslot=0xFF4A,
+ },
+ [0xFF4B]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x6B },
+ unicodeslot=0xFF4B,
+ },
+ [0xFF4C]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x6C },
+ unicodeslot=0xFF4C,
+ },
+ [0xFF4D]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x6D },
+ unicodeslot=0xFF4D,
+ },
+ [0xFF4E]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x6E },
+ unicodeslot=0xFF4E,
+ },
+ [0xFF4F]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x6F },
+ unicodeslot=0xFF4F,
+ },
+ [0xFF50]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x70 },
+ unicodeslot=0xFF50,
+ },
+ [0xFF51]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x71 },
+ unicodeslot=0xFF51,
+ },
+ [0xFF52]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x72 },
+ unicodeslot=0xFF52,
+ },
+ [0xFF53]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x73 },
+ unicodeslot=0xFF53,
+ },
+ [0xFF54]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x74 },
+ unicodeslot=0xFF54,
+ },
+ [0xFF55]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x75 },
+ unicodeslot=0xFF55,
+ },
+ [0xFF56]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x76 },
+ unicodeslot=0xFF56,
+ },
+ [0xFF57]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x77 },
+ unicodeslot=0xFF57,
+ },
+ [0xFF58]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x78 },
+ unicodeslot=0xFF58,
+ },
+ [0xFF59]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x79 },
+ unicodeslot=0xFF59,
+ },
+ [0xFF5A]={
+ category="ll",
+ direction="l",
+ linebreak="id",
+ specials={ "wide", 0x7A },
+ unicodeslot=0xFF5A,
+ },
+ [0xFF5B]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFF5D,
+ specials={ "wide", 0x7B },
+ textclass="open",
+ unicodeslot=0xFF5B,
+ },
+ [0xFF5C]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x7C },
+ unicodeslot=0xFF5C,
+ },
+ [0xFF5D]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFF5B,
+ specials={ "wide", 0x7D },
+ textclass="close",
+ unicodeslot=0xFF5D,
+ },
+ [0xFF5E]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0x7E },
+ unicodeslot=0xFF5E,
+ },
+ [0xFF5F]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFF60,
+ specials={ "wide", 0x2985 },
+ textclass="open",
+ unicodeslot=0xFF5F,
+ },
+ [0xFF60]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFF5F,
+ specials={ "wide", 0x2986 },
+ textclass="close",
+ unicodeslot=0xFF60,
+ },
+ [0xFF61]={
+ category="po",
+ direction="on",
+ linebreak="cl",
+ specials={ "narrow", 0x3002 },
+ unicodeslot=0xFF61,
+ },
+ [0xFF62]={
+ category="ps",
+ direction="on",
+ linebreak="op",
+ mirror=0xFF63,
+ specials={ "narrow", 0x300C },
+ textclass="open",
+ unicodeslot=0xFF62,
+ },
+ [0xFF63]={
+ category="pe",
+ direction="on",
+ linebreak="cl",
+ mirror=0xFF62,
+ specials={ "narrow", 0x300D },
+ textclass="close",
+ unicodeslot=0xFF63,
+ },
+ [0xFF64]={
+ category="po",
+ direction="on",
+ linebreak="cl",
+ specials={ "narrow", 0x3001 },
+ unicodeslot=0xFF64,
+ },
+ [0xFF65]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ specials={ "narrow", 0x30FB },
+ unicodeslot=0xFF65,
+ },
+ [0xFF66]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30F2 },
+ unicodeslot=0xFF66,
+ },
+ [0xFF67]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30A1 },
+ unicodeslot=0xFF67,
+ },
+ [0xFF68]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30A3 },
+ unicodeslot=0xFF68,
+ },
+ [0xFF69]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30A5 },
+ unicodeslot=0xFF69,
+ },
+ [0xFF6A]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30A7 },
+ unicodeslot=0xFF6A,
+ },
+ [0xFF6B]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30A9 },
+ unicodeslot=0xFF6B,
+ },
+ [0xFF6C]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30E3 },
+ unicodeslot=0xFF6C,
+ },
+ [0xFF6D]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30E5 },
+ unicodeslot=0xFF6D,
+ },
+ [0xFF6E]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30E7 },
+ unicodeslot=0xFF6E,
+ },
+ [0xFF6F]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30C3 },
+ unicodeslot=0xFF6F,
+ },
+ [0xFF70]={
+ category="lm",
+ direction="l",
+ linebreak="cj",
+ specials={ "narrow", 0x30FC },
+ unicodeslot=0xFF70,
+ },
+ [0xFF71]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30A2 },
+ unicodeslot=0xFF71,
+ },
+ [0xFF72]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30A4 },
+ unicodeslot=0xFF72,
+ },
+ [0xFF73]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30A6 },
+ unicodeslot=0xFF73,
+ },
+ [0xFF74]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30A8 },
+ unicodeslot=0xFF74,
+ },
+ [0xFF75]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30AA },
+ unicodeslot=0xFF75,
+ },
+ [0xFF76]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30AB },
+ unicodeslot=0xFF76,
+ },
+ [0xFF77]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30AD },
+ unicodeslot=0xFF77,
+ },
+ [0xFF78]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30AF },
+ unicodeslot=0xFF78,
+ },
+ [0xFF79]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30B1 },
+ unicodeslot=0xFF79,
+ },
+ [0xFF7A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30B3 },
+ unicodeslot=0xFF7A,
+ },
+ [0xFF7B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30B5 },
+ unicodeslot=0xFF7B,
+ },
+ [0xFF7C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30B7 },
+ unicodeslot=0xFF7C,
+ },
+ [0xFF7D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30B9 },
+ unicodeslot=0xFF7D,
+ },
+ [0xFF7E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30BB },
+ unicodeslot=0xFF7E,
+ },
+ [0xFF7F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30BD },
+ unicodeslot=0xFF7F,
+ },
+ [0xFF80]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30BF },
+ unicodeslot=0xFF80,
+ },
+ [0xFF81]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30C1 },
+ unicodeslot=0xFF81,
+ },
+ [0xFF82]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30C4 },
+ unicodeslot=0xFF82,
+ },
+ [0xFF83]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30C6 },
+ unicodeslot=0xFF83,
+ },
+ [0xFF84]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30C8 },
+ unicodeslot=0xFF84,
+ },
+ [0xFF85]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30CA },
+ unicodeslot=0xFF85,
+ },
+ [0xFF86]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30CB },
+ unicodeslot=0xFF86,
+ },
+ [0xFF87]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30CC },
+ unicodeslot=0xFF87,
+ },
+ [0xFF88]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30CD },
+ unicodeslot=0xFF88,
+ },
+ [0xFF89]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30CE },
+ unicodeslot=0xFF89,
+ },
+ [0xFF8A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30CF },
+ unicodeslot=0xFF8A,
+ },
+ [0xFF8B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30D2 },
+ unicodeslot=0xFF8B,
+ },
+ [0xFF8C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30D5 },
+ unicodeslot=0xFF8C,
+ },
+ [0xFF8D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30D8 },
+ unicodeslot=0xFF8D,
+ },
+ [0xFF8E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30DB },
+ unicodeslot=0xFF8E,
+ },
+ [0xFF8F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30DE },
+ unicodeslot=0xFF8F,
+ },
+ [0xFF90]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30DF },
+ unicodeslot=0xFF90,
+ },
+ [0xFF91]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E0 },
+ unicodeslot=0xFF91,
+ },
+ [0xFF92]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E1 },
+ unicodeslot=0xFF92,
+ },
+ [0xFF93]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E2 },
+ unicodeslot=0xFF93,
+ },
+ [0xFF94]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E4 },
+ unicodeslot=0xFF94,
+ },
+ [0xFF95]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E6 },
+ unicodeslot=0xFF95,
+ },
+ [0xFF96]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E8 },
+ unicodeslot=0xFF96,
+ },
+ [0xFF97]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30E9 },
+ unicodeslot=0xFF97,
+ },
+ [0xFF98]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30EA },
+ unicodeslot=0xFF98,
+ },
+ [0xFF99]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30EB },
+ unicodeslot=0xFF99,
+ },
+ [0xFF9A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30EC },
+ unicodeslot=0xFF9A,
+ },
+ [0xFF9B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30ED },
+ unicodeslot=0xFF9B,
+ },
+ [0xFF9C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30EF },
+ unicodeslot=0xFF9C,
+ },
+ [0xFF9D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x30F3 },
+ unicodeslot=0xFF9D,
+ },
+ [0xFF9E]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ specials={ "narrow", 0x3099 },
+ unicodeslot=0xFF9E,
+ },
+ [0xFF9F]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ specials={ "narrow", 0x309A },
+ unicodeslot=0xFF9F,
+ },
+ [0xFFA0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3164 },
+ unicodeslot=0xFFA0,
+ },
+ [0xFFA1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3131 },
+ unicodeslot=0xFFA1,
+ },
+ [0xFFA2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3132 },
+ unicodeslot=0xFFA2,
+ },
+ [0xFFA3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3133 },
+ unicodeslot=0xFFA3,
+ },
+ [0xFFA4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3134 },
+ unicodeslot=0xFFA4,
+ },
+ [0xFFA5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3135 },
+ unicodeslot=0xFFA5,
+ },
+ [0xFFA6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3136 },
+ unicodeslot=0xFFA6,
+ },
+ [0xFFA7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3137 },
+ unicodeslot=0xFFA7,
+ },
+ [0xFFA8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3138 },
+ unicodeslot=0xFFA8,
+ },
+ [0xFFA9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3139 },
+ unicodeslot=0xFFA9,
+ },
+ [0xFFAA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x313A },
+ unicodeslot=0xFFAA,
+ },
+ [0xFFAB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x313B },
+ unicodeslot=0xFFAB,
+ },
+ [0xFFAC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x313C },
+ unicodeslot=0xFFAC,
+ },
+ [0xFFAD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x313D },
+ unicodeslot=0xFFAD,
+ },
+ [0xFFAE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x313E },
+ unicodeslot=0xFFAE,
+ },
+ [0xFFAF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x313F },
+ unicodeslot=0xFFAF,
+ },
+ [0xFFB0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3140 },
+ unicodeslot=0xFFB0,
+ },
+ [0xFFB1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3141 },
+ unicodeslot=0xFFB1,
+ },
+ [0xFFB2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3142 },
+ unicodeslot=0xFFB2,
+ },
+ [0xFFB3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3143 },
+ unicodeslot=0xFFB3,
+ },
+ [0xFFB4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3144 },
+ unicodeslot=0xFFB4,
+ },
+ [0xFFB5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3145 },
+ unicodeslot=0xFFB5,
+ },
+ [0xFFB6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3146 },
+ unicodeslot=0xFFB6,
+ },
+ [0xFFB7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3147 },
+ unicodeslot=0xFFB7,
+ },
+ [0xFFB8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3148 },
+ unicodeslot=0xFFB8,
+ },
+ [0xFFB9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3149 },
+ unicodeslot=0xFFB9,
+ },
+ [0xFFBA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x314A },
+ unicodeslot=0xFFBA,
+ },
+ [0xFFBB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x314B },
+ unicodeslot=0xFFBB,
+ },
+ [0xFFBC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x314C },
+ unicodeslot=0xFFBC,
+ },
+ [0xFFBD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x314D },
+ unicodeslot=0xFFBD,
+ },
+ [0xFFBE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x314E },
+ unicodeslot=0xFFBE,
+ },
+ [0xFFC2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x314F },
+ unicodeslot=0xFFC2,
+ },
+ [0xFFC3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3150 },
+ unicodeslot=0xFFC3,
+ },
+ [0xFFC4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3151 },
+ unicodeslot=0xFFC4,
+ },
+ [0xFFC5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3152 },
+ unicodeslot=0xFFC5,
+ },
+ [0xFFC6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3153 },
+ unicodeslot=0xFFC6,
+ },
+ [0xFFC7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3154 },
+ unicodeslot=0xFFC7,
+ },
+ [0xFFCA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3155 },
+ unicodeslot=0xFFCA,
+ },
+ [0xFFCB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3156 },
+ unicodeslot=0xFFCB,
+ },
+ [0xFFCC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3157 },
+ unicodeslot=0xFFCC,
+ },
+ [0xFFCD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3158 },
+ unicodeslot=0xFFCD,
+ },
+ [0xFFCE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3159 },
+ unicodeslot=0xFFCE,
+ },
+ [0xFFCF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x315A },
+ unicodeslot=0xFFCF,
+ },
+ [0xFFD2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x315B },
+ unicodeslot=0xFFD2,
+ },
+ [0xFFD3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x315C },
+ unicodeslot=0xFFD3,
+ },
+ [0xFFD4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x315D },
+ unicodeslot=0xFFD4,
+ },
+ [0xFFD5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x315E },
+ unicodeslot=0xFFD5,
+ },
+ [0xFFD6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x315F },
+ unicodeslot=0xFFD6,
+ },
+ [0xFFD7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3160 },
+ unicodeslot=0xFFD7,
+ },
+ [0xFFDA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3161 },
+ unicodeslot=0xFFDA,
+ },
+ [0xFFDB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3162 },
+ unicodeslot=0xFFDB,
+ },
+ [0xFFDC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "narrow", 0x3163 },
+ unicodeslot=0xFFDC,
+ },
+ [0xFFE0]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ specials={ "wide", 0xA2 },
+ unicodeslot=0xFFE0,
+ },
+ [0xFFE1]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ specials={ "wide", 0xA3 },
+ unicodeslot=0xFFE1,
+ },
+ [0xFFE2]={
+ category="sm",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0xAC },
+ unicodeslot=0xFFE2,
+ },
+ [0xFFE3]={
+ category="sk",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0xAF },
+ unicodeslot=0xFFE3,
+ },
+ [0xFFE4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ specials={ "wide", 0xA6 },
+ unicodeslot=0xFFE4,
+ },
+ [0xFFE5]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ specials={ "wide", 0xA5 },
+ unicodeslot=0xFFE5,
+ },
+ [0xFFE6]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ specials={ "wide", 0x20A9 },
+ unicodeslot=0xFFE6,
+ },
+ [0xFFE8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x2502 },
+ unicodeslot=0xFFE8,
+ },
+ [0xFFE9]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x2190 },
+ unicodeslot=0xFFE9,
+ },
+ [0xFFEA]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x2191 },
+ unicodeslot=0xFFEA,
+ },
+ [0xFFEB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x2192 },
+ unicodeslot=0xFFEB,
+ },
+ [0xFFEC]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x2193 },
+ unicodeslot=0xFFEC,
+ },
+ [0xFFED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x25A0 },
+ unicodeslot=0xFFED,
+ },
+ [0xFFEE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "narrow", 0x25CB },
+ unicodeslot=0xFFEE,
+ },
+ [0xFFF9]={
+ category="cf",
+ direction="on",
+ linebreak="cm",
+ unicodeslot=0xFFF9,
+ },
+ [0xFFFA]={
+ category="cf",
+ direction="on",
+ linebreak="cm",
+ unicodeslot=0xFFFA,
+ },
+ [0xFFFB]={
+ category="cf",
+ direction="on",
+ linebreak="cm",
+ unicodeslot=0xFFFB,
+ },
+ [0xFFFC]={
+ category="so",
+ direction="on",
+ linebreak="cb",
+ unicodeslot=0xFFFC,
+ },
+ [0xFFFD]={
+ category="so",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0xFFFD,
+ },
+ [0x10000]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10000,
+ },
+ [0x10001]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10001,
+ },
+ [0x10002]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10002,
+ },
+ [0x10003]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10003,
+ },
+ [0x10004]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10004,
+ },
+ [0x10005]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10005,
+ },
+ [0x10006]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10006,
+ },
+ [0x10007]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10007,
+ },
+ [0x10008]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10008,
+ },
+ [0x10009]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10009,
+ },
+ [0x1000A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1000A,
+ },
+ [0x1000B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1000B,
+ },
+ [0x1000D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1000D,
+ },
+ [0x1000E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1000E,
+ },
+ [0x1000F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1000F,
+ },
+ [0x10010]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10010,
+ },
+ [0x10011]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10011,
+ },
+ [0x10012]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10012,
+ },
+ [0x10013]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10013,
+ },
+ [0x10014]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10014,
+ },
+ [0x10015]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10015,
+ },
+ [0x10016]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10016,
+ },
+ [0x10017]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10017,
+ },
+ [0x10018]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10018,
+ },
+ [0x10019]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10019,
+ },
+ [0x1001A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1001A,
+ },
+ [0x1001B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1001B,
+ },
+ [0x1001C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1001C,
+ },
+ [0x1001D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1001D,
+ },
+ [0x1001E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1001E,
+ },
+ [0x1001F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1001F,
+ },
+ [0x10020]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10020,
+ },
+ [0x10021]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10021,
+ },
+ [0x10022]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10022,
+ },
+ [0x10023]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10023,
+ },
+ [0x10024]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10024,
+ },
+ [0x10025]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10025,
+ },
+ [0x10026]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10026,
+ },
+ [0x10028]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10028,
+ },
+ [0x10029]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10029,
+ },
+ [0x1002A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1002A,
+ },
+ [0x1002B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1002B,
+ },
+ [0x1002C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1002C,
+ },
+ [0x1002D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1002D,
+ },
+ [0x1002E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1002E,
+ },
+ [0x1002F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1002F,
+ },
+ [0x10030]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10030,
+ },
+ [0x10031]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10031,
+ },
+ [0x10032]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10032,
+ },
+ [0x10033]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10033,
+ },
+ [0x10034]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10034,
+ },
+ [0x10035]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10035,
+ },
+ [0x10036]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10036,
+ },
+ [0x10037]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10037,
+ },
+ [0x10038]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10038,
+ },
+ [0x10039]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10039,
+ },
+ [0x1003A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1003A,
+ },
+ [0x1003C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1003C,
+ },
+ [0x1003D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1003D,
+ },
+ [0x1003F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1003F,
+ },
+ [0x10040]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10040,
+ },
+ [0x10041]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10041,
+ },
+ [0x10042]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10042,
+ },
+ [0x10043]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10043,
+ },
+ [0x10044]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10044,
+ },
+ [0x10045]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10045,
+ },
+ [0x10046]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10046,
+ },
+ [0x10047]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10047,
+ },
+ [0x10048]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10048,
+ },
+ [0x10049]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10049,
+ },
+ [0x1004A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1004A,
+ },
+ [0x1004B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1004B,
+ },
+ [0x1004C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1004C,
+ },
+ [0x1004D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1004D,
+ },
+ [0x10050]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10050,
+ },
+ [0x10051]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10051,
+ },
+ [0x10052]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10052,
+ },
+ [0x10053]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10053,
+ },
+ [0x10054]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10054,
+ },
+ [0x10055]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10055,
+ },
+ [0x10056]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10056,
+ },
+ [0x10057]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10057,
+ },
+ [0x10058]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10058,
+ },
+ [0x10059]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10059,
+ },
+ [0x1005A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1005A,
+ },
+ [0x1005B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1005B,
+ },
+ [0x1005C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1005C,
+ },
+ [0x1005D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1005D,
+ },
+ [0x10080]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10080,
+ },
+ [0x10081]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10081,
+ },
+ [0x10082]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10082,
+ },
+ [0x10083]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10083,
+ },
+ [0x10084]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10084,
+ },
+ [0x10085]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10085,
+ },
+ [0x10086]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10086,
+ },
+ [0x10087]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10087,
+ },
+ [0x10088]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10088,
+ },
+ [0x10089]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10089,
+ },
+ [0x1008A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1008A,
+ },
+ [0x1008B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1008B,
+ },
+ [0x1008C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1008C,
+ },
+ [0x1008D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1008D,
+ },
+ [0x1008E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1008E,
+ },
+ [0x1008F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1008F,
+ },
+ [0x10090]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10090,
+ },
+ [0x10091]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10091,
+ },
+ [0x10092]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10092,
+ },
+ [0x10093]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10093,
+ },
+ [0x10094]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10094,
+ },
+ [0x10095]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10095,
+ },
+ [0x10096]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10096,
+ },
+ [0x10097]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10097,
+ },
+ [0x10098]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10098,
+ },
+ [0x10099]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10099,
+ },
+ [0x1009A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1009A,
+ },
+ [0x1009B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1009B,
+ },
+ [0x1009C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1009C,
+ },
+ [0x1009D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1009D,
+ },
+ [0x1009E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1009E,
+ },
+ [0x1009F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1009F,
+ },
+ [0x100A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A0,
+ },
+ [0x100A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A1,
+ },
+ [0x100A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A2,
+ },
+ [0x100A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A3,
+ },
+ [0x100A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A4,
+ },
+ [0x100A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A5,
+ },
+ [0x100A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A6,
+ },
+ [0x100A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A7,
+ },
+ [0x100A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A8,
+ },
+ [0x100A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100A9,
+ },
+ [0x100AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100AA,
+ },
+ [0x100AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100AB,
+ },
+ [0x100AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100AC,
+ },
+ [0x100AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100AD,
+ },
+ [0x100AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100AE,
+ },
+ [0x100AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100AF,
+ },
+ [0x100B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B0,
+ },
+ [0x100B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B1,
+ },
+ [0x100B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B2,
+ },
+ [0x100B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B3,
+ },
+ [0x100B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B4,
+ },
+ [0x100B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B5,
+ },
+ [0x100B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B6,
+ },
+ [0x100B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B7,
+ },
+ [0x100B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B8,
+ },
+ [0x100B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100B9,
+ },
+ [0x100BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100BA,
+ },
+ [0x100BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100BB,
+ },
+ [0x100BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100BC,
+ },
+ [0x100BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100BD,
+ },
+ [0x100BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100BE,
+ },
+ [0x100BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100BF,
+ },
+ [0x100C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C0,
+ },
+ [0x100C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C1,
+ },
+ [0x100C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C2,
+ },
+ [0x100C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C3,
+ },
+ [0x100C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C4,
+ },
+ [0x100C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C5,
+ },
+ [0x100C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C6,
+ },
+ [0x100C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C7,
+ },
+ [0x100C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C8,
+ },
+ [0x100C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100C9,
+ },
+ [0x100CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100CA,
+ },
+ [0x100CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100CB,
+ },
+ [0x100CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100CC,
+ },
+ [0x100CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100CD,
+ },
+ [0x100CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100CE,
+ },
+ [0x100CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100CF,
+ },
+ [0x100D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D0,
+ },
+ [0x100D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D1,
+ },
+ [0x100D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D2,
+ },
+ [0x100D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D3,
+ },
+ [0x100D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D4,
+ },
+ [0x100D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D5,
+ },
+ [0x100D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D6,
+ },
+ [0x100D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D7,
+ },
+ [0x100D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D8,
+ },
+ [0x100D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100D9,
+ },
+ [0x100DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100DA,
+ },
+ [0x100DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100DB,
+ },
+ [0x100DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100DC,
+ },
+ [0x100DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100DD,
+ },
+ [0x100DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100DE,
+ },
+ [0x100DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100DF,
+ },
+ [0x100E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E0,
+ },
+ [0x100E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E1,
+ },
+ [0x100E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E2,
+ },
+ [0x100E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E3,
+ },
+ [0x100E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E4,
+ },
+ [0x100E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E5,
+ },
+ [0x100E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E6,
+ },
+ [0x100E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E7,
+ },
+ [0x100E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E8,
+ },
+ [0x100E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100E9,
+ },
+ [0x100EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100EA,
+ },
+ [0x100EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100EB,
+ },
+ [0x100EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100EC,
+ },
+ [0x100ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100ED,
+ },
+ [0x100EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100EE,
+ },
+ [0x100EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100EF,
+ },
+ [0x100F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F0,
+ },
+ [0x100F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F1,
+ },
+ [0x100F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F2,
+ },
+ [0x100F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F3,
+ },
+ [0x100F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F4,
+ },
+ [0x100F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F5,
+ },
+ [0x100F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F6,
+ },
+ [0x100F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F7,
+ },
+ [0x100F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F8,
+ },
+ [0x100F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100F9,
+ },
+ [0x100FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x100FA,
+ },
+ [0x10100]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x10100,
+ },
+ [0x10101]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10101,
+ },
+ [0x10102]={
+ category="so",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x10102,
+ },
+ [0x10107]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10107,
+ },
+ [0x10108]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10108,
+ },
+ [0x10109]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10109,
+ },
+ [0x1010A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1010A,
+ },
+ [0x1010B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1010B,
+ },
+ [0x1010C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1010C,
+ },
+ [0x1010D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1010D,
+ },
+ [0x1010E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1010E,
+ },
+ [0x1010F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1010F,
+ },
+ [0x10110]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10110,
+ },
+ [0x10111]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10111,
+ },
+ [0x10112]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10112,
+ },
+ [0x10113]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10113,
+ },
+ [0x10114]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10114,
+ },
+ [0x10115]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10115,
+ },
+ [0x10116]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10116,
+ },
+ [0x10117]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10117,
+ },
+ [0x10118]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10118,
+ },
+ [0x10119]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10119,
+ },
+ [0x1011A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1011A,
+ },
+ [0x1011B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1011B,
+ },
+ [0x1011C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1011C,
+ },
+ [0x1011D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1011D,
+ },
+ [0x1011E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1011E,
+ },
+ [0x1011F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1011F,
+ },
+ [0x10120]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10120,
+ },
+ [0x10121]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10121,
+ },
+ [0x10122]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10122,
+ },
+ [0x10123]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10123,
+ },
+ [0x10124]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10124,
+ },
+ [0x10125]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10125,
+ },
+ [0x10126]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10126,
+ },
+ [0x10127]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10127,
+ },
+ [0x10128]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10128,
+ },
+ [0x10129]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10129,
+ },
+ [0x1012A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1012A,
+ },
+ [0x1012B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1012B,
+ },
+ [0x1012C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1012C,
+ },
+ [0x1012D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1012D,
+ },
+ [0x1012E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1012E,
+ },
+ [0x1012F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1012F,
+ },
+ [0x10130]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10130,
+ },
+ [0x10131]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10131,
+ },
+ [0x10132]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10132,
+ },
+ [0x10133]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10133,
+ },
+ [0x10137]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10137,
+ },
+ [0x10138]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10138,
+ },
+ [0x10139]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10139,
+ },
+ [0x1013A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1013A,
+ },
+ [0x1013B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1013B,
+ },
+ [0x1013C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1013C,
+ },
+ [0x1013D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1013D,
+ },
+ [0x1013E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1013E,
+ },
+ [0x1013F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1013F,
+ },
+ [0x10140]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10140,
+ },
+ [0x10141]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10141,
+ },
+ [0x10142]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10142,
+ },
+ [0x10143]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10143,
+ },
+ [0x10144]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10144,
+ },
+ [0x10145]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10145,
+ },
+ [0x10146]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10146,
+ },
+ [0x10147]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10147,
+ },
+ [0x10148]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10148,
+ },
+ [0x10149]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10149,
+ },
+ [0x1014A]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1014A,
+ },
+ [0x1014B]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1014B,
+ },
+ [0x1014C]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1014C,
+ },
+ [0x1014D]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1014D,
+ },
+ [0x1014E]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1014E,
+ },
+ [0x1014F]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1014F,
+ },
+ [0x10150]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10150,
+ },
+ [0x10151]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10151,
+ },
+ [0x10152]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10152,
+ },
+ [0x10153]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10153,
+ },
+ [0x10154]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10154,
+ },
+ [0x10155]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10155,
+ },
+ [0x10156]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10156,
+ },
+ [0x10157]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10157,
+ },
+ [0x10158]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10158,
+ },
+ [0x10159]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10159,
+ },
+ [0x1015A]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1015A,
+ },
+ [0x1015B]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1015B,
+ },
+ [0x1015C]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1015C,
+ },
+ [0x1015D]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1015D,
+ },
+ [0x1015E]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1015E,
+ },
+ [0x1015F]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1015F,
+ },
+ [0x10160]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10160,
+ },
+ [0x10161]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10161,
+ },
+ [0x10162]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10162,
+ },
+ [0x10163]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10163,
+ },
+ [0x10164]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10164,
+ },
+ [0x10165]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10165,
+ },
+ [0x10166]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10166,
+ },
+ [0x10167]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10167,
+ },
+ [0x10168]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10168,
+ },
+ [0x10169]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10169,
+ },
+ [0x1016A]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1016A,
+ },
+ [0x1016B]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1016B,
+ },
+ [0x1016C]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1016C,
+ },
+ [0x1016D]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1016D,
+ },
+ [0x1016E]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1016E,
+ },
+ [0x1016F]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1016F,
+ },
+ [0x10170]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10170,
+ },
+ [0x10171]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10171,
+ },
+ [0x10172]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10172,
+ },
+ [0x10173]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10173,
+ },
+ [0x10174]={
+ category="nl",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10174,
+ },
+ [0x10175]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10175,
+ },
+ [0x10176]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10176,
+ },
+ [0x10177]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10177,
+ },
+ [0x10178]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10178,
+ },
+ [0x10179]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10179,
+ },
+ [0x1017A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1017A,
+ },
+ [0x1017B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1017B,
+ },
+ [0x1017C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1017C,
+ },
+ [0x1017D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1017D,
+ },
+ [0x1017E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1017E,
+ },
+ [0x1017F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1017F,
+ },
+ [0x10180]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10180,
+ },
+ [0x10181]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10181,
+ },
+ [0x10182]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10182,
+ },
+ [0x10183]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10183,
+ },
+ [0x10184]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10184,
+ },
+ [0x10185]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10185,
+ },
+ [0x10186]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10186,
+ },
+ [0x10187]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10187,
+ },
+ [0x10188]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10188,
+ },
+ [0x10189]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10189,
+ },
+ [0x1018A]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1018A,
+ },
+ [0x1018B]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1018B,
+ },
+ [0x1018C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1018C,
+ },
+ [0x1018D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1018D,
+ },
+ [0x1018E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1018E,
+ },
+ [0x10190]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10190,
+ },
+ [0x10191]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10191,
+ },
+ [0x10192]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10192,
+ },
+ [0x10193]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10193,
+ },
+ [0x10194]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10194,
+ },
+ [0x10195]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10195,
+ },
+ [0x10196]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10196,
+ },
+ [0x10197]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10197,
+ },
+ [0x10198]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10198,
+ },
+ [0x10199]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x10199,
+ },
+ [0x1019A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1019A,
+ },
+ [0x1019B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1019B,
+ },
+ [0x101A0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x101A0,
+ },
+ [0x101D0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D0,
+ },
+ [0x101D1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D1,
+ },
+ [0x101D2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D2,
+ },
+ [0x101D3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D3,
+ },
+ [0x101D4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D4,
+ },
+ [0x101D5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D5,
+ },
+ [0x101D6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D6,
+ },
+ [0x101D7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D7,
+ },
+ [0x101D8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D8,
+ },
+ [0x101D9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101D9,
+ },
+ [0x101DA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101DA,
+ },
+ [0x101DB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101DB,
+ },
+ [0x101DC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101DC,
+ },
+ [0x101DD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101DD,
+ },
+ [0x101DE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101DE,
+ },
+ [0x101DF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101DF,
+ },
+ [0x101E0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E0,
+ },
+ [0x101E1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E1,
+ },
+ [0x101E2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E2,
+ },
+ [0x101E3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E3,
+ },
+ [0x101E4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E4,
+ },
+ [0x101E5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E5,
+ },
+ [0x101E6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E6,
+ },
+ [0x101E7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E7,
+ },
+ [0x101E8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E8,
+ },
+ [0x101E9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101E9,
+ },
+ [0x101EA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101EA,
+ },
+ [0x101EB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101EB,
+ },
+ [0x101EC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101EC,
+ },
+ [0x101ED]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101ED,
+ },
+ [0x101EE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101EE,
+ },
+ [0x101EF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101EF,
+ },
+ [0x101F0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F0,
+ },
+ [0x101F1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F1,
+ },
+ [0x101F2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F2,
+ },
+ [0x101F3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F3,
+ },
+ [0x101F4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F4,
+ },
+ [0x101F5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F5,
+ },
+ [0x101F6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F6,
+ },
+ [0x101F7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F7,
+ },
+ [0x101F8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F8,
+ },
+ [0x101F9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101F9,
+ },
+ [0x101FA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101FA,
+ },
+ [0x101FB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101FB,
+ },
+ [0x101FC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x101FC,
+ },
+ [0x101FD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x101FD,
+ },
+ [0x10280]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10280,
+ },
+ [0x10281]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10281,
+ },
+ [0x10282]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10282,
+ },
+ [0x10283]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10283,
+ },
+ [0x10284]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10284,
+ },
+ [0x10285]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10285,
+ },
+ [0x10286]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10286,
+ },
+ [0x10287]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10287,
+ },
+ [0x10288]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10288,
+ },
+ [0x10289]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10289,
+ },
+ [0x1028A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1028A,
+ },
+ [0x1028B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1028B,
+ },
+ [0x1028C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1028C,
+ },
+ [0x1028D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1028D,
+ },
+ [0x1028E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1028E,
+ },
+ [0x1028F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1028F,
+ },
+ [0x10290]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10290,
+ },
+ [0x10291]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10291,
+ },
+ [0x10292]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10292,
+ },
+ [0x10293]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10293,
+ },
+ [0x10294]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10294,
+ },
+ [0x10295]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10295,
+ },
+ [0x10296]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10296,
+ },
+ [0x10297]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10297,
+ },
+ [0x10298]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10298,
+ },
+ [0x10299]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10299,
+ },
+ [0x1029A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1029A,
+ },
+ [0x1029B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1029B,
+ },
+ [0x1029C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1029C,
+ },
+ [0x102A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A0,
+ },
+ [0x102A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A1,
+ },
+ [0x102A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A2,
+ },
+ [0x102A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A3,
+ },
+ [0x102A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A4,
+ },
+ [0x102A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A5,
+ },
+ [0x102A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A6,
+ },
+ [0x102A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A7,
+ },
+ [0x102A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A8,
+ },
+ [0x102A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102A9,
+ },
+ [0x102AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102AA,
+ },
+ [0x102AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102AB,
+ },
+ [0x102AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102AC,
+ },
+ [0x102AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102AD,
+ },
+ [0x102AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102AE,
+ },
+ [0x102AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102AF,
+ },
+ [0x102B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B0,
+ },
+ [0x102B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B1,
+ },
+ [0x102B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B2,
+ },
+ [0x102B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B3,
+ },
+ [0x102B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B4,
+ },
+ [0x102B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B5,
+ },
+ [0x102B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B6,
+ },
+ [0x102B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B7,
+ },
+ [0x102B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B8,
+ },
+ [0x102B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102B9,
+ },
+ [0x102BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102BA,
+ },
+ [0x102BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102BB,
+ },
+ [0x102BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102BC,
+ },
+ [0x102BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102BD,
+ },
+ [0x102BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102BE,
+ },
+ [0x102BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102BF,
+ },
+ [0x102C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C0,
+ },
+ [0x102C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C1,
+ },
+ [0x102C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C2,
+ },
+ [0x102C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C3,
+ },
+ [0x102C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C4,
+ },
+ [0x102C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C5,
+ },
+ [0x102C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C6,
+ },
+ [0x102C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C7,
+ },
+ [0x102C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C8,
+ },
+ [0x102C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102C9,
+ },
+ [0x102CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102CA,
+ },
+ [0x102CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102CB,
+ },
+ [0x102CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102CC,
+ },
+ [0x102CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102CD,
+ },
+ [0x102CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102CE,
+ },
+ [0x102CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102CF,
+ },
+ [0x102D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x102D0,
+ },
+ [0x102E0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x102E0,
+ },
+ [0x102E1]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E1,
+ },
+ [0x102E2]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E2,
+ },
+ [0x102E3]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E3,
+ },
+ [0x102E4]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E4,
+ },
+ [0x102E5]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E5,
+ },
+ [0x102E6]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E6,
+ },
+ [0x102E7]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E7,
+ },
+ [0x102E8]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E8,
+ },
+ [0x102E9]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102E9,
+ },
+ [0x102EA]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102EA,
+ },
+ [0x102EB]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102EB,
+ },
+ [0x102EC]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102EC,
+ },
+ [0x102ED]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102ED,
+ },
+ [0x102EE]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102EE,
+ },
+ [0x102EF]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102EF,
+ },
+ [0x102F0]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F0,
+ },
+ [0x102F1]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F1,
+ },
+ [0x102F2]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F2,
+ },
+ [0x102F3]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F3,
+ },
+ [0x102F4]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F4,
+ },
+ [0x102F5]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F5,
+ },
+ [0x102F6]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F6,
+ },
+ [0x102F7]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F7,
+ },
+ [0x102F8]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F8,
+ },
+ [0x102F9]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102F9,
+ },
+ [0x102FA]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102FA,
+ },
+ [0x102FB]={
+ category="no",
+ direction="en",
+ linebreak="al",
+ unicodeslot=0x102FB,
+ },
+ [0x10300]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10300,
+ },
+ [0x10301]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10301,
+ },
+ [0x10302]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10302,
+ },
+ [0x10303]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10303,
+ },
+ [0x10304]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10304,
+ },
+ [0x10305]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10305,
+ },
+ [0x10306]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10306,
+ },
+ [0x10307]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10307,
+ },
+ [0x10308]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10308,
+ },
+ [0x10309]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10309,
+ },
+ [0x1030A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1030A,
+ },
+ [0x1030B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1030B,
+ },
+ [0x1030C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1030C,
+ },
+ [0x1030D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1030D,
+ },
+ [0x1030E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1030E,
+ },
+ [0x1030F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1030F,
+ },
+ [0x10310]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10310,
+ },
+ [0x10311]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10311,
+ },
+ [0x10312]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10312,
+ },
+ [0x10313]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10313,
+ },
+ [0x10314]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10314,
+ },
+ [0x10315]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10315,
+ },
+ [0x10316]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10316,
+ },
+ [0x10317]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10317,
+ },
+ [0x10318]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10318,
+ },
+ [0x10319]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10319,
+ },
+ [0x1031A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1031A,
+ },
+ [0x1031B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1031B,
+ },
+ [0x1031C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1031C,
+ },
+ [0x1031D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1031D,
+ },
+ [0x1031E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1031E,
+ },
+ [0x1031F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1031F,
+ },
+ [0x10320]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10320,
+ },
+ [0x10321]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10321,
+ },
+ [0x10322]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10322,
+ },
+ [0x10323]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10323,
+ },
+ [0x1032D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1032D,
+ },
+ [0x1032E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1032E,
+ },
+ [0x1032F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1032F,
+ },
+ [0x10330]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10330,
+ },
+ [0x10331]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10331,
+ },
+ [0x10332]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10332,
+ },
+ [0x10333]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10333,
+ },
+ [0x10334]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10334,
+ },
+ [0x10335]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10335,
+ },
+ [0x10336]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10336,
+ },
+ [0x10337]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10337,
+ },
+ [0x10338]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10338,
+ },
+ [0x10339]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10339,
+ },
+ [0x1033A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1033A,
+ },
+ [0x1033B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1033B,
+ },
+ [0x1033C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1033C,
+ },
+ [0x1033D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1033D,
+ },
+ [0x1033E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1033E,
+ },
+ [0x1033F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1033F,
+ },
+ [0x10340]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10340,
+ },
+ [0x10341]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10341,
+ },
+ [0x10342]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10342,
+ },
+ [0x10343]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10343,
+ },
+ [0x10344]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10344,
+ },
+ [0x10345]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10345,
+ },
+ [0x10346]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10346,
+ },
+ [0x10347]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10347,
+ },
+ [0x10348]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10348,
+ },
+ [0x10349]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10349,
+ },
+ [0x1034A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1034A,
+ },
+ [0x10350]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10350,
+ },
+ [0x10351]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10351,
+ },
+ [0x10352]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10352,
+ },
+ [0x10353]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10353,
+ },
+ [0x10354]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10354,
+ },
+ [0x10355]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10355,
+ },
+ [0x10356]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10356,
+ },
+ [0x10357]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10357,
+ },
+ [0x10358]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10358,
+ },
+ [0x10359]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10359,
+ },
+ [0x1035A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1035A,
+ },
+ [0x1035B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1035B,
+ },
+ [0x1035C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1035C,
+ },
+ [0x1035D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1035D,
+ },
+ [0x1035E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1035E,
+ },
+ [0x1035F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1035F,
+ },
+ [0x10360]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10360,
+ },
+ [0x10361]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10361,
+ },
+ [0x10362]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10362,
+ },
+ [0x10363]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10363,
+ },
+ [0x10364]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10364,
+ },
+ [0x10365]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10365,
+ },
+ [0x10366]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10366,
+ },
+ [0x10367]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10367,
+ },
+ [0x10368]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10368,
+ },
+ [0x10369]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10369,
+ },
+ [0x1036A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1036A,
+ },
+ [0x1036B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1036B,
+ },
+ [0x1036C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1036C,
+ },
+ [0x1036D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1036D,
+ },
+ [0x1036E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1036E,
+ },
+ [0x1036F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1036F,
+ },
+ [0x10370]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10370,
+ },
+ [0x10371]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10371,
+ },
+ [0x10372]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10372,
+ },
+ [0x10373]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10373,
+ },
+ [0x10374]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10374,
+ },
+ [0x10375]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10375,
+ },
+ [0x10376]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10376,
+ },
+ [0x10377]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10377,
+ },
+ [0x10378]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10378,
+ },
+ [0x10379]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10379,
+ },
+ [0x1037A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1037A,
+ },
+ [0x10380]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10380,
+ },
+ [0x10381]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10381,
+ },
+ [0x10382]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10382,
+ },
+ [0x10383]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10383,
+ },
+ [0x10384]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10384,
+ },
+ [0x10385]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10385,
+ },
+ [0x10386]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10386,
+ },
+ [0x10387]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10387,
+ },
+ [0x10388]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10388,
+ },
+ [0x10389]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10389,
+ },
+ [0x1038A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1038A,
+ },
+ [0x1038B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1038B,
+ },
+ [0x1038C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1038C,
+ },
+ [0x1038D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1038D,
+ },
+ [0x1038E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1038E,
+ },
+ [0x1038F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1038F,
+ },
+ [0x10390]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10390,
+ },
+ [0x10391]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10391,
+ },
+ [0x10392]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10392,
+ },
+ [0x10393]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10393,
+ },
+ [0x10394]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10394,
+ },
+ [0x10395]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10395,
+ },
+ [0x10396]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10396,
+ },
+ [0x10397]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10397,
+ },
+ [0x10398]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10398,
+ },
+ [0x10399]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10399,
+ },
+ [0x1039A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1039A,
+ },
+ [0x1039B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1039B,
+ },
+ [0x1039C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1039C,
+ },
+ [0x1039D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1039D,
+ },
+ [0x1039F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1039F,
+ },
+ [0x103A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A0,
+ },
+ [0x103A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A1,
+ },
+ [0x103A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A2,
+ },
+ [0x103A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A3,
+ },
+ [0x103A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A4,
+ },
+ [0x103A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A5,
+ },
+ [0x103A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A6,
+ },
+ [0x103A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A7,
+ },
+ [0x103A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A8,
+ },
+ [0x103A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103A9,
+ },
+ [0x103AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103AA,
+ },
+ [0x103AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103AB,
+ },
+ [0x103AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103AC,
+ },
+ [0x103AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103AD,
+ },
+ [0x103AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103AE,
+ },
+ [0x103AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103AF,
+ },
+ [0x103B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B0,
+ },
+ [0x103B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B1,
+ },
+ [0x103B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B2,
+ },
+ [0x103B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B3,
+ },
+ [0x103B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B4,
+ },
+ [0x103B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B5,
+ },
+ [0x103B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B6,
+ },
+ [0x103B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B7,
+ },
+ [0x103B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B8,
+ },
+ [0x103B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103B9,
+ },
+ [0x103BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103BA,
+ },
+ [0x103BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103BB,
+ },
+ [0x103BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103BC,
+ },
+ [0x103BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103BD,
+ },
+ [0x103BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103BE,
+ },
+ [0x103BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103BF,
+ },
+ [0x103C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103C0,
+ },
+ [0x103C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103C1,
+ },
+ [0x103C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103C2,
+ },
+ [0x103C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103C3,
+ },
+ [0x103C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103C8,
+ },
+ [0x103C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103C9,
+ },
+ [0x103CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103CA,
+ },
+ [0x103CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103CB,
+ },
+ [0x103CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103CC,
+ },
+ [0x103CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103CD,
+ },
+ [0x103CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103CE,
+ },
+ [0x103CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103CF,
+ },
+ [0x103D0]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x103D0,
+ },
+ [0x103D1]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103D1,
+ },
+ [0x103D2]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103D2,
+ },
+ [0x103D3]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103D3,
+ },
+ [0x103D4]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103D4,
+ },
+ [0x103D5]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x103D5,
+ },
+ [0x10400]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10400,
+ },
+ [0x10401]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10401,
+ },
+ [0x10402]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10402,
+ },
+ [0x10403]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10403,
+ },
+ [0x10404]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10404,
+ },
+ [0x10405]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10405,
+ },
+ [0x10406]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10406,
+ },
+ [0x10407]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10407,
+ },
+ [0x10408]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10408,
+ },
+ [0x10409]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10409,
+ },
+ [0x1040A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1040A,
+ },
+ [0x1040B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1040B,
+ },
+ [0x1040C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1040C,
+ },
+ [0x1040D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1040D,
+ },
+ [0x1040E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1040E,
+ },
+ [0x1040F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1040F,
+ },
+ [0x10410]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10410,
+ },
+ [0x10411]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10411,
+ },
+ [0x10412]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10412,
+ },
+ [0x10413]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10413,
+ },
+ [0x10414]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10414,
+ },
+ [0x10415]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10415,
+ },
+ [0x10416]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10416,
+ },
+ [0x10417]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10417,
+ },
+ [0x10418]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10418,
+ },
+ [0x10419]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10419,
+ },
+ [0x1041A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1041A,
+ },
+ [0x1041B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1041B,
+ },
+ [0x1041C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1041C,
+ },
+ [0x1041D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1041D,
+ },
+ [0x1041E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1041E,
+ },
+ [0x1041F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1041F,
+ },
+ [0x10420]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10420,
+ },
+ [0x10421]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10421,
+ },
+ [0x10422]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10422,
+ },
+ [0x10423]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10423,
+ },
+ [0x10424]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10424,
+ },
+ [0x10425]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10425,
+ },
+ [0x10426]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10426,
+ },
+ [0x10427]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10427,
+ },
+ [0x10428]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10428,
+ },
+ [0x10429]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10429,
+ },
+ [0x1042A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1042A,
+ },
+ [0x1042B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1042B,
+ },
+ [0x1042C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1042C,
+ },
+ [0x1042D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1042D,
+ },
+ [0x1042E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1042E,
+ },
+ [0x1042F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1042F,
+ },
+ [0x10430]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10430,
+ },
+ [0x10431]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10431,
+ },
+ [0x10432]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10432,
+ },
+ [0x10433]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10433,
+ },
+ [0x10434]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10434,
+ },
+ [0x10435]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10435,
+ },
+ [0x10436]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10436,
+ },
+ [0x10437]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10437,
+ },
+ [0x10438]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10438,
+ },
+ [0x10439]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10439,
+ },
+ [0x1043A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1043A,
+ },
+ [0x1043B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1043B,
+ },
+ [0x1043C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1043C,
+ },
+ [0x1043D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1043D,
+ },
+ [0x1043E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1043E,
+ },
+ [0x1043F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1043F,
+ },
+ [0x10440]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10440,
+ },
+ [0x10441]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10441,
+ },
+ [0x10442]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10442,
+ },
+ [0x10443]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10443,
+ },
+ [0x10444]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10444,
+ },
+ [0x10445]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10445,
+ },
+ [0x10446]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10446,
+ },
+ [0x10447]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10447,
+ },
+ [0x10448]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10448,
+ },
+ [0x10449]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10449,
+ },
+ [0x1044A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1044A,
+ },
+ [0x1044B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1044B,
+ },
+ [0x1044C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1044C,
+ },
+ [0x1044D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1044D,
+ },
+ [0x1044E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1044E,
+ },
+ [0x1044F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1044F,
+ },
+ [0x10450]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10450,
+ },
+ [0x10451]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10451,
+ },
+ [0x10452]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10452,
+ },
+ [0x10453]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10453,
+ },
+ [0x10454]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10454,
+ },
+ [0x10455]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10455,
+ },
+ [0x10456]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10456,
+ },
+ [0x10457]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10457,
+ },
+ [0x10458]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10458,
+ },
+ [0x10459]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10459,
+ },
+ [0x1045A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1045A,
+ },
+ [0x1045B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1045B,
+ },
+ [0x1045C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1045C,
+ },
+ [0x1045D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1045D,
+ },
+ [0x1045E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1045E,
+ },
+ [0x1045F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1045F,
+ },
+ [0x10460]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10460,
+ },
+ [0x10461]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10461,
+ },
+ [0x10462]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10462,
+ },
+ [0x10463]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10463,
+ },
+ [0x10464]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10464,
+ },
+ [0x10465]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10465,
+ },
+ [0x10466]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10466,
+ },
+ [0x10467]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10467,
+ },
+ [0x10468]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10468,
+ },
+ [0x10469]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10469,
+ },
+ [0x1046A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1046A,
+ },
+ [0x1046B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1046B,
+ },
+ [0x1046C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1046C,
+ },
+ [0x1046D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1046D,
+ },
+ [0x1046E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1046E,
+ },
+ [0x1046F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1046F,
+ },
+ [0x10470]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10470,
+ },
+ [0x10471]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10471,
+ },
+ [0x10472]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10472,
+ },
+ [0x10473]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10473,
+ },
+ [0x10474]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10474,
+ },
+ [0x10475]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10475,
+ },
+ [0x10476]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10476,
+ },
+ [0x10477]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10477,
+ },
+ [0x10478]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10478,
+ },
+ [0x10479]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10479,
+ },
+ [0x1047A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1047A,
+ },
+ [0x1047B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1047B,
+ },
+ [0x1047C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1047C,
+ },
+ [0x1047D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1047D,
+ },
+ [0x1047E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1047E,
+ },
+ [0x1047F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1047F,
+ },
+ [0x10480]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10480,
+ },
+ [0x10481]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10481,
+ },
+ [0x10482]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10482,
+ },
+ [0x10483]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10483,
+ },
+ [0x10484]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10484,
+ },
+ [0x10485]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10485,
+ },
+ [0x10486]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10486,
+ },
+ [0x10487]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10487,
+ },
+ [0x10488]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10488,
+ },
+ [0x10489]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10489,
+ },
+ [0x1048A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1048A,
+ },
+ [0x1048B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1048B,
+ },
+ [0x1048C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1048C,
+ },
+ [0x1048D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1048D,
+ },
+ [0x1048E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1048E,
+ },
+ [0x1048F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1048F,
+ },
+ [0x10490]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10490,
+ },
+ [0x10491]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10491,
+ },
+ [0x10492]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10492,
+ },
+ [0x10493]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10493,
+ },
+ [0x10494]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10494,
+ },
+ [0x10495]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10495,
+ },
+ [0x10496]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10496,
+ },
+ [0x10497]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10497,
+ },
+ [0x10498]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10498,
+ },
+ [0x10499]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10499,
+ },
+ [0x1049A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1049A,
+ },
+ [0x1049B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1049B,
+ },
+ [0x1049C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1049C,
+ },
+ [0x1049D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1049D,
+ },
+ [0x104A0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A0,
+ },
+ [0x104A1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A1,
+ },
+ [0x104A2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A2,
+ },
+ [0x104A3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A3,
+ },
+ [0x104A4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A4,
+ },
+ [0x104A5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A5,
+ },
+ [0x104A6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A6,
+ },
+ [0x104A7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A7,
+ },
+ [0x104A8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A8,
+ },
+ [0x104A9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x104A9,
+ },
+ [0x104B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B0,
+ },
+ [0x104B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B1,
+ },
+ [0x104B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B2,
+ },
+ [0x104B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B3,
+ },
+ [0x104B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B4,
+ },
+ [0x104B5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B5,
+ },
+ [0x104B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B6,
+ },
+ [0x104B7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B7,
+ },
+ [0x104B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B8,
+ },
+ [0x104B9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104B9,
+ },
+ [0x104BA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104BA,
+ },
+ [0x104BB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104BB,
+ },
+ [0x104BC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104BC,
+ },
+ [0x104BD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104BD,
+ },
+ [0x104BE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104BE,
+ },
+ [0x104BF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104BF,
+ },
+ [0x104C0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C0,
+ },
+ [0x104C1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C1,
+ },
+ [0x104C2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C2,
+ },
+ [0x104C3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C3,
+ },
+ [0x104C4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C4,
+ },
+ [0x104C5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C5,
+ },
+ [0x104C6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C6,
+ },
+ [0x104C7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C7,
+ },
+ [0x104C8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C8,
+ },
+ [0x104C9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104C9,
+ },
+ [0x104CA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104CA,
+ },
+ [0x104CB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104CB,
+ },
+ [0x104CC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104CC,
+ },
+ [0x104CD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104CD,
+ },
+ [0x104CE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104CE,
+ },
+ [0x104CF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104CF,
+ },
+ [0x104D0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104D0,
+ },
+ [0x104D1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104D1,
+ },
+ [0x104D2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104D2,
+ },
+ [0x104D3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104D3,
+ },
+ [0x104D8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104D8,
+ },
+ [0x104D9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104D9,
+ },
+ [0x104DA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104DA,
+ },
+ [0x104DB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104DB,
+ },
+ [0x104DC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104DC,
+ },
+ [0x104DD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104DD,
+ },
+ [0x104DE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104DE,
+ },
+ [0x104DF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104DF,
+ },
+ [0x104E0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E0,
+ },
+ [0x104E1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E1,
+ },
+ [0x104E2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E2,
+ },
+ [0x104E3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E3,
+ },
+ [0x104E4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E4,
+ },
+ [0x104E5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E5,
+ },
+ [0x104E6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E6,
+ },
+ [0x104E7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E7,
+ },
+ [0x104E8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E8,
+ },
+ [0x104E9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104E9,
+ },
+ [0x104EA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104EA,
+ },
+ [0x104EB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104EB,
+ },
+ [0x104EC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104EC,
+ },
+ [0x104ED]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104ED,
+ },
+ [0x104EE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104EE,
+ },
+ [0x104EF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104EF,
+ },
+ [0x104F0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F0,
+ },
+ [0x104F1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F1,
+ },
+ [0x104F2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F2,
+ },
+ [0x104F3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F3,
+ },
+ [0x104F4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F4,
+ },
+ [0x104F5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F5,
+ },
+ [0x104F6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F6,
+ },
+ [0x104F7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F7,
+ },
+ [0x104F8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F8,
+ },
+ [0x104F9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104F9,
+ },
+ [0x104FA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104FA,
+ },
+ [0x104FB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x104FB,
+ },
+ [0x10500]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10500,
+ },
+ [0x10501]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10501,
+ },
+ [0x10502]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10502,
+ },
+ [0x10503]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10503,
+ },
+ [0x10504]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10504,
+ },
+ [0x10505]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10505,
+ },
+ [0x10506]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10506,
+ },
+ [0x10507]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10507,
+ },
+ [0x10508]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10508,
+ },
+ [0x10509]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10509,
+ },
+ [0x1050A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1050A,
+ },
+ [0x1050B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1050B,
+ },
+ [0x1050C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1050C,
+ },
+ [0x1050D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1050D,
+ },
+ [0x1050E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1050E,
+ },
+ [0x1050F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1050F,
+ },
+ [0x10510]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10510,
+ },
+ [0x10511]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10511,
+ },
+ [0x10512]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10512,
+ },
+ [0x10513]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10513,
+ },
+ [0x10514]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10514,
+ },
+ [0x10515]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10515,
+ },
+ [0x10516]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10516,
+ },
+ [0x10517]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10517,
+ },
+ [0x10518]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10518,
+ },
+ [0x10519]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10519,
+ },
+ [0x1051A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1051A,
+ },
+ [0x1051B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1051B,
+ },
+ [0x1051C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1051C,
+ },
+ [0x1051D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1051D,
+ },
+ [0x1051E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1051E,
+ },
+ [0x1051F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1051F,
+ },
+ [0x10520]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10520,
+ },
+ [0x10521]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10521,
+ },
+ [0x10522]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10522,
+ },
+ [0x10523]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10523,
+ },
+ [0x10524]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10524,
+ },
+ [0x10525]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10525,
+ },
+ [0x10526]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10526,
+ },
+ [0x10527]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10527,
+ },
+ [0x10530]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10530,
+ },
+ [0x10531]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10531,
+ },
+ [0x10532]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10532,
+ },
+ [0x10533]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10533,
+ },
+ [0x10534]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10534,
+ },
+ [0x10535]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10535,
+ },
+ [0x10536]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10536,
+ },
+ [0x10537]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10537,
+ },
+ [0x10538]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10538,
+ },
+ [0x10539]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10539,
+ },
+ [0x1053A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1053A,
+ },
+ [0x1053B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1053B,
+ },
+ [0x1053C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1053C,
+ },
+ [0x1053D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1053D,
+ },
+ [0x1053E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1053E,
+ },
+ [0x1053F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1053F,
+ },
+ [0x10540]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10540,
+ },
+ [0x10541]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10541,
+ },
+ [0x10542]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10542,
+ },
+ [0x10543]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10543,
+ },
+ [0x10544]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10544,
+ },
+ [0x10545]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10545,
+ },
+ [0x10546]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10546,
+ },
+ [0x10547]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10547,
+ },
+ [0x10548]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10548,
+ },
+ [0x10549]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10549,
+ },
+ [0x1054A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1054A,
+ },
+ [0x1054B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1054B,
+ },
+ [0x1054C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1054C,
+ },
+ [0x1054D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1054D,
+ },
+ [0x1054E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1054E,
+ },
+ [0x1054F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1054F,
+ },
+ [0x10550]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10550,
+ },
+ [0x10551]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10551,
+ },
+ [0x10552]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10552,
+ },
+ [0x10553]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10553,
+ },
+ [0x10554]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10554,
+ },
+ [0x10555]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10555,
+ },
+ [0x10556]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10556,
+ },
+ [0x10557]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10557,
+ },
+ [0x10558]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10558,
+ },
+ [0x10559]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10559,
+ },
+ [0x1055A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1055A,
+ },
+ [0x1055B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1055B,
+ },
+ [0x1055C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1055C,
+ },
+ [0x1055D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1055D,
+ },
+ [0x1055E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1055E,
+ },
+ [0x1055F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1055F,
+ },
+ [0x10560]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10560,
+ },
+ [0x10561]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10561,
+ },
+ [0x10562]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10562,
+ },
+ [0x10563]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10563,
+ },
+ [0x1056F]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1056F,
+ },
+ [0x10600]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10600,
+ },
+ [0x10601]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10601,
+ },
+ [0x10602]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10602,
+ },
+ [0x10603]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10603,
+ },
+ [0x10604]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10604,
+ },
+ [0x10605]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10605,
+ },
+ [0x10606]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10606,
+ },
+ [0x10607]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10607,
+ },
+ [0x10608]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10608,
+ },
+ [0x10609]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10609,
+ },
+ [0x1060A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1060A,
+ },
+ [0x1060B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1060B,
+ },
+ [0x1060C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1060C,
+ },
+ [0x1060D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1060D,
+ },
+ [0x1060E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1060E,
+ },
+ [0x1060F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1060F,
+ },
+ [0x10610]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10610,
+ },
+ [0x10611]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10611,
+ },
+ [0x10612]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10612,
+ },
+ [0x10613]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10613,
+ },
+ [0x10614]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10614,
+ },
+ [0x10615]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10615,
+ },
+ [0x10616]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10616,
+ },
+ [0x10617]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10617,
+ },
+ [0x10618]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10618,
+ },
+ [0x10619]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10619,
+ },
+ [0x1061A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1061A,
+ },
+ [0x1061B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1061B,
+ },
+ [0x1061C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1061C,
+ },
+ [0x1061D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1061D,
+ },
+ [0x1061E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1061E,
+ },
+ [0x1061F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1061F,
+ },
+ [0x10620]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10620,
+ },
+ [0x10621]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10621,
+ },
+ [0x10622]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10622,
+ },
+ [0x10623]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10623,
+ },
+ [0x10624]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10624,
+ },
+ [0x10625]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10625,
+ },
+ [0x10626]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10626,
+ },
+ [0x10627]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10627,
+ },
+ [0x10628]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10628,
+ },
+ [0x10629]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10629,
+ },
+ [0x1062A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1062A,
+ },
+ [0x1062B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1062B,
+ },
+ [0x1062C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1062C,
+ },
+ [0x1062D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1062D,
+ },
+ [0x1062E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1062E,
+ },
+ [0x1062F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1062F,
+ },
+ [0x10630]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10630,
+ },
+ [0x10631]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10631,
+ },
+ [0x10632]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10632,
+ },
+ [0x10633]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10633,
+ },
+ [0x10634]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10634,
+ },
+ [0x10635]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10635,
+ },
+ [0x10636]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10636,
+ },
+ [0x10637]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10637,
+ },
+ [0x10638]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10638,
+ },
+ [0x10639]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10639,
+ },
+ [0x1063A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1063A,
+ },
+ [0x1063B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1063B,
+ },
+ [0x1063C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1063C,
+ },
+ [0x1063D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1063D,
+ },
+ [0x1063E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1063E,
+ },
+ [0x1063F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1063F,
+ },
+ [0x10640]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10640,
+ },
+ [0x10641]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10641,
+ },
+ [0x10642]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10642,
+ },
+ [0x10643]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10643,
+ },
+ [0x10644]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10644,
+ },
+ [0x10645]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10645,
+ },
+ [0x10646]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10646,
+ },
+ [0x10647]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10647,
+ },
+ [0x10648]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10648,
+ },
+ [0x10649]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10649,
+ },
+ [0x1064A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1064A,
+ },
+ [0x1064B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1064B,
+ },
+ [0x1064C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1064C,
+ },
+ [0x1064D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1064D,
+ },
+ [0x1064E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1064E,
+ },
+ [0x1064F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1064F,
+ },
+ [0x10650]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10650,
+ },
+ [0x10651]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10651,
+ },
+ [0x10652]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10652,
+ },
+ [0x10653]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10653,
+ },
+ [0x10654]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10654,
+ },
+ [0x10655]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10655,
+ },
+ [0x10656]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10656,
+ },
+ [0x10657]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10657,
+ },
+ [0x10658]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10658,
+ },
+ [0x10659]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10659,
+ },
+ [0x1065A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1065A,
+ },
+ [0x1065B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1065B,
+ },
+ [0x1065C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1065C,
+ },
+ [0x1065D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1065D,
+ },
+ [0x1065E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1065E,
+ },
+ [0x1065F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1065F,
+ },
+ [0x10660]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10660,
+ },
+ [0x10661]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10661,
+ },
+ [0x10662]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10662,
+ },
+ [0x10663]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10663,
+ },
+ [0x10664]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10664,
+ },
+ [0x10665]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10665,
+ },
+ [0x10666]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10666,
+ },
+ [0x10667]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10667,
+ },
+ [0x10668]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10668,
+ },
+ [0x10669]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10669,
+ },
+ [0x1066A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1066A,
+ },
+ [0x1066B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1066B,
+ },
+ [0x1066C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1066C,
+ },
+ [0x1066D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1066D,
+ },
+ [0x1066E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1066E,
+ },
+ [0x1066F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1066F,
+ },
+ [0x10670]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10670,
+ },
+ [0x10671]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10671,
+ },
+ [0x10672]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10672,
+ },
+ [0x10673]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10673,
+ },
+ [0x10674]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10674,
+ },
+ [0x10675]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10675,
+ },
+ [0x10676]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10676,
+ },
+ [0x10677]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10677,
+ },
+ [0x10678]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10678,
+ },
+ [0x10679]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10679,
+ },
+ [0x1067A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1067A,
+ },
+ [0x1067B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1067B,
+ },
+ [0x1067C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1067C,
+ },
+ [0x1067D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1067D,
+ },
+ [0x1067E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1067E,
+ },
+ [0x1067F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1067F,
+ },
+ [0x10680]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10680,
+ },
+ [0x10681]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10681,
+ },
+ [0x10682]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10682,
+ },
+ [0x10683]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10683,
+ },
+ [0x10684]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10684,
+ },
+ [0x10685]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10685,
+ },
+ [0x10686]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10686,
+ },
+ [0x10687]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10687,
+ },
+ [0x10688]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10688,
+ },
+ [0x10689]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10689,
+ },
+ [0x1068A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1068A,
+ },
+ [0x1068B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1068B,
+ },
+ [0x1068C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1068C,
+ },
+ [0x1068D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1068D,
+ },
+ [0x1068E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1068E,
+ },
+ [0x1068F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1068F,
+ },
+ [0x10690]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10690,
+ },
+ [0x10691]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10691,
+ },
+ [0x10692]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10692,
+ },
+ [0x10693]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10693,
+ },
+ [0x10694]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10694,
+ },
+ [0x10695]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10695,
+ },
+ [0x10696]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10696,
+ },
+ [0x10697]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10697,
+ },
+ [0x10698]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10698,
+ },
+ [0x10699]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10699,
+ },
+ [0x1069A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1069A,
+ },
+ [0x1069B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1069B,
+ },
+ [0x1069C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1069C,
+ },
+ [0x1069D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1069D,
+ },
+ [0x1069E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1069E,
+ },
+ [0x1069F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1069F,
+ },
+ [0x106A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A0,
+ },
+ [0x106A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A1,
+ },
+ [0x106A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A2,
+ },
+ [0x106A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A3,
+ },
+ [0x106A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A4,
+ },
+ [0x106A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A5,
+ },
+ [0x106A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A6,
+ },
+ [0x106A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A7,
+ },
+ [0x106A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A8,
+ },
+ [0x106A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106A9,
+ },
+ [0x106AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106AA,
+ },
+ [0x106AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106AB,
+ },
+ [0x106AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106AC,
+ },
+ [0x106AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106AD,
+ },
+ [0x106AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106AE,
+ },
+ [0x106AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106AF,
+ },
+ [0x106B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B0,
+ },
+ [0x106B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B1,
+ },
+ [0x106B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B2,
+ },
+ [0x106B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B3,
+ },
+ [0x106B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B4,
+ },
+ [0x106B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B5,
+ },
+ [0x106B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B6,
+ },
+ [0x106B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B7,
+ },
+ [0x106B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B8,
+ },
+ [0x106B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106B9,
+ },
+ [0x106BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106BA,
+ },
+ [0x106BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106BB,
+ },
+ [0x106BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106BC,
+ },
+ [0x106BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106BD,
+ },
+ [0x106BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106BE,
+ },
+ [0x106BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106BF,
+ },
+ [0x106C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C0,
+ },
+ [0x106C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C1,
+ },
+ [0x106C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C2,
+ },
+ [0x106C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C3,
+ },
+ [0x106C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C4,
+ },
+ [0x106C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C5,
+ },
+ [0x106C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C6,
+ },
+ [0x106C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C7,
+ },
+ [0x106C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C8,
+ },
+ [0x106C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106C9,
+ },
+ [0x106CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106CA,
+ },
+ [0x106CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106CB,
+ },
+ [0x106CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106CC,
+ },
+ [0x106CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106CD,
+ },
+ [0x106CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106CE,
+ },
+ [0x106CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106CF,
+ },
+ [0x106D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D0,
+ },
+ [0x106D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D1,
+ },
+ [0x106D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D2,
+ },
+ [0x106D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D3,
+ },
+ [0x106D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D4,
+ },
+ [0x106D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D5,
+ },
+ [0x106D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D6,
+ },
+ [0x106D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D7,
+ },
+ [0x106D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D8,
+ },
+ [0x106D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106D9,
+ },
+ [0x106DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106DA,
+ },
+ [0x106DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106DB,
+ },
+ [0x106DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106DC,
+ },
+ [0x106DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106DD,
+ },
+ [0x106DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106DE,
+ },
+ [0x106DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106DF,
+ },
+ [0x106E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E0,
+ },
+ [0x106E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E1,
+ },
+ [0x106E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E2,
+ },
+ [0x106E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E3,
+ },
+ [0x106E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E4,
+ },
+ [0x106E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E5,
+ },
+ [0x106E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E6,
+ },
+ [0x106E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E7,
+ },
+ [0x106E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E8,
+ },
+ [0x106E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106E9,
+ },
+ [0x106EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106EA,
+ },
+ [0x106EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106EB,
+ },
+ [0x106EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106EC,
+ },
+ [0x106ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106ED,
+ },
+ [0x106EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106EE,
+ },
+ [0x106EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106EF,
+ },
+ [0x106F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F0,
+ },
+ [0x106F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F1,
+ },
+ [0x106F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F2,
+ },
+ [0x106F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F3,
+ },
+ [0x106F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F4,
+ },
+ [0x106F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F5,
+ },
+ [0x106F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F6,
+ },
+ [0x106F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F7,
+ },
+ [0x106F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F8,
+ },
+ [0x106F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106F9,
+ },
+ [0x106FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106FA,
+ },
+ [0x106FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106FB,
+ },
+ [0x106FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106FC,
+ },
+ [0x106FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106FD,
+ },
+ [0x106FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106FE,
+ },
+ [0x106FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x106FF,
+ },
+ [0x10700]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10700,
+ },
+ [0x10701]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10701,
+ },
+ [0x10702]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10702,
+ },
+ [0x10703]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10703,
+ },
+ [0x10704]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10704,
+ },
+ [0x10705]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10705,
+ },
+ [0x10706]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10706,
+ },
+ [0x10707]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10707,
+ },
+ [0x10708]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10708,
+ },
+ [0x10709]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10709,
+ },
+ [0x1070A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1070A,
+ },
+ [0x1070B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1070B,
+ },
+ [0x1070C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1070C,
+ },
+ [0x1070D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1070D,
+ },
+ [0x1070E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1070E,
+ },
+ [0x1070F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1070F,
+ },
+ [0x10710]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10710,
+ },
+ [0x10711]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10711,
+ },
+ [0x10712]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10712,
+ },
+ [0x10713]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10713,
+ },
+ [0x10714]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10714,
+ },
+ [0x10715]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10715,
+ },
+ [0x10716]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10716,
+ },
+ [0x10717]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10717,
+ },
+ [0x10718]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10718,
+ },
+ [0x10719]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10719,
+ },
+ [0x1071A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1071A,
+ },
+ [0x1071B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1071B,
+ },
+ [0x1071C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1071C,
+ },
+ [0x1071D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1071D,
+ },
+ [0x1071E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1071E,
+ },
+ [0x1071F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1071F,
+ },
+ [0x10720]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10720,
+ },
+ [0x10721]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10721,
+ },
+ [0x10722]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10722,
+ },
+ [0x10723]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10723,
+ },
+ [0x10724]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10724,
+ },
+ [0x10725]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10725,
+ },
+ [0x10726]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10726,
+ },
+ [0x10727]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10727,
+ },
+ [0x10728]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10728,
+ },
+ [0x10729]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10729,
+ },
+ [0x1072A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1072A,
+ },
+ [0x1072B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1072B,
+ },
+ [0x1072C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1072C,
+ },
+ [0x1072D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1072D,
+ },
+ [0x1072E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1072E,
+ },
+ [0x1072F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1072F,
+ },
+ [0x10730]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10730,
+ },
+ [0x10731]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10731,
+ },
+ [0x10732]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10732,
+ },
+ [0x10733]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10733,
+ },
+ [0x10734]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10734,
+ },
+ [0x10735]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10735,
+ },
+ [0x10736]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10736,
+ },
+ [0x10740]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10740,
+ },
+ [0x10741]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10741,
+ },
+ [0x10742]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10742,
+ },
+ [0x10743]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10743,
+ },
+ [0x10744]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10744,
+ },
+ [0x10745]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10745,
+ },
+ [0x10746]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10746,
+ },
+ [0x10747]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10747,
+ },
+ [0x10748]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10748,
+ },
+ [0x10749]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10749,
+ },
+ [0x1074A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1074A,
+ },
+ [0x1074B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1074B,
+ },
+ [0x1074C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1074C,
+ },
+ [0x1074D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1074D,
+ },
+ [0x1074E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1074E,
+ },
+ [0x1074F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1074F,
+ },
+ [0x10750]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10750,
+ },
+ [0x10751]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10751,
+ },
+ [0x10752]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10752,
+ },
+ [0x10753]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10753,
+ },
+ [0x10754]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10754,
+ },
+ [0x10755]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10755,
+ },
+ [0x10760]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10760,
+ },
+ [0x10761]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10761,
+ },
+ [0x10762]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10762,
+ },
+ [0x10763]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10763,
+ },
+ [0x10764]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10764,
+ },
+ [0x10765]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10765,
+ },
+ [0x10766]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10766,
+ },
+ [0x10767]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x10767,
+ },
+ [0x10800]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10800,
+ },
+ [0x10801]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10801,
+ },
+ [0x10802]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10802,
+ },
+ [0x10803]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10803,
+ },
+ [0x10804]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10804,
+ },
+ [0x10805]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10805,
+ },
+ [0x10808]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10808,
+ },
+ [0x1080A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1080A,
+ },
+ [0x1080B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1080B,
+ },
+ [0x1080C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1080C,
+ },
+ [0x1080D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1080D,
+ },
+ [0x1080E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1080E,
+ },
+ [0x1080F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1080F,
+ },
+ [0x10810]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10810,
+ },
+ [0x10811]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10811,
+ },
+ [0x10812]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10812,
+ },
+ [0x10813]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10813,
+ },
+ [0x10814]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10814,
+ },
+ [0x10815]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10815,
+ },
+ [0x10816]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10816,
+ },
+ [0x10817]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10817,
+ },
+ [0x10818]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10818,
+ },
+ [0x10819]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10819,
+ },
+ [0x1081A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1081A,
+ },
+ [0x1081B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1081B,
+ },
+ [0x1081C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1081C,
+ },
+ [0x1081D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1081D,
+ },
+ [0x1081E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1081E,
+ },
+ [0x1081F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1081F,
+ },
+ [0x10820]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10820,
+ },
+ [0x10821]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10821,
+ },
+ [0x10822]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10822,
+ },
+ [0x10823]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10823,
+ },
+ [0x10824]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10824,
+ },
+ [0x10825]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10825,
+ },
+ [0x10826]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10826,
+ },
+ [0x10827]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10827,
+ },
+ [0x10828]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10828,
+ },
+ [0x10829]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10829,
+ },
+ [0x1082A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1082A,
+ },
+ [0x1082B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1082B,
+ },
+ [0x1082C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1082C,
+ },
+ [0x1082D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1082D,
+ },
+ [0x1082E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1082E,
+ },
+ [0x1082F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1082F,
+ },
+ [0x10830]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10830,
+ },
+ [0x10831]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10831,
+ },
+ [0x10832]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10832,
+ },
+ [0x10833]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10833,
+ },
+ [0x10834]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10834,
+ },
+ [0x10835]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10835,
+ },
+ [0x10837]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10837,
+ },
+ [0x10838]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10838,
+ },
+ [0x1083C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1083C,
+ },
+ [0x1083F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1083F,
+ },
+ [0x10840]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10840,
+ },
+ [0x10841]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10841,
+ },
+ [0x10842]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10842,
+ },
+ [0x10843]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10843,
+ },
+ [0x10844]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10844,
+ },
+ [0x10845]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10845,
+ },
+ [0x10846]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10846,
+ },
+ [0x10847]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10847,
+ },
+ [0x10848]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10848,
+ },
+ [0x10849]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10849,
+ },
+ [0x1084A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1084A,
+ },
+ [0x1084B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1084B,
+ },
+ [0x1084C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1084C,
+ },
+ [0x1084D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1084D,
+ },
+ [0x1084E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1084E,
+ },
+ [0x1084F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1084F,
+ },
+ [0x10850]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10850,
+ },
+ [0x10851]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10851,
+ },
+ [0x10852]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10852,
+ },
+ [0x10853]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10853,
+ },
+ [0x10854]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10854,
+ },
+ [0x10855]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10855,
+ },
+ [0x10857]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10857,
+ },
+ [0x10858]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10858,
+ },
+ [0x10859]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10859,
+ },
+ [0x1085A]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1085A,
+ },
+ [0x1085B]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1085B,
+ },
+ [0x1085C]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1085C,
+ },
+ [0x1085D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1085D,
+ },
+ [0x1085E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1085E,
+ },
+ [0x1085F]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1085F,
+ },
+ [0x10860]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10860,
+ },
+ [0x10861]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10861,
+ },
+ [0x10862]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10862,
+ },
+ [0x10863]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10863,
+ },
+ [0x10864]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10864,
+ },
+ [0x10865]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10865,
+ },
+ [0x10866]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10866,
+ },
+ [0x10867]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10867,
+ },
+ [0x10868]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10868,
+ },
+ [0x10869]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10869,
+ },
+ [0x1086A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1086A,
+ },
+ [0x1086B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1086B,
+ },
+ [0x1086C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1086C,
+ },
+ [0x1086D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1086D,
+ },
+ [0x1086E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1086E,
+ },
+ [0x1086F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1086F,
+ },
+ [0x10870]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10870,
+ },
+ [0x10871]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10871,
+ },
+ [0x10872]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10872,
+ },
+ [0x10873]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10873,
+ },
+ [0x10874]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10874,
+ },
+ [0x10875]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10875,
+ },
+ [0x10876]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10876,
+ },
+ [0x10877]={
+ category="so",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10877,
+ },
+ [0x10878]={
+ category="so",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10878,
+ },
+ [0x10879]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10879,
+ },
+ [0x1087A]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1087A,
+ },
+ [0x1087B]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1087B,
+ },
+ [0x1087C]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1087C,
+ },
+ [0x1087D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1087D,
+ },
+ [0x1087E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1087E,
+ },
+ [0x1087F]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1087F,
+ },
+ [0x10880]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10880,
+ },
+ [0x10881]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10881,
+ },
+ [0x10882]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10882,
+ },
+ [0x10883]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10883,
+ },
+ [0x10884]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10884,
+ },
+ [0x10885]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10885,
+ },
+ [0x10886]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10886,
+ },
+ [0x10887]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10887,
+ },
+ [0x10888]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10888,
+ },
+ [0x10889]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10889,
+ },
+ [0x1088A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1088A,
+ },
+ [0x1088B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1088B,
+ },
+ [0x1088C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1088C,
+ },
+ [0x1088D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1088D,
+ },
+ [0x1088E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1088E,
+ },
+ [0x1088F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1088F,
+ },
+ [0x10890]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10890,
+ },
+ [0x10891]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10891,
+ },
+ [0x10892]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10892,
+ },
+ [0x10893]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10893,
+ },
+ [0x10894]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10894,
+ },
+ [0x10895]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10895,
+ },
+ [0x10896]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10896,
+ },
+ [0x10897]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10897,
+ },
+ [0x10898]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10898,
+ },
+ [0x10899]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10899,
+ },
+ [0x1089A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1089A,
+ },
+ [0x1089B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1089B,
+ },
+ [0x1089C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1089C,
+ },
+ [0x1089D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1089D,
+ },
+ [0x1089E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1089E,
+ },
+ [0x108A7]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108A7,
+ },
+ [0x108A8]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108A8,
+ },
+ [0x108A9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108A9,
+ },
+ [0x108AA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108AA,
+ },
+ [0x108AB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108AB,
+ },
+ [0x108AC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108AC,
+ },
+ [0x108AD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108AD,
+ },
+ [0x108AE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108AE,
+ },
+ [0x108AF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108AF,
+ },
+ [0x108E0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E0,
+ },
+ [0x108E1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E1,
+ },
+ [0x108E2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E2,
+ },
+ [0x108E3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E3,
+ },
+ [0x108E4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E4,
+ },
+ [0x108E5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E5,
+ },
+ [0x108E6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E6,
+ },
+ [0x108E7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E7,
+ },
+ [0x108E8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E8,
+ },
+ [0x108E9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108E9,
+ },
+ [0x108EA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108EA,
+ },
+ [0x108EB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108EB,
+ },
+ [0x108EC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108EC,
+ },
+ [0x108ED]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108ED,
+ },
+ [0x108EE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108EE,
+ },
+ [0x108EF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108EF,
+ },
+ [0x108F0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108F0,
+ },
+ [0x108F1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108F1,
+ },
+ [0x108F2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108F2,
+ },
+ [0x108F4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108F4,
+ },
+ [0x108F5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108F5,
+ },
+ [0x108FB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108FB,
+ },
+ [0x108FC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108FC,
+ },
+ [0x108FD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108FD,
+ },
+ [0x108FE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108FE,
+ },
+ [0x108FF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x108FF,
+ },
+ [0x10900]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10900,
+ },
+ [0x10901]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10901,
+ },
+ [0x10902]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10902,
+ },
+ [0x10903]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10903,
+ },
+ [0x10904]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10904,
+ },
+ [0x10905]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10905,
+ },
+ [0x10906]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10906,
+ },
+ [0x10907]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10907,
+ },
+ [0x10908]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10908,
+ },
+ [0x10909]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10909,
+ },
+ [0x1090A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1090A,
+ },
+ [0x1090B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1090B,
+ },
+ [0x1090C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1090C,
+ },
+ [0x1090D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1090D,
+ },
+ [0x1090E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1090E,
+ },
+ [0x1090F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1090F,
+ },
+ [0x10910]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10910,
+ },
+ [0x10911]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10911,
+ },
+ [0x10912]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10912,
+ },
+ [0x10913]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10913,
+ },
+ [0x10914]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10914,
+ },
+ [0x10915]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10915,
+ },
+ [0x10916]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10916,
+ },
+ [0x10917]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10917,
+ },
+ [0x10918]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10918,
+ },
+ [0x10919]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10919,
+ },
+ [0x1091A]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1091A,
+ },
+ [0x1091B]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1091B,
+ },
+ [0x1091F]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x1091F,
+ },
+ [0x10920]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10920,
+ },
+ [0x10921]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10921,
+ },
+ [0x10922]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10922,
+ },
+ [0x10923]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10923,
+ },
+ [0x10924]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10924,
+ },
+ [0x10925]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10925,
+ },
+ [0x10926]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10926,
+ },
+ [0x10927]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10927,
+ },
+ [0x10928]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10928,
+ },
+ [0x10929]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10929,
+ },
+ [0x1092A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1092A,
+ },
+ [0x1092B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1092B,
+ },
+ [0x1092C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1092C,
+ },
+ [0x1092D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1092D,
+ },
+ [0x1092E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1092E,
+ },
+ [0x1092F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1092F,
+ },
+ [0x10930]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10930,
+ },
+ [0x10931]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10931,
+ },
+ [0x10932]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10932,
+ },
+ [0x10933]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10933,
+ },
+ [0x10934]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10934,
+ },
+ [0x10935]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10935,
+ },
+ [0x10936]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10936,
+ },
+ [0x10937]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10937,
+ },
+ [0x10938]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10938,
+ },
+ [0x10939]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10939,
+ },
+ [0x1093F]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1093F,
+ },
+ [0x10980]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10980,
+ },
+ [0x10981]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10981,
+ },
+ [0x10982]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10982,
+ },
+ [0x10983]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10983,
+ },
+ [0x10984]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10984,
+ },
+ [0x10985]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10985,
+ },
+ [0x10986]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10986,
+ },
+ [0x10987]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10987,
+ },
+ [0x10988]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10988,
+ },
+ [0x10989]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10989,
+ },
+ [0x1098A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1098A,
+ },
+ [0x1098B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1098B,
+ },
+ [0x1098C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1098C,
+ },
+ [0x1098D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1098D,
+ },
+ [0x1098E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1098E,
+ },
+ [0x1098F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1098F,
+ },
+ [0x10990]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10990,
+ },
+ [0x10991]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10991,
+ },
+ [0x10992]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10992,
+ },
+ [0x10993]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10993,
+ },
+ [0x10994]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10994,
+ },
+ [0x10995]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10995,
+ },
+ [0x10996]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10996,
+ },
+ [0x10997]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10997,
+ },
+ [0x10998]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10998,
+ },
+ [0x10999]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10999,
+ },
+ [0x1099A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1099A,
+ },
+ [0x1099B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1099B,
+ },
+ [0x1099C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1099C,
+ },
+ [0x1099D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1099D,
+ },
+ [0x1099E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1099E,
+ },
+ [0x1099F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1099F,
+ },
+ [0x109A0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A0,
+ },
+ [0x109A1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A1,
+ },
+ [0x109A2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A2,
+ },
+ [0x109A3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A3,
+ },
+ [0x109A4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A4,
+ },
+ [0x109A5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A5,
+ },
+ [0x109A6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A6,
+ },
+ [0x109A7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A7,
+ },
+ [0x109A8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A8,
+ },
+ [0x109A9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109A9,
+ },
+ [0x109AA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109AA,
+ },
+ [0x109AB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109AB,
+ },
+ [0x109AC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109AC,
+ },
+ [0x109AD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109AD,
+ },
+ [0x109AE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109AE,
+ },
+ [0x109AF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109AF,
+ },
+ [0x109B0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B0,
+ },
+ [0x109B1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B1,
+ },
+ [0x109B2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B2,
+ },
+ [0x109B3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B3,
+ },
+ [0x109B4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B4,
+ },
+ [0x109B5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B5,
+ },
+ [0x109B6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B6,
+ },
+ [0x109B7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109B7,
+ },
+ [0x109BC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109BC,
+ },
+ [0x109BD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109BD,
+ },
+ [0x109BE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109BE,
+ },
+ [0x109BF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109BF,
+ },
+ [0x109C0]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C0,
+ },
+ [0x109C1]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C1,
+ },
+ [0x109C2]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C2,
+ },
+ [0x109C3]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C3,
+ },
+ [0x109C4]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C4,
+ },
+ [0x109C5]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C5,
+ },
+ [0x109C6]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C6,
+ },
+ [0x109C7]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C7,
+ },
+ [0x109C8]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C8,
+ },
+ [0x109C9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109C9,
+ },
+ [0x109CA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109CA,
+ },
+ [0x109CB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109CB,
+ },
+ [0x109CC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109CC,
+ },
+ [0x109CD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109CD,
+ },
+ [0x109CE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109CE,
+ },
+ [0x109CF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109CF,
+ },
+ [0x109D2]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D2,
+ },
+ [0x109D3]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D3,
+ },
+ [0x109D4]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D4,
+ },
+ [0x109D5]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D5,
+ },
+ [0x109D6]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D6,
+ },
+ [0x109D7]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D7,
+ },
+ [0x109D8]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D8,
+ },
+ [0x109D9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109D9,
+ },
+ [0x109DA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109DA,
+ },
+ [0x109DB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109DB,
+ },
+ [0x109DC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109DC,
+ },
+ [0x109DD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109DD,
+ },
+ [0x109DE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109DE,
+ },
+ [0x109DF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109DF,
+ },
+ [0x109E0]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E0,
+ },
+ [0x109E1]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E1,
+ },
+ [0x109E2]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E2,
+ },
+ [0x109E3]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E3,
+ },
+ [0x109E4]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E4,
+ },
+ [0x109E5]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E5,
+ },
+ [0x109E6]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E6,
+ },
+ [0x109E7]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E7,
+ },
+ [0x109E8]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E8,
+ },
+ [0x109E9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109E9,
+ },
+ [0x109EA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109EA,
+ },
+ [0x109EB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109EB,
+ },
+ [0x109EC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109EC,
+ },
+ [0x109ED]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109ED,
+ },
+ [0x109EE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109EE,
+ },
+ [0x109EF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109EF,
+ },
+ [0x109F0]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F0,
+ },
+ [0x109F1]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F1,
+ },
+ [0x109F2]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F2,
+ },
+ [0x109F3]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F3,
+ },
+ [0x109F4]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F4,
+ },
+ [0x109F5]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F5,
+ },
+ [0x109F6]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F6,
+ },
+ [0x109F7]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F7,
+ },
+ [0x109F8]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F8,
+ },
+ [0x109F9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109F9,
+ },
+ [0x109FA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109FA,
+ },
+ [0x109FB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109FB,
+ },
+ [0x109FC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109FC,
+ },
+ [0x109FD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109FD,
+ },
+ [0x109FE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109FE,
+ },
+ [0x109FF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x109FF,
+ },
+ [0x10A00]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A00,
+ },
+ [0x10A01]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A01,
+ },
+ [0x10A02]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A02,
+ },
+ [0x10A03]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A03,
+ },
+ [0x10A05]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A05,
+ },
+ [0x10A06]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A06,
+ },
+ [0x10A0C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A0C,
+ },
+ [0x10A0D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A0D,
+ },
+ [0x10A0E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A0E,
+ },
+ [0x10A0F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A0F,
+ },
+ [0x10A10]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A10,
+ },
+ [0x10A11]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A11,
+ },
+ [0x10A12]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A12,
+ },
+ [0x10A13]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A13,
+ },
+ [0x10A15]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A15,
+ },
+ [0x10A16]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A16,
+ },
+ [0x10A17]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A17,
+ },
+ [0x10A19]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A19,
+ },
+ [0x10A1A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A1A,
+ },
+ [0x10A1B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A1B,
+ },
+ [0x10A1C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A1C,
+ },
+ [0x10A1D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A1D,
+ },
+ [0x10A1E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A1E,
+ },
+ [0x10A1F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A1F,
+ },
+ [0x10A20]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A20,
+ },
+ [0x10A21]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A21,
+ },
+ [0x10A22]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A22,
+ },
+ [0x10A23]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A23,
+ },
+ [0x10A24]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A24,
+ },
+ [0x10A25]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A25,
+ },
+ [0x10A26]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A26,
+ },
+ [0x10A27]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A27,
+ },
+ [0x10A28]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A28,
+ },
+ [0x10A29]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A29,
+ },
+ [0x10A2A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A2A,
+ },
+ [0x10A2B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A2B,
+ },
+ [0x10A2C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A2C,
+ },
+ [0x10A2D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A2D,
+ },
+ [0x10A2E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A2E,
+ },
+ [0x10A2F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A2F,
+ },
+ [0x10A30]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A30,
+ },
+ [0x10A31]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A31,
+ },
+ [0x10A32]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A32,
+ },
+ [0x10A33]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A33,
+ },
+ [0x10A34]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A34,
+ },
+ [0x10A35]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A35,
+ },
+ [0x10A38]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A38,
+ },
+ [0x10A39]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A39,
+ },
+ [0x10A3A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A3A,
+ },
+ [0x10A3F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10A3F,
+ },
+ [0x10A40]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A40,
+ },
+ [0x10A41]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A41,
+ },
+ [0x10A42]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A42,
+ },
+ [0x10A43]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A43,
+ },
+ [0x10A44]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A44,
+ },
+ [0x10A45]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A45,
+ },
+ [0x10A46]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A46,
+ },
+ [0x10A47]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A47,
+ },
+ [0x10A48]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A48,
+ },
+ [0x10A50]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A50,
+ },
+ [0x10A51]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A51,
+ },
+ [0x10A52]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A52,
+ },
+ [0x10A53]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A53,
+ },
+ [0x10A54]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A54,
+ },
+ [0x10A55]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A55,
+ },
+ [0x10A56]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A56,
+ },
+ [0x10A57]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10A57,
+ },
+ [0x10A58]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A58,
+ },
+ [0x10A60]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A60,
+ },
+ [0x10A61]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A61,
+ },
+ [0x10A62]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A62,
+ },
+ [0x10A63]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A63,
+ },
+ [0x10A64]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A64,
+ },
+ [0x10A65]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A65,
+ },
+ [0x10A66]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A66,
+ },
+ [0x10A67]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A67,
+ },
+ [0x10A68]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A68,
+ },
+ [0x10A69]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A69,
+ },
+ [0x10A6A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A6A,
+ },
+ [0x10A6B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A6B,
+ },
+ [0x10A6C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A6C,
+ },
+ [0x10A6D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A6D,
+ },
+ [0x10A6E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A6E,
+ },
+ [0x10A6F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A6F,
+ },
+ [0x10A70]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A70,
+ },
+ [0x10A71]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A71,
+ },
+ [0x10A72]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A72,
+ },
+ [0x10A73]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A73,
+ },
+ [0x10A74]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A74,
+ },
+ [0x10A75]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A75,
+ },
+ [0x10A76]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A76,
+ },
+ [0x10A77]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A77,
+ },
+ [0x10A78]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A78,
+ },
+ [0x10A79]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A79,
+ },
+ [0x10A7A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A7A,
+ },
+ [0x10A7B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A7B,
+ },
+ [0x10A7C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A7C,
+ },
+ [0x10A7D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A7D,
+ },
+ [0x10A7E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A7E,
+ },
+ [0x10A7F]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A7F,
+ },
+ [0x10A80]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A80,
+ },
+ [0x10A81]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A81,
+ },
+ [0x10A82]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A82,
+ },
+ [0x10A83]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A83,
+ },
+ [0x10A84]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A84,
+ },
+ [0x10A85]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A85,
+ },
+ [0x10A86]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A86,
+ },
+ [0x10A87]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A87,
+ },
+ [0x10A88]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A88,
+ },
+ [0x10A89]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A89,
+ },
+ [0x10A8A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A8A,
+ },
+ [0x10A8B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A8B,
+ },
+ [0x10A8C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A8C,
+ },
+ [0x10A8D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A8D,
+ },
+ [0x10A8E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A8E,
+ },
+ [0x10A8F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A8F,
+ },
+ [0x10A90]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A90,
+ },
+ [0x10A91]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A91,
+ },
+ [0x10A92]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A92,
+ },
+ [0x10A93]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A93,
+ },
+ [0x10A94]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A94,
+ },
+ [0x10A95]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A95,
+ },
+ [0x10A96]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A96,
+ },
+ [0x10A97]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A97,
+ },
+ [0x10A98]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A98,
+ },
+ [0x10A99]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A99,
+ },
+ [0x10A9A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A9A,
+ },
+ [0x10A9B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A9B,
+ },
+ [0x10A9C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A9C,
+ },
+ [0x10A9D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A9D,
+ },
+ [0x10A9E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A9E,
+ },
+ [0x10A9F]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10A9F,
+ },
+ [0x10AC0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC0,
+ },
+ [0x10AC1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC1,
+ },
+ [0x10AC2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC2,
+ },
+ [0x10AC3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC3,
+ },
+ [0x10AC4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC4,
+ },
+ [0x10AC5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC5,
+ },
+ [0x10AC6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC6,
+ },
+ [0x10AC7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC7,
+ },
+ [0x10AC8]={
+ category="so",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC8,
+ },
+ [0x10AC9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AC9,
+ },
+ [0x10ACA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ACA,
+ },
+ [0x10ACB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ACB,
+ },
+ [0x10ACC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ACC,
+ },
+ [0x10ACD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ACD,
+ },
+ [0x10ACE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ACE,
+ },
+ [0x10ACF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ACF,
+ },
+ [0x10AD0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD0,
+ },
+ [0x10AD1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD1,
+ },
+ [0x10AD2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD2,
+ },
+ [0x10AD3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD3,
+ },
+ [0x10AD4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD4,
+ },
+ [0x10AD5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD5,
+ },
+ [0x10AD6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD6,
+ },
+ [0x10AD7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD7,
+ },
+ [0x10AD8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD8,
+ },
+ [0x10AD9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AD9,
+ },
+ [0x10ADA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ADA,
+ },
+ [0x10ADB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ADB,
+ },
+ [0x10ADC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ADC,
+ },
+ [0x10ADD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ADD,
+ },
+ [0x10ADE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ADE,
+ },
+ [0x10ADF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10ADF,
+ },
+ [0x10AE0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AE0,
+ },
+ [0x10AE1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AE1,
+ },
+ [0x10AE2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AE2,
+ },
+ [0x10AE3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AE3,
+ },
+ [0x10AE4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AE4,
+ },
+ [0x10AE5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10AE5,
+ },
+ [0x10AE6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10AE6,
+ },
+ [0x10AEB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AEB,
+ },
+ [0x10AEC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AEC,
+ },
+ [0x10AED]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AED,
+ },
+ [0x10AEE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AEE,
+ },
+ [0x10AEF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10AEF,
+ },
+ [0x10AF0]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10AF0,
+ },
+ [0x10AF1]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10AF1,
+ },
+ [0x10AF2]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10AF2,
+ },
+ [0x10AF3]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10AF3,
+ },
+ [0x10AF4]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10AF4,
+ },
+ [0x10AF5]={
+ category="po",
+ direction="r",
+ linebreak="ba",
+ unicodeslot=0x10AF5,
+ },
+ [0x10AF6]={
+ category="po",
+ direction="r",
+ linebreak="in",
+ unicodeslot=0x10AF6,
+ },
+ [0x10B00]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B00,
+ },
+ [0x10B01]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B01,
+ },
+ [0x10B02]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B02,
+ },
+ [0x10B03]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B03,
+ },
+ [0x10B04]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B04,
+ },
+ [0x10B05]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B05,
+ },
+ [0x10B06]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B06,
+ },
+ [0x10B07]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B07,
+ },
+ [0x10B08]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B08,
+ },
+ [0x10B09]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B09,
+ },
+ [0x10B0A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B0A,
+ },
+ [0x10B0B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B0B,
+ },
+ [0x10B0C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B0C,
+ },
+ [0x10B0D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B0D,
+ },
+ [0x10B0E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B0E,
+ },
+ [0x10B0F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B0F,
+ },
+ [0x10B10]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B10,
+ },
+ [0x10B11]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B11,
+ },
+ [0x10B12]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B12,
+ },
+ [0x10B13]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B13,
+ },
+ [0x10B14]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B14,
+ },
+ [0x10B15]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B15,
+ },
+ [0x10B16]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B16,
+ },
+ [0x10B17]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B17,
+ },
+ [0x10B18]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B18,
+ },
+ [0x10B19]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B19,
+ },
+ [0x10B1A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B1A,
+ },
+ [0x10B1B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B1B,
+ },
+ [0x10B1C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B1C,
+ },
+ [0x10B1D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B1D,
+ },
+ [0x10B1E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B1E,
+ },
+ [0x10B1F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B1F,
+ },
+ [0x10B20]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B20,
+ },
+ [0x10B21]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B21,
+ },
+ [0x10B22]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B22,
+ },
+ [0x10B23]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B23,
+ },
+ [0x10B24]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B24,
+ },
+ [0x10B25]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B25,
+ },
+ [0x10B26]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B26,
+ },
+ [0x10B27]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B27,
+ },
+ [0x10B28]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B28,
+ },
+ [0x10B29]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B29,
+ },
+ [0x10B2A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B2A,
+ },
+ [0x10B2B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B2B,
+ },
+ [0x10B2C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B2C,
+ },
+ [0x10B2D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B2D,
+ },
+ [0x10B2E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B2E,
+ },
+ [0x10B2F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B2F,
+ },
+ [0x10B30]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B30,
+ },
+ [0x10B31]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B31,
+ },
+ [0x10B32]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B32,
+ },
+ [0x10B33]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B33,
+ },
+ [0x10B34]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B34,
+ },
+ [0x10B35]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B35,
+ },
+ [0x10B39]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B39,
+ },
+ [0x10B3A]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B3A,
+ },
+ [0x10B3B]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B3B,
+ },
+ [0x10B3C]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B3C,
+ },
+ [0x10B3D]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B3D,
+ },
+ [0x10B3E]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B3E,
+ },
+ [0x10B3F]={
+ category="po",
+ direction="on",
+ linebreak="ba",
+ unicodeslot=0x10B3F,
+ },
+ [0x10B40]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B40,
+ },
+ [0x10B41]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B41,
+ },
+ [0x10B42]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B42,
+ },
+ [0x10B43]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B43,
+ },
+ [0x10B44]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B44,
+ },
+ [0x10B45]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B45,
+ },
+ [0x10B46]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B46,
+ },
+ [0x10B47]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B47,
+ },
+ [0x10B48]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B48,
+ },
+ [0x10B49]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B49,
+ },
+ [0x10B4A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B4A,
+ },
+ [0x10B4B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B4B,
+ },
+ [0x10B4C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B4C,
+ },
+ [0x10B4D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B4D,
+ },
+ [0x10B4E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B4E,
+ },
+ [0x10B4F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B4F,
+ },
+ [0x10B50]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B50,
+ },
+ [0x10B51]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B51,
+ },
+ [0x10B52]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B52,
+ },
+ [0x10B53]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B53,
+ },
+ [0x10B54]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B54,
+ },
+ [0x10B55]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B55,
+ },
+ [0x10B58]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B58,
+ },
+ [0x10B59]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B59,
+ },
+ [0x10B5A]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B5A,
+ },
+ [0x10B5B]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B5B,
+ },
+ [0x10B5C]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B5C,
+ },
+ [0x10B5D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B5D,
+ },
+ [0x10B5E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B5E,
+ },
+ [0x10B5F]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B5F,
+ },
+ [0x10B60]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B60,
+ },
+ [0x10B61]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B61,
+ },
+ [0x10B62]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B62,
+ },
+ [0x10B63]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B63,
+ },
+ [0x10B64]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B64,
+ },
+ [0x10B65]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B65,
+ },
+ [0x10B66]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B66,
+ },
+ [0x10B67]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B67,
+ },
+ [0x10B68]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B68,
+ },
+ [0x10B69]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B69,
+ },
+ [0x10B6A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B6A,
+ },
+ [0x10B6B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B6B,
+ },
+ [0x10B6C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B6C,
+ },
+ [0x10B6D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B6D,
+ },
+ [0x10B6E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B6E,
+ },
+ [0x10B6F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B6F,
+ },
+ [0x10B70]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B70,
+ },
+ [0x10B71]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B71,
+ },
+ [0x10B72]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B72,
+ },
+ [0x10B78]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B78,
+ },
+ [0x10B79]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B79,
+ },
+ [0x10B7A]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B7A,
+ },
+ [0x10B7B]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B7B,
+ },
+ [0x10B7C]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B7C,
+ },
+ [0x10B7D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B7D,
+ },
+ [0x10B7E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B7E,
+ },
+ [0x10B7F]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B7F,
+ },
+ [0x10B80]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B80,
+ },
+ [0x10B81]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B81,
+ },
+ [0x10B82]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B82,
+ },
+ [0x10B83]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B83,
+ },
+ [0x10B84]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B84,
+ },
+ [0x10B85]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B85,
+ },
+ [0x10B86]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B86,
+ },
+ [0x10B87]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B87,
+ },
+ [0x10B88]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B88,
+ },
+ [0x10B89]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B89,
+ },
+ [0x10B8A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B8A,
+ },
+ [0x10B8B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B8B,
+ },
+ [0x10B8C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B8C,
+ },
+ [0x10B8D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B8D,
+ },
+ [0x10B8E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B8E,
+ },
+ [0x10B8F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B8F,
+ },
+ [0x10B90]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B90,
+ },
+ [0x10B91]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B91,
+ },
+ [0x10B99]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B99,
+ },
+ [0x10B9A]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B9A,
+ },
+ [0x10B9B]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B9B,
+ },
+ [0x10B9C]={
+ category="po",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10B9C,
+ },
+ [0x10BA9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BA9,
+ },
+ [0x10BAA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BAA,
+ },
+ [0x10BAB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BAB,
+ },
+ [0x10BAC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BAC,
+ },
+ [0x10BAD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BAD,
+ },
+ [0x10BAE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BAE,
+ },
+ [0x10BAF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10BAF,
+ },
+ [0x10C00]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C00,
+ },
+ [0x10C01]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C01,
+ },
+ [0x10C02]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C02,
+ },
+ [0x10C03]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C03,
+ },
+ [0x10C04]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C04,
+ },
+ [0x10C05]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C05,
+ },
+ [0x10C06]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C06,
+ },
+ [0x10C07]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C07,
+ },
+ [0x10C08]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C08,
+ },
+ [0x10C09]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C09,
+ },
+ [0x10C0A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C0A,
+ },
+ [0x10C0B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C0B,
+ },
+ [0x10C0C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C0C,
+ },
+ [0x10C0D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C0D,
+ },
+ [0x10C0E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C0E,
+ },
+ [0x10C0F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C0F,
+ },
+ [0x10C10]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C10,
+ },
+ [0x10C11]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C11,
+ },
+ [0x10C12]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C12,
+ },
+ [0x10C13]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C13,
+ },
+ [0x10C14]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C14,
+ },
+ [0x10C15]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C15,
+ },
+ [0x10C16]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C16,
+ },
+ [0x10C17]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C17,
+ },
+ [0x10C18]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C18,
+ },
+ [0x10C19]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C19,
+ },
+ [0x10C1A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C1A,
+ },
+ [0x10C1B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C1B,
+ },
+ [0x10C1C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C1C,
+ },
+ [0x10C1D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C1D,
+ },
+ [0x10C1E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C1E,
+ },
+ [0x10C1F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C1F,
+ },
+ [0x10C20]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C20,
+ },
+ [0x10C21]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C21,
+ },
+ [0x10C22]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C22,
+ },
+ [0x10C23]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C23,
+ },
+ [0x10C24]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C24,
+ },
+ [0x10C25]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C25,
+ },
+ [0x10C26]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C26,
+ },
+ [0x10C27]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C27,
+ },
+ [0x10C28]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C28,
+ },
+ [0x10C29]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C29,
+ },
+ [0x10C2A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C2A,
+ },
+ [0x10C2B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C2B,
+ },
+ [0x10C2C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C2C,
+ },
+ [0x10C2D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C2D,
+ },
+ [0x10C2E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C2E,
+ },
+ [0x10C2F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C2F,
+ },
+ [0x10C30]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C30,
+ },
+ [0x10C31]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C31,
+ },
+ [0x10C32]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C32,
+ },
+ [0x10C33]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C33,
+ },
+ [0x10C34]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C34,
+ },
+ [0x10C35]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C35,
+ },
+ [0x10C36]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C36,
+ },
+ [0x10C37]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C37,
+ },
+ [0x10C38]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C38,
+ },
+ [0x10C39]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C39,
+ },
+ [0x10C3A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C3A,
+ },
+ [0x10C3B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C3B,
+ },
+ [0x10C3C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C3C,
+ },
+ [0x10C3D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C3D,
+ },
+ [0x10C3E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C3E,
+ },
+ [0x10C3F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C3F,
+ },
+ [0x10C40]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C40,
+ },
+ [0x10C41]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C41,
+ },
+ [0x10C42]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C42,
+ },
+ [0x10C43]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C43,
+ },
+ [0x10C44]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C44,
+ },
+ [0x10C45]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C45,
+ },
+ [0x10C46]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C46,
+ },
+ [0x10C47]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C47,
+ },
+ [0x10C48]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C48,
+ },
+ [0x10C80]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C80,
+ },
+ [0x10C81]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C81,
+ },
+ [0x10C82]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C82,
+ },
+ [0x10C83]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C83,
+ },
+ [0x10C84]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C84,
+ },
+ [0x10C85]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C85,
+ },
+ [0x10C86]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C86,
+ },
+ [0x10C87]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C87,
+ },
+ [0x10C88]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C88,
+ },
+ [0x10C89]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C89,
+ },
+ [0x10C8A]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C8A,
+ },
+ [0x10C8B]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C8B,
+ },
+ [0x10C8C]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C8C,
+ },
+ [0x10C8D]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C8D,
+ },
+ [0x10C8E]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C8E,
+ },
+ [0x10C8F]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C8F,
+ },
+ [0x10C90]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C90,
+ },
+ [0x10C91]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C91,
+ },
+ [0x10C92]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C92,
+ },
+ [0x10C93]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C93,
+ },
+ [0x10C94]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C94,
+ },
+ [0x10C95]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C95,
+ },
+ [0x10C96]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C96,
+ },
+ [0x10C97]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C97,
+ },
+ [0x10C98]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C98,
+ },
+ [0x10C99]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C99,
+ },
+ [0x10C9A]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C9A,
+ },
+ [0x10C9B]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C9B,
+ },
+ [0x10C9C]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C9C,
+ },
+ [0x10C9D]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C9D,
+ },
+ [0x10C9E]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C9E,
+ },
+ [0x10C9F]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10C9F,
+ },
+ [0x10CA0]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA0,
+ },
+ [0x10CA1]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA1,
+ },
+ [0x10CA2]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA2,
+ },
+ [0x10CA3]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA3,
+ },
+ [0x10CA4]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA4,
+ },
+ [0x10CA5]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA5,
+ },
+ [0x10CA6]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA6,
+ },
+ [0x10CA7]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA7,
+ },
+ [0x10CA8]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA8,
+ },
+ [0x10CA9]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CA9,
+ },
+ [0x10CAA]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CAA,
+ },
+ [0x10CAB]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CAB,
+ },
+ [0x10CAC]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CAC,
+ },
+ [0x10CAD]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CAD,
+ },
+ [0x10CAE]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CAE,
+ },
+ [0x10CAF]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CAF,
+ },
+ [0x10CB0]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CB0,
+ },
+ [0x10CB1]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CB1,
+ },
+ [0x10CB2]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CB2,
+ },
+ [0x10CC0]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC0,
+ },
+ [0x10CC1]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC1,
+ },
+ [0x10CC2]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC2,
+ },
+ [0x10CC3]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC3,
+ },
+ [0x10CC4]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC4,
+ },
+ [0x10CC5]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC5,
+ },
+ [0x10CC6]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC6,
+ },
+ [0x10CC7]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC7,
+ },
+ [0x10CC8]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC8,
+ },
+ [0x10CC9]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CC9,
+ },
+ [0x10CCA]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CCA,
+ },
+ [0x10CCB]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CCB,
+ },
+ [0x10CCC]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CCC,
+ },
+ [0x10CCD]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CCD,
+ },
+ [0x10CCE]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CCE,
+ },
+ [0x10CCF]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CCF,
+ },
+ [0x10CD0]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD0,
+ },
+ [0x10CD1]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD1,
+ },
+ [0x10CD2]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD2,
+ },
+ [0x10CD3]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD3,
+ },
+ [0x10CD4]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD4,
+ },
+ [0x10CD5]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD5,
+ },
+ [0x10CD6]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD6,
+ },
+ [0x10CD7]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD7,
+ },
+ [0x10CD8]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD8,
+ },
+ [0x10CD9]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CD9,
+ },
+ [0x10CDA]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CDA,
+ },
+ [0x10CDB]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CDB,
+ },
+ [0x10CDC]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CDC,
+ },
+ [0x10CDD]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CDD,
+ },
+ [0x10CDE]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CDE,
+ },
+ [0x10CDF]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CDF,
+ },
+ [0x10CE0]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE0,
+ },
+ [0x10CE1]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE1,
+ },
+ [0x10CE2]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE2,
+ },
+ [0x10CE3]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE3,
+ },
+ [0x10CE4]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE4,
+ },
+ [0x10CE5]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE5,
+ },
+ [0x10CE6]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE6,
+ },
+ [0x10CE7]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE7,
+ },
+ [0x10CE8]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE8,
+ },
+ [0x10CE9]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CE9,
+ },
+ [0x10CEA]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CEA,
+ },
+ [0x10CEB]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CEB,
+ },
+ [0x10CEC]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CEC,
+ },
+ [0x10CED]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CED,
+ },
+ [0x10CEE]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CEE,
+ },
+ [0x10CEF]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CEF,
+ },
+ [0x10CF0]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CF0,
+ },
+ [0x10CF1]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CF1,
+ },
+ [0x10CF2]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CF2,
+ },
+ [0x10CFA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CFA,
+ },
+ [0x10CFB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CFB,
+ },
+ [0x10CFC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CFC,
+ },
+ [0x10CFD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CFD,
+ },
+ [0x10CFE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CFE,
+ },
+ [0x10CFF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10CFF,
+ },
+ [0x10D00]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D00,
+ },
+ [0x10D01]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D01,
+ },
+ [0x10D02]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D02,
+ },
+ [0x10D03]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D03,
+ },
+ [0x10D04]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D04,
+ },
+ [0x10D05]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D05,
+ },
+ [0x10D06]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D06,
+ },
+ [0x10D07]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D07,
+ },
+ [0x10D08]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D08,
+ },
+ [0x10D09]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D09,
+ },
+ [0x10D0A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D0A,
+ },
+ [0x10D0B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D0B,
+ },
+ [0x10D0C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D0C,
+ },
+ [0x10D0D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D0D,
+ },
+ [0x10D0E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D0E,
+ },
+ [0x10D0F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D0F,
+ },
+ [0x10D10]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D10,
+ },
+ [0x10D11]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D11,
+ },
+ [0x10D12]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D12,
+ },
+ [0x10D13]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D13,
+ },
+ [0x10D14]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D14,
+ },
+ [0x10D15]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D15,
+ },
+ [0x10D16]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D16,
+ },
+ [0x10D17]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D17,
+ },
+ [0x10D18]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D18,
+ },
+ [0x10D19]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D19,
+ },
+ [0x10D1A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D1A,
+ },
+ [0x10D1B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D1B,
+ },
+ [0x10D1C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D1C,
+ },
+ [0x10D1D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D1D,
+ },
+ [0x10D1E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D1E,
+ },
+ [0x10D1F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D1F,
+ },
+ [0x10D20]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D20,
+ },
+ [0x10D21]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D21,
+ },
+ [0x10D22]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D22,
+ },
+ [0x10D23]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10D23,
+ },
+ [0x10D24]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10D24,
+ },
+ [0x10D25]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10D25,
+ },
+ [0x10D26]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10D26,
+ },
+ [0x10D27]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10D27,
+ },
+ [0x10D30]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D30,
+ },
+ [0x10D31]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D31,
+ },
+ [0x10D32]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D32,
+ },
+ [0x10D33]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D33,
+ },
+ [0x10D34]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D34,
+ },
+ [0x10D35]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D35,
+ },
+ [0x10D36]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D36,
+ },
+ [0x10D37]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D37,
+ },
+ [0x10D38]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D38,
+ },
+ [0x10D39]={
+ category="nd",
+ direction="an",
+ linebreak="nu",
+ unicodeslot=0x10D39,
+ },
+ [0x10E60]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E60,
+ },
+ [0x10E61]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E61,
+ },
+ [0x10E62]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E62,
+ },
+ [0x10E63]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E63,
+ },
+ [0x10E64]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E64,
+ },
+ [0x10E65]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E65,
+ },
+ [0x10E66]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E66,
+ },
+ [0x10E67]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E67,
+ },
+ [0x10E68]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E68,
+ },
+ [0x10E69]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E69,
+ },
+ [0x10E6A]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E6A,
+ },
+ [0x10E6B]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E6B,
+ },
+ [0x10E6C]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E6C,
+ },
+ [0x10E6D]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E6D,
+ },
+ [0x10E6E]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E6E,
+ },
+ [0x10E6F]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E6F,
+ },
+ [0x10E70]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E70,
+ },
+ [0x10E71]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E71,
+ },
+ [0x10E72]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E72,
+ },
+ [0x10E73]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E73,
+ },
+ [0x10E74]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E74,
+ },
+ [0x10E75]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E75,
+ },
+ [0x10E76]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E76,
+ },
+ [0x10E77]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E77,
+ },
+ [0x10E78]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E78,
+ },
+ [0x10E79]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E79,
+ },
+ [0x10E7A]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E7A,
+ },
+ [0x10E7B]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E7B,
+ },
+ [0x10E7C]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E7C,
+ },
+ [0x10E7D]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E7D,
+ },
+ [0x10E7E]={
+ category="no",
+ direction="an",
+ linebreak="al",
+ unicodeslot=0x10E7E,
+ },
+ [0x10F00]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F00,
+ },
+ [0x10F01]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F01,
+ },
+ [0x10F02]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F02,
+ },
+ [0x10F03]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F03,
+ },
+ [0x10F04]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F04,
+ },
+ [0x10F05]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F05,
+ },
+ [0x10F06]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F06,
+ },
+ [0x10F07]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F07,
+ },
+ [0x10F08]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F08,
+ },
+ [0x10F09]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F09,
+ },
+ [0x10F0A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F0A,
+ },
+ [0x10F0B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F0B,
+ },
+ [0x10F0C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F0C,
+ },
+ [0x10F0D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F0D,
+ },
+ [0x10F0E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F0E,
+ },
+ [0x10F0F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F0F,
+ },
+ [0x10F10]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F10,
+ },
+ [0x10F11]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F11,
+ },
+ [0x10F12]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F12,
+ },
+ [0x10F13]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F13,
+ },
+ [0x10F14]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F14,
+ },
+ [0x10F15]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F15,
+ },
+ [0x10F16]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F16,
+ },
+ [0x10F17]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F17,
+ },
+ [0x10F18]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F18,
+ },
+ [0x10F19]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F19,
+ },
+ [0x10F1A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F1A,
+ },
+ [0x10F1B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F1B,
+ },
+ [0x10F1C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F1C,
+ },
+ [0x10F1D]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F1D,
+ },
+ [0x10F1E]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F1E,
+ },
+ [0x10F1F]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F1F,
+ },
+ [0x10F20]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F20,
+ },
+ [0x10F21]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F21,
+ },
+ [0x10F22]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F22,
+ },
+ [0x10F23]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F23,
+ },
+ [0x10F24]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F24,
+ },
+ [0x10F25]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F25,
+ },
+ [0x10F26]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F26,
+ },
+ [0x10F27]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10F27,
+ },
+ [0x10F30]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F30,
+ },
+ [0x10F31]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F31,
+ },
+ [0x10F32]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F32,
+ },
+ [0x10F33]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F33,
+ },
+ [0x10F34]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F34,
+ },
+ [0x10F35]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F35,
+ },
+ [0x10F36]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F36,
+ },
+ [0x10F37]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F37,
+ },
+ [0x10F38]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F38,
+ },
+ [0x10F39]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F39,
+ },
+ [0x10F3A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F3A,
+ },
+ [0x10F3B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F3B,
+ },
+ [0x10F3C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F3C,
+ },
+ [0x10F3D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F3D,
+ },
+ [0x10F3E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F3E,
+ },
+ [0x10F3F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F3F,
+ },
+ [0x10F40]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F40,
+ },
+ [0x10F41]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F41,
+ },
+ [0x10F42]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F42,
+ },
+ [0x10F43]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F43,
+ },
+ [0x10F44]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F44,
+ },
+ [0x10F45]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F45,
+ },
+ [0x10F46]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F46,
+ },
+ [0x10F47]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F47,
+ },
+ [0x10F48]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F48,
+ },
+ [0x10F49]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F49,
+ },
+ [0x10F4A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F4A,
+ },
+ [0x10F4B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F4B,
+ },
+ [0x10F4C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F4C,
+ },
+ [0x10F4D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F4D,
+ },
+ [0x10F4E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F4E,
+ },
+ [0x10F4F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F4F,
+ },
+ [0x10F50]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x10F50,
+ },
+ [0x10F51]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F51,
+ },
+ [0x10F52]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F52,
+ },
+ [0x10F53]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F53,
+ },
+ [0x10F54]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F54,
+ },
+ [0x10F55]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F55,
+ },
+ [0x10F56]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F56,
+ },
+ [0x10F57]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F57,
+ },
+ [0x10F58]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F58,
+ },
+ [0x10F59]={
+ category="po",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x10F59,
+ },
+ [0x10FE0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE0,
+ },
+ [0x10FE1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE1,
+ },
+ [0x10FE2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE2,
+ },
+ [0x10FE3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE3,
+ },
+ [0x10FE4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE4,
+ },
+ [0x10FE5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE5,
+ },
+ [0x10FE6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE6,
+ },
+ [0x10FE7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE7,
+ },
+ [0x10FE8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE8,
+ },
+ [0x10FE9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FE9,
+ },
+ [0x10FEA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FEA,
+ },
+ [0x10FEB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FEB,
+ },
+ [0x10FEC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FEC,
+ },
+ [0x10FED]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FED,
+ },
+ [0x10FEE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FEE,
+ },
+ [0x10FEF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FEF,
+ },
+ [0x10FF0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF0,
+ },
+ [0x10FF1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF1,
+ },
+ [0x10FF2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF2,
+ },
+ [0x10FF3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF3,
+ },
+ [0x10FF4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF4,
+ },
+ [0x10FF5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF5,
+ },
+ [0x10FF6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x10FF6,
+ },
+ [0x11000]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11000,
+ },
+ [0x11001]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11001,
+ },
+ [0x11002]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11002,
+ },
+ [0x11003]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11003,
+ },
+ [0x11004]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11004,
+ },
+ [0x11005]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11005,
+ },
+ [0x11006]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11006,
+ },
+ [0x11007]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11007,
+ },
+ [0x11008]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11008,
+ },
+ [0x11009]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11009,
+ },
+ [0x1100A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1100A,
+ },
+ [0x1100B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1100B,
+ },
+ [0x1100C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1100C,
+ },
+ [0x1100D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1100D,
+ },
+ [0x1100E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1100E,
+ },
+ [0x1100F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1100F,
+ },
+ [0x11010]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11010,
+ },
+ [0x11011]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11011,
+ },
+ [0x11012]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11012,
+ },
+ [0x11013]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11013,
+ },
+ [0x11014]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11014,
+ },
+ [0x11015]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11015,
+ },
+ [0x11016]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11016,
+ },
+ [0x11017]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11017,
+ },
+ [0x11018]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11018,
+ },
+ [0x11019]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11019,
+ },
+ [0x1101A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1101A,
+ },
+ [0x1101B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1101B,
+ },
+ [0x1101C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1101C,
+ },
+ [0x1101D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1101D,
+ },
+ [0x1101E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1101E,
+ },
+ [0x1101F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1101F,
+ },
+ [0x11020]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11020,
+ },
+ [0x11021]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11021,
+ },
+ [0x11022]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11022,
+ },
+ [0x11023]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11023,
+ },
+ [0x11024]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11024,
+ },
+ [0x11025]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11025,
+ },
+ [0x11026]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11026,
+ },
+ [0x11027]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11027,
+ },
+ [0x11028]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11028,
+ },
+ [0x11029]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11029,
+ },
+ [0x1102A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1102A,
+ },
+ [0x1102B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1102B,
+ },
+ [0x1102C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1102C,
+ },
+ [0x1102D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1102D,
+ },
+ [0x1102E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1102E,
+ },
+ [0x1102F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1102F,
+ },
+ [0x11030]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11030,
+ },
+ [0x11031]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11031,
+ },
+ [0x11032]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11032,
+ },
+ [0x11033]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11033,
+ },
+ [0x11034]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11034,
+ },
+ [0x11035]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11035,
+ },
+ [0x11036]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11036,
+ },
+ [0x11037]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11037,
+ },
+ [0x11038]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11038,
+ },
+ [0x11039]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11039,
+ },
+ [0x1103A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1103A,
+ },
+ [0x1103B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1103B,
+ },
+ [0x1103C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1103C,
+ },
+ [0x1103D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1103D,
+ },
+ [0x1103E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1103E,
+ },
+ [0x1103F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1103F,
+ },
+ [0x11040]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11040,
+ },
+ [0x11041]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11041,
+ },
+ [0x11042]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11042,
+ },
+ [0x11043]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11043,
+ },
+ [0x11044]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11044,
+ },
+ [0x11045]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11045,
+ },
+ [0x11046]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11046,
+ },
+ [0x11047]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11047,
+ },
+ [0x11048]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11048,
+ },
+ [0x11049]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11049,
+ },
+ [0x1104A]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1104A,
+ },
+ [0x1104B]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1104B,
+ },
+ [0x1104C]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1104C,
+ },
+ [0x1104D]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1104D,
+ },
+ [0x11052]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11052,
+ },
+ [0x11053]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11053,
+ },
+ [0x11054]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11054,
+ },
+ [0x11055]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11055,
+ },
+ [0x11056]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11056,
+ },
+ [0x11057]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11057,
+ },
+ [0x11058]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11058,
+ },
+ [0x11059]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11059,
+ },
+ [0x1105A]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1105A,
+ },
+ [0x1105B]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1105B,
+ },
+ [0x1105C]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1105C,
+ },
+ [0x1105D]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1105D,
+ },
+ [0x1105E]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1105E,
+ },
+ [0x1105F]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1105F,
+ },
+ [0x11060]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11060,
+ },
+ [0x11061]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11061,
+ },
+ [0x11062]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11062,
+ },
+ [0x11063]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11063,
+ },
+ [0x11064]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11064,
+ },
+ [0x11065]={
+ category="no",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11065,
+ },
+ [0x11066]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11066,
+ },
+ [0x11067]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11067,
+ },
+ [0x11068]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11068,
+ },
+ [0x11069]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11069,
+ },
+ [0x1106A]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1106A,
+ },
+ [0x1106B]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1106B,
+ },
+ [0x1106C]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1106C,
+ },
+ [0x1106D]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1106D,
+ },
+ [0x1106E]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1106E,
+ },
+ [0x1106F]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1106F,
+ },
+ [0x1107F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1107F,
+ },
+ [0x11080]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11080,
+ },
+ [0x11081]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11081,
+ },
+ [0x11082]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11082,
+ },
+ [0x11083]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11083,
+ },
+ [0x11084]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11084,
+ },
+ [0x11085]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11085,
+ },
+ [0x11086]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11086,
+ },
+ [0x11087]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11087,
+ },
+ [0x11088]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11088,
+ },
+ [0x11089]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11089,
+ },
+ [0x1108A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1108A,
+ },
+ [0x1108B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1108B,
+ },
+ [0x1108C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1108C,
+ },
+ [0x1108D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1108D,
+ },
+ [0x1108E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1108E,
+ },
+ [0x1108F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1108F,
+ },
+ [0x11090]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11090,
+ },
+ [0x11091]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11091,
+ },
+ [0x11092]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11092,
+ },
+ [0x11093]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11093,
+ },
+ [0x11094]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11094,
+ },
+ [0x11095]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11095,
+ },
+ [0x11096]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11096,
+ },
+ [0x11097]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11097,
+ },
+ [0x11098]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11098,
+ },
+ [0x11099]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11099,
+ },
+ [0x1109A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x11099, 0x110BA },
+ unicodeslot=0x1109A,
+ },
+ [0x1109B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1109B,
+ },
+ [0x1109C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1109B, 0x110BA },
+ unicodeslot=0x1109C,
+ },
+ [0x1109D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1109D,
+ },
+ [0x1109E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1109E,
+ },
+ [0x1109F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1109F,
+ },
+ [0x110A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A0,
+ },
+ [0x110A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A1,
+ },
+ [0x110A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A2,
+ },
+ [0x110A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A3,
+ },
+ [0x110A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A4,
+ },
+ [0x110A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A5,
+ },
+ [0x110A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A6,
+ },
+ [0x110A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A7,
+ },
+ [0x110A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A8,
+ },
+ [0x110A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110A9,
+ },
+ [0x110AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110AA,
+ },
+ [0x110AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x110A5, 0x110BA },
+ unicodeslot=0x110AB,
+ },
+ [0x110AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110AC,
+ },
+ [0x110AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110AD,
+ },
+ [0x110AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110AE,
+ },
+ [0x110AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110AF,
+ },
+ [0x110B0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x110B0,
+ },
+ [0x110B1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x110B1,
+ },
+ [0x110B2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x110B2,
+ },
+ [0x110B3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x110B3,
+ },
+ [0x110B4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x110B4,
+ },
+ [0x110B5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x110B5,
+ },
+ [0x110B6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x110B6,
+ },
+ [0x110B7]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x110B7,
+ },
+ [0x110B8]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x110B8,
+ },
+ [0x110B9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x110B9,
+ },
+ [0x110BA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x110BA,
+ },
+ [0x110BB]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110BB,
+ },
+ [0x110BC]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110BC,
+ },
+ [0x110BD]={
+ category="cf",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110BD,
+ },
+ [0x110BE]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x110BE,
+ },
+ [0x110BF]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x110BF,
+ },
+ [0x110C0]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x110C0,
+ },
+ [0x110C1]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x110C1,
+ },
+ [0x110CD]={
+ category="cf",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110CD,
+ },
+ [0x110D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D0,
+ },
+ [0x110D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D1,
+ },
+ [0x110D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D2,
+ },
+ [0x110D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D3,
+ },
+ [0x110D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D4,
+ },
+ [0x110D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D5,
+ },
+ [0x110D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D6,
+ },
+ [0x110D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D7,
+ },
+ [0x110D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D8,
+ },
+ [0x110D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110D9,
+ },
+ [0x110DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110DA,
+ },
+ [0x110DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110DB,
+ },
+ [0x110DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110DC,
+ },
+ [0x110DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110DD,
+ },
+ [0x110DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110DE,
+ },
+ [0x110DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110DF,
+ },
+ [0x110E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E0,
+ },
+ [0x110E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E1,
+ },
+ [0x110E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E2,
+ },
+ [0x110E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E3,
+ },
+ [0x110E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E4,
+ },
+ [0x110E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E5,
+ },
+ [0x110E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E6,
+ },
+ [0x110E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E7,
+ },
+ [0x110E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x110E8,
+ },
+ [0x110F0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F0,
+ },
+ [0x110F1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F1,
+ },
+ [0x110F2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F2,
+ },
+ [0x110F3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F3,
+ },
+ [0x110F4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F4,
+ },
+ [0x110F5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F5,
+ },
+ [0x110F6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F6,
+ },
+ [0x110F7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F7,
+ },
+ [0x110F8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F8,
+ },
+ [0x110F9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x110F9,
+ },
+ [0x11100]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11100,
+ },
+ [0x11101]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11101,
+ },
+ [0x11102]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11102,
+ },
+ [0x11103]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11103,
+ },
+ [0x11104]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11104,
+ },
+ [0x11105]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11105,
+ },
+ [0x11106]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11106,
+ },
+ [0x11107]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11107,
+ },
+ [0x11108]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11108,
+ },
+ [0x11109]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11109,
+ },
+ [0x1110A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1110A,
+ },
+ [0x1110B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1110B,
+ },
+ [0x1110C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1110C,
+ },
+ [0x1110D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1110D,
+ },
+ [0x1110E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1110E,
+ },
+ [0x1110F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1110F,
+ },
+ [0x11110]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11110,
+ },
+ [0x11111]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11111,
+ },
+ [0x11112]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11112,
+ },
+ [0x11113]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11113,
+ },
+ [0x11114]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11114,
+ },
+ [0x11115]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11115,
+ },
+ [0x11116]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11116,
+ },
+ [0x11117]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11117,
+ },
+ [0x11118]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11118,
+ },
+ [0x11119]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11119,
+ },
+ [0x1111A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1111A,
+ },
+ [0x1111B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1111B,
+ },
+ [0x1111C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1111C,
+ },
+ [0x1111D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1111D,
+ },
+ [0x1111E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1111E,
+ },
+ [0x1111F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1111F,
+ },
+ [0x11120]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11120,
+ },
+ [0x11121]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11121,
+ },
+ [0x11122]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11122,
+ },
+ [0x11123]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11123,
+ },
+ [0x11124]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11124,
+ },
+ [0x11125]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11125,
+ },
+ [0x11126]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11126,
+ },
+ [0x11127]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11127,
+ },
+ [0x11128]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11128,
+ },
+ [0x11129]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11129,
+ },
+ [0x1112A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1112A,
+ },
+ [0x1112B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1112B,
+ },
+ [0x1112C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1112C,
+ },
+ [0x1112D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1112D,
+ },
+ [0x1112E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0x11131, 0x11127 },
+ unicodeslot=0x1112E,
+ },
+ [0x1112F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ specials={ "char", 0x11132, 0x11127 },
+ unicodeslot=0x1112F,
+ },
+ [0x11130]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11130,
+ },
+ [0x11131]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11131,
+ },
+ [0x11132]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11132,
+ },
+ [0x11133]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11133,
+ },
+ [0x11134]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11134,
+ },
+ [0x11136]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11136,
+ },
+ [0x11137]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11137,
+ },
+ [0x11138]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11138,
+ },
+ [0x11139]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11139,
+ },
+ [0x1113A]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1113A,
+ },
+ [0x1113B]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1113B,
+ },
+ [0x1113C]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1113C,
+ },
+ [0x1113D]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1113D,
+ },
+ [0x1113E]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1113E,
+ },
+ [0x1113F]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1113F,
+ },
+ [0x11140]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11140,
+ },
+ [0x11141]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11141,
+ },
+ [0x11142]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11142,
+ },
+ [0x11143]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11143,
+ },
+ [0x11144]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11144,
+ },
+ [0x11145]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11145,
+ },
+ [0x11146]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11146,
+ },
+ [0x11150]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11150,
+ },
+ [0x11151]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11151,
+ },
+ [0x11152]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11152,
+ },
+ [0x11153]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11153,
+ },
+ [0x11154]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11154,
+ },
+ [0x11155]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11155,
+ },
+ [0x11156]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11156,
+ },
+ [0x11157]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11157,
+ },
+ [0x11158]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11158,
+ },
+ [0x11159]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11159,
+ },
+ [0x1115A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1115A,
+ },
+ [0x1115B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1115B,
+ },
+ [0x1115C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1115C,
+ },
+ [0x1115D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1115D,
+ },
+ [0x1115E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1115E,
+ },
+ [0x1115F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1115F,
+ },
+ [0x11160]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11160,
+ },
+ [0x11161]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11161,
+ },
+ [0x11162]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11162,
+ },
+ [0x11163]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11163,
+ },
+ [0x11164]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11164,
+ },
+ [0x11165]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11165,
+ },
+ [0x11166]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11166,
+ },
+ [0x11167]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11167,
+ },
+ [0x11168]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11168,
+ },
+ [0x11169]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11169,
+ },
+ [0x1116A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1116A,
+ },
+ [0x1116B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1116B,
+ },
+ [0x1116C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1116C,
+ },
+ [0x1116D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1116D,
+ },
+ [0x1116E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1116E,
+ },
+ [0x1116F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1116F,
+ },
+ [0x11170]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11170,
+ },
+ [0x11171]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11171,
+ },
+ [0x11172]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11172,
+ },
+ [0x11173]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11173,
+ },
+ [0x11174]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11174,
+ },
+ [0x11175]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11175,
+ },
+ [0x11176]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11176,
+ },
+ [0x11180]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11180,
+ },
+ [0x11181]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11181,
+ },
+ [0x11182]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11182,
+ },
+ [0x11183]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11183,
+ },
+ [0x11184]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11184,
+ },
+ [0x11185]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11185,
+ },
+ [0x11186]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11186,
+ },
+ [0x11187]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11187,
+ },
+ [0x11188]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11188,
+ },
+ [0x11189]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11189,
+ },
+ [0x1118A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1118A,
+ },
+ [0x1118B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1118B,
+ },
+ [0x1118C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1118C,
+ },
+ [0x1118D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1118D,
+ },
+ [0x1118E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1118E,
+ },
+ [0x1118F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1118F,
+ },
+ [0x11190]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11190,
+ },
+ [0x11191]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11191,
+ },
+ [0x11192]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11192,
+ },
+ [0x11193]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11193,
+ },
+ [0x11194]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11194,
+ },
+ [0x11195]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11195,
+ },
+ [0x11196]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11196,
+ },
+ [0x11197]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11197,
+ },
+ [0x11198]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11198,
+ },
+ [0x11199]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11199,
+ },
+ [0x1119A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1119A,
+ },
+ [0x1119B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1119B,
+ },
+ [0x1119C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1119C,
+ },
+ [0x1119D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1119D,
+ },
+ [0x1119E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1119E,
+ },
+ [0x1119F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1119F,
+ },
+ [0x111A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A0,
+ },
+ [0x111A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A1,
+ },
+ [0x111A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A2,
+ },
+ [0x111A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A3,
+ },
+ [0x111A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A4,
+ },
+ [0x111A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A5,
+ },
+ [0x111A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A6,
+ },
+ [0x111A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A7,
+ },
+ [0x111A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A8,
+ },
+ [0x111A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111A9,
+ },
+ [0x111AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111AA,
+ },
+ [0x111AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111AB,
+ },
+ [0x111AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111AC,
+ },
+ [0x111AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111AD,
+ },
+ [0x111AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111AE,
+ },
+ [0x111AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111AF,
+ },
+ [0x111B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111B0,
+ },
+ [0x111B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111B1,
+ },
+ [0x111B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111B2,
+ },
+ [0x111B3]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x111B3,
+ },
+ [0x111B4]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x111B4,
+ },
+ [0x111B5]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x111B5,
+ },
+ [0x111B6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111B6,
+ },
+ [0x111B7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111B7,
+ },
+ [0x111B8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111B8,
+ },
+ [0x111B9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111B9,
+ },
+ [0x111BA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111BA,
+ },
+ [0x111BB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111BB,
+ },
+ [0x111BC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111BC,
+ },
+ [0x111BD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111BD,
+ },
+ [0x111BE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111BE,
+ },
+ [0x111BF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x111BF,
+ },
+ [0x111C0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x111C0,
+ },
+ [0x111C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111C1,
+ },
+ [0x111C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111C2,
+ },
+ [0x111C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111C3,
+ },
+ [0x111C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111C4,
+ },
+ [0x111C5]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x111C5,
+ },
+ [0x111C6]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x111C6,
+ },
+ [0x111C7]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111C7,
+ },
+ [0x111C8]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x111C8,
+ },
+ [0x111C9]={
+ category="po",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111C9,
+ },
+ [0x111CA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111CA,
+ },
+ [0x111CB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111CB,
+ },
+ [0x111CC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x111CC,
+ },
+ [0x111CD]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111CD,
+ },
+ [0x111D0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D0,
+ },
+ [0x111D1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D1,
+ },
+ [0x111D2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D2,
+ },
+ [0x111D3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D3,
+ },
+ [0x111D4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D4,
+ },
+ [0x111D5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D5,
+ },
+ [0x111D6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D6,
+ },
+ [0x111D7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D7,
+ },
+ [0x111D8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D8,
+ },
+ [0x111D9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x111D9,
+ },
+ [0x111DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111DA,
+ },
+ [0x111DB]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x111DB,
+ },
+ [0x111DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111DC,
+ },
+ [0x111DD]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x111DD,
+ },
+ [0x111DE]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x111DE,
+ },
+ [0x111DF]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x111DF,
+ },
+ [0x111E1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E1,
+ },
+ [0x111E2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E2,
+ },
+ [0x111E3]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E3,
+ },
+ [0x111E4]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E4,
+ },
+ [0x111E5]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E5,
+ },
+ [0x111E6]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E6,
+ },
+ [0x111E7]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E7,
+ },
+ [0x111E8]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E8,
+ },
+ [0x111E9]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111E9,
+ },
+ [0x111EA]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111EA,
+ },
+ [0x111EB]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111EB,
+ },
+ [0x111EC]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111EC,
+ },
+ [0x111ED]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111ED,
+ },
+ [0x111EE]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111EE,
+ },
+ [0x111EF]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111EF,
+ },
+ [0x111F0]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111F0,
+ },
+ [0x111F1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111F1,
+ },
+ [0x111F2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111F2,
+ },
+ [0x111F3]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111F3,
+ },
+ [0x111F4]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x111F4,
+ },
+ [0x11200]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11200,
+ },
+ [0x11201]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11201,
+ },
+ [0x11202]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11202,
+ },
+ [0x11203]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11203,
+ },
+ [0x11204]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11204,
+ },
+ [0x11205]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11205,
+ },
+ [0x11206]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11206,
+ },
+ [0x11207]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11207,
+ },
+ [0x11208]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11208,
+ },
+ [0x11209]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11209,
+ },
+ [0x1120A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1120A,
+ },
+ [0x1120B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1120B,
+ },
+ [0x1120C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1120C,
+ },
+ [0x1120D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1120D,
+ },
+ [0x1120E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1120E,
+ },
+ [0x1120F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1120F,
+ },
+ [0x11210]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11210,
+ },
+ [0x11211]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11211,
+ },
+ [0x11213]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11213,
+ },
+ [0x11214]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11214,
+ },
+ [0x11215]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11215,
+ },
+ [0x11216]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11216,
+ },
+ [0x11217]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11217,
+ },
+ [0x11218]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11218,
+ },
+ [0x11219]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11219,
+ },
+ [0x1121A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1121A,
+ },
+ [0x1121B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1121B,
+ },
+ [0x1121C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1121C,
+ },
+ [0x1121D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1121D,
+ },
+ [0x1121E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1121E,
+ },
+ [0x1121F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1121F,
+ },
+ [0x11220]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11220,
+ },
+ [0x11221]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11221,
+ },
+ [0x11222]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11222,
+ },
+ [0x11223]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11223,
+ },
+ [0x11224]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11224,
+ },
+ [0x11225]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11225,
+ },
+ [0x11226]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11226,
+ },
+ [0x11227]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11227,
+ },
+ [0x11228]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11228,
+ },
+ [0x11229]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11229,
+ },
+ [0x1122A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1122A,
+ },
+ [0x1122B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1122B,
+ },
+ [0x1122C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1122C,
+ },
+ [0x1122D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1122D,
+ },
+ [0x1122E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1122E,
+ },
+ [0x1122F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1122F,
+ },
+ [0x11230]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11230,
+ },
+ [0x11231]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11231,
+ },
+ [0x11232]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11232,
+ },
+ [0x11233]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11233,
+ },
+ [0x11234]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11234,
+ },
+ [0x11235]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11235,
+ },
+ [0x11236]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11236,
+ },
+ [0x11237]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11237,
+ },
+ [0x11238]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11238,
+ },
+ [0x11239]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11239,
+ },
+ [0x1123A]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1123A,
+ },
+ [0x1123B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1123B,
+ },
+ [0x1123C]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1123C,
+ },
+ [0x1123D]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1123D,
+ },
+ [0x1123E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1123E,
+ },
+ [0x11280]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11280,
+ },
+ [0x11281]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11281,
+ },
+ [0x11282]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11282,
+ },
+ [0x11283]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11283,
+ },
+ [0x11284]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11284,
+ },
+ [0x11285]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11285,
+ },
+ [0x11286]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11286,
+ },
+ [0x11288]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11288,
+ },
+ [0x1128A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1128A,
+ },
+ [0x1128B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1128B,
+ },
+ [0x1128C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1128C,
+ },
+ [0x1128D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1128D,
+ },
+ [0x1128F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1128F,
+ },
+ [0x11290]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11290,
+ },
+ [0x11291]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11291,
+ },
+ [0x11292]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11292,
+ },
+ [0x11293]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11293,
+ },
+ [0x11294]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11294,
+ },
+ [0x11295]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11295,
+ },
+ [0x11296]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11296,
+ },
+ [0x11297]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11297,
+ },
+ [0x11298]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11298,
+ },
+ [0x11299]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11299,
+ },
+ [0x1129A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1129A,
+ },
+ [0x1129B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1129B,
+ },
+ [0x1129C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1129C,
+ },
+ [0x1129D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1129D,
+ },
+ [0x1129F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1129F,
+ },
+ [0x112A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A0,
+ },
+ [0x112A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A1,
+ },
+ [0x112A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A2,
+ },
+ [0x112A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A3,
+ },
+ [0x112A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A4,
+ },
+ [0x112A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A5,
+ },
+ [0x112A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A6,
+ },
+ [0x112A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A7,
+ },
+ [0x112A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112A8,
+ },
+ [0x112A9]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x112A9,
+ },
+ [0x112B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B0,
+ },
+ [0x112B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B1,
+ },
+ [0x112B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B2,
+ },
+ [0x112B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B3,
+ },
+ [0x112B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B4,
+ },
+ [0x112B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B5,
+ },
+ [0x112B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B6,
+ },
+ [0x112B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B7,
+ },
+ [0x112B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B8,
+ },
+ [0x112B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112B9,
+ },
+ [0x112BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112BA,
+ },
+ [0x112BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112BB,
+ },
+ [0x112BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112BC,
+ },
+ [0x112BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112BD,
+ },
+ [0x112BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112BE,
+ },
+ [0x112BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112BF,
+ },
+ [0x112C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C0,
+ },
+ [0x112C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C1,
+ },
+ [0x112C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C2,
+ },
+ [0x112C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C3,
+ },
+ [0x112C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C4,
+ },
+ [0x112C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C5,
+ },
+ [0x112C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C6,
+ },
+ [0x112C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C7,
+ },
+ [0x112C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C8,
+ },
+ [0x112C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112C9,
+ },
+ [0x112CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112CA,
+ },
+ [0x112CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112CB,
+ },
+ [0x112CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112CC,
+ },
+ [0x112CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112CD,
+ },
+ [0x112CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112CE,
+ },
+ [0x112CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112CF,
+ },
+ [0x112D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D0,
+ },
+ [0x112D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D1,
+ },
+ [0x112D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D2,
+ },
+ [0x112D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D3,
+ },
+ [0x112D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D4,
+ },
+ [0x112D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D5,
+ },
+ [0x112D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D6,
+ },
+ [0x112D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D7,
+ },
+ [0x112D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D8,
+ },
+ [0x112D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112D9,
+ },
+ [0x112DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112DA,
+ },
+ [0x112DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112DB,
+ },
+ [0x112DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112DC,
+ },
+ [0x112DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112DD,
+ },
+ [0x112DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x112DE,
+ },
+ [0x112DF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112DF,
+ },
+ [0x112E0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x112E0,
+ },
+ [0x112E1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x112E1,
+ },
+ [0x112E2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x112E2,
+ },
+ [0x112E3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E3,
+ },
+ [0x112E4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E4,
+ },
+ [0x112E5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E5,
+ },
+ [0x112E6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E6,
+ },
+ [0x112E7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E7,
+ },
+ [0x112E8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E8,
+ },
+ [0x112E9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112E9,
+ },
+ [0x112EA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x112EA,
+ },
+ [0x112F0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F0,
+ },
+ [0x112F1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F1,
+ },
+ [0x112F2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F2,
+ },
+ [0x112F3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F3,
+ },
+ [0x112F4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F4,
+ },
+ [0x112F5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F5,
+ },
+ [0x112F6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F6,
+ },
+ [0x112F7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F7,
+ },
+ [0x112F8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F8,
+ },
+ [0x112F9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x112F9,
+ },
+ [0x11300]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11300,
+ },
+ [0x11301]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11301,
+ },
+ [0x11302]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11302,
+ },
+ [0x11303]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11303,
+ },
+ [0x11305]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11305,
+ },
+ [0x11306]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11306,
+ },
+ [0x11307]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11307,
+ },
+ [0x11308]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11308,
+ },
+ [0x11309]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11309,
+ },
+ [0x1130A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1130A,
+ },
+ [0x1130B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1130B,
+ },
+ [0x1130C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1130C,
+ },
+ [0x1130F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1130F,
+ },
+ [0x11310]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11310,
+ },
+ [0x11313]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11313,
+ },
+ [0x11314]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11314,
+ },
+ [0x11315]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11315,
+ },
+ [0x11316]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11316,
+ },
+ [0x11317]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11317,
+ },
+ [0x11318]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11318,
+ },
+ [0x11319]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11319,
+ },
+ [0x1131A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1131A,
+ },
+ [0x1131B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1131B,
+ },
+ [0x1131C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1131C,
+ },
+ [0x1131D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1131D,
+ },
+ [0x1131E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1131E,
+ },
+ [0x1131F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1131F,
+ },
+ [0x11320]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11320,
+ },
+ [0x11321]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11321,
+ },
+ [0x11322]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11322,
+ },
+ [0x11323]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11323,
+ },
+ [0x11324]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11324,
+ },
+ [0x11325]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11325,
+ },
+ [0x11326]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11326,
+ },
+ [0x11327]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11327,
+ },
+ [0x11328]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11328,
+ },
+ [0x1132A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1132A,
+ },
+ [0x1132B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1132B,
+ },
+ [0x1132C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1132C,
+ },
+ [0x1132D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1132D,
+ },
+ [0x1132E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1132E,
+ },
+ [0x1132F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1132F,
+ },
+ [0x11330]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11330,
+ },
+ [0x11332]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11332,
+ },
+ [0x11333]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11333,
+ },
+ [0x11335]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11335,
+ },
+ [0x11336]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11336,
+ },
+ [0x11337]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11337,
+ },
+ [0x11338]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11338,
+ },
+ [0x11339]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11339,
+ },
+ [0x1133B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1133B,
+ },
+ [0x1133C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1133C,
+ },
+ [0x1133D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1133D,
+ },
+ [0x1133E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1133E,
+ },
+ [0x1133F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1133F,
+ },
+ [0x11340]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11340,
+ },
+ [0x11341]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11341,
+ },
+ [0x11342]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11342,
+ },
+ [0x11343]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11343,
+ },
+ [0x11344]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11344,
+ },
+ [0x11347]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11347,
+ },
+ [0x11348]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11348,
+ },
+ [0x1134B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x11347, 0x1133E },
+ unicodeslot=0x1134B,
+ },
+ [0x1134C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x11347, 0x11357 },
+ unicodeslot=0x1134C,
+ },
+ [0x1134D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1134D,
+ },
+ [0x11350]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11350,
+ },
+ [0x11357]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11357,
+ },
+ [0x1135D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1135D,
+ },
+ [0x1135E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1135E,
+ },
+ [0x1135F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1135F,
+ },
+ [0x11360]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11360,
+ },
+ [0x11361]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11361,
+ },
+ [0x11362]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11362,
+ },
+ [0x11363]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11363,
+ },
+ [0x11366]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11366,
+ },
+ [0x11367]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11367,
+ },
+ [0x11368]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11368,
+ },
+ [0x11369]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11369,
+ },
+ [0x1136A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1136A,
+ },
+ [0x1136B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1136B,
+ },
+ [0x1136C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1136C,
+ },
+ [0x11370]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11370,
+ },
+ [0x11371]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11371,
+ },
+ [0x11372]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11372,
+ },
+ [0x11373]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11373,
+ },
+ [0x11374]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11374,
+ },
+ [0x11400]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11400,
+ },
+ [0x11401]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11401,
+ },
+ [0x11402]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11402,
+ },
+ [0x11403]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11403,
+ },
+ [0x11404]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11404,
+ },
+ [0x11405]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11405,
+ },
+ [0x11406]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11406,
+ },
+ [0x11407]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11407,
+ },
+ [0x11408]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11408,
+ },
+ [0x11409]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11409,
+ },
+ [0x1140A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1140A,
+ },
+ [0x1140B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1140B,
+ },
+ [0x1140C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1140C,
+ },
+ [0x1140D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1140D,
+ },
+ [0x1140E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1140E,
+ },
+ [0x1140F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1140F,
+ },
+ [0x11410]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11410,
+ },
+ [0x11411]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11411,
+ },
+ [0x11412]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11412,
+ },
+ [0x11413]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11413,
+ },
+ [0x11414]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11414,
+ },
+ [0x11415]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11415,
+ },
+ [0x11416]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11416,
+ },
+ [0x11417]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11417,
+ },
+ [0x11418]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11418,
+ },
+ [0x11419]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11419,
+ },
+ [0x1141A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1141A,
+ },
+ [0x1141B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1141B,
+ },
+ [0x1141C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1141C,
+ },
+ [0x1141D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1141D,
+ },
+ [0x1141E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1141E,
+ },
+ [0x1141F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1141F,
+ },
+ [0x11420]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11420,
+ },
+ [0x11421]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11421,
+ },
+ [0x11422]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11422,
+ },
+ [0x11423]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11423,
+ },
+ [0x11424]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11424,
+ },
+ [0x11425]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11425,
+ },
+ [0x11426]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11426,
+ },
+ [0x11427]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11427,
+ },
+ [0x11428]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11428,
+ },
+ [0x11429]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11429,
+ },
+ [0x1142A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1142A,
+ },
+ [0x1142B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1142B,
+ },
+ [0x1142C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1142C,
+ },
+ [0x1142D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1142D,
+ },
+ [0x1142E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1142E,
+ },
+ [0x1142F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1142F,
+ },
+ [0x11430]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11430,
+ },
+ [0x11431]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11431,
+ },
+ [0x11432]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11432,
+ },
+ [0x11433]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11433,
+ },
+ [0x11434]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11434,
+ },
+ [0x11435]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11435,
+ },
+ [0x11436]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11436,
+ },
+ [0x11437]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11437,
+ },
+ [0x11438]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11438,
+ },
+ [0x11439]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11439,
+ },
+ [0x1143A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1143A,
+ },
+ [0x1143B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1143B,
+ },
+ [0x1143C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1143C,
+ },
+ [0x1143D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1143D,
+ },
+ [0x1143E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1143E,
+ },
+ [0x1143F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1143F,
+ },
+ [0x11440]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11440,
+ },
+ [0x11441]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11441,
+ },
+ [0x11442]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11442,
+ },
+ [0x11443]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11443,
+ },
+ [0x11444]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11444,
+ },
+ [0x11445]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11445,
+ },
+ [0x11446]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11446,
+ },
+ [0x11447]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11447,
+ },
+ [0x11448]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11448,
+ },
+ [0x11449]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11449,
+ },
+ [0x1144A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1144A,
+ },
+ [0x1144B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1144B,
+ },
+ [0x1144C]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1144C,
+ },
+ [0x1144D]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1144D,
+ },
+ [0x1144E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1144E,
+ },
+ [0x1144F]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1144F,
+ },
+ [0x11450]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11450,
+ },
+ [0x11451]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11451,
+ },
+ [0x11452]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11452,
+ },
+ [0x11453]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11453,
+ },
+ [0x11454]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11454,
+ },
+ [0x11455]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11455,
+ },
+ [0x11456]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11456,
+ },
+ [0x11457]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11457,
+ },
+ [0x11458]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11458,
+ },
+ [0x11459]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11459,
+ },
+ [0x1145B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1145B,
+ },
+ [0x1145D]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1145D,
+ },
+ [0x1145E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1145E,
+ },
+ [0x1145F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1145F,
+ },
+ [0x11480]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11480,
+ },
+ [0x11481]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11481,
+ },
+ [0x11482]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11482,
+ },
+ [0x11483]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11483,
+ },
+ [0x11484]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11484,
+ },
+ [0x11485]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11485,
+ },
+ [0x11486]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11486,
+ },
+ [0x11487]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11487,
+ },
+ [0x11488]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11488,
+ },
+ [0x11489]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11489,
+ },
+ [0x1148A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1148A,
+ },
+ [0x1148B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1148B,
+ },
+ [0x1148C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1148C,
+ },
+ [0x1148D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1148D,
+ },
+ [0x1148E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1148E,
+ },
+ [0x1148F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1148F,
+ },
+ [0x11490]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11490,
+ },
+ [0x11491]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11491,
+ },
+ [0x11492]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11492,
+ },
+ [0x11493]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11493,
+ },
+ [0x11494]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11494,
+ },
+ [0x11495]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11495,
+ },
+ [0x11496]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11496,
+ },
+ [0x11497]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11497,
+ },
+ [0x11498]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11498,
+ },
+ [0x11499]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11499,
+ },
+ [0x1149A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1149A,
+ },
+ [0x1149B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1149B,
+ },
+ [0x1149C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1149C,
+ },
+ [0x1149D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1149D,
+ },
+ [0x1149E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1149E,
+ },
+ [0x1149F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1149F,
+ },
+ [0x114A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A0,
+ },
+ [0x114A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A1,
+ },
+ [0x114A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A2,
+ },
+ [0x114A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A3,
+ },
+ [0x114A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A4,
+ },
+ [0x114A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A5,
+ },
+ [0x114A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A6,
+ },
+ [0x114A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A7,
+ },
+ [0x114A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A8,
+ },
+ [0x114A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114A9,
+ },
+ [0x114AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114AA,
+ },
+ [0x114AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114AB,
+ },
+ [0x114AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114AC,
+ },
+ [0x114AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114AD,
+ },
+ [0x114AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114AE,
+ },
+ [0x114AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114AF,
+ },
+ [0x114B0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x114B0,
+ },
+ [0x114B1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x114B1,
+ },
+ [0x114B2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x114B2,
+ },
+ [0x114B3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114B3,
+ },
+ [0x114B4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114B4,
+ },
+ [0x114B5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114B5,
+ },
+ [0x114B6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114B6,
+ },
+ [0x114B7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114B7,
+ },
+ [0x114B8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114B8,
+ },
+ [0x114B9]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x114B9,
+ },
+ [0x114BA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114BA,
+ },
+ [0x114BB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x114B9, 0x114BA },
+ unicodeslot=0x114BB,
+ },
+ [0x114BC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x114B9, 0x114B0 },
+ unicodeslot=0x114BC,
+ },
+ [0x114BD]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x114BD,
+ },
+ [0x114BE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x114B9, 0x114BD },
+ unicodeslot=0x114BE,
+ },
+ [0x114BF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114BF,
+ },
+ [0x114C0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114C0,
+ },
+ [0x114C1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x114C1,
+ },
+ [0x114C2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114C2,
+ },
+ [0x114C3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x114C3,
+ },
+ [0x114C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114C4,
+ },
+ [0x114C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114C5,
+ },
+ [0x114C6]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114C6,
+ },
+ [0x114C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x114C7,
+ },
+ [0x114D0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D0,
+ },
+ [0x114D1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D1,
+ },
+ [0x114D2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D2,
+ },
+ [0x114D3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D3,
+ },
+ [0x114D4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D4,
+ },
+ [0x114D5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D5,
+ },
+ [0x114D6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D6,
+ },
+ [0x114D7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D7,
+ },
+ [0x114D8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D8,
+ },
+ [0x114D9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x114D9,
+ },
+ [0x11580]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11580,
+ },
+ [0x11581]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11581,
+ },
+ [0x11582]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11582,
+ },
+ [0x11583]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11583,
+ },
+ [0x11584]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11584,
+ },
+ [0x11585]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11585,
+ },
+ [0x11586]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11586,
+ },
+ [0x11587]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11587,
+ },
+ [0x11588]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11588,
+ },
+ [0x11589]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11589,
+ },
+ [0x1158A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1158A,
+ },
+ [0x1158B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1158B,
+ },
+ [0x1158C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1158C,
+ },
+ [0x1158D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1158D,
+ },
+ [0x1158E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1158E,
+ },
+ [0x1158F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1158F,
+ },
+ [0x11590]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11590,
+ },
+ [0x11591]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11591,
+ },
+ [0x11592]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11592,
+ },
+ [0x11593]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11593,
+ },
+ [0x11594]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11594,
+ },
+ [0x11595]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11595,
+ },
+ [0x11596]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11596,
+ },
+ [0x11597]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11597,
+ },
+ [0x11598]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11598,
+ },
+ [0x11599]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11599,
+ },
+ [0x1159A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1159A,
+ },
+ [0x1159B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1159B,
+ },
+ [0x1159C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1159C,
+ },
+ [0x1159D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1159D,
+ },
+ [0x1159E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1159E,
+ },
+ [0x1159F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1159F,
+ },
+ [0x115A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A0,
+ },
+ [0x115A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A1,
+ },
+ [0x115A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A2,
+ },
+ [0x115A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A3,
+ },
+ [0x115A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A4,
+ },
+ [0x115A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A5,
+ },
+ [0x115A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A6,
+ },
+ [0x115A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A7,
+ },
+ [0x115A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A8,
+ },
+ [0x115A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115A9,
+ },
+ [0x115AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115AA,
+ },
+ [0x115AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115AB,
+ },
+ [0x115AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115AC,
+ },
+ [0x115AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115AD,
+ },
+ [0x115AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115AE,
+ },
+ [0x115AF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x115AF,
+ },
+ [0x115B0]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x115B0,
+ },
+ [0x115B1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x115B1,
+ },
+ [0x115B2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115B2,
+ },
+ [0x115B3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115B3,
+ },
+ [0x115B4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115B4,
+ },
+ [0x115B5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115B5,
+ },
+ [0x115B8]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x115B8,
+ },
+ [0x115B9]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x115B9,
+ },
+ [0x115BA]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x115B8, 0x115AF },
+ unicodeslot=0x115BA,
+ },
+ [0x115BB]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ specials={ "char", 0x115B9, 0x115AF },
+ unicodeslot=0x115BB,
+ },
+ [0x115BC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115BC,
+ },
+ [0x115BD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115BD,
+ },
+ [0x115BE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x115BE,
+ },
+ [0x115BF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115BF,
+ },
+ [0x115C0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115C0,
+ },
+ [0x115C1]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x115C1,
+ },
+ [0x115C2]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115C2,
+ },
+ [0x115C3]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115C3,
+ },
+ [0x115C4]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0x115C4,
+ },
+ [0x115C5]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0x115C5,
+ },
+ [0x115C6]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115C6,
+ },
+ [0x115C7]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115C7,
+ },
+ [0x115C8]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115C8,
+ },
+ [0x115C9]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115C9,
+ },
+ [0x115CA]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115CA,
+ },
+ [0x115CB]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115CB,
+ },
+ [0x115CC]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115CC,
+ },
+ [0x115CD]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115CD,
+ },
+ [0x115CE]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115CE,
+ },
+ [0x115CF]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115CF,
+ },
+ [0x115D0]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D0,
+ },
+ [0x115D1]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D1,
+ },
+ [0x115D2]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D2,
+ },
+ [0x115D3]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D3,
+ },
+ [0x115D4]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D4,
+ },
+ [0x115D5]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D5,
+ },
+ [0x115D6]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D6,
+ },
+ [0x115D7]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x115D7,
+ },
+ [0x115D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115D8,
+ },
+ [0x115D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115D9,
+ },
+ [0x115DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115DA,
+ },
+ [0x115DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x115DB,
+ },
+ [0x115DC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115DC,
+ },
+ [0x115DD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x115DD,
+ },
+ [0x11600]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11600,
+ },
+ [0x11601]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11601,
+ },
+ [0x11602]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11602,
+ },
+ [0x11603]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11603,
+ },
+ [0x11604]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11604,
+ },
+ [0x11605]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11605,
+ },
+ [0x11606]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11606,
+ },
+ [0x11607]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11607,
+ },
+ [0x11608]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11608,
+ },
+ [0x11609]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11609,
+ },
+ [0x1160A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1160A,
+ },
+ [0x1160B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1160B,
+ },
+ [0x1160C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1160C,
+ },
+ [0x1160D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1160D,
+ },
+ [0x1160E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1160E,
+ },
+ [0x1160F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1160F,
+ },
+ [0x11610]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11610,
+ },
+ [0x11611]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11611,
+ },
+ [0x11612]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11612,
+ },
+ [0x11613]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11613,
+ },
+ [0x11614]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11614,
+ },
+ [0x11615]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11615,
+ },
+ [0x11616]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11616,
+ },
+ [0x11617]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11617,
+ },
+ [0x11618]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11618,
+ },
+ [0x11619]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11619,
+ },
+ [0x1161A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1161A,
+ },
+ [0x1161B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1161B,
+ },
+ [0x1161C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1161C,
+ },
+ [0x1161D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1161D,
+ },
+ [0x1161E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1161E,
+ },
+ [0x1161F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1161F,
+ },
+ [0x11620]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11620,
+ },
+ [0x11621]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11621,
+ },
+ [0x11622]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11622,
+ },
+ [0x11623]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11623,
+ },
+ [0x11624]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11624,
+ },
+ [0x11625]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11625,
+ },
+ [0x11626]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11626,
+ },
+ [0x11627]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11627,
+ },
+ [0x11628]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11628,
+ },
+ [0x11629]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11629,
+ },
+ [0x1162A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1162A,
+ },
+ [0x1162B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1162B,
+ },
+ [0x1162C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1162C,
+ },
+ [0x1162D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1162D,
+ },
+ [0x1162E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1162E,
+ },
+ [0x1162F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1162F,
+ },
+ [0x11630]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11630,
+ },
+ [0x11631]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11631,
+ },
+ [0x11632]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11632,
+ },
+ [0x11633]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11633,
+ },
+ [0x11634]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11634,
+ },
+ [0x11635]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11635,
+ },
+ [0x11636]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11636,
+ },
+ [0x11637]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11637,
+ },
+ [0x11638]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11638,
+ },
+ [0x11639]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11639,
+ },
+ [0x1163A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1163A,
+ },
+ [0x1163B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1163B,
+ },
+ [0x1163C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1163C,
+ },
+ [0x1163D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1163D,
+ },
+ [0x1163E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1163E,
+ },
+ [0x1163F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1163F,
+ },
+ [0x11640]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11640,
+ },
+ [0x11641]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11641,
+ },
+ [0x11642]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11642,
+ },
+ [0x11643]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11643,
+ },
+ [0x11644]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11644,
+ },
+ [0x11650]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11650,
+ },
+ [0x11651]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11651,
+ },
+ [0x11652]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11652,
+ },
+ [0x11653]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11653,
+ },
+ [0x11654]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11654,
+ },
+ [0x11655]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11655,
+ },
+ [0x11656]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11656,
+ },
+ [0x11657]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11657,
+ },
+ [0x11658]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11658,
+ },
+ [0x11659]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11659,
+ },
+ [0x11660]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11660,
+ },
+ [0x11661]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11661,
+ },
+ [0x11662]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11662,
+ },
+ [0x11663]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11663,
+ },
+ [0x11664]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11664,
+ },
+ [0x11665]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11665,
+ },
+ [0x11666]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11666,
+ },
+ [0x11667]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11667,
+ },
+ [0x11668]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11668,
+ },
+ [0x11669]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x11669,
+ },
+ [0x1166A]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x1166A,
+ },
+ [0x1166B]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x1166B,
+ },
+ [0x1166C]={
+ category="po",
+ direction="on",
+ linebreak="bb",
+ unicodeslot=0x1166C,
+ },
+ [0x11680]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11680,
+ },
+ [0x11681]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11681,
+ },
+ [0x11682]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11682,
+ },
+ [0x11683]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11683,
+ },
+ [0x11684]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11684,
+ },
+ [0x11685]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11685,
+ },
+ [0x11686]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11686,
+ },
+ [0x11687]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11687,
+ },
+ [0x11688]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11688,
+ },
+ [0x11689]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11689,
+ },
+ [0x1168A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1168A,
+ },
+ [0x1168B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1168B,
+ },
+ [0x1168C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1168C,
+ },
+ [0x1168D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1168D,
+ },
+ [0x1168E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1168E,
+ },
+ [0x1168F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1168F,
+ },
+ [0x11690]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11690,
+ },
+ [0x11691]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11691,
+ },
+ [0x11692]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11692,
+ },
+ [0x11693]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11693,
+ },
+ [0x11694]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11694,
+ },
+ [0x11695]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11695,
+ },
+ [0x11696]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11696,
+ },
+ [0x11697]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11697,
+ },
+ [0x11698]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11698,
+ },
+ [0x11699]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11699,
+ },
+ [0x1169A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1169A,
+ },
+ [0x1169B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1169B,
+ },
+ [0x1169C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1169C,
+ },
+ [0x1169D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1169D,
+ },
+ [0x1169E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1169E,
+ },
+ [0x1169F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1169F,
+ },
+ [0x116A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A0,
+ },
+ [0x116A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A1,
+ },
+ [0x116A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A2,
+ },
+ [0x116A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A3,
+ },
+ [0x116A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A4,
+ },
+ [0x116A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A5,
+ },
+ [0x116A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A6,
+ },
+ [0x116A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A7,
+ },
+ [0x116A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A8,
+ },
+ [0x116A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116A9,
+ },
+ [0x116AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116AA,
+ },
+ [0x116AB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116AB,
+ },
+ [0x116AC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x116AC,
+ },
+ [0x116AD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116AD,
+ },
+ [0x116AE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x116AE,
+ },
+ [0x116AF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x116AF,
+ },
+ [0x116B0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B0,
+ },
+ [0x116B1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B1,
+ },
+ [0x116B2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B2,
+ },
+ [0x116B3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B3,
+ },
+ [0x116B4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B4,
+ },
+ [0x116B5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B5,
+ },
+ [0x116B6]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x116B6,
+ },
+ [0x116B7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x116B7,
+ },
+ [0x116B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x116B8,
+ },
+ [0x116C0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C0,
+ },
+ [0x116C1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C1,
+ },
+ [0x116C2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C2,
+ },
+ [0x116C3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C3,
+ },
+ [0x116C4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C4,
+ },
+ [0x116C5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C5,
+ },
+ [0x116C6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C6,
+ },
+ [0x116C7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C7,
+ },
+ [0x116C8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C8,
+ },
+ [0x116C9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x116C9,
+ },
+ [0x11700]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11700,
+ },
+ [0x11701]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11701,
+ },
+ [0x11702]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11702,
+ },
+ [0x11703]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11703,
+ },
+ [0x11704]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11704,
+ },
+ [0x11705]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11705,
+ },
+ [0x11706]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11706,
+ },
+ [0x11707]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11707,
+ },
+ [0x11708]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11708,
+ },
+ [0x11709]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11709,
+ },
+ [0x1170A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1170A,
+ },
+ [0x1170B]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1170B,
+ },
+ [0x1170C]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1170C,
+ },
+ [0x1170D]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1170D,
+ },
+ [0x1170E]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1170E,
+ },
+ [0x1170F]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1170F,
+ },
+ [0x11710]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11710,
+ },
+ [0x11711]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11711,
+ },
+ [0x11712]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11712,
+ },
+ [0x11713]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11713,
+ },
+ [0x11714]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11714,
+ },
+ [0x11715]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11715,
+ },
+ [0x11716]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11716,
+ },
+ [0x11717]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11717,
+ },
+ [0x11718]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11718,
+ },
+ [0x11719]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11719,
+ },
+ [0x1171A]={
+ category="lo",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1171A,
+ },
+ [0x1171D]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1171D,
+ },
+ [0x1171E]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1171E,
+ },
+ [0x1171F]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1171F,
+ },
+ [0x11720]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11720,
+ },
+ [0x11721]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11721,
+ },
+ [0x11722]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11722,
+ },
+ [0x11723]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11723,
+ },
+ [0x11724]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11724,
+ },
+ [0x11725]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11725,
+ },
+ [0x11726]={
+ category="mc",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x11726,
+ },
+ [0x11727]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11727,
+ },
+ [0x11728]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11728,
+ },
+ [0x11729]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x11729,
+ },
+ [0x1172A]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1172A,
+ },
+ [0x1172B]={
+ category="mn",
+ direction="nsm",
+ linebreak="sa",
+ unicodeslot=0x1172B,
+ },
+ [0x11730]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11730,
+ },
+ [0x11731]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11731,
+ },
+ [0x11732]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11732,
+ },
+ [0x11733]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11733,
+ },
+ [0x11734]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11734,
+ },
+ [0x11735]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11735,
+ },
+ [0x11736]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11736,
+ },
+ [0x11737]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11737,
+ },
+ [0x11738]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11738,
+ },
+ [0x11739]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11739,
+ },
+ [0x1173A]={
+ category="no",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1173A,
+ },
+ [0x1173B]={
+ category="no",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1173B,
+ },
+ [0x1173C]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1173C,
+ },
+ [0x1173D]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1173D,
+ },
+ [0x1173E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1173E,
+ },
+ [0x1173F]={
+ category="so",
+ direction="l",
+ linebreak="sa",
+ unicodeslot=0x1173F,
+ },
+ [0x11800]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11800,
+ },
+ [0x11801]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11801,
+ },
+ [0x11802]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11802,
+ },
+ [0x11803]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11803,
+ },
+ [0x11804]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11804,
+ },
+ [0x11805]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11805,
+ },
+ [0x11806]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11806,
+ },
+ [0x11807]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11807,
+ },
+ [0x11808]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11808,
+ },
+ [0x11809]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11809,
+ },
+ [0x1180A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1180A,
+ },
+ [0x1180B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1180B,
+ },
+ [0x1180C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1180C,
+ },
+ [0x1180D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1180D,
+ },
+ [0x1180E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1180E,
+ },
+ [0x1180F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1180F,
+ },
+ [0x11810]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11810,
+ },
+ [0x11811]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11811,
+ },
+ [0x11812]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11812,
+ },
+ [0x11813]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11813,
+ },
+ [0x11814]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11814,
+ },
+ [0x11815]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11815,
+ },
+ [0x11816]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11816,
+ },
+ [0x11817]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11817,
+ },
+ [0x11818]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11818,
+ },
+ [0x11819]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11819,
+ },
+ [0x1181A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1181A,
+ },
+ [0x1181B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1181B,
+ },
+ [0x1181C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1181C,
+ },
+ [0x1181D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1181D,
+ },
+ [0x1181E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1181E,
+ },
+ [0x1181F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1181F,
+ },
+ [0x11820]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11820,
+ },
+ [0x11821]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11821,
+ },
+ [0x11822]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11822,
+ },
+ [0x11823]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11823,
+ },
+ [0x11824]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11824,
+ },
+ [0x11825]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11825,
+ },
+ [0x11826]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11826,
+ },
+ [0x11827]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11827,
+ },
+ [0x11828]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11828,
+ },
+ [0x11829]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11829,
+ },
+ [0x1182A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1182A,
+ },
+ [0x1182B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1182B,
+ },
+ [0x1182C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1182C,
+ },
+ [0x1182D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1182D,
+ },
+ [0x1182E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1182E,
+ },
+ [0x1182F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1182F,
+ },
+ [0x11830]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11830,
+ },
+ [0x11831]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11831,
+ },
+ [0x11832]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11832,
+ },
+ [0x11833]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11833,
+ },
+ [0x11834]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11834,
+ },
+ [0x11835]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11835,
+ },
+ [0x11836]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11836,
+ },
+ [0x11837]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11837,
+ },
+ [0x11838]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11838,
+ },
+ [0x11839]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11839,
+ },
+ [0x1183A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1183A,
+ },
+ [0x1183B]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1183B,
+ },
+ [0x118A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A0,
+ },
+ [0x118A1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A1,
+ },
+ [0x118A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A2,
+ },
+ [0x118A3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A3,
+ },
+ [0x118A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A4,
+ },
+ [0x118A5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A5,
+ },
+ [0x118A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A6,
+ },
+ [0x118A7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A7,
+ },
+ [0x118A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A8,
+ },
+ [0x118A9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118A9,
+ },
+ [0x118AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118AA,
+ },
+ [0x118AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118AB,
+ },
+ [0x118AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118AC,
+ },
+ [0x118AD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118AD,
+ },
+ [0x118AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118AE,
+ },
+ [0x118AF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118AF,
+ },
+ [0x118B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B0,
+ },
+ [0x118B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B1,
+ },
+ [0x118B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B2,
+ },
+ [0x118B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B3,
+ },
+ [0x118B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B4,
+ },
+ [0x118B5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B5,
+ },
+ [0x118B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B6,
+ },
+ [0x118B7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B7,
+ },
+ [0x118B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B8,
+ },
+ [0x118B9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118B9,
+ },
+ [0x118BA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118BA,
+ },
+ [0x118BB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118BB,
+ },
+ [0x118BC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118BC,
+ },
+ [0x118BD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118BD,
+ },
+ [0x118BE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118BE,
+ },
+ [0x118BF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118BF,
+ },
+ [0x118C0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C0,
+ },
+ [0x118C1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C1,
+ },
+ [0x118C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C2,
+ },
+ [0x118C3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C3,
+ },
+ [0x118C4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C4,
+ },
+ [0x118C5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C5,
+ },
+ [0x118C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C6,
+ },
+ [0x118C7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C7,
+ },
+ [0x118C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C8,
+ },
+ [0x118C9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118C9,
+ },
+ [0x118CA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118CA,
+ },
+ [0x118CB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118CB,
+ },
+ [0x118CC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118CC,
+ },
+ [0x118CD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118CD,
+ },
+ [0x118CE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118CE,
+ },
+ [0x118CF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118CF,
+ },
+ [0x118D0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D0,
+ },
+ [0x118D1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D1,
+ },
+ [0x118D2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D2,
+ },
+ [0x118D3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D3,
+ },
+ [0x118D4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D4,
+ },
+ [0x118D5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D5,
+ },
+ [0x118D6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D6,
+ },
+ [0x118D7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D7,
+ },
+ [0x118D8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D8,
+ },
+ [0x118D9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118D9,
+ },
+ [0x118DA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118DA,
+ },
+ [0x118DB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118DB,
+ },
+ [0x118DC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118DC,
+ },
+ [0x118DD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118DD,
+ },
+ [0x118DE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118DE,
+ },
+ [0x118DF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118DF,
+ },
+ [0x118E0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E0,
+ },
+ [0x118E1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E1,
+ },
+ [0x118E2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E2,
+ },
+ [0x118E3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E3,
+ },
+ [0x118E4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E4,
+ },
+ [0x118E5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E5,
+ },
+ [0x118E6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E6,
+ },
+ [0x118E7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E7,
+ },
+ [0x118E8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E8,
+ },
+ [0x118E9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x118E9,
+ },
+ [0x118EA]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118EA,
+ },
+ [0x118EB]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118EB,
+ },
+ [0x118EC]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118EC,
+ },
+ [0x118ED]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118ED,
+ },
+ [0x118EE]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118EE,
+ },
+ [0x118EF]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118EF,
+ },
+ [0x118F0]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118F0,
+ },
+ [0x118F1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118F1,
+ },
+ [0x118F2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118F2,
+ },
+ [0x118FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x118FF,
+ },
+ [0x119A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A0,
+ },
+ [0x119A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A1,
+ },
+ [0x119A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A2,
+ },
+ [0x119A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A3,
+ },
+ [0x119A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A4,
+ },
+ [0x119A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A5,
+ },
+ [0x119A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A6,
+ },
+ [0x119A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119A7,
+ },
+ [0x119AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119AA,
+ },
+ [0x119AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119AB,
+ },
+ [0x119AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119AC,
+ },
+ [0x119AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119AD,
+ },
+ [0x119AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119AE,
+ },
+ [0x119AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119AF,
+ },
+ [0x119B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B0,
+ },
+ [0x119B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B1,
+ },
+ [0x119B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B2,
+ },
+ [0x119B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B3,
+ },
+ [0x119B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B4,
+ },
+ [0x119B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B5,
+ },
+ [0x119B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B6,
+ },
+ [0x119B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B7,
+ },
+ [0x119B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B8,
+ },
+ [0x119B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119B9,
+ },
+ [0x119BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119BA,
+ },
+ [0x119BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119BB,
+ },
+ [0x119BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119BC,
+ },
+ [0x119BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119BD,
+ },
+ [0x119BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119BE,
+ },
+ [0x119BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119BF,
+ },
+ [0x119C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C0,
+ },
+ [0x119C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C1,
+ },
+ [0x119C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C2,
+ },
+ [0x119C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C3,
+ },
+ [0x119C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C4,
+ },
+ [0x119C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C5,
+ },
+ [0x119C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C6,
+ },
+ [0x119C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C7,
+ },
+ [0x119C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C8,
+ },
+ [0x119C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119C9,
+ },
+ [0x119CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119CA,
+ },
+ [0x119CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119CB,
+ },
+ [0x119CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119CC,
+ },
+ [0x119CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119CD,
+ },
+ [0x119CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119CE,
+ },
+ [0x119CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119CF,
+ },
+ [0x119D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119D0,
+ },
+ [0x119D1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119D1,
+ },
+ [0x119D2]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119D2,
+ },
+ [0x119D3]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119D3,
+ },
+ [0x119D4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119D4,
+ },
+ [0x119D5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119D5,
+ },
+ [0x119D6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119D6,
+ },
+ [0x119D7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119D7,
+ },
+ [0x119DA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119DA,
+ },
+ [0x119DB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119DB,
+ },
+ [0x119DC]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119DC,
+ },
+ [0x119DD]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119DD,
+ },
+ [0x119DE]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119DE,
+ },
+ [0x119DF]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119DF,
+ },
+ [0x119E0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x119E0,
+ },
+ [0x119E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119E1,
+ },
+ [0x119E2]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x119E2,
+ },
+ [0x119E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x119E3,
+ },
+ [0x119E4]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x119E4,
+ },
+ [0x11A00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A00,
+ },
+ [0x11A01]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A01,
+ },
+ [0x11A02]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A02,
+ },
+ [0x11A03]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A03,
+ },
+ [0x11A04]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A04,
+ },
+ [0x11A05]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A05,
+ },
+ [0x11A06]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A06,
+ },
+ [0x11A07]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11A07,
+ },
+ [0x11A08]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11A08,
+ },
+ [0x11A09]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A09,
+ },
+ [0x11A0A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A0A,
+ },
+ [0x11A0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A0B,
+ },
+ [0x11A0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A0C,
+ },
+ [0x11A0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A0D,
+ },
+ [0x11A0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A0E,
+ },
+ [0x11A0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A0F,
+ },
+ [0x11A10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A10,
+ },
+ [0x11A11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A11,
+ },
+ [0x11A12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A12,
+ },
+ [0x11A13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A13,
+ },
+ [0x11A14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A14,
+ },
+ [0x11A15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A15,
+ },
+ [0x11A16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A16,
+ },
+ [0x11A17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A17,
+ },
+ [0x11A18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A18,
+ },
+ [0x11A19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A19,
+ },
+ [0x11A1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A1A,
+ },
+ [0x11A1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A1B,
+ },
+ [0x11A1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A1C,
+ },
+ [0x11A1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A1D,
+ },
+ [0x11A1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A1E,
+ },
+ [0x11A1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A1F,
+ },
+ [0x11A20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A20,
+ },
+ [0x11A21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A21,
+ },
+ [0x11A22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A22,
+ },
+ [0x11A23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A23,
+ },
+ [0x11A24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A24,
+ },
+ [0x11A25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A25,
+ },
+ [0x11A26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A26,
+ },
+ [0x11A27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A27,
+ },
+ [0x11A28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A28,
+ },
+ [0x11A29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A29,
+ },
+ [0x11A2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A2A,
+ },
+ [0x11A2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A2B,
+ },
+ [0x11A2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A2C,
+ },
+ [0x11A2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A2D,
+ },
+ [0x11A2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A2E,
+ },
+ [0x11A2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A2F,
+ },
+ [0x11A30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A30,
+ },
+ [0x11A31]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A31,
+ },
+ [0x11A32]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A32,
+ },
+ [0x11A33]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A33,
+ },
+ [0x11A34]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A34,
+ },
+ [0x11A35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A35,
+ },
+ [0x11A36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A36,
+ },
+ [0x11A37]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A37,
+ },
+ [0x11A38]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A38,
+ },
+ [0x11A39]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11A39,
+ },
+ [0x11A3A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A3A,
+ },
+ [0x11A3B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A3B,
+ },
+ [0x11A3C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A3C,
+ },
+ [0x11A3D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A3D,
+ },
+ [0x11A3E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A3E,
+ },
+ [0x11A3F]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11A3F,
+ },
+ [0x11A40]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A40,
+ },
+ [0x11A41]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A41,
+ },
+ [0x11A42]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A42,
+ },
+ [0x11A43]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A43,
+ },
+ [0x11A44]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A44,
+ },
+ [0x11A45]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11A45,
+ },
+ [0x11A46]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A46,
+ },
+ [0x11A47]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A47,
+ },
+ [0x11A50]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A50,
+ },
+ [0x11A51]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A51,
+ },
+ [0x11A52]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A52,
+ },
+ [0x11A53]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A53,
+ },
+ [0x11A54]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A54,
+ },
+ [0x11A55]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A55,
+ },
+ [0x11A56]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A56,
+ },
+ [0x11A57]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11A57,
+ },
+ [0x11A58]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11A58,
+ },
+ [0x11A59]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A59,
+ },
+ [0x11A5A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A5A,
+ },
+ [0x11A5B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A5B,
+ },
+ [0x11A5C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A5C,
+ },
+ [0x11A5D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A5D,
+ },
+ [0x11A5E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A5E,
+ },
+ [0x11A5F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A5F,
+ },
+ [0x11A60]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A60,
+ },
+ [0x11A61]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A61,
+ },
+ [0x11A62]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A62,
+ },
+ [0x11A63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A63,
+ },
+ [0x11A64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A64,
+ },
+ [0x11A65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A65,
+ },
+ [0x11A66]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A66,
+ },
+ [0x11A67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A67,
+ },
+ [0x11A68]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A68,
+ },
+ [0x11A69]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A69,
+ },
+ [0x11A6A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A6A,
+ },
+ [0x11A6B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A6B,
+ },
+ [0x11A6C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A6C,
+ },
+ [0x11A6D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A6D,
+ },
+ [0x11A6E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A6E,
+ },
+ [0x11A6F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A6F,
+ },
+ [0x11A70]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A70,
+ },
+ [0x11A71]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A71,
+ },
+ [0x11A72]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A72,
+ },
+ [0x11A73]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A73,
+ },
+ [0x11A74]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A74,
+ },
+ [0x11A75]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A75,
+ },
+ [0x11A76]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A76,
+ },
+ [0x11A77]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A77,
+ },
+ [0x11A78]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A78,
+ },
+ [0x11A79]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A79,
+ },
+ [0x11A7A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A7A,
+ },
+ [0x11A7B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A7B,
+ },
+ [0x11A7C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A7C,
+ },
+ [0x11A7D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A7D,
+ },
+ [0x11A7E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A7E,
+ },
+ [0x11A7F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A7F,
+ },
+ [0x11A80]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A80,
+ },
+ [0x11A81]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A81,
+ },
+ [0x11A82]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A82,
+ },
+ [0x11A83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A83,
+ },
+ [0x11A84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A84,
+ },
+ [0x11A85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A85,
+ },
+ [0x11A86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A86,
+ },
+ [0x11A87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A87,
+ },
+ [0x11A88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A88,
+ },
+ [0x11A89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A89,
+ },
+ [0x11A8A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A8A,
+ },
+ [0x11A8B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A8B,
+ },
+ [0x11A8C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A8C,
+ },
+ [0x11A8D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A8D,
+ },
+ [0x11A8E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A8E,
+ },
+ [0x11A8F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A8F,
+ },
+ [0x11A90]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A90,
+ },
+ [0x11A91]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A91,
+ },
+ [0x11A92]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A92,
+ },
+ [0x11A93]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A93,
+ },
+ [0x11A94]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A94,
+ },
+ [0x11A95]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A95,
+ },
+ [0x11A96]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A96,
+ },
+ [0x11A97]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11A97,
+ },
+ [0x11A98]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A98,
+ },
+ [0x11A99]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11A99,
+ },
+ [0x11A9A]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A9A,
+ },
+ [0x11A9B]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A9B,
+ },
+ [0x11A9C]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11A9C,
+ },
+ [0x11A9D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11A9D,
+ },
+ [0x11A9E]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11A9E,
+ },
+ [0x11A9F]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11A9F,
+ },
+ [0x11AA0]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11AA0,
+ },
+ [0x11AA1]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11AA1,
+ },
+ [0x11AA2]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11AA2,
+ },
+ [0x11AC0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC0,
+ },
+ [0x11AC1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC1,
+ },
+ [0x11AC2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC2,
+ },
+ [0x11AC3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC3,
+ },
+ [0x11AC4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC4,
+ },
+ [0x11AC5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC5,
+ },
+ [0x11AC6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC6,
+ },
+ [0x11AC7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC7,
+ },
+ [0x11AC8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC8,
+ },
+ [0x11AC9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AC9,
+ },
+ [0x11ACA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ACA,
+ },
+ [0x11ACB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ACB,
+ },
+ [0x11ACC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ACC,
+ },
+ [0x11ACD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ACD,
+ },
+ [0x11ACE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ACE,
+ },
+ [0x11ACF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ACF,
+ },
+ [0x11AD0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD0,
+ },
+ [0x11AD1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD1,
+ },
+ [0x11AD2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD2,
+ },
+ [0x11AD3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD3,
+ },
+ [0x11AD4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD4,
+ },
+ [0x11AD5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD5,
+ },
+ [0x11AD6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD6,
+ },
+ [0x11AD7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD7,
+ },
+ [0x11AD8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD8,
+ },
+ [0x11AD9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AD9,
+ },
+ [0x11ADA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ADA,
+ },
+ [0x11ADB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ADB,
+ },
+ [0x11ADC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ADC,
+ },
+ [0x11ADD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ADD,
+ },
+ [0x11ADE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ADE,
+ },
+ [0x11ADF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11ADF,
+ },
+ [0x11AE0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE0,
+ },
+ [0x11AE1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE1,
+ },
+ [0x11AE2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE2,
+ },
+ [0x11AE3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE3,
+ },
+ [0x11AE4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE4,
+ },
+ [0x11AE5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE5,
+ },
+ [0x11AE6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE6,
+ },
+ [0x11AE7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE7,
+ },
+ [0x11AE8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE8,
+ },
+ [0x11AE9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AE9,
+ },
+ [0x11AEA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AEA,
+ },
+ [0x11AEB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AEB,
+ },
+ [0x11AEC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AEC,
+ },
+ [0x11AED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AED,
+ },
+ [0x11AEE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AEE,
+ },
+ [0x11AEF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AEF,
+ },
+ [0x11AF0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF0,
+ },
+ [0x11AF1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF1,
+ },
+ [0x11AF2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF2,
+ },
+ [0x11AF3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF3,
+ },
+ [0x11AF4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF4,
+ },
+ [0x11AF5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF5,
+ },
+ [0x11AF6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF6,
+ },
+ [0x11AF7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF7,
+ },
+ [0x11AF8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11AF8,
+ },
+ [0x11C00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C00,
+ },
+ [0x11C01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C01,
+ },
+ [0x11C02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C02,
+ },
+ [0x11C03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C03,
+ },
+ [0x11C04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C04,
+ },
+ [0x11C05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C05,
+ },
+ [0x11C06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C06,
+ },
+ [0x11C07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C07,
+ },
+ [0x11C08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C08,
+ },
+ [0x11C0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C0A,
+ },
+ [0x11C0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C0B,
+ },
+ [0x11C0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C0C,
+ },
+ [0x11C0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C0D,
+ },
+ [0x11C0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C0E,
+ },
+ [0x11C0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C0F,
+ },
+ [0x11C10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C10,
+ },
+ [0x11C11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C11,
+ },
+ [0x11C12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C12,
+ },
+ [0x11C13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C13,
+ },
+ [0x11C14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C14,
+ },
+ [0x11C15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C15,
+ },
+ [0x11C16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C16,
+ },
+ [0x11C17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C17,
+ },
+ [0x11C18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C18,
+ },
+ [0x11C19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C19,
+ },
+ [0x11C1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C1A,
+ },
+ [0x11C1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C1B,
+ },
+ [0x11C1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C1C,
+ },
+ [0x11C1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C1D,
+ },
+ [0x11C1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C1E,
+ },
+ [0x11C1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C1F,
+ },
+ [0x11C20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C20,
+ },
+ [0x11C21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C21,
+ },
+ [0x11C22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C22,
+ },
+ [0x11C23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C23,
+ },
+ [0x11C24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C24,
+ },
+ [0x11C25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C25,
+ },
+ [0x11C26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C26,
+ },
+ [0x11C27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C27,
+ },
+ [0x11C28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C28,
+ },
+ [0x11C29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C29,
+ },
+ [0x11C2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C2A,
+ },
+ [0x11C2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C2B,
+ },
+ [0x11C2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C2C,
+ },
+ [0x11C2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C2D,
+ },
+ [0x11C2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C2E,
+ },
+ [0x11C2F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11C2F,
+ },
+ [0x11C30]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C30,
+ },
+ [0x11C31]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C31,
+ },
+ [0x11C32]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C32,
+ },
+ [0x11C33]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C33,
+ },
+ [0x11C34]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C34,
+ },
+ [0x11C35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C35,
+ },
+ [0x11C36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C36,
+ },
+ [0x11C38]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C38,
+ },
+ [0x11C39]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C39,
+ },
+ [0x11C3A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C3A,
+ },
+ [0x11C3B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C3B,
+ },
+ [0x11C3C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C3C,
+ },
+ [0x11C3D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C3D,
+ },
+ [0x11C3E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11C3E,
+ },
+ [0x11C3F]={
+ category="mn",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11C3F,
+ },
+ [0x11C40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C40,
+ },
+ [0x11C41]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11C41,
+ },
+ [0x11C42]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11C42,
+ },
+ [0x11C43]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11C43,
+ },
+ [0x11C44]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11C44,
+ },
+ [0x11C45]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11C45,
+ },
+ [0x11C50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C50,
+ },
+ [0x11C51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C51,
+ },
+ [0x11C52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C52,
+ },
+ [0x11C53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C53,
+ },
+ [0x11C54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C54,
+ },
+ [0x11C55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C55,
+ },
+ [0x11C56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C56,
+ },
+ [0x11C57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C57,
+ },
+ [0x11C58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C58,
+ },
+ [0x11C59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11C59,
+ },
+ [0x11C5A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C5A,
+ },
+ [0x11C5B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C5B,
+ },
+ [0x11C5C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C5C,
+ },
+ [0x11C5D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C5D,
+ },
+ [0x11C5E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C5E,
+ },
+ [0x11C5F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C5F,
+ },
+ [0x11C60]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C60,
+ },
+ [0x11C61]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C61,
+ },
+ [0x11C62]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C62,
+ },
+ [0x11C63]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C63,
+ },
+ [0x11C64]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C64,
+ },
+ [0x11C65]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C65,
+ },
+ [0x11C66]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C66,
+ },
+ [0x11C67]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C67,
+ },
+ [0x11C68]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C68,
+ },
+ [0x11C69]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C69,
+ },
+ [0x11C6A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C6A,
+ },
+ [0x11C6B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C6B,
+ },
+ [0x11C6C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C6C,
+ },
+ [0x11C70]={
+ category="po",
+ direction="l",
+ linebreak="bb",
+ unicodeslot=0x11C70,
+ },
+ [0x11C71]={
+ category="po",
+ direction="l",
+ linebreak="ex",
+ unicodeslot=0x11C71,
+ },
+ [0x11C72]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C72,
+ },
+ [0x11C73]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C73,
+ },
+ [0x11C74]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C74,
+ },
+ [0x11C75]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C75,
+ },
+ [0x11C76]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C76,
+ },
+ [0x11C77]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C77,
+ },
+ [0x11C78]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C78,
+ },
+ [0x11C79]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C79,
+ },
+ [0x11C7A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C7A,
+ },
+ [0x11C7B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C7B,
+ },
+ [0x11C7C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C7C,
+ },
+ [0x11C7D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C7D,
+ },
+ [0x11C7E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C7E,
+ },
+ [0x11C7F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C7F,
+ },
+ [0x11C80]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C80,
+ },
+ [0x11C81]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C81,
+ },
+ [0x11C82]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C82,
+ },
+ [0x11C83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C83,
+ },
+ [0x11C84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C84,
+ },
+ [0x11C85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C85,
+ },
+ [0x11C86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C86,
+ },
+ [0x11C87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C87,
+ },
+ [0x11C88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C88,
+ },
+ [0x11C89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C89,
+ },
+ [0x11C8A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C8A,
+ },
+ [0x11C8B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C8B,
+ },
+ [0x11C8C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C8C,
+ },
+ [0x11C8D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C8D,
+ },
+ [0x11C8E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C8E,
+ },
+ [0x11C8F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11C8F,
+ },
+ [0x11C92]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C92,
+ },
+ [0x11C93]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C93,
+ },
+ [0x11C94]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C94,
+ },
+ [0x11C95]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C95,
+ },
+ [0x11C96]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C96,
+ },
+ [0x11C97]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C97,
+ },
+ [0x11C98]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C98,
+ },
+ [0x11C99]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C99,
+ },
+ [0x11C9A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C9A,
+ },
+ [0x11C9B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C9B,
+ },
+ [0x11C9C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C9C,
+ },
+ [0x11C9D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C9D,
+ },
+ [0x11C9E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C9E,
+ },
+ [0x11C9F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11C9F,
+ },
+ [0x11CA0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA0,
+ },
+ [0x11CA1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA1,
+ },
+ [0x11CA2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA2,
+ },
+ [0x11CA3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA3,
+ },
+ [0x11CA4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA4,
+ },
+ [0x11CA5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA5,
+ },
+ [0x11CA6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA6,
+ },
+ [0x11CA7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CA7,
+ },
+ [0x11CA9]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11CA9,
+ },
+ [0x11CAA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CAA,
+ },
+ [0x11CAB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CAB,
+ },
+ [0x11CAC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CAC,
+ },
+ [0x11CAD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CAD,
+ },
+ [0x11CAE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CAE,
+ },
+ [0x11CAF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CAF,
+ },
+ [0x11CB0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CB0,
+ },
+ [0x11CB1]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11CB1,
+ },
+ [0x11CB2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CB2,
+ },
+ [0x11CB3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CB3,
+ },
+ [0x11CB4]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11CB4,
+ },
+ [0x11CB5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CB5,
+ },
+ [0x11CB6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11CB6,
+ },
+ [0x11D00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D00,
+ },
+ [0x11D01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D01,
+ },
+ [0x11D02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D02,
+ },
+ [0x11D03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D03,
+ },
+ [0x11D04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D04,
+ },
+ [0x11D05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D05,
+ },
+ [0x11D06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D06,
+ },
+ [0x11D08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D08,
+ },
+ [0x11D09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D09,
+ },
+ [0x11D0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D0B,
+ },
+ [0x11D0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D0C,
+ },
+ [0x11D0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D0D,
+ },
+ [0x11D0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D0E,
+ },
+ [0x11D0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D0F,
+ },
+ [0x11D10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D10,
+ },
+ [0x11D11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D11,
+ },
+ [0x11D12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D12,
+ },
+ [0x11D13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D13,
+ },
+ [0x11D14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D14,
+ },
+ [0x11D15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D15,
+ },
+ [0x11D16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D16,
+ },
+ [0x11D17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D17,
+ },
+ [0x11D18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D18,
+ },
+ [0x11D19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D19,
+ },
+ [0x11D1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D1A,
+ },
+ [0x11D1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D1B,
+ },
+ [0x11D1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D1C,
+ },
+ [0x11D1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D1D,
+ },
+ [0x11D1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D1E,
+ },
+ [0x11D1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D1F,
+ },
+ [0x11D20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D20,
+ },
+ [0x11D21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D21,
+ },
+ [0x11D22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D22,
+ },
+ [0x11D23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D23,
+ },
+ [0x11D24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D24,
+ },
+ [0x11D25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D25,
+ },
+ [0x11D26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D26,
+ },
+ [0x11D27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D27,
+ },
+ [0x11D28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D28,
+ },
+ [0x11D29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D29,
+ },
+ [0x11D2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D2A,
+ },
+ [0x11D2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D2B,
+ },
+ [0x11D2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D2C,
+ },
+ [0x11D2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D2D,
+ },
+ [0x11D2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D2E,
+ },
+ [0x11D2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D2F,
+ },
+ [0x11D30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D30,
+ },
+ [0x11D31]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D31,
+ },
+ [0x11D32]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D32,
+ },
+ [0x11D33]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D33,
+ },
+ [0x11D34]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D34,
+ },
+ [0x11D35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D35,
+ },
+ [0x11D36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D36,
+ },
+ [0x11D3A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D3A,
+ },
+ [0x11D3C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D3C,
+ },
+ [0x11D3D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D3D,
+ },
+ [0x11D3F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D3F,
+ },
+ [0x11D40]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D40,
+ },
+ [0x11D41]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D41,
+ },
+ [0x11D42]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D42,
+ },
+ [0x11D43]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D43,
+ },
+ [0x11D44]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D44,
+ },
+ [0x11D45]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D45,
+ },
+ [0x11D46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D46,
+ },
+ [0x11D47]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D47,
+ },
+ [0x11D50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D50,
+ },
+ [0x11D51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D51,
+ },
+ [0x11D52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D52,
+ },
+ [0x11D53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D53,
+ },
+ [0x11D54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D54,
+ },
+ [0x11D55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D55,
+ },
+ [0x11D56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D56,
+ },
+ [0x11D57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D57,
+ },
+ [0x11D58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D58,
+ },
+ [0x11D59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11D59,
+ },
+ [0x11D60]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D60,
+ },
+ [0x11D61]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D61,
+ },
+ [0x11D62]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D62,
+ },
+ [0x11D63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D63,
+ },
+ [0x11D64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D64,
+ },
+ [0x11D65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D65,
+ },
+ [0x11D67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D67,
+ },
+ [0x11D68]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D68,
+ },
+ [0x11D6A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D6A,
+ },
+ [0x11D6B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D6B,
+ },
+ [0x11D6C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D6C,
+ },
+ [0x11D6D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D6D,
+ },
+ [0x11D6E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D6E,
+ },
+ [0x11D6F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D6F,
+ },
+ [0x11D70]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D70,
+ },
+ [0x11D71]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D71,
+ },
+ [0x11D72]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D72,
+ },
+ [0x11D73]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D73,
+ },
+ [0x11D74]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D74,
+ },
+ [0x11D75]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D75,
+ },
+ [0x11D76]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D76,
+ },
+ [0x11D77]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D77,
+ },
+ [0x11D78]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D78,
+ },
+ [0x11D79]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D79,
+ },
+ [0x11D7A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D7A,
+ },
+ [0x11D7B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D7B,
+ },
+ [0x11D7C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D7C,
+ },
+ [0x11D7D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D7D,
+ },
+ [0x11D7E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D7E,
+ },
+ [0x11D7F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D7F,
+ },
+ [0x11D80]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D80,
+ },
+ [0x11D81]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D81,
+ },
+ [0x11D82]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D82,
+ },
+ [0x11D83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D83,
+ },
+ [0x11D84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D84,
+ },
+ [0x11D85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D85,
+ },
+ [0x11D86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D86,
+ },
+ [0x11D87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D87,
+ },
+ [0x11D88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D88,
+ },
+ [0x11D89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D89,
+ },
+ [0x11D8A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D8A,
+ },
+ [0x11D8B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D8B,
+ },
+ [0x11D8C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D8C,
+ },
+ [0x11D8D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D8D,
+ },
+ [0x11D8E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D8E,
+ },
+ [0x11D90]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D90,
+ },
+ [0x11D91]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D91,
+ },
+ [0x11D93]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D93,
+ },
+ [0x11D94]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D94,
+ },
+ [0x11D95]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D95,
+ },
+ [0x11D96]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11D96,
+ },
+ [0x11D97]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11D97,
+ },
+ [0x11D98]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11D98,
+ },
+ [0x11DA0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA0,
+ },
+ [0x11DA1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA1,
+ },
+ [0x11DA2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA2,
+ },
+ [0x11DA3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA3,
+ },
+ [0x11DA4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA4,
+ },
+ [0x11DA5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA5,
+ },
+ [0x11DA6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA6,
+ },
+ [0x11DA7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA7,
+ },
+ [0x11DA8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA8,
+ },
+ [0x11DA9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x11DA9,
+ },
+ [0x11EE0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE0,
+ },
+ [0x11EE1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE1,
+ },
+ [0x11EE2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE2,
+ },
+ [0x11EE3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE3,
+ },
+ [0x11EE4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE4,
+ },
+ [0x11EE5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE5,
+ },
+ [0x11EE6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE6,
+ },
+ [0x11EE7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE7,
+ },
+ [0x11EE8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE8,
+ },
+ [0x11EE9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EE9,
+ },
+ [0x11EEA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EEA,
+ },
+ [0x11EEB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EEB,
+ },
+ [0x11EEC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EEC,
+ },
+ [0x11EED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EED,
+ },
+ [0x11EEE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EEE,
+ },
+ [0x11EEF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EEF,
+ },
+ [0x11EF0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EF0,
+ },
+ [0x11EF1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EF1,
+ },
+ [0x11EF2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EF2,
+ },
+ [0x11EF3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11EF3,
+ },
+ [0x11EF4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x11EF4,
+ },
+ [0x11EF5]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11EF5,
+ },
+ [0x11EF6]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x11EF6,
+ },
+ [0x11EF7]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EF7,
+ },
+ [0x11EF8]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11EF8,
+ },
+ [0x11FC0]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC0,
+ },
+ [0x11FC1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC1,
+ },
+ [0x11FC2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC2,
+ },
+ [0x11FC3]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC3,
+ },
+ [0x11FC4]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC4,
+ },
+ [0x11FC5]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC5,
+ },
+ [0x11FC6]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC6,
+ },
+ [0x11FC7]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC7,
+ },
+ [0x11FC8]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC8,
+ },
+ [0x11FC9]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FC9,
+ },
+ [0x11FCA]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FCA,
+ },
+ [0x11FCB]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FCB,
+ },
+ [0x11FCC]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FCC,
+ },
+ [0x11FCD]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FCD,
+ },
+ [0x11FCE]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FCE,
+ },
+ [0x11FCF]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FCF,
+ },
+ [0x11FD0]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FD0,
+ },
+ [0x11FD1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FD1,
+ },
+ [0x11FD2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FD2,
+ },
+ [0x11FD3]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FD3,
+ },
+ [0x11FD4]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x11FD4,
+ },
+ [0x11FD5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FD5,
+ },
+ [0x11FD6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FD6,
+ },
+ [0x11FD7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FD7,
+ },
+ [0x11FD8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FD8,
+ },
+ [0x11FD9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FD9,
+ },
+ [0x11FDA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FDA,
+ },
+ [0x11FDB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FDB,
+ },
+ [0x11FDC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FDC,
+ },
+ [0x11FDD]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x11FDD,
+ },
+ [0x11FDE]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x11FDE,
+ },
+ [0x11FDF]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x11FDF,
+ },
+ [0x11FE0]={
+ category="sc",
+ direction="et",
+ linebreak="po",
+ unicodeslot=0x11FE0,
+ },
+ [0x11FE1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE1,
+ },
+ [0x11FE2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE2,
+ },
+ [0x11FE3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE3,
+ },
+ [0x11FE4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE4,
+ },
+ [0x11FE5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE5,
+ },
+ [0x11FE6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE6,
+ },
+ [0x11FE7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE7,
+ },
+ [0x11FE8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE8,
+ },
+ [0x11FE9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FE9,
+ },
+ [0x11FEA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FEA,
+ },
+ [0x11FEB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FEB,
+ },
+ [0x11FEC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FEC,
+ },
+ [0x11FED]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FED,
+ },
+ [0x11FEE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FEE,
+ },
+ [0x11FEF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FEF,
+ },
+ [0x11FF0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FF0,
+ },
+ [0x11FF1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x11FF1,
+ },
+ [0x11FFF]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x11FFF,
+ },
+ [0x12000]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12000,
+ },
+ [0x12001]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12001,
+ },
+ [0x12002]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12002,
+ },
+ [0x12003]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12003,
+ },
+ [0x12004]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12004,
+ },
+ [0x12005]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12005,
+ },
+ [0x12006]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12006,
+ },
+ [0x12007]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12007,
+ },
+ [0x12008]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12008,
+ },
+ [0x12009]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12009,
+ },
+ [0x1200A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200A,
+ },
+ [0x1200B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200B,
+ },
+ [0x1200C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200C,
+ },
+ [0x1200D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200D,
+ },
+ [0x1200E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200E,
+ },
+ [0x1200F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1200F,
+ },
+ [0x12010]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12010,
+ },
+ [0x12011]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12011,
+ },
+ [0x12012]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12012,
+ },
+ [0x12013]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12013,
+ },
+ [0x12014]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12014,
+ },
+ [0x12015]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12015,
+ },
+ [0x12016]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12016,
+ },
+ [0x12017]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12017,
+ },
+ [0x12018]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12018,
+ },
+ [0x12019]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12019,
+ },
+ [0x1201A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201A,
+ },
+ [0x1201B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201B,
+ },
+ [0x1201C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201C,
+ },
+ [0x1201D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201D,
+ },
+ [0x1201E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201E,
+ },
+ [0x1201F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1201F,
+ },
+ [0x12020]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12020,
+ },
+ [0x12021]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12021,
+ },
+ [0x12022]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12022,
+ },
+ [0x12023]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12023,
+ },
+ [0x12024]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12024,
+ },
+ [0x12025]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12025,
+ },
+ [0x12026]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12026,
+ },
+ [0x12027]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12027,
+ },
+ [0x12028]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12028,
+ },
+ [0x12029]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12029,
+ },
+ [0x1202A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202A,
+ },
+ [0x1202B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202B,
+ },
+ [0x1202C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202C,
+ },
+ [0x1202D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202D,
+ },
+ [0x1202E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202E,
+ },
+ [0x1202F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1202F,
+ },
+ [0x12030]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12030,
+ },
+ [0x12031]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12031,
+ },
+ [0x12032]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12032,
+ },
+ [0x12033]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12033,
+ },
+ [0x12034]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12034,
+ },
+ [0x12035]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12035,
+ },
+ [0x12036]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12036,
+ },
+ [0x12037]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12037,
+ },
+ [0x12038]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12038,
+ },
+ [0x12039]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12039,
+ },
+ [0x1203A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203A,
+ },
+ [0x1203B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203B,
+ },
+ [0x1203C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203C,
+ },
+ [0x1203D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203D,
+ },
+ [0x1203E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203E,
+ },
+ [0x1203F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1203F,
+ },
+ [0x12040]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12040,
+ },
+ [0x12041]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12041,
+ },
+ [0x12042]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12042,
+ },
+ [0x12043]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12043,
+ },
+ [0x12044]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12044,
+ },
+ [0x12045]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12045,
+ },
+ [0x12046]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12046,
+ },
+ [0x12047]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12047,
+ },
+ [0x12048]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12048,
+ },
+ [0x12049]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12049,
+ },
+ [0x1204A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204A,
+ },
+ [0x1204B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204B,
+ },
+ [0x1204C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204C,
+ },
+ [0x1204D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204D,
+ },
+ [0x1204E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204E,
+ },
+ [0x1204F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1204F,
+ },
+ [0x12050]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12050,
+ },
+ [0x12051]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12051,
+ },
+ [0x12052]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12052,
+ },
+ [0x12053]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12053,
+ },
+ [0x12054]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12054,
+ },
+ [0x12055]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12055,
+ },
+ [0x12056]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12056,
+ },
+ [0x12057]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12057,
+ },
+ [0x12058]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12058,
+ },
+ [0x12059]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12059,
+ },
+ [0x1205A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205A,
+ },
+ [0x1205B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205B,
+ },
+ [0x1205C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205C,
+ },
+ [0x1205D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205D,
+ },
+ [0x1205E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205E,
+ },
+ [0x1205F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1205F,
+ },
+ [0x12060]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12060,
+ },
+ [0x12061]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12061,
+ },
+ [0x12062]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12062,
+ },
+ [0x12063]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12063,
+ },
+ [0x12064]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12064,
+ },
+ [0x12065]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12065,
+ },
+ [0x12066]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12066,
+ },
+ [0x12067]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12067,
+ },
+ [0x12068]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12068,
+ },
+ [0x12069]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12069,
+ },
+ [0x1206A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206A,
+ },
+ [0x1206B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206B,
+ },
+ [0x1206C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206C,
+ },
+ [0x1206D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206D,
+ },
+ [0x1206E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206E,
+ },
+ [0x1206F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1206F,
+ },
+ [0x12070]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12070,
+ },
+ [0x12071]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12071,
+ },
+ [0x12072]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12072,
+ },
+ [0x12073]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12073,
+ },
+ [0x12074]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12074,
+ },
+ [0x12075]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12075,
+ },
+ [0x12076]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12076,
+ },
+ [0x12077]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12077,
+ },
+ [0x12078]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12078,
+ },
+ [0x12079]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12079,
+ },
+ [0x1207A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207A,
+ },
+ [0x1207B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207B,
+ },
+ [0x1207C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207C,
+ },
+ [0x1207D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207D,
+ },
+ [0x1207E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207E,
+ },
+ [0x1207F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1207F,
+ },
+ [0x12080]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12080,
+ },
+ [0x12081]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12081,
+ },
+ [0x12082]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12082,
+ },
+ [0x12083]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12083,
+ },
+ [0x12084]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12084,
+ },
+ [0x12085]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12085,
+ },
+ [0x12086]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12086,
+ },
+ [0x12087]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12087,
+ },
+ [0x12088]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12088,
+ },
+ [0x12089]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12089,
+ },
+ [0x1208A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208A,
+ },
+ [0x1208B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208B,
+ },
+ [0x1208C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208C,
+ },
+ [0x1208D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208D,
+ },
+ [0x1208E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208E,
+ },
+ [0x1208F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1208F,
+ },
+ [0x12090]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12090,
+ },
+ [0x12091]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12091,
+ },
+ [0x12092]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12092,
+ },
+ [0x12093]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12093,
+ },
+ [0x12094]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12094,
+ },
+ [0x12095]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12095,
+ },
+ [0x12096]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12096,
+ },
+ [0x12097]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12097,
+ },
+ [0x12098]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12098,
+ },
+ [0x12099]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12099,
+ },
+ [0x1209A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209A,
+ },
+ [0x1209B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209B,
+ },
+ [0x1209C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209C,
+ },
+ [0x1209D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209D,
+ },
+ [0x1209E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209E,
+ },
+ [0x1209F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1209F,
+ },
+ [0x120A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A0,
+ },
+ [0x120A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A1,
+ },
+ [0x120A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A2,
+ },
+ [0x120A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A3,
+ },
+ [0x120A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A4,
+ },
+ [0x120A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A5,
+ },
+ [0x120A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A6,
+ },
+ [0x120A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A7,
+ },
+ [0x120A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A8,
+ },
+ [0x120A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120A9,
+ },
+ [0x120AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120AA,
+ },
+ [0x120AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120AB,
+ },
+ [0x120AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120AC,
+ },
+ [0x120AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120AD,
+ },
+ [0x120AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120AE,
+ },
+ [0x120AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120AF,
+ },
+ [0x120B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B0,
+ },
+ [0x120B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B1,
+ },
+ [0x120B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B2,
+ },
+ [0x120B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B3,
+ },
+ [0x120B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B4,
+ },
+ [0x120B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B5,
+ },
+ [0x120B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B6,
+ },
+ [0x120B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B7,
+ },
+ [0x120B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B8,
+ },
+ [0x120B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120B9,
+ },
+ [0x120BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120BA,
+ },
+ [0x120BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120BB,
+ },
+ [0x120BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120BC,
+ },
+ [0x120BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120BD,
+ },
+ [0x120BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120BE,
+ },
+ [0x120BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120BF,
+ },
+ [0x120C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C0,
+ },
+ [0x120C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C1,
+ },
+ [0x120C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C2,
+ },
+ [0x120C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C3,
+ },
+ [0x120C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C4,
+ },
+ [0x120C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C5,
+ },
+ [0x120C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C6,
+ },
+ [0x120C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C7,
+ },
+ [0x120C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C8,
+ },
+ [0x120C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120C9,
+ },
+ [0x120CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120CA,
+ },
+ [0x120CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120CB,
+ },
+ [0x120CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120CC,
+ },
+ [0x120CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120CD,
+ },
+ [0x120CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120CE,
+ },
+ [0x120CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120CF,
+ },
+ [0x120D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D0,
+ },
+ [0x120D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D1,
+ },
+ [0x120D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D2,
+ },
+ [0x120D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D3,
+ },
+ [0x120D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D4,
+ },
+ [0x120D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D5,
+ },
+ [0x120D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D6,
+ },
+ [0x120D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D7,
+ },
+ [0x120D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D8,
+ },
+ [0x120D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120D9,
+ },
+ [0x120DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120DA,
+ },
+ [0x120DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120DB,
+ },
+ [0x120DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120DC,
+ },
+ [0x120DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120DD,
+ },
+ [0x120DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120DE,
+ },
+ [0x120DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120DF,
+ },
+ [0x120E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E0,
+ },
+ [0x120E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E1,
+ },
+ [0x120E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E2,
+ },
+ [0x120E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E3,
+ },
+ [0x120E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E4,
+ },
+ [0x120E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E5,
+ },
+ [0x120E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E6,
+ },
+ [0x120E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E7,
+ },
+ [0x120E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E8,
+ },
+ [0x120E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120E9,
+ },
+ [0x120EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120EA,
+ },
+ [0x120EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120EB,
+ },
+ [0x120EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120EC,
+ },
+ [0x120ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120ED,
+ },
+ [0x120EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120EE,
+ },
+ [0x120EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120EF,
+ },
+ [0x120F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F0,
+ },
+ [0x120F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F1,
+ },
+ [0x120F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F2,
+ },
+ [0x120F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F3,
+ },
+ [0x120F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F4,
+ },
+ [0x120F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F5,
+ },
+ [0x120F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F6,
+ },
+ [0x120F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F7,
+ },
+ [0x120F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F8,
+ },
+ [0x120F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120F9,
+ },
+ [0x120FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120FA,
+ },
+ [0x120FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120FB,
+ },
+ [0x120FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120FC,
+ },
+ [0x120FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120FD,
+ },
+ [0x120FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120FE,
+ },
+ [0x120FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x120FF,
+ },
+ [0x12100]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12100,
+ },
+ [0x12101]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12101,
+ },
+ [0x12102]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12102,
+ },
+ [0x12103]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12103,
+ },
+ [0x12104]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12104,
+ },
+ [0x12105]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12105,
+ },
+ [0x12106]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12106,
+ },
+ [0x12107]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12107,
+ },
+ [0x12108]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12108,
+ },
+ [0x12109]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12109,
+ },
+ [0x1210A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210A,
+ },
+ [0x1210B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210B,
+ },
+ [0x1210C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210C,
+ },
+ [0x1210D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210D,
+ },
+ [0x1210E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210E,
+ },
+ [0x1210F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1210F,
+ },
+ [0x12110]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12110,
+ },
+ [0x12111]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12111,
+ },
+ [0x12112]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12112,
+ },
+ [0x12113]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12113,
+ },
+ [0x12114]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12114,
+ },
+ [0x12115]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12115,
+ },
+ [0x12116]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12116,
+ },
+ [0x12117]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12117,
+ },
+ [0x12118]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12118,
+ },
+ [0x12119]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12119,
+ },
+ [0x1211A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211A,
+ },
+ [0x1211B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211B,
+ },
+ [0x1211C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211C,
+ },
+ [0x1211D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211D,
+ },
+ [0x1211E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211E,
+ },
+ [0x1211F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1211F,
+ },
+ [0x12120]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12120,
+ },
+ [0x12121]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12121,
+ },
+ [0x12122]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12122,
+ },
+ [0x12123]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12123,
+ },
+ [0x12124]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12124,
+ },
+ [0x12125]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12125,
+ },
+ [0x12126]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12126,
+ },
+ [0x12127]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12127,
+ },
+ [0x12128]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12128,
+ },
+ [0x12129]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12129,
+ },
+ [0x1212A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212A,
+ },
+ [0x1212B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212B,
+ },
+ [0x1212C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212C,
+ },
+ [0x1212D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212D,
+ },
+ [0x1212E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212E,
+ },
+ [0x1212F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1212F,
+ },
+ [0x12130]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12130,
+ },
+ [0x12131]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12131,
+ },
+ [0x12132]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12132,
+ },
+ [0x12133]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12133,
+ },
+ [0x12134]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12134,
+ },
+ [0x12135]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12135,
+ },
+ [0x12136]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12136,
+ },
+ [0x12137]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12137,
+ },
+ [0x12138]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12138,
+ },
+ [0x12139]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12139,
+ },
+ [0x1213A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213A,
+ },
+ [0x1213B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213B,
+ },
+ [0x1213C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213C,
+ },
+ [0x1213D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213D,
+ },
+ [0x1213E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213E,
+ },
+ [0x1213F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1213F,
+ },
+ [0x12140]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12140,
+ },
+ [0x12141]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12141,
+ },
+ [0x12142]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12142,
+ },
+ [0x12143]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12143,
+ },
+ [0x12144]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12144,
+ },
+ [0x12145]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12145,
+ },
+ [0x12146]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12146,
+ },
+ [0x12147]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12147,
+ },
+ [0x12148]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12148,
+ },
+ [0x12149]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12149,
+ },
+ [0x1214A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214A,
+ },
+ [0x1214B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214B,
+ },
+ [0x1214C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214C,
+ },
+ [0x1214D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214D,
+ },
+ [0x1214E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214E,
+ },
+ [0x1214F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1214F,
+ },
+ [0x12150]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12150,
+ },
+ [0x12151]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12151,
+ },
+ [0x12152]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12152,
+ },
+ [0x12153]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12153,
+ },
+ [0x12154]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12154,
+ },
+ [0x12155]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12155,
+ },
+ [0x12156]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12156,
+ },
+ [0x12157]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12157,
+ },
+ [0x12158]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12158,
+ },
+ [0x12159]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12159,
+ },
+ [0x1215A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215A,
+ },
+ [0x1215B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215B,
+ },
+ [0x1215C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215C,
+ },
+ [0x1215D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215D,
+ },
+ [0x1215E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215E,
+ },
+ [0x1215F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1215F,
+ },
+ [0x12160]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12160,
+ },
+ [0x12161]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12161,
+ },
+ [0x12162]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12162,
+ },
+ [0x12163]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12163,
+ },
+ [0x12164]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12164,
+ },
+ [0x12165]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12165,
+ },
+ [0x12166]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12166,
+ },
+ [0x12167]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12167,
+ },
+ [0x12168]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12168,
+ },
+ [0x12169]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12169,
+ },
+ [0x1216A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216A,
+ },
+ [0x1216B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216B,
+ },
+ [0x1216C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216C,
+ },
+ [0x1216D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216D,
+ },
+ [0x1216E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216E,
+ },
+ [0x1216F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1216F,
+ },
+ [0x12170]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12170,
+ },
+ [0x12171]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12171,
+ },
+ [0x12172]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12172,
+ },
+ [0x12173]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12173,
+ },
+ [0x12174]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12174,
+ },
+ [0x12175]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12175,
+ },
+ [0x12176]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12176,
+ },
+ [0x12177]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12177,
+ },
+ [0x12178]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12178,
+ },
+ [0x12179]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12179,
+ },
+ [0x1217A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217A,
+ },
+ [0x1217B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217B,
+ },
+ [0x1217C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217C,
+ },
+ [0x1217D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217D,
+ },
+ [0x1217E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217E,
+ },
+ [0x1217F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1217F,
+ },
+ [0x12180]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12180,
+ },
+ [0x12181]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12181,
+ },
+ [0x12182]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12182,
+ },
+ [0x12183]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12183,
+ },
+ [0x12184]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12184,
+ },
+ [0x12185]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12185,
+ },
+ [0x12186]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12186,
+ },
+ [0x12187]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12187,
+ },
+ [0x12188]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12188,
+ },
+ [0x12189]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12189,
+ },
+ [0x1218A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218A,
+ },
+ [0x1218B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218B,
+ },
+ [0x1218C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218C,
+ },
+ [0x1218D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218D,
+ },
+ [0x1218E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218E,
+ },
+ [0x1218F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1218F,
+ },
+ [0x12190]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12190,
+ },
+ [0x12191]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12191,
+ },
+ [0x12192]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12192,
+ },
+ [0x12193]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12193,
+ },
+ [0x12194]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12194,
+ },
+ [0x12195]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12195,
+ },
+ [0x12196]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12196,
+ },
+ [0x12197]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12197,
+ },
+ [0x12198]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12198,
+ },
+ [0x12199]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12199,
+ },
+ [0x1219A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219A,
+ },
+ [0x1219B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219B,
+ },
+ [0x1219C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219C,
+ },
+ [0x1219D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219D,
+ },
+ [0x1219E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219E,
+ },
+ [0x1219F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1219F,
+ },
+ [0x121A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A0,
+ },
+ [0x121A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A1,
+ },
+ [0x121A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A2,
+ },
+ [0x121A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A3,
+ },
+ [0x121A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A4,
+ },
+ [0x121A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A5,
+ },
+ [0x121A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A6,
+ },
+ [0x121A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A7,
+ },
+ [0x121A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A8,
+ },
+ [0x121A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121A9,
+ },
+ [0x121AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121AA,
+ },
+ [0x121AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121AB,
+ },
+ [0x121AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121AC,
+ },
+ [0x121AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121AD,
+ },
+ [0x121AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121AE,
+ },
+ [0x121AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121AF,
+ },
+ [0x121B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B0,
+ },
+ [0x121B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B1,
+ },
+ [0x121B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B2,
+ },
+ [0x121B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B3,
+ },
+ [0x121B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B4,
+ },
+ [0x121B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B5,
+ },
+ [0x121B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B6,
+ },
+ [0x121B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B7,
+ },
+ [0x121B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B8,
+ },
+ [0x121B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121B9,
+ },
+ [0x121BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121BA,
+ },
+ [0x121BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121BB,
+ },
+ [0x121BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121BC,
+ },
+ [0x121BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121BD,
+ },
+ [0x121BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121BE,
+ },
+ [0x121BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121BF,
+ },
+ [0x121C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C0,
+ },
+ [0x121C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C1,
+ },
+ [0x121C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C2,
+ },
+ [0x121C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C3,
+ },
+ [0x121C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C4,
+ },
+ [0x121C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C5,
+ },
+ [0x121C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C6,
+ },
+ [0x121C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C7,
+ },
+ [0x121C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C8,
+ },
+ [0x121C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121C9,
+ },
+ [0x121CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121CA,
+ },
+ [0x121CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121CB,
+ },
+ [0x121CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121CC,
+ },
+ [0x121CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121CD,
+ },
+ [0x121CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121CE,
+ },
+ [0x121CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121CF,
+ },
+ [0x121D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D0,
+ },
+ [0x121D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D1,
+ },
+ [0x121D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D2,
+ },
+ [0x121D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D3,
+ },
+ [0x121D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D4,
+ },
+ [0x121D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D5,
+ },
+ [0x121D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D6,
+ },
+ [0x121D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D7,
+ },
+ [0x121D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D8,
+ },
+ [0x121D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121D9,
+ },
+ [0x121DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121DA,
+ },
+ [0x121DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121DB,
+ },
+ [0x121DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121DC,
+ },
+ [0x121DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121DD,
+ },
+ [0x121DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121DE,
+ },
+ [0x121DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121DF,
+ },
+ [0x121E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E0,
+ },
+ [0x121E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E1,
+ },
+ [0x121E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E2,
+ },
+ [0x121E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E3,
+ },
+ [0x121E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E4,
+ },
+ [0x121E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E5,
+ },
+ [0x121E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E6,
+ },
+ [0x121E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E7,
+ },
+ [0x121E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E8,
+ },
+ [0x121E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121E9,
+ },
+ [0x121EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121EA,
+ },
+ [0x121EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121EB,
+ },
+ [0x121EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121EC,
+ },
+ [0x121ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121ED,
+ },
+ [0x121EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121EE,
+ },
+ [0x121EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121EF,
+ },
+ [0x121F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F0,
+ },
+ [0x121F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F1,
+ },
+ [0x121F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F2,
+ },
+ [0x121F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F3,
+ },
+ [0x121F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F4,
+ },
+ [0x121F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F5,
+ },
+ [0x121F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F6,
+ },
+ [0x121F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F7,
+ },
+ [0x121F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F8,
+ },
+ [0x121F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121F9,
+ },
+ [0x121FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121FA,
+ },
+ [0x121FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121FB,
+ },
+ [0x121FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121FC,
+ },
+ [0x121FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121FD,
+ },
+ [0x121FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121FE,
+ },
+ [0x121FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x121FF,
+ },
+ [0x12200]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12200,
+ },
+ [0x12201]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12201,
+ },
+ [0x12202]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12202,
+ },
+ [0x12203]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12203,
+ },
+ [0x12204]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12204,
+ },
+ [0x12205]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12205,
+ },
+ [0x12206]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12206,
+ },
+ [0x12207]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12207,
+ },
+ [0x12208]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12208,
+ },
+ [0x12209]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12209,
+ },
+ [0x1220A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220A,
+ },
+ [0x1220B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220B,
+ },
+ [0x1220C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220C,
+ },
+ [0x1220D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220D,
+ },
+ [0x1220E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220E,
+ },
+ [0x1220F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1220F,
+ },
+ [0x12210]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12210,
+ },
+ [0x12211]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12211,
+ },
+ [0x12212]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12212,
+ },
+ [0x12213]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12213,
+ },
+ [0x12214]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12214,
+ },
+ [0x12215]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12215,
+ },
+ [0x12216]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12216,
+ },
+ [0x12217]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12217,
+ },
+ [0x12218]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12218,
+ },
+ [0x12219]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12219,
+ },
+ [0x1221A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221A,
+ },
+ [0x1221B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221B,
+ },
+ [0x1221C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221C,
+ },
+ [0x1221D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221D,
+ },
+ [0x1221E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221E,
+ },
+ [0x1221F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1221F,
+ },
+ [0x12220]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12220,
+ },
+ [0x12221]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12221,
+ },
+ [0x12222]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12222,
+ },
+ [0x12223]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12223,
+ },
+ [0x12224]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12224,
+ },
+ [0x12225]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12225,
+ },
+ [0x12226]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12226,
+ },
+ [0x12227]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12227,
+ },
+ [0x12228]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12228,
+ },
+ [0x12229]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12229,
+ },
+ [0x1222A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222A,
+ },
+ [0x1222B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222B,
+ },
+ [0x1222C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222C,
+ },
+ [0x1222D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222D,
+ },
+ [0x1222E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222E,
+ },
+ [0x1222F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1222F,
+ },
+ [0x12230]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12230,
+ },
+ [0x12231]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12231,
+ },
+ [0x12232]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12232,
+ },
+ [0x12233]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12233,
+ },
+ [0x12234]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12234,
+ },
+ [0x12235]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12235,
+ },
+ [0x12236]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12236,
+ },
+ [0x12237]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12237,
+ },
+ [0x12238]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12238,
+ },
+ [0x12239]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12239,
+ },
+ [0x1223A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223A,
+ },
+ [0x1223B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223B,
+ },
+ [0x1223C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223C,
+ },
+ [0x1223D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223D,
+ },
+ [0x1223E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223E,
+ },
+ [0x1223F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1223F,
+ },
+ [0x12240]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12240,
+ },
+ [0x12241]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12241,
+ },
+ [0x12242]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12242,
+ },
+ [0x12243]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12243,
+ },
+ [0x12244]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12244,
+ },
+ [0x12245]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12245,
+ },
+ [0x12246]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12246,
+ },
+ [0x12247]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12247,
+ },
+ [0x12248]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12248,
+ },
+ [0x12249]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12249,
+ },
+ [0x1224A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224A,
+ },
+ [0x1224B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224B,
+ },
+ [0x1224C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224C,
+ },
+ [0x1224D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224D,
+ },
+ [0x1224E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224E,
+ },
+ [0x1224F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1224F,
+ },
+ [0x12250]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12250,
+ },
+ [0x12251]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12251,
+ },
+ [0x12252]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12252,
+ },
+ [0x12253]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12253,
+ },
+ [0x12254]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12254,
+ },
+ [0x12255]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12255,
+ },
+ [0x12256]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12256,
+ },
+ [0x12257]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12257,
+ },
+ [0x12258]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12258,
+ },
+ [0x12259]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12259,
+ },
+ [0x1225A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225A,
+ },
+ [0x1225B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225B,
+ },
+ [0x1225C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225C,
+ },
+ [0x1225D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225D,
+ },
+ [0x1225E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225E,
+ },
+ [0x1225F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1225F,
+ },
+ [0x12260]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12260,
+ },
+ [0x12261]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12261,
+ },
+ [0x12262]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12262,
+ },
+ [0x12263]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12263,
+ },
+ [0x12264]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12264,
+ },
+ [0x12265]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12265,
+ },
+ [0x12266]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12266,
+ },
+ [0x12267]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12267,
+ },
+ [0x12268]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12268,
+ },
+ [0x12269]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12269,
+ },
+ [0x1226A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226A,
+ },
+ [0x1226B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226B,
+ },
+ [0x1226C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226C,
+ },
+ [0x1226D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226D,
+ },
+ [0x1226E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226E,
+ },
+ [0x1226F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1226F,
+ },
+ [0x12270]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12270,
+ },
+ [0x12271]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12271,
+ },
+ [0x12272]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12272,
+ },
+ [0x12273]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12273,
+ },
+ [0x12274]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12274,
+ },
+ [0x12275]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12275,
+ },
+ [0x12276]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12276,
+ },
+ [0x12277]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12277,
+ },
+ [0x12278]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12278,
+ },
+ [0x12279]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12279,
+ },
+ [0x1227A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227A,
+ },
+ [0x1227B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227B,
+ },
+ [0x1227C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227C,
+ },
+ [0x1227D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227D,
+ },
+ [0x1227E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227E,
+ },
+ [0x1227F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1227F,
+ },
+ [0x12280]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12280,
+ },
+ [0x12281]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12281,
+ },
+ [0x12282]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12282,
+ },
+ [0x12283]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12283,
+ },
+ [0x12284]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12284,
+ },
+ [0x12285]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12285,
+ },
+ [0x12286]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12286,
+ },
+ [0x12287]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12287,
+ },
+ [0x12288]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12288,
+ },
+ [0x12289]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12289,
+ },
+ [0x1228A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228A,
+ },
+ [0x1228B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228B,
+ },
+ [0x1228C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228C,
+ },
+ [0x1228D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228D,
+ },
+ [0x1228E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228E,
+ },
+ [0x1228F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1228F,
+ },
+ [0x12290]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12290,
+ },
+ [0x12291]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12291,
+ },
+ [0x12292]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12292,
+ },
+ [0x12293]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12293,
+ },
+ [0x12294]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12294,
+ },
+ [0x12295]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12295,
+ },
+ [0x12296]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12296,
+ },
+ [0x12297]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12297,
+ },
+ [0x12298]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12298,
+ },
+ [0x12299]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12299,
+ },
+ [0x1229A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229A,
+ },
+ [0x1229B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229B,
+ },
+ [0x1229C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229C,
+ },
+ [0x1229D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229D,
+ },
+ [0x1229E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229E,
+ },
+ [0x1229F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1229F,
+ },
+ [0x122A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A0,
+ },
+ [0x122A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A1,
+ },
+ [0x122A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A2,
+ },
+ [0x122A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A3,
+ },
+ [0x122A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A4,
+ },
+ [0x122A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A5,
+ },
+ [0x122A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A6,
+ },
+ [0x122A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A7,
+ },
+ [0x122A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A8,
+ },
+ [0x122A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122A9,
+ },
+ [0x122AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122AA,
+ },
+ [0x122AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122AB,
+ },
+ [0x122AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122AC,
+ },
+ [0x122AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122AD,
+ },
+ [0x122AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122AE,
+ },
+ [0x122AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122AF,
+ },
+ [0x122B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B0,
+ },
+ [0x122B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B1,
+ },
+ [0x122B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B2,
+ },
+ [0x122B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B3,
+ },
+ [0x122B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B4,
+ },
+ [0x122B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B5,
+ },
+ [0x122B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B6,
+ },
+ [0x122B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B7,
+ },
+ [0x122B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B8,
+ },
+ [0x122B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122B9,
+ },
+ [0x122BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122BA,
+ },
+ [0x122BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122BB,
+ },
+ [0x122BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122BC,
+ },
+ [0x122BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122BD,
+ },
+ [0x122BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122BE,
+ },
+ [0x122BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122BF,
+ },
+ [0x122C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C0,
+ },
+ [0x122C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C1,
+ },
+ [0x122C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C2,
+ },
+ [0x122C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C3,
+ },
+ [0x122C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C4,
+ },
+ [0x122C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C5,
+ },
+ [0x122C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C6,
+ },
+ [0x122C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C7,
+ },
+ [0x122C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C8,
+ },
+ [0x122C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122C9,
+ },
+ [0x122CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122CA,
+ },
+ [0x122CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122CB,
+ },
+ [0x122CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122CC,
+ },
+ [0x122CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122CD,
+ },
+ [0x122CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122CE,
+ },
+ [0x122CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122CF,
+ },
+ [0x122D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D0,
+ },
+ [0x122D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D1,
+ },
+ [0x122D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D2,
+ },
+ [0x122D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D3,
+ },
+ [0x122D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D4,
+ },
+ [0x122D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D5,
+ },
+ [0x122D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D6,
+ },
+ [0x122D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D7,
+ },
+ [0x122D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D8,
+ },
+ [0x122D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122D9,
+ },
+ [0x122DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122DA,
+ },
+ [0x122DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122DB,
+ },
+ [0x122DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122DC,
+ },
+ [0x122DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122DD,
+ },
+ [0x122DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122DE,
+ },
+ [0x122DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122DF,
+ },
+ [0x122E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E0,
+ },
+ [0x122E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E1,
+ },
+ [0x122E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E2,
+ },
+ [0x122E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E3,
+ },
+ [0x122E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E4,
+ },
+ [0x122E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E5,
+ },
+ [0x122E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E6,
+ },
+ [0x122E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E7,
+ },
+ [0x122E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E8,
+ },
+ [0x122E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122E9,
+ },
+ [0x122EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122EA,
+ },
+ [0x122EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122EB,
+ },
+ [0x122EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122EC,
+ },
+ [0x122ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122ED,
+ },
+ [0x122EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122EE,
+ },
+ [0x122EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122EF,
+ },
+ [0x122F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F0,
+ },
+ [0x122F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F1,
+ },
+ [0x122F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F2,
+ },
+ [0x122F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F3,
+ },
+ [0x122F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F4,
+ },
+ [0x122F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F5,
+ },
+ [0x122F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F6,
+ },
+ [0x122F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F7,
+ },
+ [0x122F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F8,
+ },
+ [0x122F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122F9,
+ },
+ [0x122FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122FA,
+ },
+ [0x122FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122FB,
+ },
+ [0x122FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122FC,
+ },
+ [0x122FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122FD,
+ },
+ [0x122FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122FE,
+ },
+ [0x122FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x122FF,
+ },
+ [0x12300]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12300,
+ },
+ [0x12301]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12301,
+ },
+ [0x12302]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12302,
+ },
+ [0x12303]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12303,
+ },
+ [0x12304]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12304,
+ },
+ [0x12305]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12305,
+ },
+ [0x12306]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12306,
+ },
+ [0x12307]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12307,
+ },
+ [0x12308]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12308,
+ },
+ [0x12309]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12309,
+ },
+ [0x1230A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230A,
+ },
+ [0x1230B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230B,
+ },
+ [0x1230C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230C,
+ },
+ [0x1230D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230D,
+ },
+ [0x1230E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230E,
+ },
+ [0x1230F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1230F,
+ },
+ [0x12310]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12310,
+ },
+ [0x12311]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12311,
+ },
+ [0x12312]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12312,
+ },
+ [0x12313]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12313,
+ },
+ [0x12314]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12314,
+ },
+ [0x12315]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12315,
+ },
+ [0x12316]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12316,
+ },
+ [0x12317]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12317,
+ },
+ [0x12318]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12318,
+ },
+ [0x12319]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12319,
+ },
+ [0x1231A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231A,
+ },
+ [0x1231B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231B,
+ },
+ [0x1231C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231C,
+ },
+ [0x1231D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231D,
+ },
+ [0x1231E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231E,
+ },
+ [0x1231F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1231F,
+ },
+ [0x12320]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12320,
+ },
+ [0x12321]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12321,
+ },
+ [0x12322]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12322,
+ },
+ [0x12323]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12323,
+ },
+ [0x12324]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12324,
+ },
+ [0x12325]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12325,
+ },
+ [0x12326]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12326,
+ },
+ [0x12327]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12327,
+ },
+ [0x12328]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12328,
+ },
+ [0x12329]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12329,
+ },
+ [0x1232A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232A,
+ },
+ [0x1232B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232B,
+ },
+ [0x1232C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232C,
+ },
+ [0x1232D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232D,
+ },
+ [0x1232E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232E,
+ },
+ [0x1232F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1232F,
+ },
+ [0x12330]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12330,
+ },
+ [0x12331]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12331,
+ },
+ [0x12332]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12332,
+ },
+ [0x12333]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12333,
+ },
+ [0x12334]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12334,
+ },
+ [0x12335]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12335,
+ },
+ [0x12336]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12336,
+ },
+ [0x12337]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12337,
+ },
+ [0x12338]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12338,
+ },
+ [0x12339]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12339,
+ },
+ [0x1233A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233A,
+ },
+ [0x1233B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233B,
+ },
+ [0x1233C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233C,
+ },
+ [0x1233D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233D,
+ },
+ [0x1233E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233E,
+ },
+ [0x1233F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1233F,
+ },
+ [0x12340]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12340,
+ },
+ [0x12341]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12341,
+ },
+ [0x12342]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12342,
+ },
+ [0x12343]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12343,
+ },
+ [0x12344]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12344,
+ },
+ [0x12345]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12345,
+ },
+ [0x12346]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12346,
+ },
+ [0x12347]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12347,
+ },
+ [0x12348]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12348,
+ },
+ [0x12349]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12349,
+ },
+ [0x1234A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234A,
+ },
+ [0x1234B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234B,
+ },
+ [0x1234C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234C,
+ },
+ [0x1234D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234D,
+ },
+ [0x1234E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234E,
+ },
+ [0x1234F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1234F,
+ },
+ [0x12350]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12350,
+ },
+ [0x12351]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12351,
+ },
+ [0x12352]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12352,
+ },
+ [0x12353]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12353,
+ },
+ [0x12354]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12354,
+ },
+ [0x12355]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12355,
+ },
+ [0x12356]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12356,
+ },
+ [0x12357]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12357,
+ },
+ [0x12358]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12358,
+ },
+ [0x12359]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12359,
+ },
+ [0x1235A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235A,
+ },
+ [0x1235B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235B,
+ },
+ [0x1235C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235C,
+ },
+ [0x1235D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235D,
+ },
+ [0x1235E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235E,
+ },
+ [0x1235F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1235F,
+ },
+ [0x12360]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12360,
+ },
+ [0x12361]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12361,
+ },
+ [0x12362]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12362,
+ },
+ [0x12363]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12363,
+ },
+ [0x12364]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12364,
+ },
+ [0x12365]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12365,
+ },
+ [0x12366]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12366,
+ },
+ [0x12367]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12367,
+ },
+ [0x12368]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12368,
+ },
+ [0x12369]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12369,
+ },
+ [0x1236A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236A,
+ },
+ [0x1236B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236B,
+ },
+ [0x1236C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236C,
+ },
+ [0x1236D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236D,
+ },
+ [0x1236E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236E,
+ },
+ [0x1236F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1236F,
+ },
+ [0x12370]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12370,
+ },
+ [0x12371]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12371,
+ },
+ [0x12372]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12372,
+ },
+ [0x12373]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12373,
+ },
+ [0x12374]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12374,
+ },
+ [0x12375]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12375,
+ },
+ [0x12376]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12376,
+ },
+ [0x12377]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12377,
+ },
+ [0x12378]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12378,
+ },
+ [0x12379]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12379,
+ },
+ [0x1237A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237A,
+ },
+ [0x1237B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237B,
+ },
+ [0x1237C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237C,
+ },
+ [0x1237D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237D,
+ },
+ [0x1237E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237E,
+ },
+ [0x1237F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1237F,
+ },
+ [0x12380]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12380,
+ },
+ [0x12381]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12381,
+ },
+ [0x12382]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12382,
+ },
+ [0x12383]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12383,
+ },
+ [0x12384]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12384,
+ },
+ [0x12385]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12385,
+ },
+ [0x12386]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12386,
+ },
+ [0x12387]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12387,
+ },
+ [0x12388]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12388,
+ },
+ [0x12389]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12389,
+ },
+ [0x1238A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238A,
+ },
+ [0x1238B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238B,
+ },
+ [0x1238C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238C,
+ },
+ [0x1238D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238D,
+ },
+ [0x1238E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238E,
+ },
+ [0x1238F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1238F,
+ },
+ [0x12390]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12390,
+ },
+ [0x12391]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12391,
+ },
+ [0x12392]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12392,
+ },
+ [0x12393]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12393,
+ },
+ [0x12394]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12394,
+ },
+ [0x12395]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12395,
+ },
+ [0x12396]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12396,
+ },
+ [0x12397]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12397,
+ },
+ [0x12398]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12398,
+ },
+ [0x12399]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12399,
+ },
+ [0x12400]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12400,
+ },
+ [0x12401]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12401,
+ },
+ [0x12402]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12402,
+ },
+ [0x12403]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12403,
+ },
+ [0x12404]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12404,
+ },
+ [0x12405]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12405,
+ },
+ [0x12406]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12406,
+ },
+ [0x12407]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12407,
+ },
+ [0x12408]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12408,
+ },
+ [0x12409]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12409,
+ },
+ [0x1240A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240A,
+ },
+ [0x1240B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240B,
+ },
+ [0x1240C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240C,
+ },
+ [0x1240D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240D,
+ },
+ [0x1240E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240E,
+ },
+ [0x1240F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1240F,
+ },
+ [0x12410]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12410,
+ },
+ [0x12411]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12411,
+ },
+ [0x12412]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12412,
+ },
+ [0x12413]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12413,
+ },
+ [0x12414]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12414,
+ },
+ [0x12415]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12415,
+ },
+ [0x12416]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12416,
+ },
+ [0x12417]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12417,
+ },
+ [0x12418]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12418,
+ },
+ [0x12419]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12419,
+ },
+ [0x1241A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241A,
+ },
+ [0x1241B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241B,
+ },
+ [0x1241C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241C,
+ },
+ [0x1241D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241D,
+ },
+ [0x1241E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241E,
+ },
+ [0x1241F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1241F,
+ },
+ [0x12420]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12420,
+ },
+ [0x12421]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12421,
+ },
+ [0x12422]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12422,
+ },
+ [0x12423]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12423,
+ },
+ [0x12424]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12424,
+ },
+ [0x12425]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12425,
+ },
+ [0x12426]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12426,
+ },
+ [0x12427]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12427,
+ },
+ [0x12428]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12428,
+ },
+ [0x12429]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12429,
+ },
+ [0x1242A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242A,
+ },
+ [0x1242B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242B,
+ },
+ [0x1242C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242C,
+ },
+ [0x1242D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242D,
+ },
+ [0x1242E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242E,
+ },
+ [0x1242F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1242F,
+ },
+ [0x12430]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12430,
+ },
+ [0x12431]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12431,
+ },
+ [0x12432]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12432,
+ },
+ [0x12433]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12433,
+ },
+ [0x12434]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12434,
+ },
+ [0x12435]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12435,
+ },
+ [0x12436]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12436,
+ },
+ [0x12437]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12437,
+ },
+ [0x12438]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12438,
+ },
+ [0x12439]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12439,
+ },
+ [0x1243A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243A,
+ },
+ [0x1243B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243B,
+ },
+ [0x1243C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243C,
+ },
+ [0x1243D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243D,
+ },
+ [0x1243E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243E,
+ },
+ [0x1243F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1243F,
+ },
+ [0x12440]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12440,
+ },
+ [0x12441]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12441,
+ },
+ [0x12442]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12442,
+ },
+ [0x12443]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12443,
+ },
+ [0x12444]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12444,
+ },
+ [0x12445]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12445,
+ },
+ [0x12446]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12446,
+ },
+ [0x12447]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12447,
+ },
+ [0x12448]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12448,
+ },
+ [0x12449]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12449,
+ },
+ [0x1244A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244A,
+ },
+ [0x1244B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244B,
+ },
+ [0x1244C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244C,
+ },
+ [0x1244D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244D,
+ },
+ [0x1244E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244E,
+ },
+ [0x1244F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1244F,
+ },
+ [0x12450]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12450,
+ },
+ [0x12451]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12451,
+ },
+ [0x12452]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12452,
+ },
+ [0x12453]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12453,
+ },
+ [0x12454]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12454,
+ },
+ [0x12455]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12455,
+ },
+ [0x12456]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12456,
+ },
+ [0x12457]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12457,
+ },
+ [0x12458]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12458,
+ },
+ [0x12459]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12459,
+ },
+ [0x1245A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245A,
+ },
+ [0x1245B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245B,
+ },
+ [0x1245C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245C,
+ },
+ [0x1245D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245D,
+ },
+ [0x1245E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245E,
+ },
+ [0x1245F]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1245F,
+ },
+ [0x12460]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12460,
+ },
+ [0x12461]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12461,
+ },
+ [0x12462]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12462,
+ },
+ [0x12463]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12463,
+ },
+ [0x12464]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12464,
+ },
+ [0x12465]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12465,
+ },
+ [0x12466]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12466,
+ },
+ [0x12467]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12467,
+ },
+ [0x12468]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12468,
+ },
+ [0x12469]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12469,
+ },
+ [0x1246A]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1246A,
+ },
+ [0x1246B]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1246B,
+ },
+ [0x1246C]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1246C,
+ },
+ [0x1246D]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1246D,
+ },
+ [0x1246E]={
+ category="nl",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1246E,
+ },
+ [0x12470]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x12470,
+ },
+ [0x12471]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x12471,
+ },
+ [0x12472]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x12472,
+ },
+ [0x12473]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x12473,
+ },
+ [0x12474]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x12474,
+ },
+ [0x12480]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12480,
+ },
+ [0x12481]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12481,
+ },
+ [0x12482]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12482,
+ },
+ [0x12483]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12483,
+ },
+ [0x12484]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12484,
+ },
+ [0x12485]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12485,
+ },
+ [0x12486]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12486,
+ },
+ [0x12487]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12487,
+ },
+ [0x12488]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12488,
+ },
+ [0x12489]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12489,
+ },
+ [0x1248A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248A,
+ },
+ [0x1248B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248B,
+ },
+ [0x1248C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248C,
+ },
+ [0x1248D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248D,
+ },
+ [0x1248E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248E,
+ },
+ [0x1248F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1248F,
+ },
+ [0x12490]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12490,
+ },
+ [0x12491]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12491,
+ },
+ [0x12492]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12492,
+ },
+ [0x12493]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12493,
+ },
+ [0x12494]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12494,
+ },
+ [0x12495]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12495,
+ },
+ [0x12496]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12496,
+ },
+ [0x12497]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12497,
+ },
+ [0x12498]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12498,
+ },
+ [0x12499]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12499,
+ },
+ [0x1249A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1249A,
+ },
+ [0x1249B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1249B,
+ },
+ [0x1249C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1249C,
+ },
+ [0x1249D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1249D,
+ },
+ [0x1249E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1249E,
+ },
+ [0x1249F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1249F,
+ },
+ [0x124A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A0,
+ },
+ [0x124A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A1,
+ },
+ [0x124A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A2,
+ },
+ [0x124A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A3,
+ },
+ [0x124A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A4,
+ },
+ [0x124A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A5,
+ },
+ [0x124A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A6,
+ },
+ [0x124A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A7,
+ },
+ [0x124A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A8,
+ },
+ [0x124A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124A9,
+ },
+ [0x124AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124AA,
+ },
+ [0x124AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124AB,
+ },
+ [0x124AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124AC,
+ },
+ [0x124AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124AD,
+ },
+ [0x124AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124AE,
+ },
+ [0x124AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124AF,
+ },
+ [0x124B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B0,
+ },
+ [0x124B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B1,
+ },
+ [0x124B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B2,
+ },
+ [0x124B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B3,
+ },
+ [0x124B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B4,
+ },
+ [0x124B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B5,
+ },
+ [0x124B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B6,
+ },
+ [0x124B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B7,
+ },
+ [0x124B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B8,
+ },
+ [0x124B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124B9,
+ },
+ [0x124BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124BA,
+ },
+ [0x124BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124BB,
+ },
+ [0x124BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124BC,
+ },
+ [0x124BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124BD,
+ },
+ [0x124BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124BE,
+ },
+ [0x124BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124BF,
+ },
+ [0x124C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C0,
+ },
+ [0x124C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C1,
+ },
+ [0x124C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C2,
+ },
+ [0x124C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C3,
+ },
+ [0x124C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C4,
+ },
+ [0x124C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C5,
+ },
+ [0x124C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C6,
+ },
+ [0x124C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C7,
+ },
+ [0x124C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C8,
+ },
+ [0x124C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124C9,
+ },
+ [0x124CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124CA,
+ },
+ [0x124CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124CB,
+ },
+ [0x124CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124CC,
+ },
+ [0x124CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124CD,
+ },
+ [0x124CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124CE,
+ },
+ [0x124CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124CF,
+ },
+ [0x124D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D0,
+ },
+ [0x124D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D1,
+ },
+ [0x124D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D2,
+ },
+ [0x124D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D3,
+ },
+ [0x124D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D4,
+ },
+ [0x124D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D5,
+ },
+ [0x124D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D6,
+ },
+ [0x124D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D7,
+ },
+ [0x124D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D8,
+ },
+ [0x124D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124D9,
+ },
+ [0x124DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124DA,
+ },
+ [0x124DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124DB,
+ },
+ [0x124DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124DC,
+ },
+ [0x124DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124DD,
+ },
+ [0x124DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124DE,
+ },
+ [0x124DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124DF,
+ },
+ [0x124E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E0,
+ },
+ [0x124E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E1,
+ },
+ [0x124E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E2,
+ },
+ [0x124E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E3,
+ },
+ [0x124E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E4,
+ },
+ [0x124E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E5,
+ },
+ [0x124E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E6,
+ },
+ [0x124E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E7,
+ },
+ [0x124E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E8,
+ },
+ [0x124E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124E9,
+ },
+ [0x124EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124EA,
+ },
+ [0x124EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124EB,
+ },
+ [0x124EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124EC,
+ },
+ [0x124ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124ED,
+ },
+ [0x124EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124EE,
+ },
+ [0x124EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124EF,
+ },
+ [0x124F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F0,
+ },
+ [0x124F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F1,
+ },
+ [0x124F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F2,
+ },
+ [0x124F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F3,
+ },
+ [0x124F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F4,
+ },
+ [0x124F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F5,
+ },
+ [0x124F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F6,
+ },
+ [0x124F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F7,
+ },
+ [0x124F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F8,
+ },
+ [0x124F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124F9,
+ },
+ [0x124FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124FA,
+ },
+ [0x124FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124FB,
+ },
+ [0x124FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124FC,
+ },
+ [0x124FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124FD,
+ },
+ [0x124FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124FE,
+ },
+ [0x124FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x124FF,
+ },
+ [0x12500]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12500,
+ },
+ [0x12501]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12501,
+ },
+ [0x12502]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12502,
+ },
+ [0x12503]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12503,
+ },
+ [0x12504]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12504,
+ },
+ [0x12505]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12505,
+ },
+ [0x12506]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12506,
+ },
+ [0x12507]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12507,
+ },
+ [0x12508]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12508,
+ },
+ [0x12509]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12509,
+ },
+ [0x1250A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250A,
+ },
+ [0x1250B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250B,
+ },
+ [0x1250C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250C,
+ },
+ [0x1250D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250D,
+ },
+ [0x1250E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250E,
+ },
+ [0x1250F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1250F,
+ },
+ [0x12510]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12510,
+ },
+ [0x12511]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12511,
+ },
+ [0x12512]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12512,
+ },
+ [0x12513]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12513,
+ },
+ [0x12514]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12514,
+ },
+ [0x12515]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12515,
+ },
+ [0x12516]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12516,
+ },
+ [0x12517]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12517,
+ },
+ [0x12518]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12518,
+ },
+ [0x12519]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12519,
+ },
+ [0x1251A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251A,
+ },
+ [0x1251B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251B,
+ },
+ [0x1251C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251C,
+ },
+ [0x1251D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251D,
+ },
+ [0x1251E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251E,
+ },
+ [0x1251F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1251F,
+ },
+ [0x12520]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12520,
+ },
+ [0x12521]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12521,
+ },
+ [0x12522]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12522,
+ },
+ [0x12523]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12523,
+ },
+ [0x12524]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12524,
+ },
+ [0x12525]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12525,
+ },
+ [0x12526]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12526,
+ },
+ [0x12527]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12527,
+ },
+ [0x12528]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12528,
+ },
+ [0x12529]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12529,
+ },
+ [0x1252A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252A,
+ },
+ [0x1252B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252B,
+ },
+ [0x1252C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252C,
+ },
+ [0x1252D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252D,
+ },
+ [0x1252E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252E,
+ },
+ [0x1252F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1252F,
+ },
+ [0x12530]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12530,
+ },
+ [0x12531]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12531,
+ },
+ [0x12532]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12532,
+ },
+ [0x12533]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12533,
+ },
+ [0x12534]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12534,
+ },
+ [0x12535]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12535,
+ },
+ [0x12536]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12536,
+ },
+ [0x12537]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12537,
+ },
+ [0x12538]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12538,
+ },
+ [0x12539]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12539,
+ },
+ [0x1253A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253A,
+ },
+ [0x1253B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253B,
+ },
+ [0x1253C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253C,
+ },
+ [0x1253D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253D,
+ },
+ [0x1253E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253E,
+ },
+ [0x1253F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1253F,
+ },
+ [0x12540]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12540,
+ },
+ [0x12541]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12541,
+ },
+ [0x12542]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12542,
+ },
+ [0x12543]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x12543,
+ },
+ [0x13000]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13000,
+ },
+ [0x13001]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13001,
+ },
+ [0x13002]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13002,
+ },
+ [0x13003]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13003,
+ },
+ [0x13004]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13004,
+ },
+ [0x13005]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13005,
+ },
+ [0x13006]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13006,
+ },
+ [0x13007]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13007,
+ },
+ [0x13008]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13008,
+ },
+ [0x13009]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13009,
+ },
+ [0x1300A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300A,
+ },
+ [0x1300B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300B,
+ },
+ [0x1300C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300C,
+ },
+ [0x1300D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300D,
+ },
+ [0x1300E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300E,
+ },
+ [0x1300F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1300F,
+ },
+ [0x13010]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13010,
+ },
+ [0x13011]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13011,
+ },
+ [0x13012]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13012,
+ },
+ [0x13013]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13013,
+ },
+ [0x13014]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13014,
+ },
+ [0x13015]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13015,
+ },
+ [0x13016]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13016,
+ },
+ [0x13017]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13017,
+ },
+ [0x13018]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13018,
+ },
+ [0x13019]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13019,
+ },
+ [0x1301A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301A,
+ },
+ [0x1301B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301B,
+ },
+ [0x1301C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301C,
+ },
+ [0x1301D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301D,
+ },
+ [0x1301E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301E,
+ },
+ [0x1301F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1301F,
+ },
+ [0x13020]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13020,
+ },
+ [0x13021]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13021,
+ },
+ [0x13022]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13022,
+ },
+ [0x13023]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13023,
+ },
+ [0x13024]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13024,
+ },
+ [0x13025]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13025,
+ },
+ [0x13026]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13026,
+ },
+ [0x13027]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13027,
+ },
+ [0x13028]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13028,
+ },
+ [0x13029]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13029,
+ },
+ [0x1302A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302A,
+ },
+ [0x1302B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302B,
+ },
+ [0x1302C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302C,
+ },
+ [0x1302D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302D,
+ },
+ [0x1302E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302E,
+ },
+ [0x1302F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1302F,
+ },
+ [0x13030]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13030,
+ },
+ [0x13031]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13031,
+ },
+ [0x13032]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13032,
+ },
+ [0x13033]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13033,
+ },
+ [0x13034]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13034,
+ },
+ [0x13035]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13035,
+ },
+ [0x13036]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13036,
+ },
+ [0x13037]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13037,
+ },
+ [0x13038]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13038,
+ },
+ [0x13039]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13039,
+ },
+ [0x1303A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303A,
+ },
+ [0x1303B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303B,
+ },
+ [0x1303C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303C,
+ },
+ [0x1303D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303D,
+ },
+ [0x1303E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303E,
+ },
+ [0x1303F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1303F,
+ },
+ [0x13040]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13040,
+ },
+ [0x13041]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13041,
+ },
+ [0x13042]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13042,
+ },
+ [0x13043]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13043,
+ },
+ [0x13044]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13044,
+ },
+ [0x13045]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13045,
+ },
+ [0x13046]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13046,
+ },
+ [0x13047]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13047,
+ },
+ [0x13048]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13048,
+ },
+ [0x13049]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13049,
+ },
+ [0x1304A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304A,
+ },
+ [0x1304B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304B,
+ },
+ [0x1304C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304C,
+ },
+ [0x1304D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304D,
+ },
+ [0x1304E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304E,
+ },
+ [0x1304F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1304F,
+ },
+ [0x13050]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13050,
+ },
+ [0x13051]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13051,
+ },
+ [0x13052]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13052,
+ },
+ [0x13053]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13053,
+ },
+ [0x13054]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13054,
+ },
+ [0x13055]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13055,
+ },
+ [0x13056]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13056,
+ },
+ [0x13057]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13057,
+ },
+ [0x13058]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13058,
+ },
+ [0x13059]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13059,
+ },
+ [0x1305A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305A,
+ },
+ [0x1305B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305B,
+ },
+ [0x1305C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305C,
+ },
+ [0x1305D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305D,
+ },
+ [0x1305E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305E,
+ },
+ [0x1305F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1305F,
+ },
+ [0x13060]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13060,
+ },
+ [0x13061]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13061,
+ },
+ [0x13062]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13062,
+ },
+ [0x13063]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13063,
+ },
+ [0x13064]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13064,
+ },
+ [0x13065]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13065,
+ },
+ [0x13066]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13066,
+ },
+ [0x13067]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13067,
+ },
+ [0x13068]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13068,
+ },
+ [0x13069]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13069,
+ },
+ [0x1306A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306A,
+ },
+ [0x1306B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306B,
+ },
+ [0x1306C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306C,
+ },
+ [0x1306D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306D,
+ },
+ [0x1306E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306E,
+ },
+ [0x1306F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1306F,
+ },
+ [0x13070]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13070,
+ },
+ [0x13071]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13071,
+ },
+ [0x13072]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13072,
+ },
+ [0x13073]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13073,
+ },
+ [0x13074]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13074,
+ },
+ [0x13075]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13075,
+ },
+ [0x13076]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13076,
+ },
+ [0x13077]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13077,
+ },
+ [0x13078]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13078,
+ },
+ [0x13079]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13079,
+ },
+ [0x1307A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307A,
+ },
+ [0x1307B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307B,
+ },
+ [0x1307C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307C,
+ },
+ [0x1307D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307D,
+ },
+ [0x1307E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307E,
+ },
+ [0x1307F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1307F,
+ },
+ [0x13080]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13080,
+ },
+ [0x13081]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13081,
+ },
+ [0x13082]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13082,
+ },
+ [0x13083]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13083,
+ },
+ [0x13084]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13084,
+ },
+ [0x13085]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13085,
+ },
+ [0x13086]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13086,
+ },
+ [0x13087]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13087,
+ },
+ [0x13088]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13088,
+ },
+ [0x13089]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13089,
+ },
+ [0x1308A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308A,
+ },
+ [0x1308B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308B,
+ },
+ [0x1308C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308C,
+ },
+ [0x1308D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308D,
+ },
+ [0x1308E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308E,
+ },
+ [0x1308F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1308F,
+ },
+ [0x13090]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13090,
+ },
+ [0x13091]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13091,
+ },
+ [0x13092]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13092,
+ },
+ [0x13093]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13093,
+ },
+ [0x13094]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13094,
+ },
+ [0x13095]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13095,
+ },
+ [0x13096]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13096,
+ },
+ [0x13097]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13097,
+ },
+ [0x13098]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13098,
+ },
+ [0x13099]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13099,
+ },
+ [0x1309A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309A,
+ },
+ [0x1309B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309B,
+ },
+ [0x1309C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309C,
+ },
+ [0x1309D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309D,
+ },
+ [0x1309E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309E,
+ },
+ [0x1309F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1309F,
+ },
+ [0x130A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A0,
+ },
+ [0x130A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A1,
+ },
+ [0x130A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A2,
+ },
+ [0x130A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A3,
+ },
+ [0x130A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A4,
+ },
+ [0x130A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A5,
+ },
+ [0x130A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A6,
+ },
+ [0x130A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A7,
+ },
+ [0x130A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A8,
+ },
+ [0x130A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130A9,
+ },
+ [0x130AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130AA,
+ },
+ [0x130AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130AB,
+ },
+ [0x130AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130AC,
+ },
+ [0x130AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130AD,
+ },
+ [0x130AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130AE,
+ },
+ [0x130AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130AF,
+ },
+ [0x130B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B0,
+ },
+ [0x130B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B1,
+ },
+ [0x130B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B2,
+ },
+ [0x130B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B3,
+ },
+ [0x130B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B4,
+ },
+ [0x130B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B5,
+ },
+ [0x130B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B6,
+ },
+ [0x130B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B7,
+ },
+ [0x130B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B8,
+ },
+ [0x130B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130B9,
+ },
+ [0x130BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130BA,
+ },
+ [0x130BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130BB,
+ },
+ [0x130BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130BC,
+ },
+ [0x130BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130BD,
+ },
+ [0x130BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130BE,
+ },
+ [0x130BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130BF,
+ },
+ [0x130C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C0,
+ },
+ [0x130C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C1,
+ },
+ [0x130C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C2,
+ },
+ [0x130C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C3,
+ },
+ [0x130C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C4,
+ },
+ [0x130C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C5,
+ },
+ [0x130C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C6,
+ },
+ [0x130C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C7,
+ },
+ [0x130C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C8,
+ },
+ [0x130C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130C9,
+ },
+ [0x130CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130CA,
+ },
+ [0x130CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130CB,
+ },
+ [0x130CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130CC,
+ },
+ [0x130CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130CD,
+ },
+ [0x130CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130CE,
+ },
+ [0x130CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130CF,
+ },
+ [0x130D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D0,
+ },
+ [0x130D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D1,
+ },
+ [0x130D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D2,
+ },
+ [0x130D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D3,
+ },
+ [0x130D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D4,
+ },
+ [0x130D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D5,
+ },
+ [0x130D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D6,
+ },
+ [0x130D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D7,
+ },
+ [0x130D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D8,
+ },
+ [0x130D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130D9,
+ },
+ [0x130DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130DA,
+ },
+ [0x130DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130DB,
+ },
+ [0x130DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130DC,
+ },
+ [0x130DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130DD,
+ },
+ [0x130DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130DE,
+ },
+ [0x130DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130DF,
+ },
+ [0x130E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E0,
+ },
+ [0x130E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E1,
+ },
+ [0x130E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E2,
+ },
+ [0x130E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E3,
+ },
+ [0x130E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E4,
+ },
+ [0x130E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E5,
+ },
+ [0x130E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E6,
+ },
+ [0x130E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E7,
+ },
+ [0x130E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E8,
+ },
+ [0x130E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130E9,
+ },
+ [0x130EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130EA,
+ },
+ [0x130EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130EB,
+ },
+ [0x130EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130EC,
+ },
+ [0x130ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130ED,
+ },
+ [0x130EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130EE,
+ },
+ [0x130EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130EF,
+ },
+ [0x130F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F0,
+ },
+ [0x130F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F1,
+ },
+ [0x130F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F2,
+ },
+ [0x130F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F3,
+ },
+ [0x130F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F4,
+ },
+ [0x130F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F5,
+ },
+ [0x130F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F6,
+ },
+ [0x130F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F7,
+ },
+ [0x130F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F8,
+ },
+ [0x130F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130F9,
+ },
+ [0x130FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130FA,
+ },
+ [0x130FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130FB,
+ },
+ [0x130FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130FC,
+ },
+ [0x130FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130FD,
+ },
+ [0x130FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130FE,
+ },
+ [0x130FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x130FF,
+ },
+ [0x13100]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13100,
+ },
+ [0x13101]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13101,
+ },
+ [0x13102]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13102,
+ },
+ [0x13103]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13103,
+ },
+ [0x13104]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13104,
+ },
+ [0x13105]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13105,
+ },
+ [0x13106]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13106,
+ },
+ [0x13107]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13107,
+ },
+ [0x13108]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13108,
+ },
+ [0x13109]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13109,
+ },
+ [0x1310A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310A,
+ },
+ [0x1310B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310B,
+ },
+ [0x1310C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310C,
+ },
+ [0x1310D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310D,
+ },
+ [0x1310E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310E,
+ },
+ [0x1310F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1310F,
+ },
+ [0x13110]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13110,
+ },
+ [0x13111]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13111,
+ },
+ [0x13112]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13112,
+ },
+ [0x13113]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13113,
+ },
+ [0x13114]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13114,
+ },
+ [0x13115]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13115,
+ },
+ [0x13116]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13116,
+ },
+ [0x13117]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13117,
+ },
+ [0x13118]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13118,
+ },
+ [0x13119]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13119,
+ },
+ [0x1311A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1311A,
+ },
+ [0x1311B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1311B,
+ },
+ [0x1311C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1311C,
+ },
+ [0x1311D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1311D,
+ },
+ [0x1311E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1311E,
+ },
+ [0x1311F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1311F,
+ },
+ [0x13120]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13120,
+ },
+ [0x13121]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13121,
+ },
+ [0x13122]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13122,
+ },
+ [0x13123]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13123,
+ },
+ [0x13124]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13124,
+ },
+ [0x13125]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13125,
+ },
+ [0x13126]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13126,
+ },
+ [0x13127]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13127,
+ },
+ [0x13128]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13128,
+ },
+ [0x13129]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13129,
+ },
+ [0x1312A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312A,
+ },
+ [0x1312B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312B,
+ },
+ [0x1312C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312C,
+ },
+ [0x1312D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312D,
+ },
+ [0x1312E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312E,
+ },
+ [0x1312F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1312F,
+ },
+ [0x13130]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13130,
+ },
+ [0x13131]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13131,
+ },
+ [0x13132]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13132,
+ },
+ [0x13133]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13133,
+ },
+ [0x13134]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13134,
+ },
+ [0x13135]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13135,
+ },
+ [0x13136]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13136,
+ },
+ [0x13137]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13137,
+ },
+ [0x13138]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13138,
+ },
+ [0x13139]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13139,
+ },
+ [0x1313A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313A,
+ },
+ [0x1313B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313B,
+ },
+ [0x1313C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313C,
+ },
+ [0x1313D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313D,
+ },
+ [0x1313E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313E,
+ },
+ [0x1313F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1313F,
+ },
+ [0x13140]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13140,
+ },
+ [0x13141]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13141,
+ },
+ [0x13142]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13142,
+ },
+ [0x13143]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13143,
+ },
+ [0x13144]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13144,
+ },
+ [0x13145]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13145,
+ },
+ [0x13146]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13146,
+ },
+ [0x13147]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13147,
+ },
+ [0x13148]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13148,
+ },
+ [0x13149]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13149,
+ },
+ [0x1314A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314A,
+ },
+ [0x1314B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314B,
+ },
+ [0x1314C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314C,
+ },
+ [0x1314D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314D,
+ },
+ [0x1314E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314E,
+ },
+ [0x1314F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1314F,
+ },
+ [0x13150]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13150,
+ },
+ [0x13151]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13151,
+ },
+ [0x13152]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13152,
+ },
+ [0x13153]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13153,
+ },
+ [0x13154]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13154,
+ },
+ [0x13155]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13155,
+ },
+ [0x13156]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13156,
+ },
+ [0x13157]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13157,
+ },
+ [0x13158]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13158,
+ },
+ [0x13159]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13159,
+ },
+ [0x1315A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315A,
+ },
+ [0x1315B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315B,
+ },
+ [0x1315C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315C,
+ },
+ [0x1315D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315D,
+ },
+ [0x1315E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315E,
+ },
+ [0x1315F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1315F,
+ },
+ [0x13160]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13160,
+ },
+ [0x13161]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13161,
+ },
+ [0x13162]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13162,
+ },
+ [0x13163]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13163,
+ },
+ [0x13164]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13164,
+ },
+ [0x13165]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13165,
+ },
+ [0x13166]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13166,
+ },
+ [0x13167]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13167,
+ },
+ [0x13168]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13168,
+ },
+ [0x13169]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13169,
+ },
+ [0x1316A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1316A,
+ },
+ [0x1316B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1316B,
+ },
+ [0x1316C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1316C,
+ },
+ [0x1316D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1316D,
+ },
+ [0x1316E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1316E,
+ },
+ [0x1316F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1316F,
+ },
+ [0x13170]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13170,
+ },
+ [0x13171]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13171,
+ },
+ [0x13172]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13172,
+ },
+ [0x13173]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13173,
+ },
+ [0x13174]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13174,
+ },
+ [0x13175]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13175,
+ },
+ [0x13176]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13176,
+ },
+ [0x13177]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13177,
+ },
+ [0x13178]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13178,
+ },
+ [0x13179]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13179,
+ },
+ [0x1317A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1317A,
+ },
+ [0x1317B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1317B,
+ },
+ [0x1317C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1317C,
+ },
+ [0x1317D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1317D,
+ },
+ [0x1317E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1317E,
+ },
+ [0x1317F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1317F,
+ },
+ [0x13180]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13180,
+ },
+ [0x13181]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13181,
+ },
+ [0x13182]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13182,
+ },
+ [0x13183]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13183,
+ },
+ [0x13184]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13184,
+ },
+ [0x13185]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13185,
+ },
+ [0x13186]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13186,
+ },
+ [0x13187]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13187,
+ },
+ [0x13188]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13188,
+ },
+ [0x13189]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13189,
+ },
+ [0x1318A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318A,
+ },
+ [0x1318B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318B,
+ },
+ [0x1318C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318C,
+ },
+ [0x1318D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318D,
+ },
+ [0x1318E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318E,
+ },
+ [0x1318F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1318F,
+ },
+ [0x13190]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13190,
+ },
+ [0x13191]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13191,
+ },
+ [0x13192]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13192,
+ },
+ [0x13193]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13193,
+ },
+ [0x13194]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13194,
+ },
+ [0x13195]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13195,
+ },
+ [0x13196]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13196,
+ },
+ [0x13197]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13197,
+ },
+ [0x13198]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13198,
+ },
+ [0x13199]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13199,
+ },
+ [0x1319A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319A,
+ },
+ [0x1319B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319B,
+ },
+ [0x1319C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319C,
+ },
+ [0x1319D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319D,
+ },
+ [0x1319E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319E,
+ },
+ [0x1319F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1319F,
+ },
+ [0x131A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A0,
+ },
+ [0x131A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A1,
+ },
+ [0x131A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A2,
+ },
+ [0x131A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A3,
+ },
+ [0x131A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A4,
+ },
+ [0x131A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A5,
+ },
+ [0x131A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A6,
+ },
+ [0x131A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A7,
+ },
+ [0x131A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A8,
+ },
+ [0x131A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131A9,
+ },
+ [0x131AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131AA,
+ },
+ [0x131AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131AB,
+ },
+ [0x131AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131AC,
+ },
+ [0x131AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131AD,
+ },
+ [0x131AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131AE,
+ },
+ [0x131AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131AF,
+ },
+ [0x131B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B0,
+ },
+ [0x131B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B1,
+ },
+ [0x131B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B2,
+ },
+ [0x131B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B3,
+ },
+ [0x131B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B4,
+ },
+ [0x131B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B5,
+ },
+ [0x131B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B6,
+ },
+ [0x131B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B7,
+ },
+ [0x131B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B8,
+ },
+ [0x131B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131B9,
+ },
+ [0x131BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131BA,
+ },
+ [0x131BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131BB,
+ },
+ [0x131BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131BC,
+ },
+ [0x131BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131BD,
+ },
+ [0x131BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131BE,
+ },
+ [0x131BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131BF,
+ },
+ [0x131C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C0,
+ },
+ [0x131C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C1,
+ },
+ [0x131C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C2,
+ },
+ [0x131C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C3,
+ },
+ [0x131C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C4,
+ },
+ [0x131C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C5,
+ },
+ [0x131C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C6,
+ },
+ [0x131C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C7,
+ },
+ [0x131C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C8,
+ },
+ [0x131C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131C9,
+ },
+ [0x131CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131CA,
+ },
+ [0x131CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131CB,
+ },
+ [0x131CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131CC,
+ },
+ [0x131CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131CD,
+ },
+ [0x131CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131CE,
+ },
+ [0x131CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131CF,
+ },
+ [0x131D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D0,
+ },
+ [0x131D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D1,
+ },
+ [0x131D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D2,
+ },
+ [0x131D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D3,
+ },
+ [0x131D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D4,
+ },
+ [0x131D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D5,
+ },
+ [0x131D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D6,
+ },
+ [0x131D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D7,
+ },
+ [0x131D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D8,
+ },
+ [0x131D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131D9,
+ },
+ [0x131DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131DA,
+ },
+ [0x131DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131DB,
+ },
+ [0x131DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131DC,
+ },
+ [0x131DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131DD,
+ },
+ [0x131DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131DE,
+ },
+ [0x131DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131DF,
+ },
+ [0x131E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E0,
+ },
+ [0x131E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E1,
+ },
+ [0x131E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E2,
+ },
+ [0x131E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E3,
+ },
+ [0x131E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E4,
+ },
+ [0x131E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E5,
+ },
+ [0x131E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E6,
+ },
+ [0x131E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E7,
+ },
+ [0x131E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E8,
+ },
+ [0x131E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131E9,
+ },
+ [0x131EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131EA,
+ },
+ [0x131EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131EB,
+ },
+ [0x131EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131EC,
+ },
+ [0x131ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131ED,
+ },
+ [0x131EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131EE,
+ },
+ [0x131EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131EF,
+ },
+ [0x131F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F0,
+ },
+ [0x131F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F1,
+ },
+ [0x131F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F2,
+ },
+ [0x131F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F3,
+ },
+ [0x131F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F4,
+ },
+ [0x131F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F5,
+ },
+ [0x131F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F6,
+ },
+ [0x131F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F7,
+ },
+ [0x131F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F8,
+ },
+ [0x131F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131F9,
+ },
+ [0x131FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131FA,
+ },
+ [0x131FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131FB,
+ },
+ [0x131FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131FC,
+ },
+ [0x131FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131FD,
+ },
+ [0x131FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131FE,
+ },
+ [0x131FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x131FF,
+ },
+ [0x13200]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13200,
+ },
+ [0x13201]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13201,
+ },
+ [0x13202]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13202,
+ },
+ [0x13203]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13203,
+ },
+ [0x13204]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13204,
+ },
+ [0x13205]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13205,
+ },
+ [0x13206]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13206,
+ },
+ [0x13207]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13207,
+ },
+ [0x13208]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13208,
+ },
+ [0x13209]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13209,
+ },
+ [0x1320A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320A,
+ },
+ [0x1320B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320B,
+ },
+ [0x1320C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320C,
+ },
+ [0x1320D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320D,
+ },
+ [0x1320E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320E,
+ },
+ [0x1320F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1320F,
+ },
+ [0x13210]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13210,
+ },
+ [0x13211]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13211,
+ },
+ [0x13212]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13212,
+ },
+ [0x13213]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13213,
+ },
+ [0x13214]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13214,
+ },
+ [0x13215]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13215,
+ },
+ [0x13216]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13216,
+ },
+ [0x13217]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13217,
+ },
+ [0x13218]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13218,
+ },
+ [0x13219]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13219,
+ },
+ [0x1321A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321A,
+ },
+ [0x1321B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321B,
+ },
+ [0x1321C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321C,
+ },
+ [0x1321D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321D,
+ },
+ [0x1321E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321E,
+ },
+ [0x1321F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1321F,
+ },
+ [0x13220]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13220,
+ },
+ [0x13221]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13221,
+ },
+ [0x13222]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13222,
+ },
+ [0x13223]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13223,
+ },
+ [0x13224]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13224,
+ },
+ [0x13225]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13225,
+ },
+ [0x13226]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13226,
+ },
+ [0x13227]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13227,
+ },
+ [0x13228]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13228,
+ },
+ [0x13229]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13229,
+ },
+ [0x1322A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322A,
+ },
+ [0x1322B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322B,
+ },
+ [0x1322C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322C,
+ },
+ [0x1322D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322D,
+ },
+ [0x1322E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322E,
+ },
+ [0x1322F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1322F,
+ },
+ [0x13230]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13230,
+ },
+ [0x13231]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13231,
+ },
+ [0x13232]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13232,
+ },
+ [0x13233]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13233,
+ },
+ [0x13234]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13234,
+ },
+ [0x13235]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13235,
+ },
+ [0x13236]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13236,
+ },
+ [0x13237]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13237,
+ },
+ [0x13238]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13238,
+ },
+ [0x13239]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13239,
+ },
+ [0x1323A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323A,
+ },
+ [0x1323B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323B,
+ },
+ [0x1323C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323C,
+ },
+ [0x1323D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323D,
+ },
+ [0x1323E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323E,
+ },
+ [0x1323F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1323F,
+ },
+ [0x13240]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13240,
+ },
+ [0x13241]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13241,
+ },
+ [0x13242]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13242,
+ },
+ [0x13243]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13243,
+ },
+ [0x13244]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13244,
+ },
+ [0x13245]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13245,
+ },
+ [0x13246]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13246,
+ },
+ [0x13247]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13247,
+ },
+ [0x13248]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13248,
+ },
+ [0x13249]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13249,
+ },
+ [0x1324A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324A,
+ },
+ [0x1324B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324B,
+ },
+ [0x1324C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324C,
+ },
+ [0x1324D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324D,
+ },
+ [0x1324E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324E,
+ },
+ [0x1324F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1324F,
+ },
+ [0x13250]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13250,
+ },
+ [0x13251]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13251,
+ },
+ [0x13252]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13252,
+ },
+ [0x13253]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13253,
+ },
+ [0x13254]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13254,
+ },
+ [0x13255]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13255,
+ },
+ [0x13256]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13256,
+ },
+ [0x13257]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13257,
+ },
+ [0x13258]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x13258,
+ },
+ [0x13259]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x13259,
+ },
+ [0x1325A]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x1325A,
+ },
+ [0x1325B]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x1325B,
+ },
+ [0x1325C]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x1325C,
+ },
+ [0x1325D]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x1325D,
+ },
+ [0x1325E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1325E,
+ },
+ [0x1325F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1325F,
+ },
+ [0x13260]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13260,
+ },
+ [0x13261]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13261,
+ },
+ [0x13262]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13262,
+ },
+ [0x13263]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13263,
+ },
+ [0x13264]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13264,
+ },
+ [0x13265]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13265,
+ },
+ [0x13266]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13266,
+ },
+ [0x13267]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13267,
+ },
+ [0x13268]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13268,
+ },
+ [0x13269]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13269,
+ },
+ [0x1326A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326A,
+ },
+ [0x1326B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326B,
+ },
+ [0x1326C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326C,
+ },
+ [0x1326D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326D,
+ },
+ [0x1326E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326E,
+ },
+ [0x1326F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1326F,
+ },
+ [0x13270]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13270,
+ },
+ [0x13271]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13271,
+ },
+ [0x13272]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13272,
+ },
+ [0x13273]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13273,
+ },
+ [0x13274]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13274,
+ },
+ [0x13275]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13275,
+ },
+ [0x13276]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13276,
+ },
+ [0x13277]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13277,
+ },
+ [0x13278]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13278,
+ },
+ [0x13279]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13279,
+ },
+ [0x1327A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327A,
+ },
+ [0x1327B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327B,
+ },
+ [0x1327C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327C,
+ },
+ [0x1327D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327D,
+ },
+ [0x1327E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327E,
+ },
+ [0x1327F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1327F,
+ },
+ [0x13280]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13280,
+ },
+ [0x13281]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13281,
+ },
+ [0x13282]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x13282,
+ },
+ [0x13283]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13283,
+ },
+ [0x13284]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13284,
+ },
+ [0x13285]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13285,
+ },
+ [0x13286]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x13286,
+ },
+ [0x13287]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x13287,
+ },
+ [0x13288]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x13288,
+ },
+ [0x13289]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x13289,
+ },
+ [0x1328A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328A,
+ },
+ [0x1328B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328B,
+ },
+ [0x1328C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328C,
+ },
+ [0x1328D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328D,
+ },
+ [0x1328E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328E,
+ },
+ [0x1328F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1328F,
+ },
+ [0x13290]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13290,
+ },
+ [0x13291]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13291,
+ },
+ [0x13292]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13292,
+ },
+ [0x13293]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13293,
+ },
+ [0x13294]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13294,
+ },
+ [0x13295]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13295,
+ },
+ [0x13296]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13296,
+ },
+ [0x13297]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13297,
+ },
+ [0x13298]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13298,
+ },
+ [0x13299]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13299,
+ },
+ [0x1329A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329A,
+ },
+ [0x1329B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329B,
+ },
+ [0x1329C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329C,
+ },
+ [0x1329D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329D,
+ },
+ [0x1329E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329E,
+ },
+ [0x1329F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1329F,
+ },
+ [0x132A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A0,
+ },
+ [0x132A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A1,
+ },
+ [0x132A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A2,
+ },
+ [0x132A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A3,
+ },
+ [0x132A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A4,
+ },
+ [0x132A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A5,
+ },
+ [0x132A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A6,
+ },
+ [0x132A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A7,
+ },
+ [0x132A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A8,
+ },
+ [0x132A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132A9,
+ },
+ [0x132AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132AA,
+ },
+ [0x132AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132AB,
+ },
+ [0x132AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132AC,
+ },
+ [0x132AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132AD,
+ },
+ [0x132AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132AE,
+ },
+ [0x132AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132AF,
+ },
+ [0x132B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B0,
+ },
+ [0x132B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B1,
+ },
+ [0x132B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B2,
+ },
+ [0x132B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B3,
+ },
+ [0x132B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B4,
+ },
+ [0x132B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B5,
+ },
+ [0x132B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B6,
+ },
+ [0x132B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B7,
+ },
+ [0x132B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B8,
+ },
+ [0x132B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132B9,
+ },
+ [0x132BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132BA,
+ },
+ [0x132BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132BB,
+ },
+ [0x132BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132BC,
+ },
+ [0x132BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132BD,
+ },
+ [0x132BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132BE,
+ },
+ [0x132BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132BF,
+ },
+ [0x132C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C0,
+ },
+ [0x132C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C1,
+ },
+ [0x132C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C2,
+ },
+ [0x132C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C3,
+ },
+ [0x132C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C4,
+ },
+ [0x132C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C5,
+ },
+ [0x132C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C6,
+ },
+ [0x132C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C7,
+ },
+ [0x132C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C8,
+ },
+ [0x132C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132C9,
+ },
+ [0x132CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132CA,
+ },
+ [0x132CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132CB,
+ },
+ [0x132CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132CC,
+ },
+ [0x132CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132CD,
+ },
+ [0x132CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132CE,
+ },
+ [0x132CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132CF,
+ },
+ [0x132D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D0,
+ },
+ [0x132D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D1,
+ },
+ [0x132D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D2,
+ },
+ [0x132D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D3,
+ },
+ [0x132D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D4,
+ },
+ [0x132D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D5,
+ },
+ [0x132D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D6,
+ },
+ [0x132D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D7,
+ },
+ [0x132D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D8,
+ },
+ [0x132D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132D9,
+ },
+ [0x132DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132DA,
+ },
+ [0x132DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132DB,
+ },
+ [0x132DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132DC,
+ },
+ [0x132DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132DD,
+ },
+ [0x132DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132DE,
+ },
+ [0x132DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132DF,
+ },
+ [0x132E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E0,
+ },
+ [0x132E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E1,
+ },
+ [0x132E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E2,
+ },
+ [0x132E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E3,
+ },
+ [0x132E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E4,
+ },
+ [0x132E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E5,
+ },
+ [0x132E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E6,
+ },
+ [0x132E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E7,
+ },
+ [0x132E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E8,
+ },
+ [0x132E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132E9,
+ },
+ [0x132EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132EA,
+ },
+ [0x132EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132EB,
+ },
+ [0x132EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132EC,
+ },
+ [0x132ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132ED,
+ },
+ [0x132EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132EE,
+ },
+ [0x132EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132EF,
+ },
+ [0x132F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F0,
+ },
+ [0x132F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F1,
+ },
+ [0x132F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F2,
+ },
+ [0x132F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F3,
+ },
+ [0x132F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F4,
+ },
+ [0x132F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F5,
+ },
+ [0x132F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F6,
+ },
+ [0x132F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F7,
+ },
+ [0x132F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F8,
+ },
+ [0x132F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132F9,
+ },
+ [0x132FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132FA,
+ },
+ [0x132FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132FB,
+ },
+ [0x132FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132FC,
+ },
+ [0x132FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132FD,
+ },
+ [0x132FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132FE,
+ },
+ [0x132FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x132FF,
+ },
+ [0x13300]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13300,
+ },
+ [0x13301]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13301,
+ },
+ [0x13302]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13302,
+ },
+ [0x13303]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13303,
+ },
+ [0x13304]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13304,
+ },
+ [0x13305]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13305,
+ },
+ [0x13306]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13306,
+ },
+ [0x13307]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13307,
+ },
+ [0x13308]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13308,
+ },
+ [0x13309]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13309,
+ },
+ [0x1330A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330A,
+ },
+ [0x1330B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330B,
+ },
+ [0x1330C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330C,
+ },
+ [0x1330D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330D,
+ },
+ [0x1330E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330E,
+ },
+ [0x1330F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1330F,
+ },
+ [0x13310]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13310,
+ },
+ [0x13311]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13311,
+ },
+ [0x13312]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13312,
+ },
+ [0x13313]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13313,
+ },
+ [0x13314]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13314,
+ },
+ [0x13315]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13315,
+ },
+ [0x13316]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13316,
+ },
+ [0x13317]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13317,
+ },
+ [0x13318]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13318,
+ },
+ [0x13319]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13319,
+ },
+ [0x1331A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331A,
+ },
+ [0x1331B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331B,
+ },
+ [0x1331C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331C,
+ },
+ [0x1331D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331D,
+ },
+ [0x1331E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331E,
+ },
+ [0x1331F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1331F,
+ },
+ [0x13320]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13320,
+ },
+ [0x13321]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13321,
+ },
+ [0x13322]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13322,
+ },
+ [0x13323]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13323,
+ },
+ [0x13324]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13324,
+ },
+ [0x13325]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13325,
+ },
+ [0x13326]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13326,
+ },
+ [0x13327]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13327,
+ },
+ [0x13328]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13328,
+ },
+ [0x13329]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13329,
+ },
+ [0x1332A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332A,
+ },
+ [0x1332B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332B,
+ },
+ [0x1332C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332C,
+ },
+ [0x1332D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332D,
+ },
+ [0x1332E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332E,
+ },
+ [0x1332F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1332F,
+ },
+ [0x13330]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13330,
+ },
+ [0x13331]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13331,
+ },
+ [0x13332]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13332,
+ },
+ [0x13333]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13333,
+ },
+ [0x13334]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13334,
+ },
+ [0x13335]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13335,
+ },
+ [0x13336]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13336,
+ },
+ [0x13337]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13337,
+ },
+ [0x13338]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13338,
+ },
+ [0x13339]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13339,
+ },
+ [0x1333A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333A,
+ },
+ [0x1333B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333B,
+ },
+ [0x1333C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333C,
+ },
+ [0x1333D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333D,
+ },
+ [0x1333E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333E,
+ },
+ [0x1333F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1333F,
+ },
+ [0x13340]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13340,
+ },
+ [0x13341]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13341,
+ },
+ [0x13342]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13342,
+ },
+ [0x13343]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13343,
+ },
+ [0x13344]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13344,
+ },
+ [0x13345]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13345,
+ },
+ [0x13346]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13346,
+ },
+ [0x13347]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13347,
+ },
+ [0x13348]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13348,
+ },
+ [0x13349]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13349,
+ },
+ [0x1334A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334A,
+ },
+ [0x1334B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334B,
+ },
+ [0x1334C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334C,
+ },
+ [0x1334D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334D,
+ },
+ [0x1334E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334E,
+ },
+ [0x1334F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1334F,
+ },
+ [0x13350]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13350,
+ },
+ [0x13351]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13351,
+ },
+ [0x13352]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13352,
+ },
+ [0x13353]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13353,
+ },
+ [0x13354]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13354,
+ },
+ [0x13355]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13355,
+ },
+ [0x13356]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13356,
+ },
+ [0x13357]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13357,
+ },
+ [0x13358]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13358,
+ },
+ [0x13359]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13359,
+ },
+ [0x1335A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335A,
+ },
+ [0x1335B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335B,
+ },
+ [0x1335C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335C,
+ },
+ [0x1335D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335D,
+ },
+ [0x1335E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335E,
+ },
+ [0x1335F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1335F,
+ },
+ [0x13360]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13360,
+ },
+ [0x13361]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13361,
+ },
+ [0x13362]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13362,
+ },
+ [0x13363]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13363,
+ },
+ [0x13364]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13364,
+ },
+ [0x13365]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13365,
+ },
+ [0x13366]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13366,
+ },
+ [0x13367]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13367,
+ },
+ [0x13368]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13368,
+ },
+ [0x13369]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13369,
+ },
+ [0x1336A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336A,
+ },
+ [0x1336B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336B,
+ },
+ [0x1336C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336C,
+ },
+ [0x1336D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336D,
+ },
+ [0x1336E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336E,
+ },
+ [0x1336F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1336F,
+ },
+ [0x13370]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13370,
+ },
+ [0x13371]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13371,
+ },
+ [0x13372]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13372,
+ },
+ [0x13373]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13373,
+ },
+ [0x13374]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13374,
+ },
+ [0x13375]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13375,
+ },
+ [0x13376]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13376,
+ },
+ [0x13377]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13377,
+ },
+ [0x13378]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13378,
+ },
+ [0x13379]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x13379,
+ },
+ [0x1337A]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x1337A,
+ },
+ [0x1337B]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x1337B,
+ },
+ [0x1337C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1337C,
+ },
+ [0x1337D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1337D,
+ },
+ [0x1337E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1337E,
+ },
+ [0x1337F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1337F,
+ },
+ [0x13380]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13380,
+ },
+ [0x13381]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13381,
+ },
+ [0x13382]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13382,
+ },
+ [0x13383]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13383,
+ },
+ [0x13384]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13384,
+ },
+ [0x13385]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13385,
+ },
+ [0x13386]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13386,
+ },
+ [0x13387]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13387,
+ },
+ [0x13388]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13388,
+ },
+ [0x13389]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13389,
+ },
+ [0x1338A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338A,
+ },
+ [0x1338B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338B,
+ },
+ [0x1338C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338C,
+ },
+ [0x1338D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338D,
+ },
+ [0x1338E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338E,
+ },
+ [0x1338F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1338F,
+ },
+ [0x13390]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13390,
+ },
+ [0x13391]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13391,
+ },
+ [0x13392]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13392,
+ },
+ [0x13393]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13393,
+ },
+ [0x13394]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13394,
+ },
+ [0x13395]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13395,
+ },
+ [0x13396]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13396,
+ },
+ [0x13397]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13397,
+ },
+ [0x13398]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13398,
+ },
+ [0x13399]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13399,
+ },
+ [0x1339A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339A,
+ },
+ [0x1339B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339B,
+ },
+ [0x1339C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339C,
+ },
+ [0x1339D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339D,
+ },
+ [0x1339E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339E,
+ },
+ [0x1339F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1339F,
+ },
+ [0x133A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A0,
+ },
+ [0x133A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A1,
+ },
+ [0x133A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A2,
+ },
+ [0x133A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A3,
+ },
+ [0x133A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A4,
+ },
+ [0x133A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A5,
+ },
+ [0x133A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A6,
+ },
+ [0x133A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A7,
+ },
+ [0x133A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A8,
+ },
+ [0x133A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133A9,
+ },
+ [0x133AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133AA,
+ },
+ [0x133AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133AB,
+ },
+ [0x133AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133AC,
+ },
+ [0x133AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133AD,
+ },
+ [0x133AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133AE,
+ },
+ [0x133AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133AF,
+ },
+ [0x133B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B0,
+ },
+ [0x133B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B1,
+ },
+ [0x133B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B2,
+ },
+ [0x133B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B3,
+ },
+ [0x133B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B4,
+ },
+ [0x133B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B5,
+ },
+ [0x133B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B6,
+ },
+ [0x133B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B7,
+ },
+ [0x133B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B8,
+ },
+ [0x133B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133B9,
+ },
+ [0x133BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133BA,
+ },
+ [0x133BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133BB,
+ },
+ [0x133BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133BC,
+ },
+ [0x133BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133BD,
+ },
+ [0x133BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133BE,
+ },
+ [0x133BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133BF,
+ },
+ [0x133C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C0,
+ },
+ [0x133C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C1,
+ },
+ [0x133C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C2,
+ },
+ [0x133C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C3,
+ },
+ [0x133C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C4,
+ },
+ [0x133C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C5,
+ },
+ [0x133C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C6,
+ },
+ [0x133C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C7,
+ },
+ [0x133C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C8,
+ },
+ [0x133C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133C9,
+ },
+ [0x133CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133CA,
+ },
+ [0x133CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133CB,
+ },
+ [0x133CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133CC,
+ },
+ [0x133CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133CD,
+ },
+ [0x133CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133CE,
+ },
+ [0x133CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133CF,
+ },
+ [0x133D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D0,
+ },
+ [0x133D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D1,
+ },
+ [0x133D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D2,
+ },
+ [0x133D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D3,
+ },
+ [0x133D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D4,
+ },
+ [0x133D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D5,
+ },
+ [0x133D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D6,
+ },
+ [0x133D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D7,
+ },
+ [0x133D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D8,
+ },
+ [0x133D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133D9,
+ },
+ [0x133DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133DA,
+ },
+ [0x133DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133DB,
+ },
+ [0x133DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133DC,
+ },
+ [0x133DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133DD,
+ },
+ [0x133DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133DE,
+ },
+ [0x133DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133DF,
+ },
+ [0x133E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E0,
+ },
+ [0x133E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E1,
+ },
+ [0x133E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E2,
+ },
+ [0x133E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E3,
+ },
+ [0x133E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E4,
+ },
+ [0x133E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E5,
+ },
+ [0x133E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E6,
+ },
+ [0x133E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E7,
+ },
+ [0x133E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E8,
+ },
+ [0x133E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133E9,
+ },
+ [0x133EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133EA,
+ },
+ [0x133EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133EB,
+ },
+ [0x133EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133EC,
+ },
+ [0x133ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133ED,
+ },
+ [0x133EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133EE,
+ },
+ [0x133EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133EF,
+ },
+ [0x133F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F0,
+ },
+ [0x133F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F1,
+ },
+ [0x133F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F2,
+ },
+ [0x133F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F3,
+ },
+ [0x133F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F4,
+ },
+ [0x133F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F5,
+ },
+ [0x133F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F6,
+ },
+ [0x133F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F7,
+ },
+ [0x133F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F8,
+ },
+ [0x133F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133F9,
+ },
+ [0x133FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133FA,
+ },
+ [0x133FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133FB,
+ },
+ [0x133FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133FC,
+ },
+ [0x133FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133FD,
+ },
+ [0x133FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133FE,
+ },
+ [0x133FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x133FF,
+ },
+ [0x13400]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13400,
+ },
+ [0x13401]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13401,
+ },
+ [0x13402]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13402,
+ },
+ [0x13403]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13403,
+ },
+ [0x13404]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13404,
+ },
+ [0x13405]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13405,
+ },
+ [0x13406]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13406,
+ },
+ [0x13407]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13407,
+ },
+ [0x13408]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13408,
+ },
+ [0x13409]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13409,
+ },
+ [0x1340A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340A,
+ },
+ [0x1340B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340B,
+ },
+ [0x1340C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340C,
+ },
+ [0x1340D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340D,
+ },
+ [0x1340E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340E,
+ },
+ [0x1340F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1340F,
+ },
+ [0x13410]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13410,
+ },
+ [0x13411]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13411,
+ },
+ [0x13412]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13412,
+ },
+ [0x13413]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13413,
+ },
+ [0x13414]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13414,
+ },
+ [0x13415]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13415,
+ },
+ [0x13416]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13416,
+ },
+ [0x13417]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13417,
+ },
+ [0x13418]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13418,
+ },
+ [0x13419]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13419,
+ },
+ [0x1341A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341A,
+ },
+ [0x1341B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341B,
+ },
+ [0x1341C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341C,
+ },
+ [0x1341D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341D,
+ },
+ [0x1341E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341E,
+ },
+ [0x1341F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1341F,
+ },
+ [0x13420]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13420,
+ },
+ [0x13421]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13421,
+ },
+ [0x13422]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13422,
+ },
+ [0x13423]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13423,
+ },
+ [0x13424]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13424,
+ },
+ [0x13425]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13425,
+ },
+ [0x13426]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13426,
+ },
+ [0x13427]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13427,
+ },
+ [0x13428]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13428,
+ },
+ [0x13429]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x13429,
+ },
+ [0x1342A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1342A,
+ },
+ [0x1342B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1342B,
+ },
+ [0x1342C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1342C,
+ },
+ [0x1342D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1342D,
+ },
+ [0x1342E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1342E,
+ },
+ [0x13430]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13430,
+ },
+ [0x13431]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13431,
+ },
+ [0x13432]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13432,
+ },
+ [0x13433]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13433,
+ },
+ [0x13434]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13434,
+ },
+ [0x13435]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13435,
+ },
+ [0x13436]={
+ category="cf",
+ direction="l",
+ linebreak="gl",
+ unicodeslot=0x13436,
+ },
+ [0x13437]={
+ category="cf",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x13437,
+ },
+ [0x13438]={
+ category="cf",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x13438,
+ },
+ [0x14400]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14400,
+ },
+ [0x14401]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14401,
+ },
+ [0x14402]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14402,
+ },
+ [0x14403]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14403,
+ },
+ [0x14404]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14404,
+ },
+ [0x14405]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14405,
+ },
+ [0x14406]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14406,
+ },
+ [0x14407]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14407,
+ },
+ [0x14408]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14408,
+ },
+ [0x14409]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14409,
+ },
+ [0x1440A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440A,
+ },
+ [0x1440B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440B,
+ },
+ [0x1440C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440C,
+ },
+ [0x1440D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440D,
+ },
+ [0x1440E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440E,
+ },
+ [0x1440F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1440F,
+ },
+ [0x14410]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14410,
+ },
+ [0x14411]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14411,
+ },
+ [0x14412]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14412,
+ },
+ [0x14413]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14413,
+ },
+ [0x14414]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14414,
+ },
+ [0x14415]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14415,
+ },
+ [0x14416]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14416,
+ },
+ [0x14417]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14417,
+ },
+ [0x14418]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14418,
+ },
+ [0x14419]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14419,
+ },
+ [0x1441A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441A,
+ },
+ [0x1441B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441B,
+ },
+ [0x1441C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441C,
+ },
+ [0x1441D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441D,
+ },
+ [0x1441E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441E,
+ },
+ [0x1441F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1441F,
+ },
+ [0x14420]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14420,
+ },
+ [0x14421]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14421,
+ },
+ [0x14422]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14422,
+ },
+ [0x14423]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14423,
+ },
+ [0x14424]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14424,
+ },
+ [0x14425]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14425,
+ },
+ [0x14426]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14426,
+ },
+ [0x14427]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14427,
+ },
+ [0x14428]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14428,
+ },
+ [0x14429]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14429,
+ },
+ [0x1442A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442A,
+ },
+ [0x1442B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442B,
+ },
+ [0x1442C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442C,
+ },
+ [0x1442D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442D,
+ },
+ [0x1442E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442E,
+ },
+ [0x1442F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1442F,
+ },
+ [0x14430]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14430,
+ },
+ [0x14431]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14431,
+ },
+ [0x14432]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14432,
+ },
+ [0x14433]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14433,
+ },
+ [0x14434]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14434,
+ },
+ [0x14435]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14435,
+ },
+ [0x14436]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14436,
+ },
+ [0x14437]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14437,
+ },
+ [0x14438]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14438,
+ },
+ [0x14439]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14439,
+ },
+ [0x1443A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443A,
+ },
+ [0x1443B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443B,
+ },
+ [0x1443C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443C,
+ },
+ [0x1443D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443D,
+ },
+ [0x1443E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443E,
+ },
+ [0x1443F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1443F,
+ },
+ [0x14440]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14440,
+ },
+ [0x14441]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14441,
+ },
+ [0x14442]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14442,
+ },
+ [0x14443]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14443,
+ },
+ [0x14444]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14444,
+ },
+ [0x14445]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14445,
+ },
+ [0x14446]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14446,
+ },
+ [0x14447]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14447,
+ },
+ [0x14448]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14448,
+ },
+ [0x14449]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14449,
+ },
+ [0x1444A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444A,
+ },
+ [0x1444B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444B,
+ },
+ [0x1444C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444C,
+ },
+ [0x1444D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444D,
+ },
+ [0x1444E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444E,
+ },
+ [0x1444F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1444F,
+ },
+ [0x14450]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14450,
+ },
+ [0x14451]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14451,
+ },
+ [0x14452]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14452,
+ },
+ [0x14453]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14453,
+ },
+ [0x14454]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14454,
+ },
+ [0x14455]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14455,
+ },
+ [0x14456]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14456,
+ },
+ [0x14457]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14457,
+ },
+ [0x14458]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14458,
+ },
+ [0x14459]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14459,
+ },
+ [0x1445A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445A,
+ },
+ [0x1445B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445B,
+ },
+ [0x1445C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445C,
+ },
+ [0x1445D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445D,
+ },
+ [0x1445E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445E,
+ },
+ [0x1445F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1445F,
+ },
+ [0x14460]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14460,
+ },
+ [0x14461]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14461,
+ },
+ [0x14462]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14462,
+ },
+ [0x14463]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14463,
+ },
+ [0x14464]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14464,
+ },
+ [0x14465]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14465,
+ },
+ [0x14466]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14466,
+ },
+ [0x14467]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14467,
+ },
+ [0x14468]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14468,
+ },
+ [0x14469]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14469,
+ },
+ [0x1446A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446A,
+ },
+ [0x1446B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446B,
+ },
+ [0x1446C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446C,
+ },
+ [0x1446D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446D,
+ },
+ [0x1446E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446E,
+ },
+ [0x1446F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1446F,
+ },
+ [0x14470]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14470,
+ },
+ [0x14471]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14471,
+ },
+ [0x14472]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14472,
+ },
+ [0x14473]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14473,
+ },
+ [0x14474]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14474,
+ },
+ [0x14475]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14475,
+ },
+ [0x14476]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14476,
+ },
+ [0x14477]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14477,
+ },
+ [0x14478]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14478,
+ },
+ [0x14479]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14479,
+ },
+ [0x1447A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447A,
+ },
+ [0x1447B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447B,
+ },
+ [0x1447C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447C,
+ },
+ [0x1447D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447D,
+ },
+ [0x1447E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447E,
+ },
+ [0x1447F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1447F,
+ },
+ [0x14480]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14480,
+ },
+ [0x14481]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14481,
+ },
+ [0x14482]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14482,
+ },
+ [0x14483]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14483,
+ },
+ [0x14484]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14484,
+ },
+ [0x14485]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14485,
+ },
+ [0x14486]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14486,
+ },
+ [0x14487]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14487,
+ },
+ [0x14488]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14488,
+ },
+ [0x14489]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14489,
+ },
+ [0x1448A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448A,
+ },
+ [0x1448B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448B,
+ },
+ [0x1448C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448C,
+ },
+ [0x1448D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448D,
+ },
+ [0x1448E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448E,
+ },
+ [0x1448F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1448F,
+ },
+ [0x14490]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14490,
+ },
+ [0x14491]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14491,
+ },
+ [0x14492]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14492,
+ },
+ [0x14493]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14493,
+ },
+ [0x14494]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14494,
+ },
+ [0x14495]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14495,
+ },
+ [0x14496]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14496,
+ },
+ [0x14497]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14497,
+ },
+ [0x14498]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14498,
+ },
+ [0x14499]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14499,
+ },
+ [0x1449A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449A,
+ },
+ [0x1449B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449B,
+ },
+ [0x1449C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449C,
+ },
+ [0x1449D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449D,
+ },
+ [0x1449E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449E,
+ },
+ [0x1449F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1449F,
+ },
+ [0x144A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A0,
+ },
+ [0x144A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A1,
+ },
+ [0x144A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A2,
+ },
+ [0x144A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A3,
+ },
+ [0x144A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A4,
+ },
+ [0x144A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A5,
+ },
+ [0x144A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A6,
+ },
+ [0x144A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A7,
+ },
+ [0x144A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A8,
+ },
+ [0x144A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144A9,
+ },
+ [0x144AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144AA,
+ },
+ [0x144AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144AB,
+ },
+ [0x144AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144AC,
+ },
+ [0x144AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144AD,
+ },
+ [0x144AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144AE,
+ },
+ [0x144AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144AF,
+ },
+ [0x144B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B0,
+ },
+ [0x144B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B1,
+ },
+ [0x144B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B2,
+ },
+ [0x144B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B3,
+ },
+ [0x144B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B4,
+ },
+ [0x144B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B5,
+ },
+ [0x144B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B6,
+ },
+ [0x144B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B7,
+ },
+ [0x144B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B8,
+ },
+ [0x144B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144B9,
+ },
+ [0x144BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144BA,
+ },
+ [0x144BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144BB,
+ },
+ [0x144BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144BC,
+ },
+ [0x144BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144BD,
+ },
+ [0x144BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144BE,
+ },
+ [0x144BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144BF,
+ },
+ [0x144C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C0,
+ },
+ [0x144C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C1,
+ },
+ [0x144C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C2,
+ },
+ [0x144C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C3,
+ },
+ [0x144C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C4,
+ },
+ [0x144C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C5,
+ },
+ [0x144C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C6,
+ },
+ [0x144C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C7,
+ },
+ [0x144C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C8,
+ },
+ [0x144C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144C9,
+ },
+ [0x144CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144CA,
+ },
+ [0x144CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144CB,
+ },
+ [0x144CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144CC,
+ },
+ [0x144CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144CD,
+ },
+ [0x144CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144CE,
+ },
+ [0x144CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144CF,
+ },
+ [0x144D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D0,
+ },
+ [0x144D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D1,
+ },
+ [0x144D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D2,
+ },
+ [0x144D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D3,
+ },
+ [0x144D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D4,
+ },
+ [0x144D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D5,
+ },
+ [0x144D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D6,
+ },
+ [0x144D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D7,
+ },
+ [0x144D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D8,
+ },
+ [0x144D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144D9,
+ },
+ [0x144DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144DA,
+ },
+ [0x144DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144DB,
+ },
+ [0x144DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144DC,
+ },
+ [0x144DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144DD,
+ },
+ [0x144DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144DE,
+ },
+ [0x144DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144DF,
+ },
+ [0x144E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E0,
+ },
+ [0x144E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E1,
+ },
+ [0x144E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E2,
+ },
+ [0x144E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E3,
+ },
+ [0x144E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E4,
+ },
+ [0x144E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E5,
+ },
+ [0x144E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E6,
+ },
+ [0x144E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E7,
+ },
+ [0x144E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E8,
+ },
+ [0x144E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144E9,
+ },
+ [0x144EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144EA,
+ },
+ [0x144EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144EB,
+ },
+ [0x144EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144EC,
+ },
+ [0x144ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144ED,
+ },
+ [0x144EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144EE,
+ },
+ [0x144EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144EF,
+ },
+ [0x144F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F0,
+ },
+ [0x144F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F1,
+ },
+ [0x144F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F2,
+ },
+ [0x144F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F3,
+ },
+ [0x144F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F4,
+ },
+ [0x144F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F5,
+ },
+ [0x144F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F6,
+ },
+ [0x144F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F7,
+ },
+ [0x144F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F8,
+ },
+ [0x144F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144F9,
+ },
+ [0x144FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144FA,
+ },
+ [0x144FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144FB,
+ },
+ [0x144FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144FC,
+ },
+ [0x144FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144FD,
+ },
+ [0x144FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144FE,
+ },
+ [0x144FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x144FF,
+ },
+ [0x14500]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14500,
+ },
+ [0x14501]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14501,
+ },
+ [0x14502]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14502,
+ },
+ [0x14503]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14503,
+ },
+ [0x14504]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14504,
+ },
+ [0x14505]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14505,
+ },
+ [0x14506]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14506,
+ },
+ [0x14507]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14507,
+ },
+ [0x14508]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14508,
+ },
+ [0x14509]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14509,
+ },
+ [0x1450A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450A,
+ },
+ [0x1450B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450B,
+ },
+ [0x1450C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450C,
+ },
+ [0x1450D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450D,
+ },
+ [0x1450E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450E,
+ },
+ [0x1450F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1450F,
+ },
+ [0x14510]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14510,
+ },
+ [0x14511]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14511,
+ },
+ [0x14512]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14512,
+ },
+ [0x14513]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14513,
+ },
+ [0x14514]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14514,
+ },
+ [0x14515]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14515,
+ },
+ [0x14516]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14516,
+ },
+ [0x14517]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14517,
+ },
+ [0x14518]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14518,
+ },
+ [0x14519]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14519,
+ },
+ [0x1451A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451A,
+ },
+ [0x1451B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451B,
+ },
+ [0x1451C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451C,
+ },
+ [0x1451D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451D,
+ },
+ [0x1451E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451E,
+ },
+ [0x1451F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1451F,
+ },
+ [0x14520]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14520,
+ },
+ [0x14521]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14521,
+ },
+ [0x14522]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14522,
+ },
+ [0x14523]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14523,
+ },
+ [0x14524]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14524,
+ },
+ [0x14525]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14525,
+ },
+ [0x14526]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14526,
+ },
+ [0x14527]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14527,
+ },
+ [0x14528]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14528,
+ },
+ [0x14529]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14529,
+ },
+ [0x1452A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452A,
+ },
+ [0x1452B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452B,
+ },
+ [0x1452C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452C,
+ },
+ [0x1452D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452D,
+ },
+ [0x1452E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452E,
+ },
+ [0x1452F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1452F,
+ },
+ [0x14530]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14530,
+ },
+ [0x14531]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14531,
+ },
+ [0x14532]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14532,
+ },
+ [0x14533]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14533,
+ },
+ [0x14534]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14534,
+ },
+ [0x14535]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14535,
+ },
+ [0x14536]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14536,
+ },
+ [0x14537]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14537,
+ },
+ [0x14538]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14538,
+ },
+ [0x14539]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14539,
+ },
+ [0x1453A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453A,
+ },
+ [0x1453B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453B,
+ },
+ [0x1453C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453C,
+ },
+ [0x1453D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453D,
+ },
+ [0x1453E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453E,
+ },
+ [0x1453F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1453F,
+ },
+ [0x14540]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14540,
+ },
+ [0x14541]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14541,
+ },
+ [0x14542]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14542,
+ },
+ [0x14543]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14543,
+ },
+ [0x14544]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14544,
+ },
+ [0x14545]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14545,
+ },
+ [0x14546]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14546,
+ },
+ [0x14547]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14547,
+ },
+ [0x14548]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14548,
+ },
+ [0x14549]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14549,
+ },
+ [0x1454A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454A,
+ },
+ [0x1454B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454B,
+ },
+ [0x1454C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454C,
+ },
+ [0x1454D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454D,
+ },
+ [0x1454E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454E,
+ },
+ [0x1454F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1454F,
+ },
+ [0x14550]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14550,
+ },
+ [0x14551]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14551,
+ },
+ [0x14552]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14552,
+ },
+ [0x14553]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14553,
+ },
+ [0x14554]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14554,
+ },
+ [0x14555]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14555,
+ },
+ [0x14556]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14556,
+ },
+ [0x14557]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14557,
+ },
+ [0x14558]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14558,
+ },
+ [0x14559]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14559,
+ },
+ [0x1455A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455A,
+ },
+ [0x1455B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455B,
+ },
+ [0x1455C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455C,
+ },
+ [0x1455D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455D,
+ },
+ [0x1455E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455E,
+ },
+ [0x1455F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1455F,
+ },
+ [0x14560]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14560,
+ },
+ [0x14561]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14561,
+ },
+ [0x14562]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14562,
+ },
+ [0x14563]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14563,
+ },
+ [0x14564]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14564,
+ },
+ [0x14565]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14565,
+ },
+ [0x14566]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14566,
+ },
+ [0x14567]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14567,
+ },
+ [0x14568]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14568,
+ },
+ [0x14569]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14569,
+ },
+ [0x1456A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456A,
+ },
+ [0x1456B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456B,
+ },
+ [0x1456C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456C,
+ },
+ [0x1456D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456D,
+ },
+ [0x1456E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456E,
+ },
+ [0x1456F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1456F,
+ },
+ [0x14570]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14570,
+ },
+ [0x14571]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14571,
+ },
+ [0x14572]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14572,
+ },
+ [0x14573]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14573,
+ },
+ [0x14574]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14574,
+ },
+ [0x14575]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14575,
+ },
+ [0x14576]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14576,
+ },
+ [0x14577]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14577,
+ },
+ [0x14578]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14578,
+ },
+ [0x14579]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14579,
+ },
+ [0x1457A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457A,
+ },
+ [0x1457B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457B,
+ },
+ [0x1457C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457C,
+ },
+ [0x1457D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457D,
+ },
+ [0x1457E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457E,
+ },
+ [0x1457F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1457F,
+ },
+ [0x14580]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14580,
+ },
+ [0x14581]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14581,
+ },
+ [0x14582]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14582,
+ },
+ [0x14583]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14583,
+ },
+ [0x14584]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14584,
+ },
+ [0x14585]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14585,
+ },
+ [0x14586]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14586,
+ },
+ [0x14587]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14587,
+ },
+ [0x14588]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14588,
+ },
+ [0x14589]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14589,
+ },
+ [0x1458A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458A,
+ },
+ [0x1458B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458B,
+ },
+ [0x1458C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458C,
+ },
+ [0x1458D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458D,
+ },
+ [0x1458E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458E,
+ },
+ [0x1458F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1458F,
+ },
+ [0x14590]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14590,
+ },
+ [0x14591]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14591,
+ },
+ [0x14592]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14592,
+ },
+ [0x14593]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14593,
+ },
+ [0x14594]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14594,
+ },
+ [0x14595]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14595,
+ },
+ [0x14596]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14596,
+ },
+ [0x14597]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14597,
+ },
+ [0x14598]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14598,
+ },
+ [0x14599]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14599,
+ },
+ [0x1459A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459A,
+ },
+ [0x1459B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459B,
+ },
+ [0x1459C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459C,
+ },
+ [0x1459D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459D,
+ },
+ [0x1459E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459E,
+ },
+ [0x1459F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1459F,
+ },
+ [0x145A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A0,
+ },
+ [0x145A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A1,
+ },
+ [0x145A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A2,
+ },
+ [0x145A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A3,
+ },
+ [0x145A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A4,
+ },
+ [0x145A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A5,
+ },
+ [0x145A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A6,
+ },
+ [0x145A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A7,
+ },
+ [0x145A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A8,
+ },
+ [0x145A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145A9,
+ },
+ [0x145AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145AA,
+ },
+ [0x145AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145AB,
+ },
+ [0x145AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145AC,
+ },
+ [0x145AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145AD,
+ },
+ [0x145AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145AE,
+ },
+ [0x145AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145AF,
+ },
+ [0x145B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B0,
+ },
+ [0x145B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B1,
+ },
+ [0x145B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B2,
+ },
+ [0x145B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B3,
+ },
+ [0x145B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B4,
+ },
+ [0x145B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B5,
+ },
+ [0x145B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B6,
+ },
+ [0x145B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B7,
+ },
+ [0x145B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B8,
+ },
+ [0x145B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145B9,
+ },
+ [0x145BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145BA,
+ },
+ [0x145BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145BB,
+ },
+ [0x145BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145BC,
+ },
+ [0x145BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145BD,
+ },
+ [0x145BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145BE,
+ },
+ [0x145BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145BF,
+ },
+ [0x145C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C0,
+ },
+ [0x145C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C1,
+ },
+ [0x145C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C2,
+ },
+ [0x145C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C3,
+ },
+ [0x145C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C4,
+ },
+ [0x145C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C5,
+ },
+ [0x145C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C6,
+ },
+ [0x145C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C7,
+ },
+ [0x145C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C8,
+ },
+ [0x145C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145C9,
+ },
+ [0x145CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145CA,
+ },
+ [0x145CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145CB,
+ },
+ [0x145CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145CC,
+ },
+ [0x145CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145CD,
+ },
+ [0x145CE]={
+ category="lo",
+ direction="l",
+ linebreak="op",
+ unicodeslot=0x145CE,
+ },
+ [0x145CF]={
+ category="lo",
+ direction="l",
+ linebreak="cl",
+ unicodeslot=0x145CF,
+ },
+ [0x145D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D0,
+ },
+ [0x145D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D1,
+ },
+ [0x145D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D2,
+ },
+ [0x145D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D3,
+ },
+ [0x145D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D4,
+ },
+ [0x145D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D5,
+ },
+ [0x145D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D6,
+ },
+ [0x145D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D7,
+ },
+ [0x145D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D8,
+ },
+ [0x145D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145D9,
+ },
+ [0x145DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145DA,
+ },
+ [0x145DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145DB,
+ },
+ [0x145DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145DC,
+ },
+ [0x145DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145DD,
+ },
+ [0x145DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145DE,
+ },
+ [0x145DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145DF,
+ },
+ [0x145E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E0,
+ },
+ [0x145E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E1,
+ },
+ [0x145E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E2,
+ },
+ [0x145E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E3,
+ },
+ [0x145E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E4,
+ },
+ [0x145E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E5,
+ },
+ [0x145E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E6,
+ },
+ [0x145E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E7,
+ },
+ [0x145E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E8,
+ },
+ [0x145E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145E9,
+ },
+ [0x145EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145EA,
+ },
+ [0x145EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145EB,
+ },
+ [0x145EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145EC,
+ },
+ [0x145ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145ED,
+ },
+ [0x145EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145EE,
+ },
+ [0x145EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145EF,
+ },
+ [0x145F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F0,
+ },
+ [0x145F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F1,
+ },
+ [0x145F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F2,
+ },
+ [0x145F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F3,
+ },
+ [0x145F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F4,
+ },
+ [0x145F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F5,
+ },
+ [0x145F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F6,
+ },
+ [0x145F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F7,
+ },
+ [0x145F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F8,
+ },
+ [0x145F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145F9,
+ },
+ [0x145FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145FA,
+ },
+ [0x145FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145FB,
+ },
+ [0x145FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145FC,
+ },
+ [0x145FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145FD,
+ },
+ [0x145FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145FE,
+ },
+ [0x145FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x145FF,
+ },
+ [0x14600]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14600,
+ },
+ [0x14601]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14601,
+ },
+ [0x14602]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14602,
+ },
+ [0x14603]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14603,
+ },
+ [0x14604]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14604,
+ },
+ [0x14605]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14605,
+ },
+ [0x14606]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14606,
+ },
+ [0x14607]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14607,
+ },
+ [0x14608]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14608,
+ },
+ [0x14609]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14609,
+ },
+ [0x1460A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460A,
+ },
+ [0x1460B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460B,
+ },
+ [0x1460C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460C,
+ },
+ [0x1460D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460D,
+ },
+ [0x1460E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460E,
+ },
+ [0x1460F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1460F,
+ },
+ [0x14610]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14610,
+ },
+ [0x14611]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14611,
+ },
+ [0x14612]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14612,
+ },
+ [0x14613]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14613,
+ },
+ [0x14614]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14614,
+ },
+ [0x14615]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14615,
+ },
+ [0x14616]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14616,
+ },
+ [0x14617]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14617,
+ },
+ [0x14618]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14618,
+ },
+ [0x14619]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14619,
+ },
+ [0x1461A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461A,
+ },
+ [0x1461B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461B,
+ },
+ [0x1461C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461C,
+ },
+ [0x1461D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461D,
+ },
+ [0x1461E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461E,
+ },
+ [0x1461F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1461F,
+ },
+ [0x14620]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14620,
+ },
+ [0x14621]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14621,
+ },
+ [0x14622]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14622,
+ },
+ [0x14623]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14623,
+ },
+ [0x14624]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14624,
+ },
+ [0x14625]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14625,
+ },
+ [0x14626]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14626,
+ },
+ [0x14627]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14627,
+ },
+ [0x14628]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14628,
+ },
+ [0x14629]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14629,
+ },
+ [0x1462A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462A,
+ },
+ [0x1462B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462B,
+ },
+ [0x1462C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462C,
+ },
+ [0x1462D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462D,
+ },
+ [0x1462E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462E,
+ },
+ [0x1462F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1462F,
+ },
+ [0x14630]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14630,
+ },
+ [0x14631]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14631,
+ },
+ [0x14632]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14632,
+ },
+ [0x14633]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14633,
+ },
+ [0x14634]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14634,
+ },
+ [0x14635]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14635,
+ },
+ [0x14636]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14636,
+ },
+ [0x14637]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14637,
+ },
+ [0x14638]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14638,
+ },
+ [0x14639]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14639,
+ },
+ [0x1463A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463A,
+ },
+ [0x1463B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463B,
+ },
+ [0x1463C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463C,
+ },
+ [0x1463D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463D,
+ },
+ [0x1463E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463E,
+ },
+ [0x1463F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1463F,
+ },
+ [0x14640]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14640,
+ },
+ [0x14641]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14641,
+ },
+ [0x14642]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14642,
+ },
+ [0x14643]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14643,
+ },
+ [0x14644]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14644,
+ },
+ [0x14645]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14645,
+ },
+ [0x14646]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x14646,
+ },
+ [0x16800]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16800,
+ },
+ [0x16801]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16801,
+ },
+ [0x16802]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16802,
+ },
+ [0x16803]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16803,
+ },
+ [0x16804]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16804,
+ },
+ [0x16805]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16805,
+ },
+ [0x16806]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16806,
+ },
+ [0x16807]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16807,
+ },
+ [0x16808]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16808,
+ },
+ [0x16809]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16809,
+ },
+ [0x1680A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1680A,
+ },
+ [0x1680B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1680B,
+ },
+ [0x1680C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1680C,
+ },
+ [0x1680D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1680D,
+ },
+ [0x1680E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1680E,
+ },
+ [0x1680F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1680F,
+ },
+ [0x16810]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16810,
+ },
+ [0x16811]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16811,
+ },
+ [0x16812]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16812,
+ },
+ [0x16813]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16813,
+ },
+ [0x16814]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16814,
+ },
+ [0x16815]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16815,
+ },
+ [0x16816]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16816,
+ },
+ [0x16817]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16817,
+ },
+ [0x16818]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16818,
+ },
+ [0x16819]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16819,
+ },
+ [0x1681A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681A,
+ },
+ [0x1681B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681B,
+ },
+ [0x1681C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681C,
+ },
+ [0x1681D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681D,
+ },
+ [0x1681E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681E,
+ },
+ [0x1681F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1681F,
+ },
+ [0x16820]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16820,
+ },
+ [0x16821]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16821,
+ },
+ [0x16822]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16822,
+ },
+ [0x16823]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16823,
+ },
+ [0x16824]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16824,
+ },
+ [0x16825]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16825,
+ },
+ [0x16826]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16826,
+ },
+ [0x16827]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16827,
+ },
+ [0x16828]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16828,
+ },
+ [0x16829]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16829,
+ },
+ [0x1682A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682A,
+ },
+ [0x1682B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682B,
+ },
+ [0x1682C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682C,
+ },
+ [0x1682D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682D,
+ },
+ [0x1682E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682E,
+ },
+ [0x1682F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1682F,
+ },
+ [0x16830]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16830,
+ },
+ [0x16831]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16831,
+ },
+ [0x16832]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16832,
+ },
+ [0x16833]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16833,
+ },
+ [0x16834]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16834,
+ },
+ [0x16835]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16835,
+ },
+ [0x16836]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16836,
+ },
+ [0x16837]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16837,
+ },
+ [0x16838]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16838,
+ },
+ [0x16839]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16839,
+ },
+ [0x1683A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683A,
+ },
+ [0x1683B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683B,
+ },
+ [0x1683C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683C,
+ },
+ [0x1683D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683D,
+ },
+ [0x1683E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683E,
+ },
+ [0x1683F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1683F,
+ },
+ [0x16840]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16840,
+ },
+ [0x16841]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16841,
+ },
+ [0x16842]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16842,
+ },
+ [0x16843]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16843,
+ },
+ [0x16844]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16844,
+ },
+ [0x16845]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16845,
+ },
+ [0x16846]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16846,
+ },
+ [0x16847]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16847,
+ },
+ [0x16848]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16848,
+ },
+ [0x16849]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16849,
+ },
+ [0x1684A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684A,
+ },
+ [0x1684B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684B,
+ },
+ [0x1684C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684C,
+ },
+ [0x1684D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684D,
+ },
+ [0x1684E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684E,
+ },
+ [0x1684F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1684F,
+ },
+ [0x16850]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16850,
+ },
+ [0x16851]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16851,
+ },
+ [0x16852]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16852,
+ },
+ [0x16853]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16853,
+ },
+ [0x16854]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16854,
+ },
+ [0x16855]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16855,
+ },
+ [0x16856]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16856,
+ },
+ [0x16857]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16857,
+ },
+ [0x16858]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16858,
+ },
+ [0x16859]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16859,
+ },
+ [0x1685A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685A,
+ },
+ [0x1685B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685B,
+ },
+ [0x1685C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685C,
+ },
+ [0x1685D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685D,
+ },
+ [0x1685E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685E,
+ },
+ [0x1685F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1685F,
+ },
+ [0x16860]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16860,
+ },
+ [0x16861]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16861,
+ },
+ [0x16862]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16862,
+ },
+ [0x16863]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16863,
+ },
+ [0x16864]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16864,
+ },
+ [0x16865]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16865,
+ },
+ [0x16866]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16866,
+ },
+ [0x16867]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16867,
+ },
+ [0x16868]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16868,
+ },
+ [0x16869]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16869,
+ },
+ [0x1686A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686A,
+ },
+ [0x1686B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686B,
+ },
+ [0x1686C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686C,
+ },
+ [0x1686D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686D,
+ },
+ [0x1686E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686E,
+ },
+ [0x1686F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1686F,
+ },
+ [0x16870]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16870,
+ },
+ [0x16871]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16871,
+ },
+ [0x16872]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16872,
+ },
+ [0x16873]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16873,
+ },
+ [0x16874]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16874,
+ },
+ [0x16875]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16875,
+ },
+ [0x16876]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16876,
+ },
+ [0x16877]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16877,
+ },
+ [0x16878]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16878,
+ },
+ [0x16879]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16879,
+ },
+ [0x1687A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687A,
+ },
+ [0x1687B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687B,
+ },
+ [0x1687C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687C,
+ },
+ [0x1687D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687D,
+ },
+ [0x1687E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687E,
+ },
+ [0x1687F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1687F,
+ },
+ [0x16880]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16880,
+ },
+ [0x16881]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16881,
+ },
+ [0x16882]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16882,
+ },
+ [0x16883]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16883,
+ },
+ [0x16884]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16884,
+ },
+ [0x16885]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16885,
+ },
+ [0x16886]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16886,
+ },
+ [0x16887]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16887,
+ },
+ [0x16888]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16888,
+ },
+ [0x16889]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16889,
+ },
+ [0x1688A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688A,
+ },
+ [0x1688B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688B,
+ },
+ [0x1688C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688C,
+ },
+ [0x1688D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688D,
+ },
+ [0x1688E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688E,
+ },
+ [0x1688F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1688F,
+ },
+ [0x16890]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16890,
+ },
+ [0x16891]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16891,
+ },
+ [0x16892]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16892,
+ },
+ [0x16893]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16893,
+ },
+ [0x16894]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16894,
+ },
+ [0x16895]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16895,
+ },
+ [0x16896]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16896,
+ },
+ [0x16897]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16897,
+ },
+ [0x16898]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16898,
+ },
+ [0x16899]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16899,
+ },
+ [0x1689A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689A,
+ },
+ [0x1689B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689B,
+ },
+ [0x1689C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689C,
+ },
+ [0x1689D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689D,
+ },
+ [0x1689E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689E,
+ },
+ [0x1689F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1689F,
+ },
+ [0x168A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A0,
+ },
+ [0x168A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A1,
+ },
+ [0x168A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A2,
+ },
+ [0x168A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A3,
+ },
+ [0x168A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A4,
+ },
+ [0x168A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A5,
+ },
+ [0x168A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A6,
+ },
+ [0x168A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A7,
+ },
+ [0x168A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A8,
+ },
+ [0x168A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168A9,
+ },
+ [0x168AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168AA,
+ },
+ [0x168AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168AB,
+ },
+ [0x168AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168AC,
+ },
+ [0x168AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168AD,
+ },
+ [0x168AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168AE,
+ },
+ [0x168AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168AF,
+ },
+ [0x168B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B0,
+ },
+ [0x168B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B1,
+ },
+ [0x168B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B2,
+ },
+ [0x168B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B3,
+ },
+ [0x168B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B4,
+ },
+ [0x168B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B5,
+ },
+ [0x168B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B6,
+ },
+ [0x168B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B7,
+ },
+ [0x168B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B8,
+ },
+ [0x168B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168B9,
+ },
+ [0x168BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168BA,
+ },
+ [0x168BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168BB,
+ },
+ [0x168BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168BC,
+ },
+ [0x168BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168BD,
+ },
+ [0x168BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168BE,
+ },
+ [0x168BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168BF,
+ },
+ [0x168C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C0,
+ },
+ [0x168C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C1,
+ },
+ [0x168C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C2,
+ },
+ [0x168C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C3,
+ },
+ [0x168C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C4,
+ },
+ [0x168C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C5,
+ },
+ [0x168C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C6,
+ },
+ [0x168C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C7,
+ },
+ [0x168C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C8,
+ },
+ [0x168C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168C9,
+ },
+ [0x168CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168CA,
+ },
+ [0x168CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168CB,
+ },
+ [0x168CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168CC,
+ },
+ [0x168CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168CD,
+ },
+ [0x168CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168CE,
+ },
+ [0x168CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168CF,
+ },
+ [0x168D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D0,
+ },
+ [0x168D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D1,
+ },
+ [0x168D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D2,
+ },
+ [0x168D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D3,
+ },
+ [0x168D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D4,
+ },
+ [0x168D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D5,
+ },
+ [0x168D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D6,
+ },
+ [0x168D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D7,
+ },
+ [0x168D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D8,
+ },
+ [0x168D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168D9,
+ },
+ [0x168DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168DA,
+ },
+ [0x168DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168DB,
+ },
+ [0x168DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168DC,
+ },
+ [0x168DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168DD,
+ },
+ [0x168DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168DE,
+ },
+ [0x168DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168DF,
+ },
+ [0x168E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E0,
+ },
+ [0x168E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E1,
+ },
+ [0x168E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E2,
+ },
+ [0x168E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E3,
+ },
+ [0x168E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E4,
+ },
+ [0x168E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E5,
+ },
+ [0x168E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E6,
+ },
+ [0x168E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E7,
+ },
+ [0x168E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E8,
+ },
+ [0x168E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168E9,
+ },
+ [0x168EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168EA,
+ },
+ [0x168EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168EB,
+ },
+ [0x168EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168EC,
+ },
+ [0x168ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168ED,
+ },
+ [0x168EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168EE,
+ },
+ [0x168EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168EF,
+ },
+ [0x168F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F0,
+ },
+ [0x168F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F1,
+ },
+ [0x168F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F2,
+ },
+ [0x168F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F3,
+ },
+ [0x168F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F4,
+ },
+ [0x168F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F5,
+ },
+ [0x168F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F6,
+ },
+ [0x168F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F7,
+ },
+ [0x168F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F8,
+ },
+ [0x168F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168F9,
+ },
+ [0x168FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168FA,
+ },
+ [0x168FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168FB,
+ },
+ [0x168FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168FC,
+ },
+ [0x168FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168FD,
+ },
+ [0x168FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168FE,
+ },
+ [0x168FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x168FF,
+ },
+ [0x16900]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16900,
+ },
+ [0x16901]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16901,
+ },
+ [0x16902]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16902,
+ },
+ [0x16903]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16903,
+ },
+ [0x16904]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16904,
+ },
+ [0x16905]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16905,
+ },
+ [0x16906]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16906,
+ },
+ [0x16907]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16907,
+ },
+ [0x16908]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16908,
+ },
+ [0x16909]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16909,
+ },
+ [0x1690A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690A,
+ },
+ [0x1690B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690B,
+ },
+ [0x1690C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690C,
+ },
+ [0x1690D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690D,
+ },
+ [0x1690E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690E,
+ },
+ [0x1690F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1690F,
+ },
+ [0x16910]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16910,
+ },
+ [0x16911]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16911,
+ },
+ [0x16912]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16912,
+ },
+ [0x16913]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16913,
+ },
+ [0x16914]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16914,
+ },
+ [0x16915]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16915,
+ },
+ [0x16916]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16916,
+ },
+ [0x16917]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16917,
+ },
+ [0x16918]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16918,
+ },
+ [0x16919]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16919,
+ },
+ [0x1691A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691A,
+ },
+ [0x1691B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691B,
+ },
+ [0x1691C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691C,
+ },
+ [0x1691D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691D,
+ },
+ [0x1691E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691E,
+ },
+ [0x1691F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1691F,
+ },
+ [0x16920]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16920,
+ },
+ [0x16921]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16921,
+ },
+ [0x16922]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16922,
+ },
+ [0x16923]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16923,
+ },
+ [0x16924]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16924,
+ },
+ [0x16925]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16925,
+ },
+ [0x16926]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16926,
+ },
+ [0x16927]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16927,
+ },
+ [0x16928]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16928,
+ },
+ [0x16929]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16929,
+ },
+ [0x1692A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692A,
+ },
+ [0x1692B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692B,
+ },
+ [0x1692C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692C,
+ },
+ [0x1692D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692D,
+ },
+ [0x1692E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692E,
+ },
+ [0x1692F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1692F,
+ },
+ [0x16930]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16930,
+ },
+ [0x16931]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16931,
+ },
+ [0x16932]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16932,
+ },
+ [0x16933]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16933,
+ },
+ [0x16934]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16934,
+ },
+ [0x16935]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16935,
+ },
+ [0x16936]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16936,
+ },
+ [0x16937]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16937,
+ },
+ [0x16938]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16938,
+ },
+ [0x16939]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16939,
+ },
+ [0x1693A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693A,
+ },
+ [0x1693B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693B,
+ },
+ [0x1693C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693C,
+ },
+ [0x1693D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693D,
+ },
+ [0x1693E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693E,
+ },
+ [0x1693F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1693F,
+ },
+ [0x16940]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16940,
+ },
+ [0x16941]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16941,
+ },
+ [0x16942]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16942,
+ },
+ [0x16943]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16943,
+ },
+ [0x16944]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16944,
+ },
+ [0x16945]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16945,
+ },
+ [0x16946]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16946,
+ },
+ [0x16947]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16947,
+ },
+ [0x16948]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16948,
+ },
+ [0x16949]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16949,
+ },
+ [0x1694A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694A,
+ },
+ [0x1694B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694B,
+ },
+ [0x1694C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694C,
+ },
+ [0x1694D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694D,
+ },
+ [0x1694E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694E,
+ },
+ [0x1694F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1694F,
+ },
+ [0x16950]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16950,
+ },
+ [0x16951]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16951,
+ },
+ [0x16952]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16952,
+ },
+ [0x16953]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16953,
+ },
+ [0x16954]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16954,
+ },
+ [0x16955]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16955,
+ },
+ [0x16956]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16956,
+ },
+ [0x16957]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16957,
+ },
+ [0x16958]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16958,
+ },
+ [0x16959]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16959,
+ },
+ [0x1695A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695A,
+ },
+ [0x1695B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695B,
+ },
+ [0x1695C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695C,
+ },
+ [0x1695D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695D,
+ },
+ [0x1695E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695E,
+ },
+ [0x1695F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1695F,
+ },
+ [0x16960]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16960,
+ },
+ [0x16961]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16961,
+ },
+ [0x16962]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16962,
+ },
+ [0x16963]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16963,
+ },
+ [0x16964]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16964,
+ },
+ [0x16965]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16965,
+ },
+ [0x16966]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16966,
+ },
+ [0x16967]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16967,
+ },
+ [0x16968]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16968,
+ },
+ [0x16969]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16969,
+ },
+ [0x1696A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696A,
+ },
+ [0x1696B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696B,
+ },
+ [0x1696C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696C,
+ },
+ [0x1696D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696D,
+ },
+ [0x1696E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696E,
+ },
+ [0x1696F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1696F,
+ },
+ [0x16970]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16970,
+ },
+ [0x16971]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16971,
+ },
+ [0x16972]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16972,
+ },
+ [0x16973]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16973,
+ },
+ [0x16974]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16974,
+ },
+ [0x16975]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16975,
+ },
+ [0x16976]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16976,
+ },
+ [0x16977]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16977,
+ },
+ [0x16978]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16978,
+ },
+ [0x16979]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16979,
+ },
+ [0x1697A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697A,
+ },
+ [0x1697B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697B,
+ },
+ [0x1697C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697C,
+ },
+ [0x1697D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697D,
+ },
+ [0x1697E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697E,
+ },
+ [0x1697F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1697F,
+ },
+ [0x16980]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16980,
+ },
+ [0x16981]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16981,
+ },
+ [0x16982]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16982,
+ },
+ [0x16983]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16983,
+ },
+ [0x16984]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16984,
+ },
+ [0x16985]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16985,
+ },
+ [0x16986]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16986,
+ },
+ [0x16987]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16987,
+ },
+ [0x16988]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16988,
+ },
+ [0x16989]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16989,
+ },
+ [0x1698A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698A,
+ },
+ [0x1698B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698B,
+ },
+ [0x1698C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698C,
+ },
+ [0x1698D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698D,
+ },
+ [0x1698E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698E,
+ },
+ [0x1698F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1698F,
+ },
+ [0x16990]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16990,
+ },
+ [0x16991]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16991,
+ },
+ [0x16992]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16992,
+ },
+ [0x16993]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16993,
+ },
+ [0x16994]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16994,
+ },
+ [0x16995]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16995,
+ },
+ [0x16996]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16996,
+ },
+ [0x16997]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16997,
+ },
+ [0x16998]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16998,
+ },
+ [0x16999]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16999,
+ },
+ [0x1699A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699A,
+ },
+ [0x1699B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699B,
+ },
+ [0x1699C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699C,
+ },
+ [0x1699D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699D,
+ },
+ [0x1699E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699E,
+ },
+ [0x1699F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1699F,
+ },
+ [0x169A0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A0,
+ },
+ [0x169A1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A1,
+ },
+ [0x169A2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A2,
+ },
+ [0x169A3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A3,
+ },
+ [0x169A4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A4,
+ },
+ [0x169A5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A5,
+ },
+ [0x169A6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A6,
+ },
+ [0x169A7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A7,
+ },
+ [0x169A8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A8,
+ },
+ [0x169A9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169A9,
+ },
+ [0x169AA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169AA,
+ },
+ [0x169AB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169AB,
+ },
+ [0x169AC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169AC,
+ },
+ [0x169AD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169AD,
+ },
+ [0x169AE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169AE,
+ },
+ [0x169AF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169AF,
+ },
+ [0x169B0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B0,
+ },
+ [0x169B1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B1,
+ },
+ [0x169B2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B2,
+ },
+ [0x169B3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B3,
+ },
+ [0x169B4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B4,
+ },
+ [0x169B5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B5,
+ },
+ [0x169B6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B6,
+ },
+ [0x169B7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B7,
+ },
+ [0x169B8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B8,
+ },
+ [0x169B9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169B9,
+ },
+ [0x169BA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169BA,
+ },
+ [0x169BB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169BB,
+ },
+ [0x169BC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169BC,
+ },
+ [0x169BD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169BD,
+ },
+ [0x169BE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169BE,
+ },
+ [0x169BF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169BF,
+ },
+ [0x169C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C0,
+ },
+ [0x169C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C1,
+ },
+ [0x169C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C2,
+ },
+ [0x169C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C3,
+ },
+ [0x169C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C4,
+ },
+ [0x169C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C5,
+ },
+ [0x169C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C6,
+ },
+ [0x169C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C7,
+ },
+ [0x169C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C8,
+ },
+ [0x169C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169C9,
+ },
+ [0x169CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169CA,
+ },
+ [0x169CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169CB,
+ },
+ [0x169CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169CC,
+ },
+ [0x169CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169CD,
+ },
+ [0x169CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169CE,
+ },
+ [0x169CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169CF,
+ },
+ [0x169D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D0,
+ },
+ [0x169D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D1,
+ },
+ [0x169D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D2,
+ },
+ [0x169D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D3,
+ },
+ [0x169D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D4,
+ },
+ [0x169D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D5,
+ },
+ [0x169D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D6,
+ },
+ [0x169D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D7,
+ },
+ [0x169D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D8,
+ },
+ [0x169D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169D9,
+ },
+ [0x169DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169DA,
+ },
+ [0x169DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169DB,
+ },
+ [0x169DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169DC,
+ },
+ [0x169DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169DD,
+ },
+ [0x169DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169DE,
+ },
+ [0x169DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169DF,
+ },
+ [0x169E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E0,
+ },
+ [0x169E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E1,
+ },
+ [0x169E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E2,
+ },
+ [0x169E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E3,
+ },
+ [0x169E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E4,
+ },
+ [0x169E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E5,
+ },
+ [0x169E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E6,
+ },
+ [0x169E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E7,
+ },
+ [0x169E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E8,
+ },
+ [0x169E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169E9,
+ },
+ [0x169EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169EA,
+ },
+ [0x169EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169EB,
+ },
+ [0x169EC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169EC,
+ },
+ [0x169ED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169ED,
+ },
+ [0x169EE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169EE,
+ },
+ [0x169EF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169EF,
+ },
+ [0x169F0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F0,
+ },
+ [0x169F1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F1,
+ },
+ [0x169F2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F2,
+ },
+ [0x169F3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F3,
+ },
+ [0x169F4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F4,
+ },
+ [0x169F5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F5,
+ },
+ [0x169F6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F6,
+ },
+ [0x169F7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F7,
+ },
+ [0x169F8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F8,
+ },
+ [0x169F9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169F9,
+ },
+ [0x169FA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169FA,
+ },
+ [0x169FB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169FB,
+ },
+ [0x169FC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169FC,
+ },
+ [0x169FD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169FD,
+ },
+ [0x169FE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169FE,
+ },
+ [0x169FF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x169FF,
+ },
+ [0x16A00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A00,
+ },
+ [0x16A01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A01,
+ },
+ [0x16A02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A02,
+ },
+ [0x16A03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A03,
+ },
+ [0x16A04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A04,
+ },
+ [0x16A05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A05,
+ },
+ [0x16A06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A06,
+ },
+ [0x16A07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A07,
+ },
+ [0x16A08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A08,
+ },
+ [0x16A09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A09,
+ },
+ [0x16A0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0A,
+ },
+ [0x16A0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0B,
+ },
+ [0x16A0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0C,
+ },
+ [0x16A0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0D,
+ },
+ [0x16A0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0E,
+ },
+ [0x16A0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A0F,
+ },
+ [0x16A10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A10,
+ },
+ [0x16A11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A11,
+ },
+ [0x16A12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A12,
+ },
+ [0x16A13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A13,
+ },
+ [0x16A14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A14,
+ },
+ [0x16A15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A15,
+ },
+ [0x16A16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A16,
+ },
+ [0x16A17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A17,
+ },
+ [0x16A18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A18,
+ },
+ [0x16A19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A19,
+ },
+ [0x16A1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1A,
+ },
+ [0x16A1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1B,
+ },
+ [0x16A1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1C,
+ },
+ [0x16A1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1D,
+ },
+ [0x16A1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1E,
+ },
+ [0x16A1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A1F,
+ },
+ [0x16A20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A20,
+ },
+ [0x16A21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A21,
+ },
+ [0x16A22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A22,
+ },
+ [0x16A23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A23,
+ },
+ [0x16A24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A24,
+ },
+ [0x16A25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A25,
+ },
+ [0x16A26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A26,
+ },
+ [0x16A27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A27,
+ },
+ [0x16A28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A28,
+ },
+ [0x16A29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A29,
+ },
+ [0x16A2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2A,
+ },
+ [0x16A2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2B,
+ },
+ [0x16A2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2C,
+ },
+ [0x16A2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2D,
+ },
+ [0x16A2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2E,
+ },
+ [0x16A2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A2F,
+ },
+ [0x16A30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A30,
+ },
+ [0x16A31]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A31,
+ },
+ [0x16A32]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A32,
+ },
+ [0x16A33]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A33,
+ },
+ [0x16A34]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A34,
+ },
+ [0x16A35]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A35,
+ },
+ [0x16A36]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A36,
+ },
+ [0x16A37]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A37,
+ },
+ [0x16A38]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A38,
+ },
+ [0x16A40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A40,
+ },
+ [0x16A41]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A41,
+ },
+ [0x16A42]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A42,
+ },
+ [0x16A43]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A43,
+ },
+ [0x16A44]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A44,
+ },
+ [0x16A45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A45,
+ },
+ [0x16A46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A46,
+ },
+ [0x16A47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A47,
+ },
+ [0x16A48]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A48,
+ },
+ [0x16A49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A49,
+ },
+ [0x16A4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4A,
+ },
+ [0x16A4B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4B,
+ },
+ [0x16A4C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4C,
+ },
+ [0x16A4D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4D,
+ },
+ [0x16A4E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4E,
+ },
+ [0x16A4F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A4F,
+ },
+ [0x16A50]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A50,
+ },
+ [0x16A51]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A51,
+ },
+ [0x16A52]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A52,
+ },
+ [0x16A53]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A53,
+ },
+ [0x16A54]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A54,
+ },
+ [0x16A55]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A55,
+ },
+ [0x16A56]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A56,
+ },
+ [0x16A57]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A57,
+ },
+ [0x16A58]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A58,
+ },
+ [0x16A59]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A59,
+ },
+ [0x16A5A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A5A,
+ },
+ [0x16A5B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A5B,
+ },
+ [0x16A5C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A5C,
+ },
+ [0x16A5D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A5D,
+ },
+ [0x16A5E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16A5E,
+ },
+ [0x16A60]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A60,
+ },
+ [0x16A61]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A61,
+ },
+ [0x16A62]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A62,
+ },
+ [0x16A63]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A63,
+ },
+ [0x16A64]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A64,
+ },
+ [0x16A65]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A65,
+ },
+ [0x16A66]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A66,
+ },
+ [0x16A67]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A67,
+ },
+ [0x16A68]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A68,
+ },
+ [0x16A69]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16A69,
+ },
+ [0x16A6E]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16A6E,
+ },
+ [0x16A6F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16A6F,
+ },
+ [0x16AD0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD0,
+ },
+ [0x16AD1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD1,
+ },
+ [0x16AD2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD2,
+ },
+ [0x16AD3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD3,
+ },
+ [0x16AD4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD4,
+ },
+ [0x16AD5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD5,
+ },
+ [0x16AD6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD6,
+ },
+ [0x16AD7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD7,
+ },
+ [0x16AD8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD8,
+ },
+ [0x16AD9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AD9,
+ },
+ [0x16ADA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16ADA,
+ },
+ [0x16ADB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16ADB,
+ },
+ [0x16ADC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16ADC,
+ },
+ [0x16ADD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16ADD,
+ },
+ [0x16ADE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16ADE,
+ },
+ [0x16ADF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16ADF,
+ },
+ [0x16AE0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE0,
+ },
+ [0x16AE1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE1,
+ },
+ [0x16AE2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE2,
+ },
+ [0x16AE3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE3,
+ },
+ [0x16AE4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE4,
+ },
+ [0x16AE5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE5,
+ },
+ [0x16AE6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE6,
+ },
+ [0x16AE7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE7,
+ },
+ [0x16AE8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE8,
+ },
+ [0x16AE9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AE9,
+ },
+ [0x16AEA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AEA,
+ },
+ [0x16AEB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AEB,
+ },
+ [0x16AEC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AEC,
+ },
+ [0x16AED]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16AED,
+ },
+ [0x16AF0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16AF0,
+ },
+ [0x16AF1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16AF1,
+ },
+ [0x16AF2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16AF2,
+ },
+ [0x16AF3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16AF3,
+ },
+ [0x16AF4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16AF4,
+ },
+ [0x16AF5]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16AF5,
+ },
+ [0x16B00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B00,
+ },
+ [0x16B01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B01,
+ },
+ [0x16B02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B02,
+ },
+ [0x16B03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B03,
+ },
+ [0x16B04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B04,
+ },
+ [0x16B05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B05,
+ },
+ [0x16B06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B06,
+ },
+ [0x16B07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B07,
+ },
+ [0x16B08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B08,
+ },
+ [0x16B09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B09,
+ },
+ [0x16B0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0A,
+ },
+ [0x16B0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0B,
+ },
+ [0x16B0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0C,
+ },
+ [0x16B0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0D,
+ },
+ [0x16B0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0E,
+ },
+ [0x16B0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B0F,
+ },
+ [0x16B10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B10,
+ },
+ [0x16B11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B11,
+ },
+ [0x16B12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B12,
+ },
+ [0x16B13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B13,
+ },
+ [0x16B14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B14,
+ },
+ [0x16B15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B15,
+ },
+ [0x16B16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B16,
+ },
+ [0x16B17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B17,
+ },
+ [0x16B18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B18,
+ },
+ [0x16B19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B19,
+ },
+ [0x16B1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1A,
+ },
+ [0x16B1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1B,
+ },
+ [0x16B1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1C,
+ },
+ [0x16B1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1D,
+ },
+ [0x16B1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1E,
+ },
+ [0x16B1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B1F,
+ },
+ [0x16B20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B20,
+ },
+ [0x16B21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B21,
+ },
+ [0x16B22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B22,
+ },
+ [0x16B23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B23,
+ },
+ [0x16B24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B24,
+ },
+ [0x16B25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B25,
+ },
+ [0x16B26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B26,
+ },
+ [0x16B27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B27,
+ },
+ [0x16B28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B28,
+ },
+ [0x16B29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B29,
+ },
+ [0x16B2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2A,
+ },
+ [0x16B2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2B,
+ },
+ [0x16B2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2C,
+ },
+ [0x16B2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2D,
+ },
+ [0x16B2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2E,
+ },
+ [0x16B2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B2F,
+ },
+ [0x16B30]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B30,
+ },
+ [0x16B31]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B31,
+ },
+ [0x16B32]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B32,
+ },
+ [0x16B33]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B33,
+ },
+ [0x16B34]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B34,
+ },
+ [0x16B35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B35,
+ },
+ [0x16B36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16B36,
+ },
+ [0x16B37]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16B37,
+ },
+ [0x16B38]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16B38,
+ },
+ [0x16B39]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16B39,
+ },
+ [0x16B3A]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3A,
+ },
+ [0x16B3B]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3B,
+ },
+ [0x16B3C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3C,
+ },
+ [0x16B3D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3D,
+ },
+ [0x16B3E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3E,
+ },
+ [0x16B3F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B3F,
+ },
+ [0x16B40]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B40,
+ },
+ [0x16B41]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B41,
+ },
+ [0x16B42]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B42,
+ },
+ [0x16B43]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B43,
+ },
+ [0x16B44]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16B44,
+ },
+ [0x16B45]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B45,
+ },
+ [0x16B50]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B50,
+ },
+ [0x16B51]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B51,
+ },
+ [0x16B52]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B52,
+ },
+ [0x16B53]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B53,
+ },
+ [0x16B54]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B54,
+ },
+ [0x16B55]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B55,
+ },
+ [0x16B56]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B56,
+ },
+ [0x16B57]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B57,
+ },
+ [0x16B58]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B58,
+ },
+ [0x16B59]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x16B59,
+ },
+ [0x16B5B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B5B,
+ },
+ [0x16B5C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B5C,
+ },
+ [0x16B5D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B5D,
+ },
+ [0x16B5E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B5E,
+ },
+ [0x16B5F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B5F,
+ },
+ [0x16B60]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B60,
+ },
+ [0x16B61]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B61,
+ },
+ [0x16B63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B63,
+ },
+ [0x16B64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B64,
+ },
+ [0x16B65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B65,
+ },
+ [0x16B66]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B66,
+ },
+ [0x16B67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B67,
+ },
+ [0x16B68]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B68,
+ },
+ [0x16B69]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B69,
+ },
+ [0x16B6A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6A,
+ },
+ [0x16B6B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6B,
+ },
+ [0x16B6C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6C,
+ },
+ [0x16B6D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6D,
+ },
+ [0x16B6E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6E,
+ },
+ [0x16B6F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B6F,
+ },
+ [0x16B70]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B70,
+ },
+ [0x16B71]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B71,
+ },
+ [0x16B72]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B72,
+ },
+ [0x16B73]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B73,
+ },
+ [0x16B74]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B74,
+ },
+ [0x16B75]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B75,
+ },
+ [0x16B76]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B76,
+ },
+ [0x16B77]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B77,
+ },
+ [0x16B7D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B7D,
+ },
+ [0x16B7E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B7E,
+ },
+ [0x16B7F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B7F,
+ },
+ [0x16B80]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B80,
+ },
+ [0x16B81]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B81,
+ },
+ [0x16B82]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B82,
+ },
+ [0x16B83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B83,
+ },
+ [0x16B84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B84,
+ },
+ [0x16B85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B85,
+ },
+ [0x16B86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B86,
+ },
+ [0x16B87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B87,
+ },
+ [0x16B88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B88,
+ },
+ [0x16B89]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B89,
+ },
+ [0x16B8A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8A,
+ },
+ [0x16B8B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8B,
+ },
+ [0x16B8C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8C,
+ },
+ [0x16B8D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8D,
+ },
+ [0x16B8E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8E,
+ },
+ [0x16B8F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16B8F,
+ },
+ [0x16E40]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E40,
+ },
+ [0x16E41]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E41,
+ },
+ [0x16E42]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E42,
+ },
+ [0x16E43]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E43,
+ },
+ [0x16E44]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E44,
+ },
+ [0x16E45]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E45,
+ },
+ [0x16E46]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E46,
+ },
+ [0x16E47]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E47,
+ },
+ [0x16E48]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E48,
+ },
+ [0x16E49]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E49,
+ },
+ [0x16E4A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4A,
+ },
+ [0x16E4B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4B,
+ },
+ [0x16E4C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4C,
+ },
+ [0x16E4D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4D,
+ },
+ [0x16E4E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4E,
+ },
+ [0x16E4F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E4F,
+ },
+ [0x16E50]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E50,
+ },
+ [0x16E51]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E51,
+ },
+ [0x16E52]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E52,
+ },
+ [0x16E53]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E53,
+ },
+ [0x16E54]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E54,
+ },
+ [0x16E55]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E55,
+ },
+ [0x16E56]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E56,
+ },
+ [0x16E57]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E57,
+ },
+ [0x16E58]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E58,
+ },
+ [0x16E59]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E59,
+ },
+ [0x16E5A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5A,
+ },
+ [0x16E5B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5B,
+ },
+ [0x16E5C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5C,
+ },
+ [0x16E5D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5D,
+ },
+ [0x16E5E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5E,
+ },
+ [0x16E5F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E5F,
+ },
+ [0x16E60]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E60,
+ },
+ [0x16E61]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E61,
+ },
+ [0x16E62]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E62,
+ },
+ [0x16E63]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E63,
+ },
+ [0x16E64]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E64,
+ },
+ [0x16E65]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E65,
+ },
+ [0x16E66]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E66,
+ },
+ [0x16E67]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E67,
+ },
+ [0x16E68]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E68,
+ },
+ [0x16E69]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E69,
+ },
+ [0x16E6A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6A,
+ },
+ [0x16E6B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6B,
+ },
+ [0x16E6C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6C,
+ },
+ [0x16E6D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6D,
+ },
+ [0x16E6E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6E,
+ },
+ [0x16E6F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E6F,
+ },
+ [0x16E70]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E70,
+ },
+ [0x16E71]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E71,
+ },
+ [0x16E72]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E72,
+ },
+ [0x16E73]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E73,
+ },
+ [0x16E74]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E74,
+ },
+ [0x16E75]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E75,
+ },
+ [0x16E76]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E76,
+ },
+ [0x16E77]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E77,
+ },
+ [0x16E78]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E78,
+ },
+ [0x16E79]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E79,
+ },
+ [0x16E7A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7A,
+ },
+ [0x16E7B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7B,
+ },
+ [0x16E7C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7C,
+ },
+ [0x16E7D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7D,
+ },
+ [0x16E7E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7E,
+ },
+ [0x16E7F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E7F,
+ },
+ [0x16E80]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E80,
+ },
+ [0x16E81]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E81,
+ },
+ [0x16E82]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E82,
+ },
+ [0x16E83]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E83,
+ },
+ [0x16E84]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E84,
+ },
+ [0x16E85]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E85,
+ },
+ [0x16E86]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E86,
+ },
+ [0x16E87]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E87,
+ },
+ [0x16E88]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E88,
+ },
+ [0x16E89]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E89,
+ },
+ [0x16E8A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8A,
+ },
+ [0x16E8B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8B,
+ },
+ [0x16E8C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8C,
+ },
+ [0x16E8D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8D,
+ },
+ [0x16E8E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8E,
+ },
+ [0x16E8F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E8F,
+ },
+ [0x16E90]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E90,
+ },
+ [0x16E91]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E91,
+ },
+ [0x16E92]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E92,
+ },
+ [0x16E93]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E93,
+ },
+ [0x16E94]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E94,
+ },
+ [0x16E95]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E95,
+ },
+ [0x16E96]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E96,
+ },
+ [0x16E97]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16E97,
+ },
+ [0x16E98]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x16E98,
+ },
+ [0x16E99]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E99,
+ },
+ [0x16E9A]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16E9A,
+ },
+ [0x16F00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F00,
+ },
+ [0x16F01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F01,
+ },
+ [0x16F02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F02,
+ },
+ [0x16F03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F03,
+ },
+ [0x16F04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F04,
+ },
+ [0x16F05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F05,
+ },
+ [0x16F06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F06,
+ },
+ [0x16F07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F07,
+ },
+ [0x16F08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F08,
+ },
+ [0x16F09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F09,
+ },
+ [0x16F0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0A,
+ },
+ [0x16F0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0B,
+ },
+ [0x16F0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0C,
+ },
+ [0x16F0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0D,
+ },
+ [0x16F0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0E,
+ },
+ [0x16F0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F0F,
+ },
+ [0x16F10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F10,
+ },
+ [0x16F11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F11,
+ },
+ [0x16F12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F12,
+ },
+ [0x16F13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F13,
+ },
+ [0x16F14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F14,
+ },
+ [0x16F15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F15,
+ },
+ [0x16F16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F16,
+ },
+ [0x16F17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F17,
+ },
+ [0x16F18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F18,
+ },
+ [0x16F19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F19,
+ },
+ [0x16F1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1A,
+ },
+ [0x16F1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1B,
+ },
+ [0x16F1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1C,
+ },
+ [0x16F1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1D,
+ },
+ [0x16F1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1E,
+ },
+ [0x16F1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F1F,
+ },
+ [0x16F20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F20,
+ },
+ [0x16F21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F21,
+ },
+ [0x16F22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F22,
+ },
+ [0x16F23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F23,
+ },
+ [0x16F24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F24,
+ },
+ [0x16F25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F25,
+ },
+ [0x16F26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F26,
+ },
+ [0x16F27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F27,
+ },
+ [0x16F28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F28,
+ },
+ [0x16F29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F29,
+ },
+ [0x16F2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2A,
+ },
+ [0x16F2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2B,
+ },
+ [0x16F2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2C,
+ },
+ [0x16F2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2D,
+ },
+ [0x16F2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2E,
+ },
+ [0x16F2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F2F,
+ },
+ [0x16F30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F30,
+ },
+ [0x16F31]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F31,
+ },
+ [0x16F32]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F32,
+ },
+ [0x16F33]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F33,
+ },
+ [0x16F34]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F34,
+ },
+ [0x16F35]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F35,
+ },
+ [0x16F36]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F36,
+ },
+ [0x16F37]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F37,
+ },
+ [0x16F38]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F38,
+ },
+ [0x16F39]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F39,
+ },
+ [0x16F3A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3A,
+ },
+ [0x16F3B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3B,
+ },
+ [0x16F3C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3C,
+ },
+ [0x16F3D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3D,
+ },
+ [0x16F3E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3E,
+ },
+ [0x16F3F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F3F,
+ },
+ [0x16F40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F40,
+ },
+ [0x16F41]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F41,
+ },
+ [0x16F42]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F42,
+ },
+ [0x16F43]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F43,
+ },
+ [0x16F44]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F44,
+ },
+ [0x16F45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F45,
+ },
+ [0x16F46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F46,
+ },
+ [0x16F47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F47,
+ },
+ [0x16F48]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F48,
+ },
+ [0x16F49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F49,
+ },
+ [0x16F4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F4A,
+ },
+ [0x16F4F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16F4F,
+ },
+ [0x16F50]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F50,
+ },
+ [0x16F51]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F51,
+ },
+ [0x16F52]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F52,
+ },
+ [0x16F53]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F53,
+ },
+ [0x16F54]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F54,
+ },
+ [0x16F55]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F55,
+ },
+ [0x16F56]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F56,
+ },
+ [0x16F57]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F57,
+ },
+ [0x16F58]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F58,
+ },
+ [0x16F59]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F59,
+ },
+ [0x16F5A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F5A,
+ },
+ [0x16F5B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F5B,
+ },
+ [0x16F5C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F5C,
+ },
+ [0x16F5D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F5D,
+ },
+ [0x16F5E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F5E,
+ },
+ [0x16F5F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F5F,
+ },
+ [0x16F60]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F60,
+ },
+ [0x16F61]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F61,
+ },
+ [0x16F62]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F62,
+ },
+ [0x16F63]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F63,
+ },
+ [0x16F64]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F64,
+ },
+ [0x16F65]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F65,
+ },
+ [0x16F66]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F66,
+ },
+ [0x16F67]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F67,
+ },
+ [0x16F68]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F68,
+ },
+ [0x16F69]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F69,
+ },
+ [0x16F6A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F6A,
+ },
+ [0x16F6B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F6B,
+ },
+ [0x16F6C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F6C,
+ },
+ [0x16F6D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F6D,
+ },
+ [0x16F6E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F6E,
+ },
+ [0x16F6F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F6F,
+ },
+ [0x16F70]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F70,
+ },
+ [0x16F71]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F71,
+ },
+ [0x16F72]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F72,
+ },
+ [0x16F73]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F73,
+ },
+ [0x16F74]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F74,
+ },
+ [0x16F75]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F75,
+ },
+ [0x16F76]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F76,
+ },
+ [0x16F77]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F77,
+ },
+ [0x16F78]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F78,
+ },
+ [0x16F79]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F79,
+ },
+ [0x16F7A]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F7A,
+ },
+ [0x16F7B]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F7B,
+ },
+ [0x16F7C]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F7C,
+ },
+ [0x16F7D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F7D,
+ },
+ [0x16F7E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F7E,
+ },
+ [0x16F7F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F7F,
+ },
+ [0x16F80]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F80,
+ },
+ [0x16F81]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F81,
+ },
+ [0x16F82]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F82,
+ },
+ [0x16F83]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F83,
+ },
+ [0x16F84]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F84,
+ },
+ [0x16F85]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F85,
+ },
+ [0x16F86]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F86,
+ },
+ [0x16F87]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x16F87,
+ },
+ [0x16F8F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16F8F,
+ },
+ [0x16F90]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16F90,
+ },
+ [0x16F91]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16F91,
+ },
+ [0x16F92]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x16F92,
+ },
+ [0x16F93]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F93,
+ },
+ [0x16F94]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F94,
+ },
+ [0x16F95]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F95,
+ },
+ [0x16F96]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F96,
+ },
+ [0x16F97]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F97,
+ },
+ [0x16F98]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F98,
+ },
+ [0x16F99]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F99,
+ },
+ [0x16F9A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F9A,
+ },
+ [0x16F9B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F9B,
+ },
+ [0x16F9C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F9C,
+ },
+ [0x16F9D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F9D,
+ },
+ [0x16F9E]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F9E,
+ },
+ [0x16F9F]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x16F9F,
+ },
+ [0x16FE0]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x16FE0,
+ },
+ [0x16FE1]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x16FE1,
+ },
+ [0x16FE2]={
+ category="po",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x16FE2,
+ },
+ [0x16FE3]={
+ category="lm",
+ direction="l",
+ linebreak="ns",
+ unicodeslot=0x16FE3,
+ },
+ [0x18800]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18800,
+ },
+ [0x18801]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18801,
+ },
+ [0x18802]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18802,
+ },
+ [0x18803]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18803,
+ },
+ [0x18804]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18804,
+ },
+ [0x18805]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18805,
+ },
+ [0x18806]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18806,
+ },
+ [0x18807]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18807,
+ },
+ [0x18808]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18808,
+ },
+ [0x18809]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18809,
+ },
+ [0x1880A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1880A,
+ },
+ [0x1880B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1880B,
+ },
+ [0x1880C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1880C,
+ },
+ [0x1880D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1880D,
+ },
+ [0x1880E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1880E,
+ },
+ [0x1880F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1880F,
+ },
+ [0x18810]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18810,
+ },
+ [0x18811]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18811,
+ },
+ [0x18812]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18812,
+ },
+ [0x18813]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18813,
+ },
+ [0x18814]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18814,
+ },
+ [0x18815]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18815,
+ },
+ [0x18816]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18816,
+ },
+ [0x18817]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18817,
+ },
+ [0x18818]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18818,
+ },
+ [0x18819]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18819,
+ },
+ [0x1881A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1881A,
+ },
+ [0x1881B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1881B,
+ },
+ [0x1881C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1881C,
+ },
+ [0x1881D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1881D,
+ },
+ [0x1881E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1881E,
+ },
+ [0x1881F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1881F,
+ },
+ [0x18820]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18820,
+ },
+ [0x18821]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18821,
+ },
+ [0x18822]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18822,
+ },
+ [0x18823]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18823,
+ },
+ [0x18824]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18824,
+ },
+ [0x18825]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18825,
+ },
+ [0x18826]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18826,
+ },
+ [0x18827]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18827,
+ },
+ [0x18828]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18828,
+ },
+ [0x18829]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18829,
+ },
+ [0x1882A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1882A,
+ },
+ [0x1882B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1882B,
+ },
+ [0x1882C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1882C,
+ },
+ [0x1882D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1882D,
+ },
+ [0x1882E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1882E,
+ },
+ [0x1882F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1882F,
+ },
+ [0x18830]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18830,
+ },
+ [0x18831]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18831,
+ },
+ [0x18832]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18832,
+ },
+ [0x18833]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18833,
+ },
+ [0x18834]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18834,
+ },
+ [0x18835]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18835,
+ },
+ [0x18836]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18836,
+ },
+ [0x18837]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18837,
+ },
+ [0x18838]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18838,
+ },
+ [0x18839]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18839,
+ },
+ [0x1883A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1883A,
+ },
+ [0x1883B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1883B,
+ },
+ [0x1883C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1883C,
+ },
+ [0x1883D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1883D,
+ },
+ [0x1883E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1883E,
+ },
+ [0x1883F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1883F,
+ },
+ [0x18840]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18840,
+ },
+ [0x18841]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18841,
+ },
+ [0x18842]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18842,
+ },
+ [0x18843]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18843,
+ },
+ [0x18844]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18844,
+ },
+ [0x18845]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18845,
+ },
+ [0x18846]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18846,
+ },
+ [0x18847]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18847,
+ },
+ [0x18848]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18848,
+ },
+ [0x18849]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18849,
+ },
+ [0x1884A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1884A,
+ },
+ [0x1884B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1884B,
+ },
+ [0x1884C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1884C,
+ },
+ [0x1884D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1884D,
+ },
+ [0x1884E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1884E,
+ },
+ [0x1884F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1884F,
+ },
+ [0x18850]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18850,
+ },
+ [0x18851]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18851,
+ },
+ [0x18852]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18852,
+ },
+ [0x18853]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18853,
+ },
+ [0x18854]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18854,
+ },
+ [0x18855]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18855,
+ },
+ [0x18856]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18856,
+ },
+ [0x18857]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18857,
+ },
+ [0x18858]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18858,
+ },
+ [0x18859]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18859,
+ },
+ [0x1885A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1885A,
+ },
+ [0x1885B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1885B,
+ },
+ [0x1885C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1885C,
+ },
+ [0x1885D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1885D,
+ },
+ [0x1885E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1885E,
+ },
+ [0x1885F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1885F,
+ },
+ [0x18860]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18860,
+ },
+ [0x18861]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18861,
+ },
+ [0x18862]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18862,
+ },
+ [0x18863]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18863,
+ },
+ [0x18864]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18864,
+ },
+ [0x18865]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18865,
+ },
+ [0x18866]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18866,
+ },
+ [0x18867]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18867,
+ },
+ [0x18868]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18868,
+ },
+ [0x18869]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18869,
+ },
+ [0x1886A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1886A,
+ },
+ [0x1886B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1886B,
+ },
+ [0x1886C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1886C,
+ },
+ [0x1886D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1886D,
+ },
+ [0x1886E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1886E,
+ },
+ [0x1886F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1886F,
+ },
+ [0x18870]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18870,
+ },
+ [0x18871]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18871,
+ },
+ [0x18872]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18872,
+ },
+ [0x18873]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18873,
+ },
+ [0x18874]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18874,
+ },
+ [0x18875]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18875,
+ },
+ [0x18876]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18876,
+ },
+ [0x18877]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18877,
+ },
+ [0x18878]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18878,
+ },
+ [0x18879]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18879,
+ },
+ [0x1887A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1887A,
+ },
+ [0x1887B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1887B,
+ },
+ [0x1887C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1887C,
+ },
+ [0x1887D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1887D,
+ },
+ [0x1887E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1887E,
+ },
+ [0x1887F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1887F,
+ },
+ [0x18880]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18880,
+ },
+ [0x18881]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18881,
+ },
+ [0x18882]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18882,
+ },
+ [0x18883]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18883,
+ },
+ [0x18884]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18884,
+ },
+ [0x18885]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18885,
+ },
+ [0x18886]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18886,
+ },
+ [0x18887]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18887,
+ },
+ [0x18888]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18888,
+ },
+ [0x18889]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18889,
+ },
+ [0x1888A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1888A,
+ },
+ [0x1888B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1888B,
+ },
+ [0x1888C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1888C,
+ },
+ [0x1888D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1888D,
+ },
+ [0x1888E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1888E,
+ },
+ [0x1888F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1888F,
+ },
+ [0x18890]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18890,
+ },
+ [0x18891]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18891,
+ },
+ [0x18892]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18892,
+ },
+ [0x18893]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18893,
+ },
+ [0x18894]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18894,
+ },
+ [0x18895]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18895,
+ },
+ [0x18896]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18896,
+ },
+ [0x18897]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18897,
+ },
+ [0x18898]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18898,
+ },
+ [0x18899]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18899,
+ },
+ [0x1889A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1889A,
+ },
+ [0x1889B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1889B,
+ },
+ [0x1889C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1889C,
+ },
+ [0x1889D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1889D,
+ },
+ [0x1889E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1889E,
+ },
+ [0x1889F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1889F,
+ },
+ [0x188A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A0,
+ },
+ [0x188A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A1,
+ },
+ [0x188A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A2,
+ },
+ [0x188A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A3,
+ },
+ [0x188A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A4,
+ },
+ [0x188A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A5,
+ },
+ [0x188A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A6,
+ },
+ [0x188A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A7,
+ },
+ [0x188A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A8,
+ },
+ [0x188A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188A9,
+ },
+ [0x188AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188AA,
+ },
+ [0x188AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188AB,
+ },
+ [0x188AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188AC,
+ },
+ [0x188AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188AD,
+ },
+ [0x188AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188AE,
+ },
+ [0x188AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188AF,
+ },
+ [0x188B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B0,
+ },
+ [0x188B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B1,
+ },
+ [0x188B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B2,
+ },
+ [0x188B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B3,
+ },
+ [0x188B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B4,
+ },
+ [0x188B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B5,
+ },
+ [0x188B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B6,
+ },
+ [0x188B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B7,
+ },
+ [0x188B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B8,
+ },
+ [0x188B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188B9,
+ },
+ [0x188BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188BA,
+ },
+ [0x188BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188BB,
+ },
+ [0x188BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188BC,
+ },
+ [0x188BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188BD,
+ },
+ [0x188BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188BE,
+ },
+ [0x188BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188BF,
+ },
+ [0x188C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C0,
+ },
+ [0x188C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C1,
+ },
+ [0x188C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C2,
+ },
+ [0x188C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C3,
+ },
+ [0x188C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C4,
+ },
+ [0x188C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C5,
+ },
+ [0x188C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C6,
+ },
+ [0x188C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C7,
+ },
+ [0x188C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C8,
+ },
+ [0x188C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188C9,
+ },
+ [0x188CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188CA,
+ },
+ [0x188CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188CB,
+ },
+ [0x188CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188CC,
+ },
+ [0x188CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188CD,
+ },
+ [0x188CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188CE,
+ },
+ [0x188CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188CF,
+ },
+ [0x188D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D0,
+ },
+ [0x188D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D1,
+ },
+ [0x188D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D2,
+ },
+ [0x188D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D3,
+ },
+ [0x188D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D4,
+ },
+ [0x188D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D5,
+ },
+ [0x188D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D6,
+ },
+ [0x188D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D7,
+ },
+ [0x188D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D8,
+ },
+ [0x188D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188D9,
+ },
+ [0x188DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188DA,
+ },
+ [0x188DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188DB,
+ },
+ [0x188DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188DC,
+ },
+ [0x188DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188DD,
+ },
+ [0x188DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188DE,
+ },
+ [0x188DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188DF,
+ },
+ [0x188E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E0,
+ },
+ [0x188E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E1,
+ },
+ [0x188E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E2,
+ },
+ [0x188E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E3,
+ },
+ [0x188E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E4,
+ },
+ [0x188E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E5,
+ },
+ [0x188E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E6,
+ },
+ [0x188E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E7,
+ },
+ [0x188E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E8,
+ },
+ [0x188E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188E9,
+ },
+ [0x188EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188EA,
+ },
+ [0x188EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188EB,
+ },
+ [0x188EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188EC,
+ },
+ [0x188ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188ED,
+ },
+ [0x188EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188EE,
+ },
+ [0x188EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188EF,
+ },
+ [0x188F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F0,
+ },
+ [0x188F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F1,
+ },
+ [0x188F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F2,
+ },
+ [0x188F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F3,
+ },
+ [0x188F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F4,
+ },
+ [0x188F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F5,
+ },
+ [0x188F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F6,
+ },
+ [0x188F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F7,
+ },
+ [0x188F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F8,
+ },
+ [0x188F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188F9,
+ },
+ [0x188FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188FA,
+ },
+ [0x188FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188FB,
+ },
+ [0x188FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188FC,
+ },
+ [0x188FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188FD,
+ },
+ [0x188FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188FE,
+ },
+ [0x188FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x188FF,
+ },
+ [0x18900]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18900,
+ },
+ [0x18901]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18901,
+ },
+ [0x18902]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18902,
+ },
+ [0x18903]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18903,
+ },
+ [0x18904]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18904,
+ },
+ [0x18905]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18905,
+ },
+ [0x18906]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18906,
+ },
+ [0x18907]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18907,
+ },
+ [0x18908]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18908,
+ },
+ [0x18909]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18909,
+ },
+ [0x1890A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1890A,
+ },
+ [0x1890B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1890B,
+ },
+ [0x1890C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1890C,
+ },
+ [0x1890D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1890D,
+ },
+ [0x1890E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1890E,
+ },
+ [0x1890F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1890F,
+ },
+ [0x18910]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18910,
+ },
+ [0x18911]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18911,
+ },
+ [0x18912]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18912,
+ },
+ [0x18913]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18913,
+ },
+ [0x18914]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18914,
+ },
+ [0x18915]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18915,
+ },
+ [0x18916]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18916,
+ },
+ [0x18917]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18917,
+ },
+ [0x18918]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18918,
+ },
+ [0x18919]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18919,
+ },
+ [0x1891A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1891A,
+ },
+ [0x1891B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1891B,
+ },
+ [0x1891C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1891C,
+ },
+ [0x1891D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1891D,
+ },
+ [0x1891E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1891E,
+ },
+ [0x1891F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1891F,
+ },
+ [0x18920]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18920,
+ },
+ [0x18921]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18921,
+ },
+ [0x18922]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18922,
+ },
+ [0x18923]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18923,
+ },
+ [0x18924]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18924,
+ },
+ [0x18925]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18925,
+ },
+ [0x18926]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18926,
+ },
+ [0x18927]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18927,
+ },
+ [0x18928]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18928,
+ },
+ [0x18929]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18929,
+ },
+ [0x1892A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1892A,
+ },
+ [0x1892B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1892B,
+ },
+ [0x1892C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1892C,
+ },
+ [0x1892D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1892D,
+ },
+ [0x1892E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1892E,
+ },
+ [0x1892F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1892F,
+ },
+ [0x18930]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18930,
+ },
+ [0x18931]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18931,
+ },
+ [0x18932]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18932,
+ },
+ [0x18933]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18933,
+ },
+ [0x18934]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18934,
+ },
+ [0x18935]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18935,
+ },
+ [0x18936]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18936,
+ },
+ [0x18937]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18937,
+ },
+ [0x18938]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18938,
+ },
+ [0x18939]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18939,
+ },
+ [0x1893A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1893A,
+ },
+ [0x1893B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1893B,
+ },
+ [0x1893C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1893C,
+ },
+ [0x1893D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1893D,
+ },
+ [0x1893E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1893E,
+ },
+ [0x1893F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1893F,
+ },
+ [0x18940]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18940,
+ },
+ [0x18941]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18941,
+ },
+ [0x18942]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18942,
+ },
+ [0x18943]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18943,
+ },
+ [0x18944]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18944,
+ },
+ [0x18945]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18945,
+ },
+ [0x18946]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18946,
+ },
+ [0x18947]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18947,
+ },
+ [0x18948]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18948,
+ },
+ [0x18949]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18949,
+ },
+ [0x1894A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1894A,
+ },
+ [0x1894B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1894B,
+ },
+ [0x1894C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1894C,
+ },
+ [0x1894D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1894D,
+ },
+ [0x1894E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1894E,
+ },
+ [0x1894F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1894F,
+ },
+ [0x18950]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18950,
+ },
+ [0x18951]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18951,
+ },
+ [0x18952]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18952,
+ },
+ [0x18953]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18953,
+ },
+ [0x18954]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18954,
+ },
+ [0x18955]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18955,
+ },
+ [0x18956]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18956,
+ },
+ [0x18957]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18957,
+ },
+ [0x18958]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18958,
+ },
+ [0x18959]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18959,
+ },
+ [0x1895A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1895A,
+ },
+ [0x1895B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1895B,
+ },
+ [0x1895C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1895C,
+ },
+ [0x1895D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1895D,
+ },
+ [0x1895E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1895E,
+ },
+ [0x1895F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1895F,
+ },
+ [0x18960]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18960,
+ },
+ [0x18961]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18961,
+ },
+ [0x18962]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18962,
+ },
+ [0x18963]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18963,
+ },
+ [0x18964]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18964,
+ },
+ [0x18965]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18965,
+ },
+ [0x18966]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18966,
+ },
+ [0x18967]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18967,
+ },
+ [0x18968]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18968,
+ },
+ [0x18969]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18969,
+ },
+ [0x1896A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1896A,
+ },
+ [0x1896B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1896B,
+ },
+ [0x1896C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1896C,
+ },
+ [0x1896D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1896D,
+ },
+ [0x1896E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1896E,
+ },
+ [0x1896F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1896F,
+ },
+ [0x18970]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18970,
+ },
+ [0x18971]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18971,
+ },
+ [0x18972]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18972,
+ },
+ [0x18973]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18973,
+ },
+ [0x18974]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18974,
+ },
+ [0x18975]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18975,
+ },
+ [0x18976]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18976,
+ },
+ [0x18977]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18977,
+ },
+ [0x18978]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18978,
+ },
+ [0x18979]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18979,
+ },
+ [0x1897A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1897A,
+ },
+ [0x1897B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1897B,
+ },
+ [0x1897C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1897C,
+ },
+ [0x1897D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1897D,
+ },
+ [0x1897E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1897E,
+ },
+ [0x1897F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1897F,
+ },
+ [0x18980]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18980,
+ },
+ [0x18981]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18981,
+ },
+ [0x18982]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18982,
+ },
+ [0x18983]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18983,
+ },
+ [0x18984]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18984,
+ },
+ [0x18985]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18985,
+ },
+ [0x18986]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18986,
+ },
+ [0x18987]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18987,
+ },
+ [0x18988]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18988,
+ },
+ [0x18989]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18989,
+ },
+ [0x1898A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1898A,
+ },
+ [0x1898B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1898B,
+ },
+ [0x1898C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1898C,
+ },
+ [0x1898D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1898D,
+ },
+ [0x1898E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1898E,
+ },
+ [0x1898F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1898F,
+ },
+ [0x18990]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18990,
+ },
+ [0x18991]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18991,
+ },
+ [0x18992]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18992,
+ },
+ [0x18993]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18993,
+ },
+ [0x18994]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18994,
+ },
+ [0x18995]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18995,
+ },
+ [0x18996]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18996,
+ },
+ [0x18997]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18997,
+ },
+ [0x18998]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18998,
+ },
+ [0x18999]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18999,
+ },
+ [0x1899A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1899A,
+ },
+ [0x1899B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1899B,
+ },
+ [0x1899C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1899C,
+ },
+ [0x1899D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1899D,
+ },
+ [0x1899E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1899E,
+ },
+ [0x1899F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1899F,
+ },
+ [0x189A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A0,
+ },
+ [0x189A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A1,
+ },
+ [0x189A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A2,
+ },
+ [0x189A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A3,
+ },
+ [0x189A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A4,
+ },
+ [0x189A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A5,
+ },
+ [0x189A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A6,
+ },
+ [0x189A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A7,
+ },
+ [0x189A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A8,
+ },
+ [0x189A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189A9,
+ },
+ [0x189AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189AA,
+ },
+ [0x189AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189AB,
+ },
+ [0x189AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189AC,
+ },
+ [0x189AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189AD,
+ },
+ [0x189AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189AE,
+ },
+ [0x189AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189AF,
+ },
+ [0x189B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B0,
+ },
+ [0x189B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B1,
+ },
+ [0x189B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B2,
+ },
+ [0x189B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B3,
+ },
+ [0x189B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B4,
+ },
+ [0x189B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B5,
+ },
+ [0x189B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B6,
+ },
+ [0x189B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B7,
+ },
+ [0x189B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B8,
+ },
+ [0x189B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189B9,
+ },
+ [0x189BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189BA,
+ },
+ [0x189BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189BB,
+ },
+ [0x189BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189BC,
+ },
+ [0x189BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189BD,
+ },
+ [0x189BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189BE,
+ },
+ [0x189BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189BF,
+ },
+ [0x189C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C0,
+ },
+ [0x189C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C1,
+ },
+ [0x189C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C2,
+ },
+ [0x189C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C3,
+ },
+ [0x189C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C4,
+ },
+ [0x189C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C5,
+ },
+ [0x189C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C6,
+ },
+ [0x189C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C7,
+ },
+ [0x189C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C8,
+ },
+ [0x189C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189C9,
+ },
+ [0x189CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189CA,
+ },
+ [0x189CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189CB,
+ },
+ [0x189CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189CC,
+ },
+ [0x189CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189CD,
+ },
+ [0x189CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189CE,
+ },
+ [0x189CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189CF,
+ },
+ [0x189D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D0,
+ },
+ [0x189D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D1,
+ },
+ [0x189D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D2,
+ },
+ [0x189D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D3,
+ },
+ [0x189D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D4,
+ },
+ [0x189D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D5,
+ },
+ [0x189D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D6,
+ },
+ [0x189D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D7,
+ },
+ [0x189D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D8,
+ },
+ [0x189D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189D9,
+ },
+ [0x189DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189DA,
+ },
+ [0x189DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189DB,
+ },
+ [0x189DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189DC,
+ },
+ [0x189DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189DD,
+ },
+ [0x189DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189DE,
+ },
+ [0x189DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189DF,
+ },
+ [0x189E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E0,
+ },
+ [0x189E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E1,
+ },
+ [0x189E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E2,
+ },
+ [0x189E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E3,
+ },
+ [0x189E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E4,
+ },
+ [0x189E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E5,
+ },
+ [0x189E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E6,
+ },
+ [0x189E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E7,
+ },
+ [0x189E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E8,
+ },
+ [0x189E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189E9,
+ },
+ [0x189EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189EA,
+ },
+ [0x189EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189EB,
+ },
+ [0x189EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189EC,
+ },
+ [0x189ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189ED,
+ },
+ [0x189EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189EE,
+ },
+ [0x189EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189EF,
+ },
+ [0x189F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F0,
+ },
+ [0x189F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F1,
+ },
+ [0x189F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F2,
+ },
+ [0x189F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F3,
+ },
+ [0x189F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F4,
+ },
+ [0x189F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F5,
+ },
+ [0x189F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F6,
+ },
+ [0x189F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F7,
+ },
+ [0x189F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F8,
+ },
+ [0x189F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189F9,
+ },
+ [0x189FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189FA,
+ },
+ [0x189FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189FB,
+ },
+ [0x189FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189FC,
+ },
+ [0x189FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189FD,
+ },
+ [0x189FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189FE,
+ },
+ [0x189FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x189FF,
+ },
+ [0x18A00]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A00,
+ },
+ [0x18A01]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A01,
+ },
+ [0x18A02]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A02,
+ },
+ [0x18A03]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A03,
+ },
+ [0x18A04]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A04,
+ },
+ [0x18A05]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A05,
+ },
+ [0x18A06]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A06,
+ },
+ [0x18A07]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A07,
+ },
+ [0x18A08]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A08,
+ },
+ [0x18A09]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A09,
+ },
+ [0x18A0A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A0A,
+ },
+ [0x18A0B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A0B,
+ },
+ [0x18A0C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A0C,
+ },
+ [0x18A0D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A0D,
+ },
+ [0x18A0E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A0E,
+ },
+ [0x18A0F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A0F,
+ },
+ [0x18A10]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A10,
+ },
+ [0x18A11]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A11,
+ },
+ [0x18A12]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A12,
+ },
+ [0x18A13]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A13,
+ },
+ [0x18A14]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A14,
+ },
+ [0x18A15]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A15,
+ },
+ [0x18A16]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A16,
+ },
+ [0x18A17]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A17,
+ },
+ [0x18A18]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A18,
+ },
+ [0x18A19]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A19,
+ },
+ [0x18A1A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A1A,
+ },
+ [0x18A1B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A1B,
+ },
+ [0x18A1C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A1C,
+ },
+ [0x18A1D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A1D,
+ },
+ [0x18A1E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A1E,
+ },
+ [0x18A1F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A1F,
+ },
+ [0x18A20]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A20,
+ },
+ [0x18A21]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A21,
+ },
+ [0x18A22]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A22,
+ },
+ [0x18A23]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A23,
+ },
+ [0x18A24]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A24,
+ },
+ [0x18A25]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A25,
+ },
+ [0x18A26]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A26,
+ },
+ [0x18A27]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A27,
+ },
+ [0x18A28]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A28,
+ },
+ [0x18A29]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A29,
+ },
+ [0x18A2A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A2A,
+ },
+ [0x18A2B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A2B,
+ },
+ [0x18A2C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A2C,
+ },
+ [0x18A2D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A2D,
+ },
+ [0x18A2E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A2E,
+ },
+ [0x18A2F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A2F,
+ },
+ [0x18A30]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A30,
+ },
+ [0x18A31]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A31,
+ },
+ [0x18A32]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A32,
+ },
+ [0x18A33]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A33,
+ },
+ [0x18A34]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A34,
+ },
+ [0x18A35]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A35,
+ },
+ [0x18A36]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A36,
+ },
+ [0x18A37]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A37,
+ },
+ [0x18A38]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A38,
+ },
+ [0x18A39]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A39,
+ },
+ [0x18A3A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A3A,
+ },
+ [0x18A3B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A3B,
+ },
+ [0x18A3C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A3C,
+ },
+ [0x18A3D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A3D,
+ },
+ [0x18A3E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A3E,
+ },
+ [0x18A3F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A3F,
+ },
+ [0x18A40]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A40,
+ },
+ [0x18A41]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A41,
+ },
+ [0x18A42]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A42,
+ },
+ [0x18A43]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A43,
+ },
+ [0x18A44]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A44,
+ },
+ [0x18A45]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A45,
+ },
+ [0x18A46]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A46,
+ },
+ [0x18A47]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A47,
+ },
+ [0x18A48]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A48,
+ },
+ [0x18A49]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A49,
+ },
+ [0x18A4A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A4A,
+ },
+ [0x18A4B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A4B,
+ },
+ [0x18A4C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A4C,
+ },
+ [0x18A4D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A4D,
+ },
+ [0x18A4E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A4E,
+ },
+ [0x18A4F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A4F,
+ },
+ [0x18A50]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A50,
+ },
+ [0x18A51]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A51,
+ },
+ [0x18A52]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A52,
+ },
+ [0x18A53]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A53,
+ },
+ [0x18A54]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A54,
+ },
+ [0x18A55]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A55,
+ },
+ [0x18A56]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A56,
+ },
+ [0x18A57]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A57,
+ },
+ [0x18A58]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A58,
+ },
+ [0x18A59]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A59,
+ },
+ [0x18A5A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A5A,
+ },
+ [0x18A5B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A5B,
+ },
+ [0x18A5C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A5C,
+ },
+ [0x18A5D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A5D,
+ },
+ [0x18A5E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A5E,
+ },
+ [0x18A5F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A5F,
+ },
+ [0x18A60]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A60,
+ },
+ [0x18A61]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A61,
+ },
+ [0x18A62]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A62,
+ },
+ [0x18A63]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A63,
+ },
+ [0x18A64]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A64,
+ },
+ [0x18A65]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A65,
+ },
+ [0x18A66]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A66,
+ },
+ [0x18A67]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A67,
+ },
+ [0x18A68]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A68,
+ },
+ [0x18A69]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A69,
+ },
+ [0x18A6A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A6A,
+ },
+ [0x18A6B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A6B,
+ },
+ [0x18A6C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A6C,
+ },
+ [0x18A6D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A6D,
+ },
+ [0x18A6E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A6E,
+ },
+ [0x18A6F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A6F,
+ },
+ [0x18A70]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A70,
+ },
+ [0x18A71]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A71,
+ },
+ [0x18A72]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A72,
+ },
+ [0x18A73]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A73,
+ },
+ [0x18A74]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A74,
+ },
+ [0x18A75]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A75,
+ },
+ [0x18A76]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A76,
+ },
+ [0x18A77]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A77,
+ },
+ [0x18A78]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A78,
+ },
+ [0x18A79]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A79,
+ },
+ [0x18A7A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A7A,
+ },
+ [0x18A7B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A7B,
+ },
+ [0x18A7C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A7C,
+ },
+ [0x18A7D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A7D,
+ },
+ [0x18A7E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A7E,
+ },
+ [0x18A7F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A7F,
+ },
+ [0x18A80]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A80,
+ },
+ [0x18A81]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A81,
+ },
+ [0x18A82]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A82,
+ },
+ [0x18A83]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A83,
+ },
+ [0x18A84]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A84,
+ },
+ [0x18A85]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A85,
+ },
+ [0x18A86]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A86,
+ },
+ [0x18A87]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A87,
+ },
+ [0x18A88]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A88,
+ },
+ [0x18A89]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A89,
+ },
+ [0x18A8A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A8A,
+ },
+ [0x18A8B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A8B,
+ },
+ [0x18A8C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A8C,
+ },
+ [0x18A8D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A8D,
+ },
+ [0x18A8E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A8E,
+ },
+ [0x18A8F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A8F,
+ },
+ [0x18A90]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A90,
+ },
+ [0x18A91]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A91,
+ },
+ [0x18A92]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A92,
+ },
+ [0x18A93]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A93,
+ },
+ [0x18A94]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A94,
+ },
+ [0x18A95]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A95,
+ },
+ [0x18A96]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A96,
+ },
+ [0x18A97]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A97,
+ },
+ [0x18A98]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A98,
+ },
+ [0x18A99]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A99,
+ },
+ [0x18A9A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A9A,
+ },
+ [0x18A9B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A9B,
+ },
+ [0x18A9C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A9C,
+ },
+ [0x18A9D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A9D,
+ },
+ [0x18A9E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A9E,
+ },
+ [0x18A9F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18A9F,
+ },
+ [0x18AA0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA0,
+ },
+ [0x18AA1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA1,
+ },
+ [0x18AA2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA2,
+ },
+ [0x18AA3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA3,
+ },
+ [0x18AA4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA4,
+ },
+ [0x18AA5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA5,
+ },
+ [0x18AA6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA6,
+ },
+ [0x18AA7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA7,
+ },
+ [0x18AA8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA8,
+ },
+ [0x18AA9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AA9,
+ },
+ [0x18AAA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AAA,
+ },
+ [0x18AAB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AAB,
+ },
+ [0x18AAC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AAC,
+ },
+ [0x18AAD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AAD,
+ },
+ [0x18AAE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AAE,
+ },
+ [0x18AAF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AAF,
+ },
+ [0x18AB0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB0,
+ },
+ [0x18AB1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB1,
+ },
+ [0x18AB2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB2,
+ },
+ [0x18AB3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB3,
+ },
+ [0x18AB4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB4,
+ },
+ [0x18AB5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB5,
+ },
+ [0x18AB6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB6,
+ },
+ [0x18AB7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB7,
+ },
+ [0x18AB8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB8,
+ },
+ [0x18AB9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AB9,
+ },
+ [0x18ABA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ABA,
+ },
+ [0x18ABB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ABB,
+ },
+ [0x18ABC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ABC,
+ },
+ [0x18ABD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ABD,
+ },
+ [0x18ABE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ABE,
+ },
+ [0x18ABF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ABF,
+ },
+ [0x18AC0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC0,
+ },
+ [0x18AC1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC1,
+ },
+ [0x18AC2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC2,
+ },
+ [0x18AC3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC3,
+ },
+ [0x18AC4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC4,
+ },
+ [0x18AC5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC5,
+ },
+ [0x18AC6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC6,
+ },
+ [0x18AC7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC7,
+ },
+ [0x18AC8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC8,
+ },
+ [0x18AC9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AC9,
+ },
+ [0x18ACA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ACA,
+ },
+ [0x18ACB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ACB,
+ },
+ [0x18ACC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ACC,
+ },
+ [0x18ACD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ACD,
+ },
+ [0x18ACE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ACE,
+ },
+ [0x18ACF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ACF,
+ },
+ [0x18AD0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD0,
+ },
+ [0x18AD1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD1,
+ },
+ [0x18AD2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD2,
+ },
+ [0x18AD3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD3,
+ },
+ [0x18AD4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD4,
+ },
+ [0x18AD5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD5,
+ },
+ [0x18AD6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD6,
+ },
+ [0x18AD7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD7,
+ },
+ [0x18AD8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD8,
+ },
+ [0x18AD9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AD9,
+ },
+ [0x18ADA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ADA,
+ },
+ [0x18ADB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ADB,
+ },
+ [0x18ADC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ADC,
+ },
+ [0x18ADD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ADD,
+ },
+ [0x18ADE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ADE,
+ },
+ [0x18ADF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18ADF,
+ },
+ [0x18AE0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE0,
+ },
+ [0x18AE1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE1,
+ },
+ [0x18AE2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE2,
+ },
+ [0x18AE3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE3,
+ },
+ [0x18AE4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE4,
+ },
+ [0x18AE5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE5,
+ },
+ [0x18AE6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE6,
+ },
+ [0x18AE7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE7,
+ },
+ [0x18AE8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE8,
+ },
+ [0x18AE9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AE9,
+ },
+ [0x18AEA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AEA,
+ },
+ [0x18AEB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AEB,
+ },
+ [0x18AEC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AEC,
+ },
+ [0x18AED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AED,
+ },
+ [0x18AEE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AEE,
+ },
+ [0x18AEF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AEF,
+ },
+ [0x18AF0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AF0,
+ },
+ [0x18AF1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AF1,
+ },
+ [0x18AF2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x18AF2,
+ },
+ [0x1B000]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B000,
+ },
+ [0x1B001]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B001,
+ },
+ [0x1B002]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B002,
+ },
+ [0x1B003]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B003,
+ },
+ [0x1B004]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B004,
+ },
+ [0x1B005]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B005,
+ },
+ [0x1B006]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B006,
+ },
+ [0x1B007]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B007,
+ },
+ [0x1B008]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B008,
+ },
+ [0x1B009]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B009,
+ },
+ [0x1B00A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B00A,
+ },
+ [0x1B00B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B00B,
+ },
+ [0x1B00C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B00C,
+ },
+ [0x1B00D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B00D,
+ },
+ [0x1B00E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B00E,
+ },
+ [0x1B00F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B00F,
+ },
+ [0x1B010]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B010,
+ },
+ [0x1B011]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B011,
+ },
+ [0x1B012]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B012,
+ },
+ [0x1B013]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B013,
+ },
+ [0x1B014]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B014,
+ },
+ [0x1B015]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B015,
+ },
+ [0x1B016]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B016,
+ },
+ [0x1B017]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B017,
+ },
+ [0x1B018]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B018,
+ },
+ [0x1B019]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B019,
+ },
+ [0x1B01A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B01A,
+ },
+ [0x1B01B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B01B,
+ },
+ [0x1B01C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B01C,
+ },
+ [0x1B01D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B01D,
+ },
+ [0x1B01E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B01E,
+ },
+ [0x1B01F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B01F,
+ },
+ [0x1B020]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B020,
+ },
+ [0x1B021]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B021,
+ },
+ [0x1B022]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B022,
+ },
+ [0x1B023]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B023,
+ },
+ [0x1B024]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B024,
+ },
+ [0x1B025]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B025,
+ },
+ [0x1B026]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B026,
+ },
+ [0x1B027]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B027,
+ },
+ [0x1B028]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B028,
+ },
+ [0x1B029]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B029,
+ },
+ [0x1B02A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B02A,
+ },
+ [0x1B02B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B02B,
+ },
+ [0x1B02C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B02C,
+ },
+ [0x1B02D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B02D,
+ },
+ [0x1B02E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B02E,
+ },
+ [0x1B02F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B02F,
+ },
+ [0x1B030]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B030,
+ },
+ [0x1B031]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B031,
+ },
+ [0x1B032]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B032,
+ },
+ [0x1B033]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B033,
+ },
+ [0x1B034]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B034,
+ },
+ [0x1B035]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B035,
+ },
+ [0x1B036]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B036,
+ },
+ [0x1B037]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B037,
+ },
+ [0x1B038]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B038,
+ },
+ [0x1B039]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B039,
+ },
+ [0x1B03A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B03A,
+ },
+ [0x1B03B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B03B,
+ },
+ [0x1B03C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B03C,
+ },
+ [0x1B03D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B03D,
+ },
+ [0x1B03E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B03E,
+ },
+ [0x1B03F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B03F,
+ },
+ [0x1B040]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B040,
+ },
+ [0x1B041]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B041,
+ },
+ [0x1B042]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B042,
+ },
+ [0x1B043]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B043,
+ },
+ [0x1B044]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B044,
+ },
+ [0x1B045]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B045,
+ },
+ [0x1B046]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B046,
+ },
+ [0x1B047]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B047,
+ },
+ [0x1B048]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B048,
+ },
+ [0x1B049]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B049,
+ },
+ [0x1B04A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B04A,
+ },
+ [0x1B04B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B04B,
+ },
+ [0x1B04C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B04C,
+ },
+ [0x1B04D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B04D,
+ },
+ [0x1B04E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B04E,
+ },
+ [0x1B04F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B04F,
+ },
+ [0x1B050]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B050,
+ },
+ [0x1B051]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B051,
+ },
+ [0x1B052]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B052,
+ },
+ [0x1B053]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B053,
+ },
+ [0x1B054]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B054,
+ },
+ [0x1B055]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B055,
+ },
+ [0x1B056]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B056,
+ },
+ [0x1B057]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B057,
+ },
+ [0x1B058]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B058,
+ },
+ [0x1B059]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B059,
+ },
+ [0x1B05A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B05A,
+ },
+ [0x1B05B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B05B,
+ },
+ [0x1B05C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B05C,
+ },
+ [0x1B05D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B05D,
+ },
+ [0x1B05E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B05E,
+ },
+ [0x1B05F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B05F,
+ },
+ [0x1B060]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B060,
+ },
+ [0x1B061]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B061,
+ },
+ [0x1B062]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B062,
+ },
+ [0x1B063]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B063,
+ },
+ [0x1B064]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B064,
+ },
+ [0x1B065]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B065,
+ },
+ [0x1B066]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B066,
+ },
+ [0x1B067]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B067,
+ },
+ [0x1B068]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B068,
+ },
+ [0x1B069]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B069,
+ },
+ [0x1B06A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B06A,
+ },
+ [0x1B06B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B06B,
+ },
+ [0x1B06C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B06C,
+ },
+ [0x1B06D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B06D,
+ },
+ [0x1B06E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B06E,
+ },
+ [0x1B06F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B06F,
+ },
+ [0x1B070]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B070,
+ },
+ [0x1B071]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B071,
+ },
+ [0x1B072]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B072,
+ },
+ [0x1B073]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B073,
+ },
+ [0x1B074]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B074,
+ },
+ [0x1B075]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B075,
+ },
+ [0x1B076]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B076,
+ },
+ [0x1B077]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B077,
+ },
+ [0x1B078]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B078,
+ },
+ [0x1B079]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B079,
+ },
+ [0x1B07A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B07A,
+ },
+ [0x1B07B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B07B,
+ },
+ [0x1B07C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B07C,
+ },
+ [0x1B07D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B07D,
+ },
+ [0x1B07E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B07E,
+ },
+ [0x1B07F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B07F,
+ },
+ [0x1B080]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B080,
+ },
+ [0x1B081]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B081,
+ },
+ [0x1B082]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B082,
+ },
+ [0x1B083]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B083,
+ },
+ [0x1B084]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B084,
+ },
+ [0x1B085]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B085,
+ },
+ [0x1B086]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B086,
+ },
+ [0x1B087]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B087,
+ },
+ [0x1B088]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B088,
+ },
+ [0x1B089]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B089,
+ },
+ [0x1B08A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B08A,
+ },
+ [0x1B08B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B08B,
+ },
+ [0x1B08C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B08C,
+ },
+ [0x1B08D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B08D,
+ },
+ [0x1B08E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B08E,
+ },
+ [0x1B08F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B08F,
+ },
+ [0x1B090]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B090,
+ },
+ [0x1B091]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B091,
+ },
+ [0x1B092]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B092,
+ },
+ [0x1B093]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B093,
+ },
+ [0x1B094]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B094,
+ },
+ [0x1B095]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B095,
+ },
+ [0x1B096]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B096,
+ },
+ [0x1B097]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B097,
+ },
+ [0x1B098]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B098,
+ },
+ [0x1B099]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B099,
+ },
+ [0x1B09A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B09A,
+ },
+ [0x1B09B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B09B,
+ },
+ [0x1B09C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B09C,
+ },
+ [0x1B09D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B09D,
+ },
+ [0x1B09E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B09E,
+ },
+ [0x1B09F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B09F,
+ },
+ [0x1B0A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A0,
+ },
+ [0x1B0A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A1,
+ },
+ [0x1B0A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A2,
+ },
+ [0x1B0A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A3,
+ },
+ [0x1B0A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A4,
+ },
+ [0x1B0A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A5,
+ },
+ [0x1B0A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A6,
+ },
+ [0x1B0A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A7,
+ },
+ [0x1B0A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A8,
+ },
+ [0x1B0A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0A9,
+ },
+ [0x1B0AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0AA,
+ },
+ [0x1B0AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0AB,
+ },
+ [0x1B0AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0AC,
+ },
+ [0x1B0AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0AD,
+ },
+ [0x1B0AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0AE,
+ },
+ [0x1B0AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0AF,
+ },
+ [0x1B0B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B0,
+ },
+ [0x1B0B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B1,
+ },
+ [0x1B0B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B2,
+ },
+ [0x1B0B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B3,
+ },
+ [0x1B0B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B4,
+ },
+ [0x1B0B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B5,
+ },
+ [0x1B0B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B6,
+ },
+ [0x1B0B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B7,
+ },
+ [0x1B0B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B8,
+ },
+ [0x1B0B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0B9,
+ },
+ [0x1B0BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0BA,
+ },
+ [0x1B0BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0BB,
+ },
+ [0x1B0BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0BC,
+ },
+ [0x1B0BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0BD,
+ },
+ [0x1B0BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0BE,
+ },
+ [0x1B0BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0BF,
+ },
+ [0x1B0C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C0,
+ },
+ [0x1B0C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C1,
+ },
+ [0x1B0C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C2,
+ },
+ [0x1B0C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C3,
+ },
+ [0x1B0C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C4,
+ },
+ [0x1B0C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C5,
+ },
+ [0x1B0C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C6,
+ },
+ [0x1B0C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C7,
+ },
+ [0x1B0C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C8,
+ },
+ [0x1B0C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0C9,
+ },
+ [0x1B0CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0CA,
+ },
+ [0x1B0CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0CB,
+ },
+ [0x1B0CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0CC,
+ },
+ [0x1B0CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0CD,
+ },
+ [0x1B0CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0CE,
+ },
+ [0x1B0CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0CF,
+ },
+ [0x1B0D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D0,
+ },
+ [0x1B0D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D1,
+ },
+ [0x1B0D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D2,
+ },
+ [0x1B0D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D3,
+ },
+ [0x1B0D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D4,
+ },
+ [0x1B0D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D5,
+ },
+ [0x1B0D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D6,
+ },
+ [0x1B0D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D7,
+ },
+ [0x1B0D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D8,
+ },
+ [0x1B0D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0D9,
+ },
+ [0x1B0DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0DA,
+ },
+ [0x1B0DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0DB,
+ },
+ [0x1B0DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0DC,
+ },
+ [0x1B0DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0DD,
+ },
+ [0x1B0DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0DE,
+ },
+ [0x1B0DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0DF,
+ },
+ [0x1B0E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E0,
+ },
+ [0x1B0E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E1,
+ },
+ [0x1B0E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E2,
+ },
+ [0x1B0E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E3,
+ },
+ [0x1B0E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E4,
+ },
+ [0x1B0E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E5,
+ },
+ [0x1B0E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E6,
+ },
+ [0x1B0E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E7,
+ },
+ [0x1B0E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E8,
+ },
+ [0x1B0E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0E9,
+ },
+ [0x1B0EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0EA,
+ },
+ [0x1B0EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0EB,
+ },
+ [0x1B0EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0EC,
+ },
+ [0x1B0ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0ED,
+ },
+ [0x1B0EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0EE,
+ },
+ [0x1B0EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0EF,
+ },
+ [0x1B0F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F0,
+ },
+ [0x1B0F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F1,
+ },
+ [0x1B0F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F2,
+ },
+ [0x1B0F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F3,
+ },
+ [0x1B0F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F4,
+ },
+ [0x1B0F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F5,
+ },
+ [0x1B0F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F6,
+ },
+ [0x1B0F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F7,
+ },
+ [0x1B0F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F8,
+ },
+ [0x1B0F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0F9,
+ },
+ [0x1B0FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0FA,
+ },
+ [0x1B0FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0FB,
+ },
+ [0x1B0FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0FC,
+ },
+ [0x1B0FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0FD,
+ },
+ [0x1B0FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0FE,
+ },
+ [0x1B0FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B0FF,
+ },
+ [0x1B100]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B100,
+ },
+ [0x1B101]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B101,
+ },
+ [0x1B102]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B102,
+ },
+ [0x1B103]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B103,
+ },
+ [0x1B104]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B104,
+ },
+ [0x1B105]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B105,
+ },
+ [0x1B106]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B106,
+ },
+ [0x1B107]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B107,
+ },
+ [0x1B108]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B108,
+ },
+ [0x1B109]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B109,
+ },
+ [0x1B10A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B10A,
+ },
+ [0x1B10B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B10B,
+ },
+ [0x1B10C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B10C,
+ },
+ [0x1B10D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B10D,
+ },
+ [0x1B10E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B10E,
+ },
+ [0x1B10F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B10F,
+ },
+ [0x1B110]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B110,
+ },
+ [0x1B111]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B111,
+ },
+ [0x1B112]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B112,
+ },
+ [0x1B113]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B113,
+ },
+ [0x1B114]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B114,
+ },
+ [0x1B115]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B115,
+ },
+ [0x1B116]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B116,
+ },
+ [0x1B117]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B117,
+ },
+ [0x1B118]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B118,
+ },
+ [0x1B119]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B119,
+ },
+ [0x1B11A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B11A,
+ },
+ [0x1B11B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B11B,
+ },
+ [0x1B11C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B11C,
+ },
+ [0x1B11D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B11D,
+ },
+ [0x1B11E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B11E,
+ },
+ [0x1B150]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B150,
+ },
+ [0x1B151]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B151,
+ },
+ [0x1B152]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B152,
+ },
+ [0x1B164]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B164,
+ },
+ [0x1B165]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B165,
+ },
+ [0x1B166]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B166,
+ },
+ [0x1B167]={
+ category="lo",
+ direction="l",
+ linebreak="cj",
+ unicodeslot=0x1B167,
+ },
+ [0x1B170]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B170,
+ },
+ [0x1B171]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B171,
+ },
+ [0x1B172]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B172,
+ },
+ [0x1B173]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B173,
+ },
+ [0x1B174]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B174,
+ },
+ [0x1B175]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B175,
+ },
+ [0x1B176]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B176,
+ },
+ [0x1B177]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B177,
+ },
+ [0x1B178]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B178,
+ },
+ [0x1B179]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B179,
+ },
+ [0x1B17A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B17A,
+ },
+ [0x1B17B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B17B,
+ },
+ [0x1B17C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B17C,
+ },
+ [0x1B17D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B17D,
+ },
+ [0x1B17E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B17E,
+ },
+ [0x1B17F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B17F,
+ },
+ [0x1B180]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B180,
+ },
+ [0x1B181]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B181,
+ },
+ [0x1B182]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B182,
+ },
+ [0x1B183]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B183,
+ },
+ [0x1B184]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B184,
+ },
+ [0x1B185]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B185,
+ },
+ [0x1B186]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B186,
+ },
+ [0x1B187]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B187,
+ },
+ [0x1B188]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B188,
+ },
+ [0x1B189]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B189,
+ },
+ [0x1B18A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B18A,
+ },
+ [0x1B18B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B18B,
+ },
+ [0x1B18C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B18C,
+ },
+ [0x1B18D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B18D,
+ },
+ [0x1B18E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B18E,
+ },
+ [0x1B18F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B18F,
+ },
+ [0x1B190]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B190,
+ },
+ [0x1B191]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B191,
+ },
+ [0x1B192]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B192,
+ },
+ [0x1B193]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B193,
+ },
+ [0x1B194]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B194,
+ },
+ [0x1B195]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B195,
+ },
+ [0x1B196]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B196,
+ },
+ [0x1B197]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B197,
+ },
+ [0x1B198]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B198,
+ },
+ [0x1B199]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B199,
+ },
+ [0x1B19A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B19A,
+ },
+ [0x1B19B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B19B,
+ },
+ [0x1B19C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B19C,
+ },
+ [0x1B19D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B19D,
+ },
+ [0x1B19E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B19E,
+ },
+ [0x1B19F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B19F,
+ },
+ [0x1B1A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A0,
+ },
+ [0x1B1A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A1,
+ },
+ [0x1B1A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A2,
+ },
+ [0x1B1A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A3,
+ },
+ [0x1B1A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A4,
+ },
+ [0x1B1A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A5,
+ },
+ [0x1B1A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A6,
+ },
+ [0x1B1A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A7,
+ },
+ [0x1B1A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A8,
+ },
+ [0x1B1A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1A9,
+ },
+ [0x1B1AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1AA,
+ },
+ [0x1B1AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1AB,
+ },
+ [0x1B1AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1AC,
+ },
+ [0x1B1AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1AD,
+ },
+ [0x1B1AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1AE,
+ },
+ [0x1B1AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1AF,
+ },
+ [0x1B1B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B0,
+ },
+ [0x1B1B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B1,
+ },
+ [0x1B1B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B2,
+ },
+ [0x1B1B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B3,
+ },
+ [0x1B1B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B4,
+ },
+ [0x1B1B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B5,
+ },
+ [0x1B1B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B6,
+ },
+ [0x1B1B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B7,
+ },
+ [0x1B1B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B8,
+ },
+ [0x1B1B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1B9,
+ },
+ [0x1B1BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1BA,
+ },
+ [0x1B1BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1BB,
+ },
+ [0x1B1BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1BC,
+ },
+ [0x1B1BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1BD,
+ },
+ [0x1B1BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1BE,
+ },
+ [0x1B1BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1BF,
+ },
+ [0x1B1C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C0,
+ },
+ [0x1B1C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C1,
+ },
+ [0x1B1C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C2,
+ },
+ [0x1B1C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C3,
+ },
+ [0x1B1C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C4,
+ },
+ [0x1B1C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C5,
+ },
+ [0x1B1C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C6,
+ },
+ [0x1B1C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C7,
+ },
+ [0x1B1C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C8,
+ },
+ [0x1B1C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1C9,
+ },
+ [0x1B1CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1CA,
+ },
+ [0x1B1CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1CB,
+ },
+ [0x1B1CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1CC,
+ },
+ [0x1B1CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1CD,
+ },
+ [0x1B1CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1CE,
+ },
+ [0x1B1CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1CF,
+ },
+ [0x1B1D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D0,
+ },
+ [0x1B1D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D1,
+ },
+ [0x1B1D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D2,
+ },
+ [0x1B1D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D3,
+ },
+ [0x1B1D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D4,
+ },
+ [0x1B1D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D5,
+ },
+ [0x1B1D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D6,
+ },
+ [0x1B1D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D7,
+ },
+ [0x1B1D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D8,
+ },
+ [0x1B1D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1D9,
+ },
+ [0x1B1DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1DA,
+ },
+ [0x1B1DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1DB,
+ },
+ [0x1B1DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1DC,
+ },
+ [0x1B1DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1DD,
+ },
+ [0x1B1DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1DE,
+ },
+ [0x1B1DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1DF,
+ },
+ [0x1B1E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E0,
+ },
+ [0x1B1E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E1,
+ },
+ [0x1B1E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E2,
+ },
+ [0x1B1E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E3,
+ },
+ [0x1B1E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E4,
+ },
+ [0x1B1E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E5,
+ },
+ [0x1B1E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E6,
+ },
+ [0x1B1E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E7,
+ },
+ [0x1B1E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E8,
+ },
+ [0x1B1E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1E9,
+ },
+ [0x1B1EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1EA,
+ },
+ [0x1B1EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1EB,
+ },
+ [0x1B1EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1EC,
+ },
+ [0x1B1ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1ED,
+ },
+ [0x1B1EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1EE,
+ },
+ [0x1B1EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1EF,
+ },
+ [0x1B1F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F0,
+ },
+ [0x1B1F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F1,
+ },
+ [0x1B1F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F2,
+ },
+ [0x1B1F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F3,
+ },
+ [0x1B1F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F4,
+ },
+ [0x1B1F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F5,
+ },
+ [0x1B1F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F6,
+ },
+ [0x1B1F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F7,
+ },
+ [0x1B1F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F8,
+ },
+ [0x1B1F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1F9,
+ },
+ [0x1B1FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1FA,
+ },
+ [0x1B1FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1FB,
+ },
+ [0x1B1FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1FC,
+ },
+ [0x1B1FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1FD,
+ },
+ [0x1B1FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1FE,
+ },
+ [0x1B1FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B1FF,
+ },
+ [0x1B200]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B200,
+ },
+ [0x1B201]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B201,
+ },
+ [0x1B202]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B202,
+ },
+ [0x1B203]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B203,
+ },
+ [0x1B204]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B204,
+ },
+ [0x1B205]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B205,
+ },
+ [0x1B206]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B206,
+ },
+ [0x1B207]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B207,
+ },
+ [0x1B208]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B208,
+ },
+ [0x1B209]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B209,
+ },
+ [0x1B20A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B20A,
+ },
+ [0x1B20B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B20B,
+ },
+ [0x1B20C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B20C,
+ },
+ [0x1B20D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B20D,
+ },
+ [0x1B20E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B20E,
+ },
+ [0x1B20F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B20F,
+ },
+ [0x1B210]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B210,
+ },
+ [0x1B211]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B211,
+ },
+ [0x1B212]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B212,
+ },
+ [0x1B213]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B213,
+ },
+ [0x1B214]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B214,
+ },
+ [0x1B215]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B215,
+ },
+ [0x1B216]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B216,
+ },
+ [0x1B217]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B217,
+ },
+ [0x1B218]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B218,
+ },
+ [0x1B219]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B219,
+ },
+ [0x1B21A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B21A,
+ },
+ [0x1B21B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B21B,
+ },
+ [0x1B21C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B21C,
+ },
+ [0x1B21D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B21D,
+ },
+ [0x1B21E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B21E,
+ },
+ [0x1B21F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B21F,
+ },
+ [0x1B220]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B220,
+ },
+ [0x1B221]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B221,
+ },
+ [0x1B222]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B222,
+ },
+ [0x1B223]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B223,
+ },
+ [0x1B224]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B224,
+ },
+ [0x1B225]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B225,
+ },
+ [0x1B226]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B226,
+ },
+ [0x1B227]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B227,
+ },
+ [0x1B228]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B228,
+ },
+ [0x1B229]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B229,
+ },
+ [0x1B22A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B22A,
+ },
+ [0x1B22B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B22B,
+ },
+ [0x1B22C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B22C,
+ },
+ [0x1B22D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B22D,
+ },
+ [0x1B22E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B22E,
+ },
+ [0x1B22F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B22F,
+ },
+ [0x1B230]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B230,
+ },
+ [0x1B231]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B231,
+ },
+ [0x1B232]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B232,
+ },
+ [0x1B233]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B233,
+ },
+ [0x1B234]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B234,
+ },
+ [0x1B235]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B235,
+ },
+ [0x1B236]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B236,
+ },
+ [0x1B237]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B237,
+ },
+ [0x1B238]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B238,
+ },
+ [0x1B239]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B239,
+ },
+ [0x1B23A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B23A,
+ },
+ [0x1B23B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B23B,
+ },
+ [0x1B23C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B23C,
+ },
+ [0x1B23D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B23D,
+ },
+ [0x1B23E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B23E,
+ },
+ [0x1B23F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B23F,
+ },
+ [0x1B240]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B240,
+ },
+ [0x1B241]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B241,
+ },
+ [0x1B242]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B242,
+ },
+ [0x1B243]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B243,
+ },
+ [0x1B244]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B244,
+ },
+ [0x1B245]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B245,
+ },
+ [0x1B246]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B246,
+ },
+ [0x1B247]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B247,
+ },
+ [0x1B248]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B248,
+ },
+ [0x1B249]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B249,
+ },
+ [0x1B24A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B24A,
+ },
+ [0x1B24B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B24B,
+ },
+ [0x1B24C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B24C,
+ },
+ [0x1B24D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B24D,
+ },
+ [0x1B24E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B24E,
+ },
+ [0x1B24F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B24F,
+ },
+ [0x1B250]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B250,
+ },
+ [0x1B251]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B251,
+ },
+ [0x1B252]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B252,
+ },
+ [0x1B253]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B253,
+ },
+ [0x1B254]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B254,
+ },
+ [0x1B255]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B255,
+ },
+ [0x1B256]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B256,
+ },
+ [0x1B257]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B257,
+ },
+ [0x1B258]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B258,
+ },
+ [0x1B259]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B259,
+ },
+ [0x1B25A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B25A,
+ },
+ [0x1B25B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B25B,
+ },
+ [0x1B25C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B25C,
+ },
+ [0x1B25D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B25D,
+ },
+ [0x1B25E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B25E,
+ },
+ [0x1B25F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B25F,
+ },
+ [0x1B260]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B260,
+ },
+ [0x1B261]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B261,
+ },
+ [0x1B262]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B262,
+ },
+ [0x1B263]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B263,
+ },
+ [0x1B264]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B264,
+ },
+ [0x1B265]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B265,
+ },
+ [0x1B266]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B266,
+ },
+ [0x1B267]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B267,
+ },
+ [0x1B268]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B268,
+ },
+ [0x1B269]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B269,
+ },
+ [0x1B26A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B26A,
+ },
+ [0x1B26B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B26B,
+ },
+ [0x1B26C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B26C,
+ },
+ [0x1B26D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B26D,
+ },
+ [0x1B26E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B26E,
+ },
+ [0x1B26F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B26F,
+ },
+ [0x1B270]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B270,
+ },
+ [0x1B271]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B271,
+ },
+ [0x1B272]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B272,
+ },
+ [0x1B273]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B273,
+ },
+ [0x1B274]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B274,
+ },
+ [0x1B275]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B275,
+ },
+ [0x1B276]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B276,
+ },
+ [0x1B277]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B277,
+ },
+ [0x1B278]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B278,
+ },
+ [0x1B279]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B279,
+ },
+ [0x1B27A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B27A,
+ },
+ [0x1B27B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B27B,
+ },
+ [0x1B27C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B27C,
+ },
+ [0x1B27D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B27D,
+ },
+ [0x1B27E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B27E,
+ },
+ [0x1B27F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B27F,
+ },
+ [0x1B280]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B280,
+ },
+ [0x1B281]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B281,
+ },
+ [0x1B282]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B282,
+ },
+ [0x1B283]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B283,
+ },
+ [0x1B284]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B284,
+ },
+ [0x1B285]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B285,
+ },
+ [0x1B286]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B286,
+ },
+ [0x1B287]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B287,
+ },
+ [0x1B288]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B288,
+ },
+ [0x1B289]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B289,
+ },
+ [0x1B28A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B28A,
+ },
+ [0x1B28B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B28B,
+ },
+ [0x1B28C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B28C,
+ },
+ [0x1B28D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B28D,
+ },
+ [0x1B28E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B28E,
+ },
+ [0x1B28F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B28F,
+ },
+ [0x1B290]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B290,
+ },
+ [0x1B291]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B291,
+ },
+ [0x1B292]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B292,
+ },
+ [0x1B293]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B293,
+ },
+ [0x1B294]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B294,
+ },
+ [0x1B295]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B295,
+ },
+ [0x1B296]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B296,
+ },
+ [0x1B297]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B297,
+ },
+ [0x1B298]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B298,
+ },
+ [0x1B299]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B299,
+ },
+ [0x1B29A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B29A,
+ },
+ [0x1B29B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B29B,
+ },
+ [0x1B29C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B29C,
+ },
+ [0x1B29D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B29D,
+ },
+ [0x1B29E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B29E,
+ },
+ [0x1B29F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B29F,
+ },
+ [0x1B2A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A0,
+ },
+ [0x1B2A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A1,
+ },
+ [0x1B2A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A2,
+ },
+ [0x1B2A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A3,
+ },
+ [0x1B2A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A4,
+ },
+ [0x1B2A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A5,
+ },
+ [0x1B2A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A6,
+ },
+ [0x1B2A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A7,
+ },
+ [0x1B2A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A8,
+ },
+ [0x1B2A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2A9,
+ },
+ [0x1B2AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2AA,
+ },
+ [0x1B2AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2AB,
+ },
+ [0x1B2AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2AC,
+ },
+ [0x1B2AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2AD,
+ },
+ [0x1B2AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2AE,
+ },
+ [0x1B2AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2AF,
+ },
+ [0x1B2B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B0,
+ },
+ [0x1B2B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B1,
+ },
+ [0x1B2B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B2,
+ },
+ [0x1B2B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B3,
+ },
+ [0x1B2B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B4,
+ },
+ [0x1B2B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B5,
+ },
+ [0x1B2B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B6,
+ },
+ [0x1B2B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B7,
+ },
+ [0x1B2B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B8,
+ },
+ [0x1B2B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2B9,
+ },
+ [0x1B2BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2BA,
+ },
+ [0x1B2BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2BB,
+ },
+ [0x1B2BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2BC,
+ },
+ [0x1B2BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2BD,
+ },
+ [0x1B2BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2BE,
+ },
+ [0x1B2BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2BF,
+ },
+ [0x1B2C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C0,
+ },
+ [0x1B2C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C1,
+ },
+ [0x1B2C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C2,
+ },
+ [0x1B2C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C3,
+ },
+ [0x1B2C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C4,
+ },
+ [0x1B2C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C5,
+ },
+ [0x1B2C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C6,
+ },
+ [0x1B2C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C7,
+ },
+ [0x1B2C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C8,
+ },
+ [0x1B2C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2C9,
+ },
+ [0x1B2CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2CA,
+ },
+ [0x1B2CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2CB,
+ },
+ [0x1B2CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2CC,
+ },
+ [0x1B2CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2CD,
+ },
+ [0x1B2CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2CE,
+ },
+ [0x1B2CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2CF,
+ },
+ [0x1B2D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D0,
+ },
+ [0x1B2D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D1,
+ },
+ [0x1B2D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D2,
+ },
+ [0x1B2D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D3,
+ },
+ [0x1B2D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D4,
+ },
+ [0x1B2D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D5,
+ },
+ [0x1B2D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D6,
+ },
+ [0x1B2D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D7,
+ },
+ [0x1B2D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D8,
+ },
+ [0x1B2D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2D9,
+ },
+ [0x1B2DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2DA,
+ },
+ [0x1B2DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2DB,
+ },
+ [0x1B2DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2DC,
+ },
+ [0x1B2DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2DD,
+ },
+ [0x1B2DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2DE,
+ },
+ [0x1B2DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2DF,
+ },
+ [0x1B2E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E0,
+ },
+ [0x1B2E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E1,
+ },
+ [0x1B2E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E2,
+ },
+ [0x1B2E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E3,
+ },
+ [0x1B2E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E4,
+ },
+ [0x1B2E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E5,
+ },
+ [0x1B2E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E6,
+ },
+ [0x1B2E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E7,
+ },
+ [0x1B2E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E8,
+ },
+ [0x1B2E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2E9,
+ },
+ [0x1B2EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2EA,
+ },
+ [0x1B2EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2EB,
+ },
+ [0x1B2EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2EC,
+ },
+ [0x1B2ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2ED,
+ },
+ [0x1B2EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2EE,
+ },
+ [0x1B2EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2EF,
+ },
+ [0x1B2F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F0,
+ },
+ [0x1B2F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F1,
+ },
+ [0x1B2F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F2,
+ },
+ [0x1B2F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F3,
+ },
+ [0x1B2F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F4,
+ },
+ [0x1B2F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F5,
+ },
+ [0x1B2F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F6,
+ },
+ [0x1B2F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F7,
+ },
+ [0x1B2F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F8,
+ },
+ [0x1B2F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2F9,
+ },
+ [0x1B2FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2FA,
+ },
+ [0x1B2FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ unicodeslot=0x1B2FB,
+ },
+ [0x1BC00]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC00,
+ },
+ [0x1BC01]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC01,
+ },
+ [0x1BC02]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC02,
+ },
+ [0x1BC03]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC03,
+ },
+ [0x1BC04]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC04,
+ },
+ [0x1BC05]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC05,
+ },
+ [0x1BC06]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC06,
+ },
+ [0x1BC07]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC07,
+ },
+ [0x1BC08]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC08,
+ },
+ [0x1BC09]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC09,
+ },
+ [0x1BC0A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0A,
+ },
+ [0x1BC0B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0B,
+ },
+ [0x1BC0C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0C,
+ },
+ [0x1BC0D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0D,
+ },
+ [0x1BC0E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0E,
+ },
+ [0x1BC0F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC0F,
+ },
+ [0x1BC10]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC10,
+ },
+ [0x1BC11]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC11,
+ },
+ [0x1BC12]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC12,
+ },
+ [0x1BC13]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC13,
+ },
+ [0x1BC14]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC14,
+ },
+ [0x1BC15]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC15,
+ },
+ [0x1BC16]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC16,
+ },
+ [0x1BC17]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC17,
+ },
+ [0x1BC18]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC18,
+ },
+ [0x1BC19]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC19,
+ },
+ [0x1BC1A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1A,
+ },
+ [0x1BC1B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1B,
+ },
+ [0x1BC1C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1C,
+ },
+ [0x1BC1D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1D,
+ },
+ [0x1BC1E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1E,
+ },
+ [0x1BC1F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC1F,
+ },
+ [0x1BC20]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC20,
+ },
+ [0x1BC21]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC21,
+ },
+ [0x1BC22]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC22,
+ },
+ [0x1BC23]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC23,
+ },
+ [0x1BC24]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC24,
+ },
+ [0x1BC25]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC25,
+ },
+ [0x1BC26]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC26,
+ },
+ [0x1BC27]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC27,
+ },
+ [0x1BC28]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC28,
+ },
+ [0x1BC29]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC29,
+ },
+ [0x1BC2A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2A,
+ },
+ [0x1BC2B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2B,
+ },
+ [0x1BC2C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2C,
+ },
+ [0x1BC2D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2D,
+ },
+ [0x1BC2E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2E,
+ },
+ [0x1BC2F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC2F,
+ },
+ [0x1BC30]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC30,
+ },
+ [0x1BC31]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC31,
+ },
+ [0x1BC32]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC32,
+ },
+ [0x1BC33]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC33,
+ },
+ [0x1BC34]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC34,
+ },
+ [0x1BC35]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC35,
+ },
+ [0x1BC36]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC36,
+ },
+ [0x1BC37]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC37,
+ },
+ [0x1BC38]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC38,
+ },
+ [0x1BC39]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC39,
+ },
+ [0x1BC3A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3A,
+ },
+ [0x1BC3B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3B,
+ },
+ [0x1BC3C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3C,
+ },
+ [0x1BC3D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3D,
+ },
+ [0x1BC3E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3E,
+ },
+ [0x1BC3F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC3F,
+ },
+ [0x1BC40]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC40,
+ },
+ [0x1BC41]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC41,
+ },
+ [0x1BC42]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC42,
+ },
+ [0x1BC43]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC43,
+ },
+ [0x1BC44]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC44,
+ },
+ [0x1BC45]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC45,
+ },
+ [0x1BC46]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC46,
+ },
+ [0x1BC47]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC47,
+ },
+ [0x1BC48]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC48,
+ },
+ [0x1BC49]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC49,
+ },
+ [0x1BC4A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4A,
+ },
+ [0x1BC4B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4B,
+ },
+ [0x1BC4C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4C,
+ },
+ [0x1BC4D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4D,
+ },
+ [0x1BC4E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4E,
+ },
+ [0x1BC4F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC4F,
+ },
+ [0x1BC50]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC50,
+ },
+ [0x1BC51]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC51,
+ },
+ [0x1BC52]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC52,
+ },
+ [0x1BC53]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC53,
+ },
+ [0x1BC54]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC54,
+ },
+ [0x1BC55]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC55,
+ },
+ [0x1BC56]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC56,
+ },
+ [0x1BC57]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC57,
+ },
+ [0x1BC58]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC58,
+ },
+ [0x1BC59]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC59,
+ },
+ [0x1BC5A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5A,
+ },
+ [0x1BC5B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5B,
+ },
+ [0x1BC5C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5C,
+ },
+ [0x1BC5D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5D,
+ },
+ [0x1BC5E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5E,
+ },
+ [0x1BC5F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC5F,
+ },
+ [0x1BC60]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC60,
+ },
+ [0x1BC61]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC61,
+ },
+ [0x1BC62]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC62,
+ },
+ [0x1BC63]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC63,
+ },
+ [0x1BC64]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC64,
+ },
+ [0x1BC65]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC65,
+ },
+ [0x1BC66]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC66,
+ },
+ [0x1BC67]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC67,
+ },
+ [0x1BC68]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC68,
+ },
+ [0x1BC69]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC69,
+ },
+ [0x1BC6A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC6A,
+ },
+ [0x1BC70]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC70,
+ },
+ [0x1BC71]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC71,
+ },
+ [0x1BC72]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC72,
+ },
+ [0x1BC73]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC73,
+ },
+ [0x1BC74]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC74,
+ },
+ [0x1BC75]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC75,
+ },
+ [0x1BC76]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC76,
+ },
+ [0x1BC77]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC77,
+ },
+ [0x1BC78]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC78,
+ },
+ [0x1BC79]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC79,
+ },
+ [0x1BC7A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC7A,
+ },
+ [0x1BC7B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC7B,
+ },
+ [0x1BC7C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC7C,
+ },
+ [0x1BC80]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC80,
+ },
+ [0x1BC81]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC81,
+ },
+ [0x1BC82]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC82,
+ },
+ [0x1BC83]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC83,
+ },
+ [0x1BC84]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC84,
+ },
+ [0x1BC85]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC85,
+ },
+ [0x1BC86]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC86,
+ },
+ [0x1BC87]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC87,
+ },
+ [0x1BC88]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC88,
+ },
+ [0x1BC90]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC90,
+ },
+ [0x1BC91]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC91,
+ },
+ [0x1BC92]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC92,
+ },
+ [0x1BC93]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC93,
+ },
+ [0x1BC94]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC94,
+ },
+ [0x1BC95]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC95,
+ },
+ [0x1BC96]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC96,
+ },
+ [0x1BC97]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC97,
+ },
+ [0x1BC98]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC98,
+ },
+ [0x1BC99]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC99,
+ },
+ [0x1BC9C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1BC9C,
+ },
+ [0x1BC9D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BC9D,
+ },
+ [0x1BC9E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1BC9E,
+ },
+ [0x1BC9F]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1BC9F,
+ },
+ [0x1BCA0]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1BCA0,
+ },
+ [0x1BCA1]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1BCA1,
+ },
+ [0x1BCA2]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1BCA2,
+ },
+ [0x1BCA3]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1BCA3,
+ },
+ [0x1D000]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D000,
+ },
+ [0x1D001]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D001,
+ },
+ [0x1D002]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D002,
+ },
+ [0x1D003]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D003,
+ },
+ [0x1D004]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D004,
+ },
+ [0x1D005]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D005,
+ },
+ [0x1D006]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D006,
+ },
+ [0x1D007]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D007,
+ },
+ [0x1D008]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D008,
+ },
+ [0x1D009]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D009,
+ },
+ [0x1D00A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00A,
+ },
+ [0x1D00B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00B,
+ },
+ [0x1D00C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00C,
+ },
+ [0x1D00D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00D,
+ },
+ [0x1D00E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00E,
+ },
+ [0x1D00F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D00F,
+ },
+ [0x1D010]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D010,
+ },
+ [0x1D011]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D011,
+ },
+ [0x1D012]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D012,
+ },
+ [0x1D013]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D013,
+ },
+ [0x1D014]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D014,
+ },
+ [0x1D015]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D015,
+ },
+ [0x1D016]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D016,
+ },
+ [0x1D017]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D017,
+ },
+ [0x1D018]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D018,
+ },
+ [0x1D019]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D019,
+ },
+ [0x1D01A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01A,
+ },
+ [0x1D01B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01B,
+ },
+ [0x1D01C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01C,
+ },
+ [0x1D01D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01D,
+ },
+ [0x1D01E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01E,
+ },
+ [0x1D01F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D01F,
+ },
+ [0x1D020]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D020,
+ },
+ [0x1D021]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D021,
+ },
+ [0x1D022]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D022,
+ },
+ [0x1D023]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D023,
+ },
+ [0x1D024]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D024,
+ },
+ [0x1D025]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D025,
+ },
+ [0x1D026]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D026,
+ },
+ [0x1D027]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D027,
+ },
+ [0x1D028]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D028,
+ },
+ [0x1D029]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D029,
+ },
+ [0x1D02A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02A,
+ },
+ [0x1D02B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02B,
+ },
+ [0x1D02C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02C,
+ },
+ [0x1D02D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02D,
+ },
+ [0x1D02E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02E,
+ },
+ [0x1D02F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D02F,
+ },
+ [0x1D030]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D030,
+ },
+ [0x1D031]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D031,
+ },
+ [0x1D032]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D032,
+ },
+ [0x1D033]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D033,
+ },
+ [0x1D034]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D034,
+ },
+ [0x1D035]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D035,
+ },
+ [0x1D036]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D036,
+ },
+ [0x1D037]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D037,
+ },
+ [0x1D038]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D038,
+ },
+ [0x1D039]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D039,
+ },
+ [0x1D03A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03A,
+ },
+ [0x1D03B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03B,
+ },
+ [0x1D03C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03C,
+ },
+ [0x1D03D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03D,
+ },
+ [0x1D03E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03E,
+ },
+ [0x1D03F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D03F,
+ },
+ [0x1D040]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D040,
+ },
+ [0x1D041]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D041,
+ },
+ [0x1D042]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D042,
+ },
+ [0x1D043]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D043,
+ },
+ [0x1D044]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D044,
+ },
+ [0x1D045]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D045,
+ },
+ [0x1D046]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D046,
+ },
+ [0x1D047]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D047,
+ },
+ [0x1D048]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D048,
+ },
+ [0x1D049]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D049,
+ },
+ [0x1D04A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04A,
+ },
+ [0x1D04B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04B,
+ },
+ [0x1D04C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04C,
+ },
+ [0x1D04D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04D,
+ },
+ [0x1D04E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04E,
+ },
+ [0x1D04F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D04F,
+ },
+ [0x1D050]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D050,
+ },
+ [0x1D051]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D051,
+ },
+ [0x1D052]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D052,
+ },
+ [0x1D053]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D053,
+ },
+ [0x1D054]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D054,
+ },
+ [0x1D055]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D055,
+ },
+ [0x1D056]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D056,
+ },
+ [0x1D057]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D057,
+ },
+ [0x1D058]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D058,
+ },
+ [0x1D059]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D059,
+ },
+ [0x1D05A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05A,
+ },
+ [0x1D05B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05B,
+ },
+ [0x1D05C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05C,
+ },
+ [0x1D05D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05D,
+ },
+ [0x1D05E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05E,
+ },
+ [0x1D05F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D05F,
+ },
+ [0x1D060]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D060,
+ },
+ [0x1D061]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D061,
+ },
+ [0x1D062]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D062,
+ },
+ [0x1D063]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D063,
+ },
+ [0x1D064]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D064,
+ },
+ [0x1D065]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D065,
+ },
+ [0x1D066]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D066,
+ },
+ [0x1D067]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D067,
+ },
+ [0x1D068]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D068,
+ },
+ [0x1D069]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D069,
+ },
+ [0x1D06A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06A,
+ },
+ [0x1D06B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06B,
+ },
+ [0x1D06C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06C,
+ },
+ [0x1D06D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06D,
+ },
+ [0x1D06E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06E,
+ },
+ [0x1D06F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D06F,
+ },
+ [0x1D070]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D070,
+ },
+ [0x1D071]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D071,
+ },
+ [0x1D072]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D072,
+ },
+ [0x1D073]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D073,
+ },
+ [0x1D074]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D074,
+ },
+ [0x1D075]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D075,
+ },
+ [0x1D076]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D076,
+ },
+ [0x1D077]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D077,
+ },
+ [0x1D078]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D078,
+ },
+ [0x1D079]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D079,
+ },
+ [0x1D07A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07A,
+ },
+ [0x1D07B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07B,
+ },
+ [0x1D07C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07C,
+ },
+ [0x1D07D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07D,
+ },
+ [0x1D07E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07E,
+ },
+ [0x1D07F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D07F,
+ },
+ [0x1D080]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D080,
+ },
+ [0x1D081]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D081,
+ },
+ [0x1D082]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D082,
+ },
+ [0x1D083]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D083,
+ },
+ [0x1D084]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D084,
+ },
+ [0x1D085]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D085,
+ },
+ [0x1D086]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D086,
+ },
+ [0x1D087]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D087,
+ },
+ [0x1D088]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D088,
+ },
+ [0x1D089]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D089,
+ },
+ [0x1D08A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08A,
+ },
+ [0x1D08B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08B,
+ },
+ [0x1D08C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08C,
+ },
+ [0x1D08D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08D,
+ },
+ [0x1D08E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08E,
+ },
+ [0x1D08F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D08F,
+ },
+ [0x1D090]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D090,
+ },
+ [0x1D091]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D091,
+ },
+ [0x1D092]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D092,
+ },
+ [0x1D093]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D093,
+ },
+ [0x1D094]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D094,
+ },
+ [0x1D095]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D095,
+ },
+ [0x1D096]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D096,
+ },
+ [0x1D097]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D097,
+ },
+ [0x1D098]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D098,
+ },
+ [0x1D099]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D099,
+ },
+ [0x1D09A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09A,
+ },
+ [0x1D09B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09B,
+ },
+ [0x1D09C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09C,
+ },
+ [0x1D09D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09D,
+ },
+ [0x1D09E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09E,
+ },
+ [0x1D09F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D09F,
+ },
+ [0x1D0A0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A0,
+ },
+ [0x1D0A1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A1,
+ },
+ [0x1D0A2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A2,
+ },
+ [0x1D0A3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A3,
+ },
+ [0x1D0A4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A4,
+ },
+ [0x1D0A5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A5,
+ },
+ [0x1D0A6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A6,
+ },
+ [0x1D0A7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A7,
+ },
+ [0x1D0A8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A8,
+ },
+ [0x1D0A9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0A9,
+ },
+ [0x1D0AA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0AA,
+ },
+ [0x1D0AB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0AB,
+ },
+ [0x1D0AC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0AC,
+ },
+ [0x1D0AD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0AD,
+ },
+ [0x1D0AE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0AE,
+ },
+ [0x1D0AF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0AF,
+ },
+ [0x1D0B0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B0,
+ },
+ [0x1D0B1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B1,
+ },
+ [0x1D0B2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B2,
+ },
+ [0x1D0B3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B3,
+ },
+ [0x1D0B4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B4,
+ },
+ [0x1D0B5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B5,
+ },
+ [0x1D0B6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B6,
+ },
+ [0x1D0B7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B7,
+ },
+ [0x1D0B8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B8,
+ },
+ [0x1D0B9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0B9,
+ },
+ [0x1D0BA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0BA,
+ },
+ [0x1D0BB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0BB,
+ },
+ [0x1D0BC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0BC,
+ },
+ [0x1D0BD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0BD,
+ },
+ [0x1D0BE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0BE,
+ },
+ [0x1D0BF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0BF,
+ },
+ [0x1D0C0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C0,
+ },
+ [0x1D0C1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C1,
+ },
+ [0x1D0C2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C2,
+ },
+ [0x1D0C3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C3,
+ },
+ [0x1D0C4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C4,
+ },
+ [0x1D0C5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C5,
+ },
+ [0x1D0C6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C6,
+ },
+ [0x1D0C7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C7,
+ },
+ [0x1D0C8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C8,
+ },
+ [0x1D0C9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0C9,
+ },
+ [0x1D0CA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0CA,
+ },
+ [0x1D0CB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0CB,
+ },
+ [0x1D0CC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0CC,
+ },
+ [0x1D0CD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0CD,
+ },
+ [0x1D0CE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0CE,
+ },
+ [0x1D0CF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0CF,
+ },
+ [0x1D0D0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D0,
+ },
+ [0x1D0D1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D1,
+ },
+ [0x1D0D2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D2,
+ },
+ [0x1D0D3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D3,
+ },
+ [0x1D0D4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D4,
+ },
+ [0x1D0D5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D5,
+ },
+ [0x1D0D6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D6,
+ },
+ [0x1D0D7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D7,
+ },
+ [0x1D0D8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D8,
+ },
+ [0x1D0D9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0D9,
+ },
+ [0x1D0DA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0DA,
+ },
+ [0x1D0DB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0DB,
+ },
+ [0x1D0DC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0DC,
+ },
+ [0x1D0DD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0DD,
+ },
+ [0x1D0DE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0DE,
+ },
+ [0x1D0DF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0DF,
+ },
+ [0x1D0E0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E0,
+ },
+ [0x1D0E1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E1,
+ },
+ [0x1D0E2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E2,
+ },
+ [0x1D0E3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E3,
+ },
+ [0x1D0E4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E4,
+ },
+ [0x1D0E5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E5,
+ },
+ [0x1D0E6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E6,
+ },
+ [0x1D0E7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E7,
+ },
+ [0x1D0E8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E8,
+ },
+ [0x1D0E9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0E9,
+ },
+ [0x1D0EA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0EA,
+ },
+ [0x1D0EB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0EB,
+ },
+ [0x1D0EC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0EC,
+ },
+ [0x1D0ED]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0ED,
+ },
+ [0x1D0EE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0EE,
+ },
+ [0x1D0EF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0EF,
+ },
+ [0x1D0F0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F0,
+ },
+ [0x1D0F1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F1,
+ },
+ [0x1D0F2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F2,
+ },
+ [0x1D0F3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F3,
+ },
+ [0x1D0F4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F4,
+ },
+ [0x1D0F5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D0F5,
+ },
+ [0x1D100]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D100,
+ },
+ [0x1D101]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D101,
+ },
+ [0x1D102]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D102,
+ },
+ [0x1D103]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D103,
+ },
+ [0x1D104]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D104,
+ },
+ [0x1D105]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D105,
+ },
+ [0x1D106]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D106,
+ },
+ [0x1D107]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D107,
+ },
+ [0x1D108]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D108,
+ },
+ [0x1D109]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D109,
+ },
+ [0x1D10A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10A,
+ },
+ [0x1D10B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10B,
+ },
+ [0x1D10C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10C,
+ },
+ [0x1D10D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10D,
+ },
+ [0x1D10E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10E,
+ },
+ [0x1D10F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D10F,
+ },
+ [0x1D110]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D110,
+ },
+ [0x1D111]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D111,
+ },
+ [0x1D112]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D112,
+ },
+ [0x1D113]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D113,
+ },
+ [0x1D114]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D114,
+ },
+ [0x1D115]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D115,
+ },
+ [0x1D116]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D116,
+ },
+ [0x1D117]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D117,
+ },
+ [0x1D118]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D118,
+ },
+ [0x1D119]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D119,
+ },
+ [0x1D11A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11A,
+ },
+ [0x1D11B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11B,
+ },
+ [0x1D11C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11C,
+ },
+ [0x1D11D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11D,
+ },
+ [0x1D11E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11E,
+ },
+ [0x1D11F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D11F,
+ },
+ [0x1D120]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D120,
+ },
+ [0x1D121]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D121,
+ },
+ [0x1D122]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D122,
+ },
+ [0x1D123]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D123,
+ },
+ [0x1D124]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D124,
+ },
+ [0x1D125]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D125,
+ },
+ [0x1D126]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D126,
+ },
+ [0x1D129]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D129,
+ },
+ [0x1D12A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12A,
+ },
+ [0x1D12B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12B,
+ },
+ [0x1D12C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12C,
+ },
+ [0x1D12D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12D,
+ },
+ [0x1D12E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12E,
+ },
+ [0x1D12F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D12F,
+ },
+ [0x1D130]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D130,
+ },
+ [0x1D131]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D131,
+ },
+ [0x1D132]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D132,
+ },
+ [0x1D133]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D133,
+ },
+ [0x1D134]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D134,
+ },
+ [0x1D135]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D135,
+ },
+ [0x1D136]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D136,
+ },
+ [0x1D137]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D137,
+ },
+ [0x1D138]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D138,
+ },
+ [0x1D139]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D139,
+ },
+ [0x1D13A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13A,
+ },
+ [0x1D13B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13B,
+ },
+ [0x1D13C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13C,
+ },
+ [0x1D13D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13D,
+ },
+ [0x1D13E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13E,
+ },
+ [0x1D13F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D13F,
+ },
+ [0x1D140]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D140,
+ },
+ [0x1D141]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D141,
+ },
+ [0x1D142]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D142,
+ },
+ [0x1D143]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D143,
+ },
+ [0x1D144]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D144,
+ },
+ [0x1D145]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D145,
+ },
+ [0x1D146]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D146,
+ },
+ [0x1D147]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D147,
+ },
+ [0x1D148]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D148,
+ },
+ [0x1D149]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D149,
+ },
+ [0x1D14A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14A,
+ },
+ [0x1D14B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14B,
+ },
+ [0x1D14C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14C,
+ },
+ [0x1D14D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14D,
+ },
+ [0x1D14E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14E,
+ },
+ [0x1D14F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D14F,
+ },
+ [0x1D150]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D150,
+ },
+ [0x1D151]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D151,
+ },
+ [0x1D152]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D152,
+ },
+ [0x1D153]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D153,
+ },
+ [0x1D154]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D154,
+ },
+ [0x1D155]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D155,
+ },
+ [0x1D156]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D156,
+ },
+ [0x1D157]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D157,
+ },
+ [0x1D158]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D158,
+ },
+ [0x1D159]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D159,
+ },
+ [0x1D15A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D15A,
+ },
+ [0x1D15B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D15B,
+ },
+ [0x1D15C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D15C,
+ },
+ [0x1D15D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D15D,
+ },
+ [0x1D15E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D157, 0x1D165 },
+ unicodeslot=0x1D15E,
+ },
+ [0x1D15F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D158, 0x1D165 },
+ unicodeslot=0x1D15F,
+ },
+ [0x1D160]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D15F, 0x1D16E },
+ unicodeslot=0x1D160,
+ },
+ [0x1D161]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D15F, 0x1D16F },
+ unicodeslot=0x1D161,
+ },
+ [0x1D162]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D15F, 0x1D170 },
+ unicodeslot=0x1D162,
+ },
+ [0x1D163]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D15F, 0x1D171 },
+ unicodeslot=0x1D163,
+ },
+ [0x1D164]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D15F, 0x1D172 },
+ unicodeslot=0x1D164,
+ },
+ [0x1D165]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D165,
+ },
+ [0x1D166]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D166,
+ },
+ [0x1D167]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D167,
+ },
+ [0x1D168]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D168,
+ },
+ [0x1D169]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D169,
+ },
+ [0x1D16A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D16A,
+ },
+ [0x1D16B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D16B,
+ },
+ [0x1D16C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D16C,
+ },
+ [0x1D16D]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D16D,
+ },
+ [0x1D16E]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D16E,
+ },
+ [0x1D16F]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D16F,
+ },
+ [0x1D170]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D170,
+ },
+ [0x1D171]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D171,
+ },
+ [0x1D172]={
+ category="mc",
+ direction="l",
+ linebreak="cm",
+ unicodeslot=0x1D172,
+ },
+ [0x1D173]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D173,
+ },
+ [0x1D174]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D174,
+ },
+ [0x1D175]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D175,
+ },
+ [0x1D176]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D176,
+ },
+ [0x1D177]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D177,
+ },
+ [0x1D178]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D178,
+ },
+ [0x1D179]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D179,
+ },
+ [0x1D17A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0x1D17A,
+ },
+ [0x1D17B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D17B,
+ },
+ [0x1D17C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D17C,
+ },
+ [0x1D17D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D17D,
+ },
+ [0x1D17E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D17E,
+ },
+ [0x1D17F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D17F,
+ },
+ [0x1D180]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D180,
+ },
+ [0x1D181]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D181,
+ },
+ [0x1D182]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D182,
+ },
+ [0x1D183]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D183,
+ },
+ [0x1D184]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D184,
+ },
+ [0x1D185]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D185,
+ },
+ [0x1D186]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D186,
+ },
+ [0x1D187]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D187,
+ },
+ [0x1D188]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D188,
+ },
+ [0x1D189]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D189,
+ },
+ [0x1D18A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D18A,
+ },
+ [0x1D18B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D18B,
+ },
+ [0x1D18C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D18C,
+ },
+ [0x1D18D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D18D,
+ },
+ [0x1D18E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D18E,
+ },
+ [0x1D18F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D18F,
+ },
+ [0x1D190]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D190,
+ },
+ [0x1D191]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D191,
+ },
+ [0x1D192]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D192,
+ },
+ [0x1D193]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D193,
+ },
+ [0x1D194]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D194,
+ },
+ [0x1D195]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D195,
+ },
+ [0x1D196]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D196,
+ },
+ [0x1D197]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D197,
+ },
+ [0x1D198]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D198,
+ },
+ [0x1D199]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D199,
+ },
+ [0x1D19A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19A,
+ },
+ [0x1D19B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19B,
+ },
+ [0x1D19C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19C,
+ },
+ [0x1D19D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19D,
+ },
+ [0x1D19E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19E,
+ },
+ [0x1D19F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D19F,
+ },
+ [0x1D1A0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A0,
+ },
+ [0x1D1A1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A1,
+ },
+ [0x1D1A2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A2,
+ },
+ [0x1D1A3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A3,
+ },
+ [0x1D1A4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A4,
+ },
+ [0x1D1A5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A5,
+ },
+ [0x1D1A6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A6,
+ },
+ [0x1D1A7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A7,
+ },
+ [0x1D1A8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A8,
+ },
+ [0x1D1A9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1A9,
+ },
+ [0x1D1AA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D1AA,
+ },
+ [0x1D1AB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D1AB,
+ },
+ [0x1D1AC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D1AC,
+ },
+ [0x1D1AD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D1AD,
+ },
+ [0x1D1AE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1AE,
+ },
+ [0x1D1AF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1AF,
+ },
+ [0x1D1B0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B0,
+ },
+ [0x1D1B1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B1,
+ },
+ [0x1D1B2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B2,
+ },
+ [0x1D1B3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B3,
+ },
+ [0x1D1B4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B4,
+ },
+ [0x1D1B5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B5,
+ },
+ [0x1D1B6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B6,
+ },
+ [0x1D1B7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B7,
+ },
+ [0x1D1B8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B8,
+ },
+ [0x1D1B9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1B9,
+ },
+ [0x1D1BA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1BA,
+ },
+ [0x1D1BB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D1B9, 0x1D165 },
+ unicodeslot=0x1D1BB,
+ },
+ [0x1D1BC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D1BA, 0x1D165 },
+ unicodeslot=0x1D1BC,
+ },
+ [0x1D1BD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D1BB, 0x1D16E },
+ unicodeslot=0x1D1BD,
+ },
+ [0x1D1BE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D1BC, 0x1D16E },
+ unicodeslot=0x1D1BE,
+ },
+ [0x1D1BF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D1BB, 0x1D16F },
+ unicodeslot=0x1D1BF,
+ },
+ [0x1D1C0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "char", 0x1D1BC, 0x1D16F },
+ unicodeslot=0x1D1C0,
+ },
+ [0x1D1C1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C1,
+ },
+ [0x1D1C2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C2,
+ },
+ [0x1D1C3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C3,
+ },
+ [0x1D1C4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C4,
+ },
+ [0x1D1C5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C5,
+ },
+ [0x1D1C6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C6,
+ },
+ [0x1D1C7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C7,
+ },
+ [0x1D1C8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C8,
+ },
+ [0x1D1C9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1C9,
+ },
+ [0x1D1CA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1CA,
+ },
+ [0x1D1CB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1CB,
+ },
+ [0x1D1CC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1CC,
+ },
+ [0x1D1CD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1CD,
+ },
+ [0x1D1CE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1CE,
+ },
+ [0x1D1CF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1CF,
+ },
+ [0x1D1D0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D0,
+ },
+ [0x1D1D1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D1,
+ },
+ [0x1D1D2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D2,
+ },
+ [0x1D1D3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D3,
+ },
+ [0x1D1D4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D4,
+ },
+ [0x1D1D5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D5,
+ },
+ [0x1D1D6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D6,
+ },
+ [0x1D1D7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D7,
+ },
+ [0x1D1D8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D8,
+ },
+ [0x1D1D9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1D9,
+ },
+ [0x1D1DA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1DA,
+ },
+ [0x1D1DB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1DB,
+ },
+ [0x1D1DC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1DC,
+ },
+ [0x1D1DD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1DD,
+ },
+ [0x1D1DE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1DE,
+ },
+ [0x1D1DF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1DF,
+ },
+ [0x1D1E0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E0,
+ },
+ [0x1D1E1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E1,
+ },
+ [0x1D1E2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E2,
+ },
+ [0x1D1E3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E3,
+ },
+ [0x1D1E4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E4,
+ },
+ [0x1D1E5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E5,
+ },
+ [0x1D1E6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E6,
+ },
+ [0x1D1E7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E7,
+ },
+ [0x1D1E8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D1E8,
+ },
+ [0x1D200]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D200,
+ },
+ [0x1D201]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D201,
+ },
+ [0x1D202]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D202,
+ },
+ [0x1D203]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D203,
+ },
+ [0x1D204]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D204,
+ },
+ [0x1D205]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D205,
+ },
+ [0x1D206]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D206,
+ },
+ [0x1D207]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D207,
+ },
+ [0x1D208]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D208,
+ },
+ [0x1D209]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D209,
+ },
+ [0x1D20A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D20A,
+ },
+ [0x1D20B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D20B,
+ },
+ [0x1D20C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D20C,
+ },
+ [0x1D20D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D20D,
+ },
+ [0x1D20E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D20E,
+ },
+ [0x1D20F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D20F,
+ },
+ [0x1D210]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D210,
+ },
+ [0x1D211]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D211,
+ },
+ [0x1D212]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D212,
+ },
+ [0x1D213]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D213,
+ },
+ [0x1D214]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D214,
+ },
+ [0x1D215]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D215,
+ },
+ [0x1D216]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D216,
+ },
+ [0x1D217]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D217,
+ },
+ [0x1D218]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D218,
+ },
+ [0x1D219]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D219,
+ },
+ [0x1D21A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D21A,
+ },
+ [0x1D21B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D21B,
+ },
+ [0x1D21C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D21C,
+ },
+ [0x1D21D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D21D,
+ },
+ [0x1D21E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D21E,
+ },
+ [0x1D21F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D21F,
+ },
+ [0x1D220]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D220,
+ },
+ [0x1D221]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D221,
+ },
+ [0x1D222]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D222,
+ },
+ [0x1D223]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D223,
+ },
+ [0x1D224]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D224,
+ },
+ [0x1D225]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D225,
+ },
+ [0x1D226]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D226,
+ },
+ [0x1D227]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D227,
+ },
+ [0x1D228]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D228,
+ },
+ [0x1D229]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D229,
+ },
+ [0x1D22A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D22A,
+ },
+ [0x1D22B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D22B,
+ },
+ [0x1D22C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D22C,
+ },
+ [0x1D22D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D22D,
+ },
+ [0x1D22E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D22E,
+ },
+ [0x1D22F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D22F,
+ },
+ [0x1D230]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D230,
+ },
+ [0x1D231]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D231,
+ },
+ [0x1D232]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D232,
+ },
+ [0x1D233]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D233,
+ },
+ [0x1D234]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D234,
+ },
+ [0x1D235]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D235,
+ },
+ [0x1D236]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D236,
+ },
+ [0x1D237]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D237,
+ },
+ [0x1D238]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D238,
+ },
+ [0x1D239]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D239,
+ },
+ [0x1D23A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D23A,
+ },
+ [0x1D23B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D23B,
+ },
+ [0x1D23C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D23C,
+ },
+ [0x1D23D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D23D,
+ },
+ [0x1D23E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D23E,
+ },
+ [0x1D23F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D23F,
+ },
+ [0x1D240]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D240,
+ },
+ [0x1D241]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D241,
+ },
+ [0x1D242]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D242,
+ },
+ [0x1D243]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D243,
+ },
+ [0x1D244]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1D244,
+ },
+ [0x1D245]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D245,
+ },
+ [0x1D2E0]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E0,
+ },
+ [0x1D2E1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E1,
+ },
+ [0x1D2E2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E2,
+ },
+ [0x1D2E3]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E3,
+ },
+ [0x1D2E4]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E4,
+ },
+ [0x1D2E5]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E5,
+ },
+ [0x1D2E6]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E6,
+ },
+ [0x1D2E7]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E7,
+ },
+ [0x1D2E8]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E8,
+ },
+ [0x1D2E9]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2E9,
+ },
+ [0x1D2EA]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2EA,
+ },
+ [0x1D2EB]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2EB,
+ },
+ [0x1D2EC]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2EC,
+ },
+ [0x1D2ED]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2ED,
+ },
+ [0x1D2EE]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2EE,
+ },
+ [0x1D2EF]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2EF,
+ },
+ [0x1D2F0]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2F0,
+ },
+ [0x1D2F1]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2F1,
+ },
+ [0x1D2F2]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2F2,
+ },
+ [0x1D2F3]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D2F3,
+ },
+ [0x1D300]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D300,
+ },
+ [0x1D301]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D301,
+ },
+ [0x1D302]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D302,
+ },
+ [0x1D303]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D303,
+ },
+ [0x1D304]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D304,
+ },
+ [0x1D305]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D305,
+ },
+ [0x1D306]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D306,
+ },
+ [0x1D307]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D307,
+ },
+ [0x1D308]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D308,
+ },
+ [0x1D309]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D309,
+ },
+ [0x1D30A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D30A,
+ },
+ [0x1D30B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D30B,
+ },
+ [0x1D30C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D30C,
+ },
+ [0x1D30D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D30D,
+ },
+ [0x1D30E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D30E,
+ },
+ [0x1D30F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D30F,
+ },
+ [0x1D310]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D310,
+ },
+ [0x1D311]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D311,
+ },
+ [0x1D312]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D312,
+ },
+ [0x1D313]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D313,
+ },
+ [0x1D314]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D314,
+ },
+ [0x1D315]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D315,
+ },
+ [0x1D316]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D316,
+ },
+ [0x1D317]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D317,
+ },
+ [0x1D318]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D318,
+ },
+ [0x1D319]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D319,
+ },
+ [0x1D31A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D31A,
+ },
+ [0x1D31B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D31B,
+ },
+ [0x1D31C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D31C,
+ },
+ [0x1D31D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D31D,
+ },
+ [0x1D31E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D31E,
+ },
+ [0x1D31F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D31F,
+ },
+ [0x1D320]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D320,
+ },
+ [0x1D321]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D321,
+ },
+ [0x1D322]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D322,
+ },
+ [0x1D323]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D323,
+ },
+ [0x1D324]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D324,
+ },
+ [0x1D325]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D325,
+ },
+ [0x1D326]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D326,
+ },
+ [0x1D327]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D327,
+ },
+ [0x1D328]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D328,
+ },
+ [0x1D329]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D329,
+ },
+ [0x1D32A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D32A,
+ },
+ [0x1D32B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D32B,
+ },
+ [0x1D32C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D32C,
+ },
+ [0x1D32D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D32D,
+ },
+ [0x1D32E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D32E,
+ },
+ [0x1D32F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D32F,
+ },
+ [0x1D330]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D330,
+ },
+ [0x1D331]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D331,
+ },
+ [0x1D332]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D332,
+ },
+ [0x1D333]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D333,
+ },
+ [0x1D334]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D334,
+ },
+ [0x1D335]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D335,
+ },
+ [0x1D336]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D336,
+ },
+ [0x1D337]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D337,
+ },
+ [0x1D338]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D338,
+ },
+ [0x1D339]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D339,
+ },
+ [0x1D33A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D33A,
+ },
+ [0x1D33B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D33B,
+ },
+ [0x1D33C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D33C,
+ },
+ [0x1D33D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D33D,
+ },
+ [0x1D33E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D33E,
+ },
+ [0x1D33F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D33F,
+ },
+ [0x1D340]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D340,
+ },
+ [0x1D341]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D341,
+ },
+ [0x1D342]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D342,
+ },
+ [0x1D343]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D343,
+ },
+ [0x1D344]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D344,
+ },
+ [0x1D345]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D345,
+ },
+ [0x1D346]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D346,
+ },
+ [0x1D347]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D347,
+ },
+ [0x1D348]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D348,
+ },
+ [0x1D349]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D349,
+ },
+ [0x1D34A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D34A,
+ },
+ [0x1D34B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D34B,
+ },
+ [0x1D34C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D34C,
+ },
+ [0x1D34D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D34D,
+ },
+ [0x1D34E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D34E,
+ },
+ [0x1D34F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D34F,
+ },
+ [0x1D350]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D350,
+ },
+ [0x1D351]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D351,
+ },
+ [0x1D352]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D352,
+ },
+ [0x1D353]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D353,
+ },
+ [0x1D354]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D354,
+ },
+ [0x1D355]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D355,
+ },
+ [0x1D356]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1D356,
+ },
+ [0x1D360]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D360,
+ },
+ [0x1D361]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D361,
+ },
+ [0x1D362]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D362,
+ },
+ [0x1D363]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D363,
+ },
+ [0x1D364]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D364,
+ },
+ [0x1D365]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D365,
+ },
+ [0x1D366]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D366,
+ },
+ [0x1D367]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D367,
+ },
+ [0x1D368]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D368,
+ },
+ [0x1D369]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D369,
+ },
+ [0x1D36A]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D36A,
+ },
+ [0x1D36B]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D36B,
+ },
+ [0x1D36C]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D36C,
+ },
+ [0x1D36D]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D36D,
+ },
+ [0x1D36E]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D36E,
+ },
+ [0x1D36F]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D36F,
+ },
+ [0x1D370]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D370,
+ },
+ [0x1D371]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D371,
+ },
+ [0x1D372]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D372,
+ },
+ [0x1D373]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D373,
+ },
+ [0x1D374]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D374,
+ },
+ [0x1D375]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D375,
+ },
+ [0x1D376]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D376,
+ },
+ [0x1D377]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D377,
+ },
+ [0x1D378]={
+ category="no",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D378,
+ },
+ [0x1D400]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D400,
+ },
+ [0x1D401]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D401,
+ },
+ [0x1D402]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D402,
+ },
+ [0x1D403]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D403,
+ },
+ [0x1D404]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D404,
+ },
+ [0x1D405]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D405,
+ },
+ [0x1D406]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D406,
+ },
+ [0x1D407]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D407,
+ },
+ [0x1D408]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D408,
+ },
+ [0x1D409]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D409,
+ },
+ [0x1D40A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D40A,
+ },
+ [0x1D40B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D40B,
+ },
+ [0x1D40C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D40C,
+ },
+ [0x1D40D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D40D,
+ },
+ [0x1D40E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D40E,
+ },
+ [0x1D40F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D40F,
+ },
+ [0x1D410]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D410,
+ },
+ [0x1D411]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D411,
+ },
+ [0x1D412]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D412,
+ },
+ [0x1D413]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D413,
+ },
+ [0x1D414]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D414,
+ },
+ [0x1D415]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D415,
+ },
+ [0x1D416]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D416,
+ },
+ [0x1D417]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D417,
+ },
+ [0x1D418]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D418,
+ },
+ [0x1D419]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D419,
+ },
+ [0x1D41A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D41A,
+ },
+ [0x1D41B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D41B,
+ },
+ [0x1D41C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D41C,
+ },
+ [0x1D41D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D41D,
+ },
+ [0x1D41E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D41E,
+ },
+ [0x1D41F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D41F,
+ },
+ [0x1D420]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D420,
+ },
+ [0x1D421]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D421,
+ },
+ [0x1D422]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D422,
+ },
+ [0x1D423]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D423,
+ },
+ [0x1D424]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D424,
+ },
+ [0x1D425]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D425,
+ },
+ [0x1D426]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D426,
+ },
+ [0x1D427]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D427,
+ },
+ [0x1D428]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D428,
+ },
+ [0x1D429]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D429,
+ },
+ [0x1D42A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D42A,
+ },
+ [0x1D42B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D42B,
+ },
+ [0x1D42C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D42C,
+ },
+ [0x1D42D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D42D,
+ },
+ [0x1D42E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D42E,
+ },
+ [0x1D42F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D42F,
+ },
+ [0x1D430]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D430,
+ },
+ [0x1D431]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D431,
+ },
+ [0x1D432]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D432,
+ },
+ [0x1D433]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D433,
+ },
+ [0x1D434]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D434,
+ },
+ [0x1D435]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D435,
+ },
+ [0x1D436]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D436,
+ },
+ [0x1D437]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D437,
+ },
+ [0x1D438]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D438,
+ },
+ [0x1D439]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D439,
+ },
+ [0x1D43A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D43A,
+ },
+ [0x1D43B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D43B,
+ },
+ [0x1D43C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D43C,
+ },
+ [0x1D43D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D43D,
+ },
+ [0x1D43E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D43E,
+ },
+ [0x1D43F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D43F,
+ },
+ [0x1D440]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D440,
+ },
+ [0x1D441]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D441,
+ },
+ [0x1D442]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D442,
+ },
+ [0x1D443]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D443,
+ },
+ [0x1D444]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D444,
+ },
+ [0x1D445]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D445,
+ },
+ [0x1D446]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D446,
+ },
+ [0x1D447]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D447,
+ },
+ [0x1D448]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D448,
+ },
+ [0x1D449]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D449,
+ },
+ [0x1D44A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D44A,
+ },
+ [0x1D44B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D44B,
+ },
+ [0x1D44C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D44C,
+ },
+ [0x1D44D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D44D,
+ },
+ [0x1D44E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D44E,
+ },
+ [0x1D44F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D44F,
+ },
+ [0x1D450]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D450,
+ },
+ [0x1D451]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D451,
+ },
+ [0x1D452]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D452,
+ },
+ [0x1D453]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D453,
+ },
+ [0x1D454]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D454,
+ },
+ [0x1D456]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D456,
+ },
+ [0x1D457]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D457,
+ },
+ [0x1D458]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D458,
+ },
+ [0x1D459]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D459,
+ },
+ [0x1D45A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D45A,
+ },
+ [0x1D45B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D45B,
+ },
+ [0x1D45C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D45C,
+ },
+ [0x1D45D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D45D,
+ },
+ [0x1D45E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D45E,
+ },
+ [0x1D45F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D45F,
+ },
+ [0x1D460]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D460,
+ },
+ [0x1D461]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D461,
+ },
+ [0x1D462]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D462,
+ },
+ [0x1D463]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D463,
+ },
+ [0x1D464]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D464,
+ },
+ [0x1D465]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D465,
+ },
+ [0x1D466]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D466,
+ },
+ [0x1D467]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D467,
+ },
+ [0x1D468]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D468,
+ },
+ [0x1D469]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D469,
+ },
+ [0x1D46A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D46A,
+ },
+ [0x1D46B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D46B,
+ },
+ [0x1D46C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D46C,
+ },
+ [0x1D46D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D46D,
+ },
+ [0x1D46E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D46E,
+ },
+ [0x1D46F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D46F,
+ },
+ [0x1D470]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D470,
+ },
+ [0x1D471]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D471,
+ },
+ [0x1D472]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D472,
+ },
+ [0x1D473]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D473,
+ },
+ [0x1D474]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D474,
+ },
+ [0x1D475]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D475,
+ },
+ [0x1D476]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D476,
+ },
+ [0x1D477]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D477,
+ },
+ [0x1D478]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D478,
+ },
+ [0x1D479]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D479,
+ },
+ [0x1D47A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D47A,
+ },
+ [0x1D47B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D47B,
+ },
+ [0x1D47C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D47C,
+ },
+ [0x1D47D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D47D,
+ },
+ [0x1D47E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D47E,
+ },
+ [0x1D47F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D47F,
+ },
+ [0x1D480]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D480,
+ },
+ [0x1D481]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D481,
+ },
+ [0x1D482]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D482,
+ },
+ [0x1D483]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D483,
+ },
+ [0x1D484]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D484,
+ },
+ [0x1D485]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D485,
+ },
+ [0x1D486]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D486,
+ },
+ [0x1D487]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D487,
+ },
+ [0x1D488]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D488,
+ },
+ [0x1D489]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D489,
+ },
+ [0x1D48A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D48A,
+ },
+ [0x1D48B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D48B,
+ },
+ [0x1D48C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D48C,
+ },
+ [0x1D48D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D48D,
+ },
+ [0x1D48E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D48E,
+ },
+ [0x1D48F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D48F,
+ },
+ [0x1D490]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D490,
+ },
+ [0x1D491]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D491,
+ },
+ [0x1D492]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D492,
+ },
+ [0x1D493]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D493,
+ },
+ [0x1D494]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D494,
+ },
+ [0x1D495]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D495,
+ },
+ [0x1D496]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D496,
+ },
+ [0x1D497]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D497,
+ },
+ [0x1D498]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D498,
+ },
+ [0x1D499]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D499,
+ },
+ [0x1D49A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D49A,
+ },
+ [0x1D49B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D49B,
+ },
+ [0x1D49C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D49C,
+ },
+ [0x1D49E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D49E,
+ },
+ [0x1D49F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D49F,
+ },
+ [0x1D4A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D4A2,
+ },
+ [0x1D4A5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D4A5,
+ },
+ [0x1D4A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D4A6,
+ },
+ [0x1D4A9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D4A9,
+ },
+ [0x1D4AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D4AA,
+ },
+ [0x1D4AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D4AB,
+ },
+ [0x1D4AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D4AC,
+ },
+ [0x1D4AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D4AE,
+ },
+ [0x1D4AF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D4AF,
+ },
+ [0x1D4B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D4B0,
+ },
+ [0x1D4B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D4B1,
+ },
+ [0x1D4B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D4B2,
+ },
+ [0x1D4B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D4B3,
+ },
+ [0x1D4B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D4B4,
+ },
+ [0x1D4B5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D4B5,
+ },
+ [0x1D4B6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D4B6,
+ },
+ [0x1D4B7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D4B7,
+ },
+ [0x1D4B8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D4B8,
+ },
+ [0x1D4B9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D4B9,
+ },
+ [0x1D4BB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D4BB,
+ },
+ [0x1D4BD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D4BD,
+ },
+ [0x1D4BE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D4BE,
+ },
+ [0x1D4BF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D4BF,
+ },
+ [0x1D4C0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D4C0,
+ },
+ [0x1D4C1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D4C1,
+ },
+ [0x1D4C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D4C2,
+ },
+ [0x1D4C3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D4C3,
+ },
+ [0x1D4C5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D4C5,
+ },
+ [0x1D4C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D4C6,
+ },
+ [0x1D4C7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D4C7,
+ },
+ [0x1D4C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D4C8,
+ },
+ [0x1D4C9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D4C9,
+ },
+ [0x1D4CA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D4CA,
+ },
+ [0x1D4CB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D4CB,
+ },
+ [0x1D4CC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D4CC,
+ },
+ [0x1D4CD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D4CD,
+ },
+ [0x1D4CE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D4CE,
+ },
+ [0x1D4CF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D4CF,
+ },
+ [0x1D4D0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D4D0,
+ },
+ [0x1D4D1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D4D1,
+ },
+ [0x1D4D2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D4D2,
+ },
+ [0x1D4D3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D4D3,
+ },
+ [0x1D4D4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D4D4,
+ },
+ [0x1D4D5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D4D5,
+ },
+ [0x1D4D6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D4D6,
+ },
+ [0x1D4D7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D4D7,
+ },
+ [0x1D4D8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D4D8,
+ },
+ [0x1D4D9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D4D9,
+ },
+ [0x1D4DA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D4DA,
+ },
+ [0x1D4DB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D4DB,
+ },
+ [0x1D4DC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D4DC,
+ },
+ [0x1D4DD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D4DD,
+ },
+ [0x1D4DE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D4DE,
+ },
+ [0x1D4DF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D4DF,
+ },
+ [0x1D4E0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D4E0,
+ },
+ [0x1D4E1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D4E1,
+ },
+ [0x1D4E2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D4E2,
+ },
+ [0x1D4E3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D4E3,
+ },
+ [0x1D4E4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D4E4,
+ },
+ [0x1D4E5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D4E5,
+ },
+ [0x1D4E6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D4E6,
+ },
+ [0x1D4E7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D4E7,
+ },
+ [0x1D4E8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D4E8,
+ },
+ [0x1D4E9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D4E9,
+ },
+ [0x1D4EA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D4EA,
+ },
+ [0x1D4EB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D4EB,
+ },
+ [0x1D4EC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D4EC,
+ },
+ [0x1D4ED]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D4ED,
+ },
+ [0x1D4EE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D4EE,
+ },
+ [0x1D4EF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D4EF,
+ },
+ [0x1D4F0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D4F0,
+ },
+ [0x1D4F1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D4F1,
+ },
+ [0x1D4F2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D4F2,
+ },
+ [0x1D4F3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D4F3,
+ },
+ [0x1D4F4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D4F4,
+ },
+ [0x1D4F5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D4F5,
+ },
+ [0x1D4F6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D4F6,
+ },
+ [0x1D4F7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D4F7,
+ },
+ [0x1D4F8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D4F8,
+ },
+ [0x1D4F9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D4F9,
+ },
+ [0x1D4FA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D4FA,
+ },
+ [0x1D4FB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D4FB,
+ },
+ [0x1D4FC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D4FC,
+ },
+ [0x1D4FD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D4FD,
+ },
+ [0x1D4FE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D4FE,
+ },
+ [0x1D4FF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D4FF,
+ },
+ [0x1D500]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D500,
+ },
+ [0x1D501]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D501,
+ },
+ [0x1D502]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D502,
+ },
+ [0x1D503]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D503,
+ },
+ [0x1D504]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D504,
+ },
+ [0x1D505]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D505,
+ },
+ [0x1D507]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D507,
+ },
+ [0x1D508]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D508,
+ },
+ [0x1D509]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D509,
+ },
+ [0x1D50A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D50A,
+ },
+ [0x1D50D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D50D,
+ },
+ [0x1D50E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D50E,
+ },
+ [0x1D50F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D50F,
+ },
+ [0x1D510]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D510,
+ },
+ [0x1D511]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D511,
+ },
+ [0x1D512]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D512,
+ },
+ [0x1D513]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D513,
+ },
+ [0x1D514]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D514,
+ },
+ [0x1D516]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D516,
+ },
+ [0x1D517]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D517,
+ },
+ [0x1D518]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D518,
+ },
+ [0x1D519]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D519,
+ },
+ [0x1D51A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D51A,
+ },
+ [0x1D51B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D51B,
+ },
+ [0x1D51C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D51C,
+ },
+ [0x1D51E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D51E,
+ },
+ [0x1D51F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D51F,
+ },
+ [0x1D520]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D520,
+ },
+ [0x1D521]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D521,
+ },
+ [0x1D522]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D522,
+ },
+ [0x1D523]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D523,
+ },
+ [0x1D524]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D524,
+ },
+ [0x1D525]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D525,
+ },
+ [0x1D526]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D526,
+ },
+ [0x1D527]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D527,
+ },
+ [0x1D528]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D528,
+ },
+ [0x1D529]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D529,
+ },
+ [0x1D52A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D52A,
+ },
+ [0x1D52B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D52B,
+ },
+ [0x1D52C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D52C,
+ },
+ [0x1D52D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D52D,
+ },
+ [0x1D52E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D52E,
+ },
+ [0x1D52F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D52F,
+ },
+ [0x1D530]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D530,
+ },
+ [0x1D531]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D531,
+ },
+ [0x1D532]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D532,
+ },
+ [0x1D533]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D533,
+ },
+ [0x1D534]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D534,
+ },
+ [0x1D535]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D535,
+ },
+ [0x1D536]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D536,
+ },
+ [0x1D537]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D537,
+ },
+ [0x1D538]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D538,
+ },
+ [0x1D539]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D539,
+ },
+ [0x1D53B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D53B,
+ },
+ [0x1D53C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D53C,
+ },
+ [0x1D53D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D53D,
+ },
+ [0x1D53E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D53E,
+ },
+ [0x1D540]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D540,
+ },
+ [0x1D541]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D541,
+ },
+ [0x1D542]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D542,
+ },
+ [0x1D543]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D543,
+ },
+ [0x1D544]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D544,
+ },
+ [0x1D546]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D546,
+ },
+ [0x1D54A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D54A,
+ },
+ [0x1D54B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D54B,
+ },
+ [0x1D54C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D54C,
+ },
+ [0x1D54D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D54D,
+ },
+ [0x1D54E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D54E,
+ },
+ [0x1D54F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D54F,
+ },
+ [0x1D550]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D550,
+ },
+ [0x1D552]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D552,
+ },
+ [0x1D553]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D553,
+ },
+ [0x1D554]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D554,
+ },
+ [0x1D555]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D555,
+ },
+ [0x1D556]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D556,
+ },
+ [0x1D557]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D557,
+ },
+ [0x1D558]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D558,
+ },
+ [0x1D559]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D559,
+ },
+ [0x1D55A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D55A,
+ },
+ [0x1D55B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D55B,
+ },
+ [0x1D55C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D55C,
+ },
+ [0x1D55D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D55D,
+ },
+ [0x1D55E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D55E,
+ },
+ [0x1D55F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D55F,
+ },
+ [0x1D560]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D560,
+ },
+ [0x1D561]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D561,
+ },
+ [0x1D562]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D562,
+ },
+ [0x1D563]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D563,
+ },
+ [0x1D564]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D564,
+ },
+ [0x1D565]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D565,
+ },
+ [0x1D566]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D566,
+ },
+ [0x1D567]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D567,
+ },
+ [0x1D568]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D568,
+ },
+ [0x1D569]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D569,
+ },
+ [0x1D56A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D56A,
+ },
+ [0x1D56B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D56B,
+ },
+ [0x1D56C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D56C,
+ },
+ [0x1D56D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D56D,
+ },
+ [0x1D56E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D56E,
+ },
+ [0x1D56F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D56F,
+ },
+ [0x1D570]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D570,
+ },
+ [0x1D571]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D571,
+ },
+ [0x1D572]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D572,
+ },
+ [0x1D573]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D573,
+ },
+ [0x1D574]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D574,
+ },
+ [0x1D575]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D575,
+ },
+ [0x1D576]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D576,
+ },
+ [0x1D577]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D577,
+ },
+ [0x1D578]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D578,
+ },
+ [0x1D579]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D579,
+ },
+ [0x1D57A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D57A,
+ },
+ [0x1D57B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D57B,
+ },
+ [0x1D57C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D57C,
+ },
+ [0x1D57D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D57D,
+ },
+ [0x1D57E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D57E,
+ },
+ [0x1D57F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D57F,
+ },
+ [0x1D580]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D580,
+ },
+ [0x1D581]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D581,
+ },
+ [0x1D582]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D582,
+ },
+ [0x1D583]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D583,
+ },
+ [0x1D584]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D584,
+ },
+ [0x1D585]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D585,
+ },
+ [0x1D586]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D586,
+ },
+ [0x1D587]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D587,
+ },
+ [0x1D588]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D588,
+ },
+ [0x1D589]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D589,
+ },
+ [0x1D58A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D58A,
+ },
+ [0x1D58B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D58B,
+ },
+ [0x1D58C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D58C,
+ },
+ [0x1D58D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D58D,
+ },
+ [0x1D58E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D58E,
+ },
+ [0x1D58F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D58F,
+ },
+ [0x1D590]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D590,
+ },
+ [0x1D591]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D591,
+ },
+ [0x1D592]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D592,
+ },
+ [0x1D593]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D593,
+ },
+ [0x1D594]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D594,
+ },
+ [0x1D595]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D595,
+ },
+ [0x1D596]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D596,
+ },
+ [0x1D597]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D597,
+ },
+ [0x1D598]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D598,
+ },
+ [0x1D599]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D599,
+ },
+ [0x1D59A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D59A,
+ },
+ [0x1D59B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D59B,
+ },
+ [0x1D59C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D59C,
+ },
+ [0x1D59D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D59D,
+ },
+ [0x1D59E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D59E,
+ },
+ [0x1D59F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D59F,
+ },
+ [0x1D5A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D5A0,
+ },
+ [0x1D5A1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D5A1,
+ },
+ [0x1D5A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D5A2,
+ },
+ [0x1D5A3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D5A3,
+ },
+ [0x1D5A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D5A4,
+ },
+ [0x1D5A5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D5A5,
+ },
+ [0x1D5A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D5A6,
+ },
+ [0x1D5A7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D5A7,
+ },
+ [0x1D5A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D5A8,
+ },
+ [0x1D5A9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D5A9,
+ },
+ [0x1D5AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D5AA,
+ },
+ [0x1D5AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D5AB,
+ },
+ [0x1D5AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D5AC,
+ },
+ [0x1D5AD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D5AD,
+ },
+ [0x1D5AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D5AE,
+ },
+ [0x1D5AF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D5AF,
+ },
+ [0x1D5B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D5B0,
+ },
+ [0x1D5B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D5B1,
+ },
+ [0x1D5B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D5B2,
+ },
+ [0x1D5B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D5B3,
+ },
+ [0x1D5B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D5B4,
+ },
+ [0x1D5B5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D5B5,
+ },
+ [0x1D5B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D5B6,
+ },
+ [0x1D5B7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D5B7,
+ },
+ [0x1D5B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D5B8,
+ },
+ [0x1D5B9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D5B9,
+ },
+ [0x1D5BA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D5BA,
+ },
+ [0x1D5BB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D5BB,
+ },
+ [0x1D5BC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D5BC,
+ },
+ [0x1D5BD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D5BD,
+ },
+ [0x1D5BE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D5BE,
+ },
+ [0x1D5BF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D5BF,
+ },
+ [0x1D5C0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D5C0,
+ },
+ [0x1D5C1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D5C1,
+ },
+ [0x1D5C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D5C2,
+ },
+ [0x1D5C3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D5C3,
+ },
+ [0x1D5C4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D5C4,
+ },
+ [0x1D5C5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D5C5,
+ },
+ [0x1D5C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D5C6,
+ },
+ [0x1D5C7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D5C7,
+ },
+ [0x1D5C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D5C8,
+ },
+ [0x1D5C9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D5C9,
+ },
+ [0x1D5CA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D5CA,
+ },
+ [0x1D5CB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D5CB,
+ },
+ [0x1D5CC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D5CC,
+ },
+ [0x1D5CD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D5CD,
+ },
+ [0x1D5CE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D5CE,
+ },
+ [0x1D5CF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D5CF,
+ },
+ [0x1D5D0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D5D0,
+ },
+ [0x1D5D1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D5D1,
+ },
+ [0x1D5D2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D5D2,
+ },
+ [0x1D5D3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D5D3,
+ },
+ [0x1D5D4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D5D4,
+ },
+ [0x1D5D5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D5D5,
+ },
+ [0x1D5D6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D5D6,
+ },
+ [0x1D5D7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D5D7,
+ },
+ [0x1D5D8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D5D8,
+ },
+ [0x1D5D9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D5D9,
+ },
+ [0x1D5DA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D5DA,
+ },
+ [0x1D5DB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D5DB,
+ },
+ [0x1D5DC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D5DC,
+ },
+ [0x1D5DD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D5DD,
+ },
+ [0x1D5DE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D5DE,
+ },
+ [0x1D5DF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D5DF,
+ },
+ [0x1D5E0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D5E0,
+ },
+ [0x1D5E1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D5E1,
+ },
+ [0x1D5E2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D5E2,
+ },
+ [0x1D5E3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D5E3,
+ },
+ [0x1D5E4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D5E4,
+ },
+ [0x1D5E5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D5E5,
+ },
+ [0x1D5E6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D5E6,
+ },
+ [0x1D5E7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D5E7,
+ },
+ [0x1D5E8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D5E8,
+ },
+ [0x1D5E9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D5E9,
+ },
+ [0x1D5EA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D5EA,
+ },
+ [0x1D5EB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D5EB,
+ },
+ [0x1D5EC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D5EC,
+ },
+ [0x1D5ED]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D5ED,
+ },
+ [0x1D5EE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D5EE,
+ },
+ [0x1D5EF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D5EF,
+ },
+ [0x1D5F0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D5F0,
+ },
+ [0x1D5F1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D5F1,
+ },
+ [0x1D5F2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D5F2,
+ },
+ [0x1D5F3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D5F3,
+ },
+ [0x1D5F4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D5F4,
+ },
+ [0x1D5F5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D5F5,
+ },
+ [0x1D5F6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D5F6,
+ },
+ [0x1D5F7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D5F7,
+ },
+ [0x1D5F8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D5F8,
+ },
+ [0x1D5F9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D5F9,
+ },
+ [0x1D5FA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D5FA,
+ },
+ [0x1D5FB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D5FB,
+ },
+ [0x1D5FC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D5FC,
+ },
+ [0x1D5FD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D5FD,
+ },
+ [0x1D5FE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D5FE,
+ },
+ [0x1D5FF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D5FF,
+ },
+ [0x1D600]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D600,
+ },
+ [0x1D601]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D601,
+ },
+ [0x1D602]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D602,
+ },
+ [0x1D603]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D603,
+ },
+ [0x1D604]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D604,
+ },
+ [0x1D605]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D605,
+ },
+ [0x1D606]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D606,
+ },
+ [0x1D607]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D607,
+ },
+ [0x1D608]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D608,
+ },
+ [0x1D609]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D609,
+ },
+ [0x1D60A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D60A,
+ },
+ [0x1D60B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D60B,
+ },
+ [0x1D60C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D60C,
+ },
+ [0x1D60D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D60D,
+ },
+ [0x1D60E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D60E,
+ },
+ [0x1D60F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D60F,
+ },
+ [0x1D610]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D610,
+ },
+ [0x1D611]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D611,
+ },
+ [0x1D612]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D612,
+ },
+ [0x1D613]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D613,
+ },
+ [0x1D614]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D614,
+ },
+ [0x1D615]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D615,
+ },
+ [0x1D616]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D616,
+ },
+ [0x1D617]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D617,
+ },
+ [0x1D618]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D618,
+ },
+ [0x1D619]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D619,
+ },
+ [0x1D61A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D61A,
+ },
+ [0x1D61B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D61B,
+ },
+ [0x1D61C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D61C,
+ },
+ [0x1D61D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D61D,
+ },
+ [0x1D61E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D61E,
+ },
+ [0x1D61F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D61F,
+ },
+ [0x1D620]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D620,
+ },
+ [0x1D621]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D621,
+ },
+ [0x1D622]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D622,
+ },
+ [0x1D623]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D623,
+ },
+ [0x1D624]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D624,
+ },
+ [0x1D625]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D625,
+ },
+ [0x1D626]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D626,
+ },
+ [0x1D627]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D627,
+ },
+ [0x1D628]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D628,
+ },
+ [0x1D629]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D629,
+ },
+ [0x1D62A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D62A,
+ },
+ [0x1D62B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D62B,
+ },
+ [0x1D62C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D62C,
+ },
+ [0x1D62D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D62D,
+ },
+ [0x1D62E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D62E,
+ },
+ [0x1D62F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D62F,
+ },
+ [0x1D630]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D630,
+ },
+ [0x1D631]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D631,
+ },
+ [0x1D632]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D632,
+ },
+ [0x1D633]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D633,
+ },
+ [0x1D634]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D634,
+ },
+ [0x1D635]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D635,
+ },
+ [0x1D636]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D636,
+ },
+ [0x1D637]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D637,
+ },
+ [0x1D638]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D638,
+ },
+ [0x1D639]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D639,
+ },
+ [0x1D63A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D63A,
+ },
+ [0x1D63B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D63B,
+ },
+ [0x1D63C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D63C,
+ },
+ [0x1D63D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D63D,
+ },
+ [0x1D63E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D63E,
+ },
+ [0x1D63F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D63F,
+ },
+ [0x1D640]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D640,
+ },
+ [0x1D641]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D641,
+ },
+ [0x1D642]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D642,
+ },
+ [0x1D643]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D643,
+ },
+ [0x1D644]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D644,
+ },
+ [0x1D645]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D645,
+ },
+ [0x1D646]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D646,
+ },
+ [0x1D647]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D647,
+ },
+ [0x1D648]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D648,
+ },
+ [0x1D649]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D649,
+ },
+ [0x1D64A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D64A,
+ },
+ [0x1D64B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D64B,
+ },
+ [0x1D64C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D64C,
+ },
+ [0x1D64D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D64D,
+ },
+ [0x1D64E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D64E,
+ },
+ [0x1D64F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D64F,
+ },
+ [0x1D650]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D650,
+ },
+ [0x1D651]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D651,
+ },
+ [0x1D652]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D652,
+ },
+ [0x1D653]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D653,
+ },
+ [0x1D654]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D654,
+ },
+ [0x1D655]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D655,
+ },
+ [0x1D656]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D656,
+ },
+ [0x1D657]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D657,
+ },
+ [0x1D658]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D658,
+ },
+ [0x1D659]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D659,
+ },
+ [0x1D65A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D65A,
+ },
+ [0x1D65B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D65B,
+ },
+ [0x1D65C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D65C,
+ },
+ [0x1D65D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D65D,
+ },
+ [0x1D65E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D65E,
+ },
+ [0x1D65F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D65F,
+ },
+ [0x1D660]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D660,
+ },
+ [0x1D661]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D661,
+ },
+ [0x1D662]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D662,
+ },
+ [0x1D663]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D663,
+ },
+ [0x1D664]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D664,
+ },
+ [0x1D665]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D665,
+ },
+ [0x1D666]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D666,
+ },
+ [0x1D667]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D667,
+ },
+ [0x1D668]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D668,
+ },
+ [0x1D669]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D669,
+ },
+ [0x1D66A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D66A,
+ },
+ [0x1D66B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D66B,
+ },
+ [0x1D66C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D66C,
+ },
+ [0x1D66D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D66D,
+ },
+ [0x1D66E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D66E,
+ },
+ [0x1D66F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D66F,
+ },
+ [0x1D670]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x41 },
+ unicodeslot=0x1D670,
+ },
+ [0x1D671]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x42 },
+ unicodeslot=0x1D671,
+ },
+ [0x1D672]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x43 },
+ unicodeslot=0x1D672,
+ },
+ [0x1D673]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x44 },
+ unicodeslot=0x1D673,
+ },
+ [0x1D674]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x45 },
+ unicodeslot=0x1D674,
+ },
+ [0x1D675]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x46 },
+ unicodeslot=0x1D675,
+ },
+ [0x1D676]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x47 },
+ unicodeslot=0x1D676,
+ },
+ [0x1D677]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x48 },
+ unicodeslot=0x1D677,
+ },
+ [0x1D678]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x49 },
+ unicodeslot=0x1D678,
+ },
+ [0x1D679]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4A },
+ unicodeslot=0x1D679,
+ },
+ [0x1D67A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4B },
+ unicodeslot=0x1D67A,
+ },
+ [0x1D67B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4C },
+ unicodeslot=0x1D67B,
+ },
+ [0x1D67C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4D },
+ unicodeslot=0x1D67C,
+ },
+ [0x1D67D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4E },
+ unicodeslot=0x1D67D,
+ },
+ [0x1D67E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x4F },
+ unicodeslot=0x1D67E,
+ },
+ [0x1D67F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x50 },
+ unicodeslot=0x1D67F,
+ },
+ [0x1D680]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x51 },
+ unicodeslot=0x1D680,
+ },
+ [0x1D681]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x52 },
+ unicodeslot=0x1D681,
+ },
+ [0x1D682]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x53 },
+ unicodeslot=0x1D682,
+ },
+ [0x1D683]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x54 },
+ unicodeslot=0x1D683,
+ },
+ [0x1D684]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x55 },
+ unicodeslot=0x1D684,
+ },
+ [0x1D685]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x56 },
+ unicodeslot=0x1D685,
+ },
+ [0x1D686]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x57 },
+ unicodeslot=0x1D686,
+ },
+ [0x1D687]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x58 },
+ unicodeslot=0x1D687,
+ },
+ [0x1D688]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x59 },
+ unicodeslot=0x1D688,
+ },
+ [0x1D689]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x5A },
+ unicodeslot=0x1D689,
+ },
+ [0x1D68A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x61 },
+ unicodeslot=0x1D68A,
+ },
+ [0x1D68B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x62 },
+ unicodeslot=0x1D68B,
+ },
+ [0x1D68C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x63 },
+ unicodeslot=0x1D68C,
+ },
+ [0x1D68D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x64 },
+ unicodeslot=0x1D68D,
+ },
+ [0x1D68E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x65 },
+ unicodeslot=0x1D68E,
+ },
+ [0x1D68F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x66 },
+ unicodeslot=0x1D68F,
+ },
+ [0x1D690]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x67 },
+ unicodeslot=0x1D690,
+ },
+ [0x1D691]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x68 },
+ unicodeslot=0x1D691,
+ },
+ [0x1D692]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x69 },
+ unicodeslot=0x1D692,
+ },
+ [0x1D693]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6A },
+ unicodeslot=0x1D693,
+ },
+ [0x1D694]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6B },
+ unicodeslot=0x1D694,
+ },
+ [0x1D695]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6C },
+ unicodeslot=0x1D695,
+ },
+ [0x1D696]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6D },
+ unicodeslot=0x1D696,
+ },
+ [0x1D697]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6E },
+ unicodeslot=0x1D697,
+ },
+ [0x1D698]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x6F },
+ unicodeslot=0x1D698,
+ },
+ [0x1D699]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x70 },
+ unicodeslot=0x1D699,
+ },
+ [0x1D69A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x71 },
+ unicodeslot=0x1D69A,
+ },
+ [0x1D69B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x72 },
+ unicodeslot=0x1D69B,
+ },
+ [0x1D69C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x73 },
+ unicodeslot=0x1D69C,
+ },
+ [0x1D69D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x74 },
+ unicodeslot=0x1D69D,
+ },
+ [0x1D69E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x75 },
+ unicodeslot=0x1D69E,
+ },
+ [0x1D69F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x76 },
+ unicodeslot=0x1D69F,
+ },
+ [0x1D6A0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x77 },
+ unicodeslot=0x1D6A0,
+ },
+ [0x1D6A1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x78 },
+ unicodeslot=0x1D6A1,
+ },
+ [0x1D6A2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x79 },
+ unicodeslot=0x1D6A2,
+ },
+ [0x1D6A3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x7A },
+ unicodeslot=0x1D6A3,
+ },
+ [0x1D6A4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x131 },
+ unicodeslot=0x1D6A4,
+ },
+ [0x1D6A5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x237 },
+ unicodeslot=0x1D6A5,
+ },
+ [0x1D6A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x391 },
+ unicodeslot=0x1D6A8,
+ },
+ [0x1D6A9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x392 },
+ unicodeslot=0x1D6A9,
+ },
+ [0x1D6AA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x393 },
+ unicodeslot=0x1D6AA,
+ },
+ [0x1D6AB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x394 },
+ unicodeslot=0x1D6AB,
+ },
+ [0x1D6AC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x395 },
+ unicodeslot=0x1D6AC,
+ },
+ [0x1D6AD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x396 },
+ unicodeslot=0x1D6AD,
+ },
+ [0x1D6AE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x397 },
+ unicodeslot=0x1D6AE,
+ },
+ [0x1D6AF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x398 },
+ unicodeslot=0x1D6AF,
+ },
+ [0x1D6B0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x399 },
+ unicodeslot=0x1D6B0,
+ },
+ [0x1D6B1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39A },
+ unicodeslot=0x1D6B1,
+ },
+ [0x1D6B2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39B },
+ unicodeslot=0x1D6B2,
+ },
+ [0x1D6B3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39C },
+ unicodeslot=0x1D6B3,
+ },
+ [0x1D6B4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39D },
+ unicodeslot=0x1D6B4,
+ },
+ [0x1D6B5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39E },
+ unicodeslot=0x1D6B5,
+ },
+ [0x1D6B6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39F },
+ unicodeslot=0x1D6B6,
+ },
+ [0x1D6B7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A0 },
+ unicodeslot=0x1D6B7,
+ },
+ [0x1D6B8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A1 },
+ unicodeslot=0x1D6B8,
+ },
+ [0x1D6B9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F4 },
+ unicodeslot=0x1D6B9,
+ },
+ [0x1D6BA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A3 },
+ unicodeslot=0x1D6BA,
+ },
+ [0x1D6BB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A4 },
+ unicodeslot=0x1D6BB,
+ },
+ [0x1D6BC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A5 },
+ unicodeslot=0x1D6BC,
+ },
+ [0x1D6BD]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A6 },
+ unicodeslot=0x1D6BD,
+ },
+ [0x1D6BE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A7 },
+ unicodeslot=0x1D6BE,
+ },
+ [0x1D6BF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A8 },
+ unicodeslot=0x1D6BF,
+ },
+ [0x1D6C0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A9 },
+ unicodeslot=0x1D6C0,
+ },
+ [0x1D6C1]={
+ category="sm",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x2207 },
+ unicodeslot=0x1D6C1,
+ },
+ [0x1D6C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B1 },
+ unicodeslot=0x1D6C2,
+ },
+ [0x1D6C3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B2 },
+ unicodeslot=0x1D6C3,
+ },
+ [0x1D6C4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B3 },
+ unicodeslot=0x1D6C4,
+ },
+ [0x1D6C5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B4 },
+ unicodeslot=0x1D6C5,
+ },
+ [0x1D6C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B5 },
+ unicodeslot=0x1D6C6,
+ },
+ [0x1D6C7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B6 },
+ unicodeslot=0x1D6C7,
+ },
+ [0x1D6C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B7 },
+ unicodeslot=0x1D6C8,
+ },
+ [0x1D6C9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B8 },
+ unicodeslot=0x1D6C9,
+ },
+ [0x1D6CA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B9 },
+ unicodeslot=0x1D6CA,
+ },
+ [0x1D6CB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BA },
+ unicodeslot=0x1D6CB,
+ },
+ [0x1D6CC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BB },
+ unicodeslot=0x1D6CC,
+ },
+ [0x1D6CD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BC },
+ unicodeslot=0x1D6CD,
+ },
+ [0x1D6CE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BD },
+ unicodeslot=0x1D6CE,
+ },
+ [0x1D6CF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BE },
+ unicodeslot=0x1D6CF,
+ },
+ [0x1D6D0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BF },
+ unicodeslot=0x1D6D0,
+ },
+ [0x1D6D1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C0 },
+ unicodeslot=0x1D6D1,
+ },
+ [0x1D6D2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C1 },
+ unicodeslot=0x1D6D2,
+ },
+ [0x1D6D3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C2 },
+ unicodeslot=0x1D6D3,
+ },
+ [0x1D6D4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C3 },
+ unicodeslot=0x1D6D4,
+ },
+ [0x1D6D5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C4 },
+ unicodeslot=0x1D6D5,
+ },
+ [0x1D6D6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C5 },
+ unicodeslot=0x1D6D6,
+ },
+ [0x1D6D7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C6 },
+ unicodeslot=0x1D6D7,
+ },
+ [0x1D6D8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C7 },
+ unicodeslot=0x1D6D8,
+ },
+ [0x1D6D9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C8 },
+ unicodeslot=0x1D6D9,
+ },
+ [0x1D6DA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C9 },
+ unicodeslot=0x1D6DA,
+ },
+ [0x1D6DB]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "font", 0x2202 },
+ unicodeslot=0x1D6DB,
+ },
+ [0x1D6DC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F5 },
+ unicodeslot=0x1D6DC,
+ },
+ [0x1D6DD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D1 },
+ unicodeslot=0x1D6DD,
+ },
+ [0x1D6DE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F0 },
+ unicodeslot=0x1D6DE,
+ },
+ [0x1D6DF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D5 },
+ unicodeslot=0x1D6DF,
+ },
+ [0x1D6E0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F1 },
+ unicodeslot=0x1D6E0,
+ },
+ [0x1D6E1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D6 },
+ unicodeslot=0x1D6E1,
+ },
+ [0x1D6E2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x391 },
+ unicodeslot=0x1D6E2,
+ },
+ [0x1D6E3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x392 },
+ unicodeslot=0x1D6E3,
+ },
+ [0x1D6E4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x393 },
+ unicodeslot=0x1D6E4,
+ },
+ [0x1D6E5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x394 },
+ unicodeslot=0x1D6E5,
+ },
+ [0x1D6E6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x395 },
+ unicodeslot=0x1D6E6,
+ },
+ [0x1D6E7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x396 },
+ unicodeslot=0x1D6E7,
+ },
+ [0x1D6E8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x397 },
+ unicodeslot=0x1D6E8,
+ },
+ [0x1D6E9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x398 },
+ unicodeslot=0x1D6E9,
+ },
+ [0x1D6EA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x399 },
+ unicodeslot=0x1D6EA,
+ },
+ [0x1D6EB]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39A },
+ unicodeslot=0x1D6EB,
+ },
+ [0x1D6EC]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39B },
+ unicodeslot=0x1D6EC,
+ },
+ [0x1D6ED]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39C },
+ unicodeslot=0x1D6ED,
+ },
+ [0x1D6EE]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39D },
+ unicodeslot=0x1D6EE,
+ },
+ [0x1D6EF]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39E },
+ unicodeslot=0x1D6EF,
+ },
+ [0x1D6F0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39F },
+ unicodeslot=0x1D6F0,
+ },
+ [0x1D6F1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A0 },
+ unicodeslot=0x1D6F1,
+ },
+ [0x1D6F2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A1 },
+ unicodeslot=0x1D6F2,
+ },
+ [0x1D6F3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F4 },
+ unicodeslot=0x1D6F3,
+ },
+ [0x1D6F4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A3 },
+ unicodeslot=0x1D6F4,
+ },
+ [0x1D6F5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A4 },
+ unicodeslot=0x1D6F5,
+ },
+ [0x1D6F6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A5 },
+ unicodeslot=0x1D6F6,
+ },
+ [0x1D6F7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A6 },
+ unicodeslot=0x1D6F7,
+ },
+ [0x1D6F8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A7 },
+ unicodeslot=0x1D6F8,
+ },
+ [0x1D6F9]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A8 },
+ unicodeslot=0x1D6F9,
+ },
+ [0x1D6FA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A9 },
+ unicodeslot=0x1D6FA,
+ },
+ [0x1D6FB]={
+ category="sm",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x2207 },
+ unicodeslot=0x1D6FB,
+ },
+ [0x1D6FC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B1 },
+ unicodeslot=0x1D6FC,
+ },
+ [0x1D6FD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B2 },
+ unicodeslot=0x1D6FD,
+ },
+ [0x1D6FE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B3 },
+ unicodeslot=0x1D6FE,
+ },
+ [0x1D6FF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B4 },
+ unicodeslot=0x1D6FF,
+ },
+ [0x1D700]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B5 },
+ unicodeslot=0x1D700,
+ },
+ [0x1D701]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B6 },
+ unicodeslot=0x1D701,
+ },
+ [0x1D702]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B7 },
+ unicodeslot=0x1D702,
+ },
+ [0x1D703]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B8 },
+ unicodeslot=0x1D703,
+ },
+ [0x1D704]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B9 },
+ unicodeslot=0x1D704,
+ },
+ [0x1D705]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BA },
+ unicodeslot=0x1D705,
+ },
+ [0x1D706]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BB },
+ unicodeslot=0x1D706,
+ },
+ [0x1D707]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BC },
+ unicodeslot=0x1D707,
+ },
+ [0x1D708]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BD },
+ unicodeslot=0x1D708,
+ },
+ [0x1D709]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BE },
+ unicodeslot=0x1D709,
+ },
+ [0x1D70A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BF },
+ unicodeslot=0x1D70A,
+ },
+ [0x1D70B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C0 },
+ unicodeslot=0x1D70B,
+ },
+ [0x1D70C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C1 },
+ unicodeslot=0x1D70C,
+ },
+ [0x1D70D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C2 },
+ unicodeslot=0x1D70D,
+ },
+ [0x1D70E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C3 },
+ unicodeslot=0x1D70E,
+ },
+ [0x1D70F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C4 },
+ unicodeslot=0x1D70F,
+ },
+ [0x1D710]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C5 },
+ unicodeslot=0x1D710,
+ },
+ [0x1D711]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C6 },
+ unicodeslot=0x1D711,
+ },
+ [0x1D712]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C7 },
+ unicodeslot=0x1D712,
+ },
+ [0x1D713]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C8 },
+ unicodeslot=0x1D713,
+ },
+ [0x1D714]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C9 },
+ unicodeslot=0x1D714,
+ },
+ [0x1D715]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "font", 0x2202 },
+ unicodeslot=0x1D715,
+ },
+ [0x1D716]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F5 },
+ unicodeslot=0x1D716,
+ },
+ [0x1D717]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D1 },
+ unicodeslot=0x1D717,
+ },
+ [0x1D718]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F0 },
+ unicodeslot=0x1D718,
+ },
+ [0x1D719]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D5 },
+ unicodeslot=0x1D719,
+ },
+ [0x1D71A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F1 },
+ unicodeslot=0x1D71A,
+ },
+ [0x1D71B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D6 },
+ unicodeslot=0x1D71B,
+ },
+ [0x1D71C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x391 },
+ unicodeslot=0x1D71C,
+ },
+ [0x1D71D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x392 },
+ unicodeslot=0x1D71D,
+ },
+ [0x1D71E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x393 },
+ unicodeslot=0x1D71E,
+ },
+ [0x1D71F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x394 },
+ unicodeslot=0x1D71F,
+ },
+ [0x1D720]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x395 },
+ unicodeslot=0x1D720,
+ },
+ [0x1D721]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x396 },
+ unicodeslot=0x1D721,
+ },
+ [0x1D722]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x397 },
+ unicodeslot=0x1D722,
+ },
+ [0x1D723]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x398 },
+ unicodeslot=0x1D723,
+ },
+ [0x1D724]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x399 },
+ unicodeslot=0x1D724,
+ },
+ [0x1D725]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39A },
+ unicodeslot=0x1D725,
+ },
+ [0x1D726]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39B },
+ unicodeslot=0x1D726,
+ },
+ [0x1D727]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39C },
+ unicodeslot=0x1D727,
+ },
+ [0x1D728]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39D },
+ unicodeslot=0x1D728,
+ },
+ [0x1D729]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39E },
+ unicodeslot=0x1D729,
+ },
+ [0x1D72A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39F },
+ unicodeslot=0x1D72A,
+ },
+ [0x1D72B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A0 },
+ unicodeslot=0x1D72B,
+ },
+ [0x1D72C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A1 },
+ unicodeslot=0x1D72C,
+ },
+ [0x1D72D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F4 },
+ unicodeslot=0x1D72D,
+ },
+ [0x1D72E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A3 },
+ unicodeslot=0x1D72E,
+ },
+ [0x1D72F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A4 },
+ unicodeslot=0x1D72F,
+ },
+ [0x1D730]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A5 },
+ unicodeslot=0x1D730,
+ },
+ [0x1D731]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A6 },
+ unicodeslot=0x1D731,
+ },
+ [0x1D732]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A7 },
+ unicodeslot=0x1D732,
+ },
+ [0x1D733]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A8 },
+ unicodeslot=0x1D733,
+ },
+ [0x1D734]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A9 },
+ unicodeslot=0x1D734,
+ },
+ [0x1D735]={
+ category="sm",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x2207 },
+ unicodeslot=0x1D735,
+ },
+ [0x1D736]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B1 },
+ unicodeslot=0x1D736,
+ },
+ [0x1D737]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B2 },
+ unicodeslot=0x1D737,
+ },
+ [0x1D738]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B3 },
+ unicodeslot=0x1D738,
+ },
+ [0x1D739]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B4 },
+ unicodeslot=0x1D739,
+ },
+ [0x1D73A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B5 },
+ unicodeslot=0x1D73A,
+ },
+ [0x1D73B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B6 },
+ unicodeslot=0x1D73B,
+ },
+ [0x1D73C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B7 },
+ unicodeslot=0x1D73C,
+ },
+ [0x1D73D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B8 },
+ unicodeslot=0x1D73D,
+ },
+ [0x1D73E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B9 },
+ unicodeslot=0x1D73E,
+ },
+ [0x1D73F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BA },
+ unicodeslot=0x1D73F,
+ },
+ [0x1D740]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BB },
+ unicodeslot=0x1D740,
+ },
+ [0x1D741]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BC },
+ unicodeslot=0x1D741,
+ },
+ [0x1D742]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BD },
+ unicodeslot=0x1D742,
+ },
+ [0x1D743]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BE },
+ unicodeslot=0x1D743,
+ },
+ [0x1D744]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BF },
+ unicodeslot=0x1D744,
+ },
+ [0x1D745]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C0 },
+ unicodeslot=0x1D745,
+ },
+ [0x1D746]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C1 },
+ unicodeslot=0x1D746,
+ },
+ [0x1D747]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C2 },
+ unicodeslot=0x1D747,
+ },
+ [0x1D748]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C3 },
+ unicodeslot=0x1D748,
+ },
+ [0x1D749]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C4 },
+ unicodeslot=0x1D749,
+ },
+ [0x1D74A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C5 },
+ unicodeslot=0x1D74A,
+ },
+ [0x1D74B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C6 },
+ unicodeslot=0x1D74B,
+ },
+ [0x1D74C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C7 },
+ unicodeslot=0x1D74C,
+ },
+ [0x1D74D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C8 },
+ unicodeslot=0x1D74D,
+ },
+ [0x1D74E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C9 },
+ unicodeslot=0x1D74E,
+ },
+ [0x1D74F]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "font", 0x2202 },
+ unicodeslot=0x1D74F,
+ },
+ [0x1D750]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F5 },
+ unicodeslot=0x1D750,
+ },
+ [0x1D751]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D1 },
+ unicodeslot=0x1D751,
+ },
+ [0x1D752]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F0 },
+ unicodeslot=0x1D752,
+ },
+ [0x1D753]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D5 },
+ unicodeslot=0x1D753,
+ },
+ [0x1D754]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F1 },
+ unicodeslot=0x1D754,
+ },
+ [0x1D755]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D6 },
+ unicodeslot=0x1D755,
+ },
+ [0x1D756]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x391 },
+ unicodeslot=0x1D756,
+ },
+ [0x1D757]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x392 },
+ unicodeslot=0x1D757,
+ },
+ [0x1D758]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x393 },
+ unicodeslot=0x1D758,
+ },
+ [0x1D759]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x394 },
+ unicodeslot=0x1D759,
+ },
+ [0x1D75A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x395 },
+ unicodeslot=0x1D75A,
+ },
+ [0x1D75B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x396 },
+ unicodeslot=0x1D75B,
+ },
+ [0x1D75C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x397 },
+ unicodeslot=0x1D75C,
+ },
+ [0x1D75D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x398 },
+ unicodeslot=0x1D75D,
+ },
+ [0x1D75E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x399 },
+ unicodeslot=0x1D75E,
+ },
+ [0x1D75F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39A },
+ unicodeslot=0x1D75F,
+ },
+ [0x1D760]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39B },
+ unicodeslot=0x1D760,
+ },
+ [0x1D761]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39C },
+ unicodeslot=0x1D761,
+ },
+ [0x1D762]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39D },
+ unicodeslot=0x1D762,
+ },
+ [0x1D763]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39E },
+ unicodeslot=0x1D763,
+ },
+ [0x1D764]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39F },
+ unicodeslot=0x1D764,
+ },
+ [0x1D765]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A0 },
+ unicodeslot=0x1D765,
+ },
+ [0x1D766]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A1 },
+ unicodeslot=0x1D766,
+ },
+ [0x1D767]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F4 },
+ unicodeslot=0x1D767,
+ },
+ [0x1D768]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A3 },
+ unicodeslot=0x1D768,
+ },
+ [0x1D769]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A4 },
+ unicodeslot=0x1D769,
+ },
+ [0x1D76A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A5 },
+ unicodeslot=0x1D76A,
+ },
+ [0x1D76B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A6 },
+ unicodeslot=0x1D76B,
+ },
+ [0x1D76C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A7 },
+ unicodeslot=0x1D76C,
+ },
+ [0x1D76D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A8 },
+ unicodeslot=0x1D76D,
+ },
+ [0x1D76E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A9 },
+ unicodeslot=0x1D76E,
+ },
+ [0x1D76F]={
+ category="sm",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x2207 },
+ unicodeslot=0x1D76F,
+ },
+ [0x1D770]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B1 },
+ unicodeslot=0x1D770,
+ },
+ [0x1D771]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B2 },
+ unicodeslot=0x1D771,
+ },
+ [0x1D772]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B3 },
+ unicodeslot=0x1D772,
+ },
+ [0x1D773]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B4 },
+ unicodeslot=0x1D773,
+ },
+ [0x1D774]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B5 },
+ unicodeslot=0x1D774,
+ },
+ [0x1D775]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B6 },
+ unicodeslot=0x1D775,
+ },
+ [0x1D776]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B7 },
+ unicodeslot=0x1D776,
+ },
+ [0x1D777]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B8 },
+ unicodeslot=0x1D777,
+ },
+ [0x1D778]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B9 },
+ unicodeslot=0x1D778,
+ },
+ [0x1D779]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BA },
+ unicodeslot=0x1D779,
+ },
+ [0x1D77A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BB },
+ unicodeslot=0x1D77A,
+ },
+ [0x1D77B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BC },
+ unicodeslot=0x1D77B,
+ },
+ [0x1D77C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BD },
+ unicodeslot=0x1D77C,
+ },
+ [0x1D77D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BE },
+ unicodeslot=0x1D77D,
+ },
+ [0x1D77E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BF },
+ unicodeslot=0x1D77E,
+ },
+ [0x1D77F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C0 },
+ unicodeslot=0x1D77F,
+ },
+ [0x1D780]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C1 },
+ unicodeslot=0x1D780,
+ },
+ [0x1D781]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C2 },
+ unicodeslot=0x1D781,
+ },
+ [0x1D782]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C3 },
+ unicodeslot=0x1D782,
+ },
+ [0x1D783]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C4 },
+ unicodeslot=0x1D783,
+ },
+ [0x1D784]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C5 },
+ unicodeslot=0x1D784,
+ },
+ [0x1D785]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C6 },
+ unicodeslot=0x1D785,
+ },
+ [0x1D786]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C7 },
+ unicodeslot=0x1D786,
+ },
+ [0x1D787]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C8 },
+ unicodeslot=0x1D787,
+ },
+ [0x1D788]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C9 },
+ unicodeslot=0x1D788,
+ },
+ [0x1D789]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "font", 0x2202 },
+ unicodeslot=0x1D789,
+ },
+ [0x1D78A]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F5 },
+ unicodeslot=0x1D78A,
+ },
+ [0x1D78B]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D1 },
+ unicodeslot=0x1D78B,
+ },
+ [0x1D78C]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F0 },
+ unicodeslot=0x1D78C,
+ },
+ [0x1D78D]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D5 },
+ unicodeslot=0x1D78D,
+ },
+ [0x1D78E]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F1 },
+ unicodeslot=0x1D78E,
+ },
+ [0x1D78F]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D6 },
+ unicodeslot=0x1D78F,
+ },
+ [0x1D790]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x391 },
+ unicodeslot=0x1D790,
+ },
+ [0x1D791]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x392 },
+ unicodeslot=0x1D791,
+ },
+ [0x1D792]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x393 },
+ unicodeslot=0x1D792,
+ },
+ [0x1D793]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x394 },
+ unicodeslot=0x1D793,
+ },
+ [0x1D794]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x395 },
+ unicodeslot=0x1D794,
+ },
+ [0x1D795]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x396 },
+ unicodeslot=0x1D795,
+ },
+ [0x1D796]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x397 },
+ unicodeslot=0x1D796,
+ },
+ [0x1D797]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x398 },
+ unicodeslot=0x1D797,
+ },
+ [0x1D798]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x399 },
+ unicodeslot=0x1D798,
+ },
+ [0x1D799]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39A },
+ unicodeslot=0x1D799,
+ },
+ [0x1D79A]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39B },
+ unicodeslot=0x1D79A,
+ },
+ [0x1D79B]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39C },
+ unicodeslot=0x1D79B,
+ },
+ [0x1D79C]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39D },
+ unicodeslot=0x1D79C,
+ },
+ [0x1D79D]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39E },
+ unicodeslot=0x1D79D,
+ },
+ [0x1D79E]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x39F },
+ unicodeslot=0x1D79E,
+ },
+ [0x1D79F]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A0 },
+ unicodeslot=0x1D79F,
+ },
+ [0x1D7A0]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A1 },
+ unicodeslot=0x1D7A0,
+ },
+ [0x1D7A1]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F4 },
+ unicodeslot=0x1D7A1,
+ },
+ [0x1D7A2]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A3 },
+ unicodeslot=0x1D7A2,
+ },
+ [0x1D7A3]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A4 },
+ unicodeslot=0x1D7A3,
+ },
+ [0x1D7A4]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A5 },
+ unicodeslot=0x1D7A4,
+ },
+ [0x1D7A5]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A6 },
+ unicodeslot=0x1D7A5,
+ },
+ [0x1D7A6]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A7 },
+ unicodeslot=0x1D7A6,
+ },
+ [0x1D7A7]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A8 },
+ unicodeslot=0x1D7A7,
+ },
+ [0x1D7A8]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3A9 },
+ unicodeslot=0x1D7A8,
+ },
+ [0x1D7A9]={
+ category="sm",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x2207 },
+ unicodeslot=0x1D7A9,
+ },
+ [0x1D7AA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B1 },
+ unicodeslot=0x1D7AA,
+ },
+ [0x1D7AB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B2 },
+ unicodeslot=0x1D7AB,
+ },
+ [0x1D7AC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B3 },
+ unicodeslot=0x1D7AC,
+ },
+ [0x1D7AD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B4 },
+ unicodeslot=0x1D7AD,
+ },
+ [0x1D7AE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B5 },
+ unicodeslot=0x1D7AE,
+ },
+ [0x1D7AF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B6 },
+ unicodeslot=0x1D7AF,
+ },
+ [0x1D7B0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B7 },
+ unicodeslot=0x1D7B0,
+ },
+ [0x1D7B1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B8 },
+ unicodeslot=0x1D7B1,
+ },
+ [0x1D7B2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3B9 },
+ unicodeslot=0x1D7B2,
+ },
+ [0x1D7B3]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BA },
+ unicodeslot=0x1D7B3,
+ },
+ [0x1D7B4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BB },
+ unicodeslot=0x1D7B4,
+ },
+ [0x1D7B5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BC },
+ unicodeslot=0x1D7B5,
+ },
+ [0x1D7B6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BD },
+ unicodeslot=0x1D7B6,
+ },
+ [0x1D7B7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BE },
+ unicodeslot=0x1D7B7,
+ },
+ [0x1D7B8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3BF },
+ unicodeslot=0x1D7B8,
+ },
+ [0x1D7B9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C0 },
+ unicodeslot=0x1D7B9,
+ },
+ [0x1D7BA]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C1 },
+ unicodeslot=0x1D7BA,
+ },
+ [0x1D7BB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C2 },
+ unicodeslot=0x1D7BB,
+ },
+ [0x1D7BC]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C3 },
+ unicodeslot=0x1D7BC,
+ },
+ [0x1D7BD]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C4 },
+ unicodeslot=0x1D7BD,
+ },
+ [0x1D7BE]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C5 },
+ unicodeslot=0x1D7BE,
+ },
+ [0x1D7BF]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C6 },
+ unicodeslot=0x1D7BF,
+ },
+ [0x1D7C0]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C7 },
+ unicodeslot=0x1D7C0,
+ },
+ [0x1D7C1]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C8 },
+ unicodeslot=0x1D7C1,
+ },
+ [0x1D7C2]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3C9 },
+ unicodeslot=0x1D7C2,
+ },
+ [0x1D7C3]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ specials={ "font", 0x2202 },
+ unicodeslot=0x1D7C3,
+ },
+ [0x1D7C4]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F5 },
+ unicodeslot=0x1D7C4,
+ },
+ [0x1D7C5]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D1 },
+ unicodeslot=0x1D7C5,
+ },
+ [0x1D7C6]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F0 },
+ unicodeslot=0x1D7C6,
+ },
+ [0x1D7C7]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D5 },
+ unicodeslot=0x1D7C7,
+ },
+ [0x1D7C8]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3F1 },
+ unicodeslot=0x1D7C8,
+ },
+ [0x1D7C9]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3D6 },
+ unicodeslot=0x1D7C9,
+ },
+ [0x1D7CA]={
+ category="lu",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3DC },
+ unicodeslot=0x1D7CA,
+ },
+ [0x1D7CB]={
+ category="ll",
+ direction="l",
+ linebreak="al",
+ specials={ "font", 0x3DD },
+ unicodeslot=0x1D7CB,
+ },
+ [0x1D7CE]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x30 },
+ unicodeslot=0x1D7CE,
+ },
+ [0x1D7CF]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x31 },
+ unicodeslot=0x1D7CF,
+ },
+ [0x1D7D0]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x32 },
+ unicodeslot=0x1D7D0,
+ },
+ [0x1D7D1]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x33 },
+ unicodeslot=0x1D7D1,
+ },
+ [0x1D7D2]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x34 },
+ unicodeslot=0x1D7D2,
+ },
+ [0x1D7D3]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x35 },
+ unicodeslot=0x1D7D3,
+ },
+ [0x1D7D4]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x36 },
+ unicodeslot=0x1D7D4,
+ },
+ [0x1D7D5]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x37 },
+ unicodeslot=0x1D7D5,
+ },
+ [0x1D7D6]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x38 },
+ unicodeslot=0x1D7D6,
+ },
+ [0x1D7D7]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x39 },
+ unicodeslot=0x1D7D7,
+ },
+ [0x1D7D8]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x30 },
+ unicodeslot=0x1D7D8,
+ },
+ [0x1D7D9]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x31 },
+ unicodeslot=0x1D7D9,
+ },
+ [0x1D7DA]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x32 },
+ unicodeslot=0x1D7DA,
+ },
+ [0x1D7DB]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x33 },
+ unicodeslot=0x1D7DB,
+ },
+ [0x1D7DC]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x34 },
+ unicodeslot=0x1D7DC,
+ },
+ [0x1D7DD]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x35 },
+ unicodeslot=0x1D7DD,
+ },
+ [0x1D7DE]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x36 },
+ unicodeslot=0x1D7DE,
+ },
+ [0x1D7DF]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x37 },
+ unicodeslot=0x1D7DF,
+ },
+ [0x1D7E0]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x38 },
+ unicodeslot=0x1D7E0,
+ },
+ [0x1D7E1]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x39 },
+ unicodeslot=0x1D7E1,
+ },
+ [0x1D7E2]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x30 },
+ unicodeslot=0x1D7E2,
+ },
+ [0x1D7E3]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x31 },
+ unicodeslot=0x1D7E3,
+ },
+ [0x1D7E4]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x32 },
+ unicodeslot=0x1D7E4,
+ },
+ [0x1D7E5]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x33 },
+ unicodeslot=0x1D7E5,
+ },
+ [0x1D7E6]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x34 },
+ unicodeslot=0x1D7E6,
+ },
+ [0x1D7E7]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x35 },
+ unicodeslot=0x1D7E7,
+ },
+ [0x1D7E8]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x36 },
+ unicodeslot=0x1D7E8,
+ },
+ [0x1D7E9]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x37 },
+ unicodeslot=0x1D7E9,
+ },
+ [0x1D7EA]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x38 },
+ unicodeslot=0x1D7EA,
+ },
+ [0x1D7EB]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x39 },
+ unicodeslot=0x1D7EB,
+ },
+ [0x1D7EC]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x30 },
+ unicodeslot=0x1D7EC,
+ },
+ [0x1D7ED]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x31 },
+ unicodeslot=0x1D7ED,
+ },
+ [0x1D7EE]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x32 },
+ unicodeslot=0x1D7EE,
+ },
+ [0x1D7EF]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x33 },
+ unicodeslot=0x1D7EF,
+ },
+ [0x1D7F0]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x34 },
+ unicodeslot=0x1D7F0,
+ },
+ [0x1D7F1]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x35 },
+ unicodeslot=0x1D7F1,
+ },
+ [0x1D7F2]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x36 },
+ unicodeslot=0x1D7F2,
+ },
+ [0x1D7F3]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x37 },
+ unicodeslot=0x1D7F3,
+ },
+ [0x1D7F4]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x38 },
+ unicodeslot=0x1D7F4,
+ },
+ [0x1D7F5]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x39 },
+ unicodeslot=0x1D7F5,
+ },
+ [0x1D7F6]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x30 },
+ unicodeslot=0x1D7F6,
+ },
+ [0x1D7F7]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x31 },
+ unicodeslot=0x1D7F7,
+ },
+ [0x1D7F8]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x32 },
+ unicodeslot=0x1D7F8,
+ },
+ [0x1D7F9]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x33 },
+ unicodeslot=0x1D7F9,
+ },
+ [0x1D7FA]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x34 },
+ unicodeslot=0x1D7FA,
+ },
+ [0x1D7FB]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x35 },
+ unicodeslot=0x1D7FB,
+ },
+ [0x1D7FC]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x36 },
+ unicodeslot=0x1D7FC,
+ },
+ [0x1D7FD]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x37 },
+ unicodeslot=0x1D7FD,
+ },
+ [0x1D7FE]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x38 },
+ unicodeslot=0x1D7FE,
+ },
+ [0x1D7FF]={
+ category="nd",
+ direction="en",
+ linebreak="nu",
+ specials={ "font", 0x39 },
+ unicodeslot=0x1D7FF,
+ },
+ [0x1D800]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D800,
+ },
+ [0x1D801]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D801,
+ },
+ [0x1D802]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D802,
+ },
+ [0x1D803]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D803,
+ },
+ [0x1D804]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D804,
+ },
+ [0x1D805]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D805,
+ },
+ [0x1D806]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D806,
+ },
+ [0x1D807]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D807,
+ },
+ [0x1D808]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D808,
+ },
+ [0x1D809]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D809,
+ },
+ [0x1D80A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80A,
+ },
+ [0x1D80B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80B,
+ },
+ [0x1D80C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80C,
+ },
+ [0x1D80D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80D,
+ },
+ [0x1D80E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80E,
+ },
+ [0x1D80F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D80F,
+ },
+ [0x1D810]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D810,
+ },
+ [0x1D811]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D811,
+ },
+ [0x1D812]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D812,
+ },
+ [0x1D813]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D813,
+ },
+ [0x1D814]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D814,
+ },
+ [0x1D815]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D815,
+ },
+ [0x1D816]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D816,
+ },
+ [0x1D817]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D817,
+ },
+ [0x1D818]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D818,
+ },
+ [0x1D819]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D819,
+ },
+ [0x1D81A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81A,
+ },
+ [0x1D81B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81B,
+ },
+ [0x1D81C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81C,
+ },
+ [0x1D81D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81D,
+ },
+ [0x1D81E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81E,
+ },
+ [0x1D81F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D81F,
+ },
+ [0x1D820]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D820,
+ },
+ [0x1D821]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D821,
+ },
+ [0x1D822]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D822,
+ },
+ [0x1D823]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D823,
+ },
+ [0x1D824]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D824,
+ },
+ [0x1D825]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D825,
+ },
+ [0x1D826]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D826,
+ },
+ [0x1D827]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D827,
+ },
+ [0x1D828]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D828,
+ },
+ [0x1D829]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D829,
+ },
+ [0x1D82A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82A,
+ },
+ [0x1D82B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82B,
+ },
+ [0x1D82C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82C,
+ },
+ [0x1D82D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82D,
+ },
+ [0x1D82E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82E,
+ },
+ [0x1D82F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D82F,
+ },
+ [0x1D830]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D830,
+ },
+ [0x1D831]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D831,
+ },
+ [0x1D832]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D832,
+ },
+ [0x1D833]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D833,
+ },
+ [0x1D834]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D834,
+ },
+ [0x1D835]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D835,
+ },
+ [0x1D836]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D836,
+ },
+ [0x1D837]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D837,
+ },
+ [0x1D838]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D838,
+ },
+ [0x1D839]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D839,
+ },
+ [0x1D83A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83A,
+ },
+ [0x1D83B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83B,
+ },
+ [0x1D83C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83C,
+ },
+ [0x1D83D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83D,
+ },
+ [0x1D83E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83E,
+ },
+ [0x1D83F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D83F,
+ },
+ [0x1D840]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D840,
+ },
+ [0x1D841]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D841,
+ },
+ [0x1D842]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D842,
+ },
+ [0x1D843]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D843,
+ },
+ [0x1D844]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D844,
+ },
+ [0x1D845]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D845,
+ },
+ [0x1D846]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D846,
+ },
+ [0x1D847]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D847,
+ },
+ [0x1D848]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D848,
+ },
+ [0x1D849]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D849,
+ },
+ [0x1D84A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84A,
+ },
+ [0x1D84B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84B,
+ },
+ [0x1D84C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84C,
+ },
+ [0x1D84D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84D,
+ },
+ [0x1D84E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84E,
+ },
+ [0x1D84F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D84F,
+ },
+ [0x1D850]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D850,
+ },
+ [0x1D851]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D851,
+ },
+ [0x1D852]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D852,
+ },
+ [0x1D853]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D853,
+ },
+ [0x1D854]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D854,
+ },
+ [0x1D855]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D855,
+ },
+ [0x1D856]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D856,
+ },
+ [0x1D857]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D857,
+ },
+ [0x1D858]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D858,
+ },
+ [0x1D859]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D859,
+ },
+ [0x1D85A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85A,
+ },
+ [0x1D85B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85B,
+ },
+ [0x1D85C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85C,
+ },
+ [0x1D85D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85D,
+ },
+ [0x1D85E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85E,
+ },
+ [0x1D85F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D85F,
+ },
+ [0x1D860]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D860,
+ },
+ [0x1D861]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D861,
+ },
+ [0x1D862]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D862,
+ },
+ [0x1D863]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D863,
+ },
+ [0x1D864]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D864,
+ },
+ [0x1D865]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D865,
+ },
+ [0x1D866]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D866,
+ },
+ [0x1D867]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D867,
+ },
+ [0x1D868]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D868,
+ },
+ [0x1D869]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D869,
+ },
+ [0x1D86A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86A,
+ },
+ [0x1D86B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86B,
+ },
+ [0x1D86C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86C,
+ },
+ [0x1D86D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86D,
+ },
+ [0x1D86E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86E,
+ },
+ [0x1D86F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D86F,
+ },
+ [0x1D870]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D870,
+ },
+ [0x1D871]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D871,
+ },
+ [0x1D872]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D872,
+ },
+ [0x1D873]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D873,
+ },
+ [0x1D874]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D874,
+ },
+ [0x1D875]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D875,
+ },
+ [0x1D876]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D876,
+ },
+ [0x1D877]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D877,
+ },
+ [0x1D878]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D878,
+ },
+ [0x1D879]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D879,
+ },
+ [0x1D87A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87A,
+ },
+ [0x1D87B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87B,
+ },
+ [0x1D87C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87C,
+ },
+ [0x1D87D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87D,
+ },
+ [0x1D87E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87E,
+ },
+ [0x1D87F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D87F,
+ },
+ [0x1D880]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D880,
+ },
+ [0x1D881]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D881,
+ },
+ [0x1D882]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D882,
+ },
+ [0x1D883]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D883,
+ },
+ [0x1D884]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D884,
+ },
+ [0x1D885]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D885,
+ },
+ [0x1D886]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D886,
+ },
+ [0x1D887]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D887,
+ },
+ [0x1D888]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D888,
+ },
+ [0x1D889]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D889,
+ },
+ [0x1D88A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88A,
+ },
+ [0x1D88B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88B,
+ },
+ [0x1D88C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88C,
+ },
+ [0x1D88D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88D,
+ },
+ [0x1D88E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88E,
+ },
+ [0x1D88F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D88F,
+ },
+ [0x1D890]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D890,
+ },
+ [0x1D891]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D891,
+ },
+ [0x1D892]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D892,
+ },
+ [0x1D893]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D893,
+ },
+ [0x1D894]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D894,
+ },
+ [0x1D895]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D895,
+ },
+ [0x1D896]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D896,
+ },
+ [0x1D897]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D897,
+ },
+ [0x1D898]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D898,
+ },
+ [0x1D899]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D899,
+ },
+ [0x1D89A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89A,
+ },
+ [0x1D89B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89B,
+ },
+ [0x1D89C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89C,
+ },
+ [0x1D89D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89D,
+ },
+ [0x1D89E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89E,
+ },
+ [0x1D89F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D89F,
+ },
+ [0x1D8A0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A0,
+ },
+ [0x1D8A1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A1,
+ },
+ [0x1D8A2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A2,
+ },
+ [0x1D8A3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A3,
+ },
+ [0x1D8A4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A4,
+ },
+ [0x1D8A5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A5,
+ },
+ [0x1D8A6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A6,
+ },
+ [0x1D8A7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A7,
+ },
+ [0x1D8A8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A8,
+ },
+ [0x1D8A9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8A9,
+ },
+ [0x1D8AA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8AA,
+ },
+ [0x1D8AB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8AB,
+ },
+ [0x1D8AC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8AC,
+ },
+ [0x1D8AD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8AD,
+ },
+ [0x1D8AE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8AE,
+ },
+ [0x1D8AF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8AF,
+ },
+ [0x1D8B0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B0,
+ },
+ [0x1D8B1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B1,
+ },
+ [0x1D8B2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B2,
+ },
+ [0x1D8B3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B3,
+ },
+ [0x1D8B4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B4,
+ },
+ [0x1D8B5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B5,
+ },
+ [0x1D8B6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B6,
+ },
+ [0x1D8B7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B7,
+ },
+ [0x1D8B8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B8,
+ },
+ [0x1D8B9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8B9,
+ },
+ [0x1D8BA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8BA,
+ },
+ [0x1D8BB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8BB,
+ },
+ [0x1D8BC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8BC,
+ },
+ [0x1D8BD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8BD,
+ },
+ [0x1D8BE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8BE,
+ },
+ [0x1D8BF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8BF,
+ },
+ [0x1D8C0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C0,
+ },
+ [0x1D8C1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C1,
+ },
+ [0x1D8C2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C2,
+ },
+ [0x1D8C3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C3,
+ },
+ [0x1D8C4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C4,
+ },
+ [0x1D8C5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C5,
+ },
+ [0x1D8C6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C6,
+ },
+ [0x1D8C7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C7,
+ },
+ [0x1D8C8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C8,
+ },
+ [0x1D8C9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8C9,
+ },
+ [0x1D8CA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8CA,
+ },
+ [0x1D8CB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8CB,
+ },
+ [0x1D8CC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8CC,
+ },
+ [0x1D8CD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8CD,
+ },
+ [0x1D8CE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8CE,
+ },
+ [0x1D8CF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8CF,
+ },
+ [0x1D8D0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D0,
+ },
+ [0x1D8D1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D1,
+ },
+ [0x1D8D2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D2,
+ },
+ [0x1D8D3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D3,
+ },
+ [0x1D8D4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D4,
+ },
+ [0x1D8D5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D5,
+ },
+ [0x1D8D6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D6,
+ },
+ [0x1D8D7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D7,
+ },
+ [0x1D8D8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D8,
+ },
+ [0x1D8D9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8D9,
+ },
+ [0x1D8DA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8DA,
+ },
+ [0x1D8DB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8DB,
+ },
+ [0x1D8DC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8DC,
+ },
+ [0x1D8DD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8DD,
+ },
+ [0x1D8DE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8DE,
+ },
+ [0x1D8DF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8DF,
+ },
+ [0x1D8E0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E0,
+ },
+ [0x1D8E1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E1,
+ },
+ [0x1D8E2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E2,
+ },
+ [0x1D8E3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E3,
+ },
+ [0x1D8E4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E4,
+ },
+ [0x1D8E5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E5,
+ },
+ [0x1D8E6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E6,
+ },
+ [0x1D8E7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E7,
+ },
+ [0x1D8E8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E8,
+ },
+ [0x1D8E9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8E9,
+ },
+ [0x1D8EA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8EA,
+ },
+ [0x1D8EB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8EB,
+ },
+ [0x1D8EC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8EC,
+ },
+ [0x1D8ED]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8ED,
+ },
+ [0x1D8EE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8EE,
+ },
+ [0x1D8EF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8EF,
+ },
+ [0x1D8F0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F0,
+ },
+ [0x1D8F1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F1,
+ },
+ [0x1D8F2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F2,
+ },
+ [0x1D8F3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F3,
+ },
+ [0x1D8F4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F4,
+ },
+ [0x1D8F5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F5,
+ },
+ [0x1D8F6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F6,
+ },
+ [0x1D8F7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F7,
+ },
+ [0x1D8F8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F8,
+ },
+ [0x1D8F9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8F9,
+ },
+ [0x1D8FA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8FA,
+ },
+ [0x1D8FB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8FB,
+ },
+ [0x1D8FC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8FC,
+ },
+ [0x1D8FD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8FD,
+ },
+ [0x1D8FE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8FE,
+ },
+ [0x1D8FF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D8FF,
+ },
+ [0x1D900]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D900,
+ },
+ [0x1D901]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D901,
+ },
+ [0x1D902]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D902,
+ },
+ [0x1D903]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D903,
+ },
+ [0x1D904]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D904,
+ },
+ [0x1D905]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D905,
+ },
+ [0x1D906]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D906,
+ },
+ [0x1D907]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D907,
+ },
+ [0x1D908]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D908,
+ },
+ [0x1D909]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D909,
+ },
+ [0x1D90A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90A,
+ },
+ [0x1D90B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90B,
+ },
+ [0x1D90C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90C,
+ },
+ [0x1D90D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90D,
+ },
+ [0x1D90E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90E,
+ },
+ [0x1D90F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D90F,
+ },
+ [0x1D910]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D910,
+ },
+ [0x1D911]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D911,
+ },
+ [0x1D912]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D912,
+ },
+ [0x1D913]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D913,
+ },
+ [0x1D914]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D914,
+ },
+ [0x1D915]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D915,
+ },
+ [0x1D916]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D916,
+ },
+ [0x1D917]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D917,
+ },
+ [0x1D918]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D918,
+ },
+ [0x1D919]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D919,
+ },
+ [0x1D91A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91A,
+ },
+ [0x1D91B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91B,
+ },
+ [0x1D91C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91C,
+ },
+ [0x1D91D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91D,
+ },
+ [0x1D91E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91E,
+ },
+ [0x1D91F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D91F,
+ },
+ [0x1D920]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D920,
+ },
+ [0x1D921]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D921,
+ },
+ [0x1D922]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D922,
+ },
+ [0x1D923]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D923,
+ },
+ [0x1D924]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D924,
+ },
+ [0x1D925]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D925,
+ },
+ [0x1D926]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D926,
+ },
+ [0x1D927]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D927,
+ },
+ [0x1D928]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D928,
+ },
+ [0x1D929]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D929,
+ },
+ [0x1D92A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92A,
+ },
+ [0x1D92B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92B,
+ },
+ [0x1D92C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92C,
+ },
+ [0x1D92D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92D,
+ },
+ [0x1D92E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92E,
+ },
+ [0x1D92F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D92F,
+ },
+ [0x1D930]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D930,
+ },
+ [0x1D931]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D931,
+ },
+ [0x1D932]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D932,
+ },
+ [0x1D933]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D933,
+ },
+ [0x1D934]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D934,
+ },
+ [0x1D935]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D935,
+ },
+ [0x1D936]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D936,
+ },
+ [0x1D937]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D937,
+ },
+ [0x1D938]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D938,
+ },
+ [0x1D939]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D939,
+ },
+ [0x1D93A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93A,
+ },
+ [0x1D93B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93B,
+ },
+ [0x1D93C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93C,
+ },
+ [0x1D93D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93D,
+ },
+ [0x1D93E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93E,
+ },
+ [0x1D93F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D93F,
+ },
+ [0x1D940]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D940,
+ },
+ [0x1D941]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D941,
+ },
+ [0x1D942]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D942,
+ },
+ [0x1D943]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D943,
+ },
+ [0x1D944]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D944,
+ },
+ [0x1D945]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D945,
+ },
+ [0x1D946]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D946,
+ },
+ [0x1D947]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D947,
+ },
+ [0x1D948]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D948,
+ },
+ [0x1D949]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D949,
+ },
+ [0x1D94A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94A,
+ },
+ [0x1D94B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94B,
+ },
+ [0x1D94C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94C,
+ },
+ [0x1D94D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94D,
+ },
+ [0x1D94E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94E,
+ },
+ [0x1D94F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D94F,
+ },
+ [0x1D950]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D950,
+ },
+ [0x1D951]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D951,
+ },
+ [0x1D952]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D952,
+ },
+ [0x1D953]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D953,
+ },
+ [0x1D954]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D954,
+ },
+ [0x1D955]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D955,
+ },
+ [0x1D956]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D956,
+ },
+ [0x1D957]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D957,
+ },
+ [0x1D958]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D958,
+ },
+ [0x1D959]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D959,
+ },
+ [0x1D95A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95A,
+ },
+ [0x1D95B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95B,
+ },
+ [0x1D95C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95C,
+ },
+ [0x1D95D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95D,
+ },
+ [0x1D95E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95E,
+ },
+ [0x1D95F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D95F,
+ },
+ [0x1D960]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D960,
+ },
+ [0x1D961]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D961,
+ },
+ [0x1D962]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D962,
+ },
+ [0x1D963]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D963,
+ },
+ [0x1D964]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D964,
+ },
+ [0x1D965]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D965,
+ },
+ [0x1D966]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D966,
+ },
+ [0x1D967]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D967,
+ },
+ [0x1D968]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D968,
+ },
+ [0x1D969]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D969,
+ },
+ [0x1D96A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96A,
+ },
+ [0x1D96B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96B,
+ },
+ [0x1D96C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96C,
+ },
+ [0x1D96D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96D,
+ },
+ [0x1D96E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96E,
+ },
+ [0x1D96F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D96F,
+ },
+ [0x1D970]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D970,
+ },
+ [0x1D971]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D971,
+ },
+ [0x1D972]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D972,
+ },
+ [0x1D973]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D973,
+ },
+ [0x1D974]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D974,
+ },
+ [0x1D975]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D975,
+ },
+ [0x1D976]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D976,
+ },
+ [0x1D977]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D977,
+ },
+ [0x1D978]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D978,
+ },
+ [0x1D979]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D979,
+ },
+ [0x1D97A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97A,
+ },
+ [0x1D97B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97B,
+ },
+ [0x1D97C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97C,
+ },
+ [0x1D97D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97D,
+ },
+ [0x1D97E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97E,
+ },
+ [0x1D97F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D97F,
+ },
+ [0x1D980]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D980,
+ },
+ [0x1D981]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D981,
+ },
+ [0x1D982]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D982,
+ },
+ [0x1D983]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D983,
+ },
+ [0x1D984]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D984,
+ },
+ [0x1D985]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D985,
+ },
+ [0x1D986]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D986,
+ },
+ [0x1D987]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D987,
+ },
+ [0x1D988]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D988,
+ },
+ [0x1D989]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D989,
+ },
+ [0x1D98A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98A,
+ },
+ [0x1D98B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98B,
+ },
+ [0x1D98C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98C,
+ },
+ [0x1D98D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98D,
+ },
+ [0x1D98E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98E,
+ },
+ [0x1D98F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D98F,
+ },
+ [0x1D990]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D990,
+ },
+ [0x1D991]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D991,
+ },
+ [0x1D992]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D992,
+ },
+ [0x1D993]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D993,
+ },
+ [0x1D994]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D994,
+ },
+ [0x1D995]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D995,
+ },
+ [0x1D996]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D996,
+ },
+ [0x1D997]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D997,
+ },
+ [0x1D998]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D998,
+ },
+ [0x1D999]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D999,
+ },
+ [0x1D99A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99A,
+ },
+ [0x1D99B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99B,
+ },
+ [0x1D99C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99C,
+ },
+ [0x1D99D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99D,
+ },
+ [0x1D99E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99E,
+ },
+ [0x1D99F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D99F,
+ },
+ [0x1D9A0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A0,
+ },
+ [0x1D9A1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A1,
+ },
+ [0x1D9A2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A2,
+ },
+ [0x1D9A3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A3,
+ },
+ [0x1D9A4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A4,
+ },
+ [0x1D9A5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A5,
+ },
+ [0x1D9A6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A6,
+ },
+ [0x1D9A7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A7,
+ },
+ [0x1D9A8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A8,
+ },
+ [0x1D9A9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9A9,
+ },
+ [0x1D9AA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9AA,
+ },
+ [0x1D9AB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9AB,
+ },
+ [0x1D9AC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9AC,
+ },
+ [0x1D9AD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9AD,
+ },
+ [0x1D9AE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9AE,
+ },
+ [0x1D9AF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9AF,
+ },
+ [0x1D9B0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B0,
+ },
+ [0x1D9B1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B1,
+ },
+ [0x1D9B2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B2,
+ },
+ [0x1D9B3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B3,
+ },
+ [0x1D9B4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B4,
+ },
+ [0x1D9B5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B5,
+ },
+ [0x1D9B6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B6,
+ },
+ [0x1D9B7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B7,
+ },
+ [0x1D9B8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B8,
+ },
+ [0x1D9B9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9B9,
+ },
+ [0x1D9BA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9BA,
+ },
+ [0x1D9BB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9BB,
+ },
+ [0x1D9BC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9BC,
+ },
+ [0x1D9BD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9BD,
+ },
+ [0x1D9BE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9BE,
+ },
+ [0x1D9BF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9BF,
+ },
+ [0x1D9C0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C0,
+ },
+ [0x1D9C1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C1,
+ },
+ [0x1D9C2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C2,
+ },
+ [0x1D9C3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C3,
+ },
+ [0x1D9C4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C4,
+ },
+ [0x1D9C5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C5,
+ },
+ [0x1D9C6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C6,
+ },
+ [0x1D9C7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C7,
+ },
+ [0x1D9C8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C8,
+ },
+ [0x1D9C9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9C9,
+ },
+ [0x1D9CA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9CA,
+ },
+ [0x1D9CB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9CB,
+ },
+ [0x1D9CC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9CC,
+ },
+ [0x1D9CD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9CD,
+ },
+ [0x1D9CE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9CE,
+ },
+ [0x1D9CF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9CF,
+ },
+ [0x1D9D0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D0,
+ },
+ [0x1D9D1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D1,
+ },
+ [0x1D9D2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D2,
+ },
+ [0x1D9D3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D3,
+ },
+ [0x1D9D4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D4,
+ },
+ [0x1D9D5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D5,
+ },
+ [0x1D9D6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D6,
+ },
+ [0x1D9D7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D7,
+ },
+ [0x1D9D8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D8,
+ },
+ [0x1D9D9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9D9,
+ },
+ [0x1D9DA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9DA,
+ },
+ [0x1D9DB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9DB,
+ },
+ [0x1D9DC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9DC,
+ },
+ [0x1D9DD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9DD,
+ },
+ [0x1D9DE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9DE,
+ },
+ [0x1D9DF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9DF,
+ },
+ [0x1D9E0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E0,
+ },
+ [0x1D9E1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E1,
+ },
+ [0x1D9E2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E2,
+ },
+ [0x1D9E3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E3,
+ },
+ [0x1D9E4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E4,
+ },
+ [0x1D9E5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E5,
+ },
+ [0x1D9E6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E6,
+ },
+ [0x1D9E7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E7,
+ },
+ [0x1D9E8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E8,
+ },
+ [0x1D9E9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9E9,
+ },
+ [0x1D9EA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9EA,
+ },
+ [0x1D9EB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9EB,
+ },
+ [0x1D9EC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9EC,
+ },
+ [0x1D9ED]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9ED,
+ },
+ [0x1D9EE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9EE,
+ },
+ [0x1D9EF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9EF,
+ },
+ [0x1D9F0]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F0,
+ },
+ [0x1D9F1]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F1,
+ },
+ [0x1D9F2]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F2,
+ },
+ [0x1D9F3]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F3,
+ },
+ [0x1D9F4]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F4,
+ },
+ [0x1D9F5]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F5,
+ },
+ [0x1D9F6]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F6,
+ },
+ [0x1D9F7]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F7,
+ },
+ [0x1D9F8]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F8,
+ },
+ [0x1D9F9]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9F9,
+ },
+ [0x1D9FA]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9FA,
+ },
+ [0x1D9FB]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9FB,
+ },
+ [0x1D9FC]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9FC,
+ },
+ [0x1D9FD]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9FD,
+ },
+ [0x1D9FE]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9FE,
+ },
+ [0x1D9FF]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1D9FF,
+ },
+ [0x1DA00]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA00,
+ },
+ [0x1DA01]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA01,
+ },
+ [0x1DA02]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA02,
+ },
+ [0x1DA03]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA03,
+ },
+ [0x1DA04]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA04,
+ },
+ [0x1DA05]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA05,
+ },
+ [0x1DA06]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA06,
+ },
+ [0x1DA07]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA07,
+ },
+ [0x1DA08]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA08,
+ },
+ [0x1DA09]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA09,
+ },
+ [0x1DA0A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA0A,
+ },
+ [0x1DA0B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA0B,
+ },
+ [0x1DA0C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA0C,
+ },
+ [0x1DA0D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA0D,
+ },
+ [0x1DA0E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA0E,
+ },
+ [0x1DA0F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA0F,
+ },
+ [0x1DA10]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA10,
+ },
+ [0x1DA11]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA11,
+ },
+ [0x1DA12]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA12,
+ },
+ [0x1DA13]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA13,
+ },
+ [0x1DA14]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA14,
+ },
+ [0x1DA15]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA15,
+ },
+ [0x1DA16]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA16,
+ },
+ [0x1DA17]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA17,
+ },
+ [0x1DA18]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA18,
+ },
+ [0x1DA19]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA19,
+ },
+ [0x1DA1A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA1A,
+ },
+ [0x1DA1B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA1B,
+ },
+ [0x1DA1C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA1C,
+ },
+ [0x1DA1D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA1D,
+ },
+ [0x1DA1E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA1E,
+ },
+ [0x1DA1F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA1F,
+ },
+ [0x1DA20]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA20,
+ },
+ [0x1DA21]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA21,
+ },
+ [0x1DA22]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA22,
+ },
+ [0x1DA23]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA23,
+ },
+ [0x1DA24]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA24,
+ },
+ [0x1DA25]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA25,
+ },
+ [0x1DA26]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA26,
+ },
+ [0x1DA27]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA27,
+ },
+ [0x1DA28]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA28,
+ },
+ [0x1DA29]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA29,
+ },
+ [0x1DA2A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA2A,
+ },
+ [0x1DA2B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA2B,
+ },
+ [0x1DA2C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA2C,
+ },
+ [0x1DA2D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA2D,
+ },
+ [0x1DA2E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA2E,
+ },
+ [0x1DA2F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA2F,
+ },
+ [0x1DA30]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA30,
+ },
+ [0x1DA31]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA31,
+ },
+ [0x1DA32]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA32,
+ },
+ [0x1DA33]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA33,
+ },
+ [0x1DA34]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA34,
+ },
+ [0x1DA35]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA35,
+ },
+ [0x1DA36]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA36,
+ },
+ [0x1DA37]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA37,
+ },
+ [0x1DA38]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA38,
+ },
+ [0x1DA39]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA39,
+ },
+ [0x1DA3A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA3A,
+ },
+ [0x1DA3B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA3B,
+ },
+ [0x1DA3C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA3C,
+ },
+ [0x1DA3D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA3D,
+ },
+ [0x1DA3E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA3E,
+ },
+ [0x1DA3F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA3F,
+ },
+ [0x1DA40]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA40,
+ },
+ [0x1DA41]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA41,
+ },
+ [0x1DA42]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA42,
+ },
+ [0x1DA43]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA43,
+ },
+ [0x1DA44]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA44,
+ },
+ [0x1DA45]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA45,
+ },
+ [0x1DA46]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA46,
+ },
+ [0x1DA47]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA47,
+ },
+ [0x1DA48]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA48,
+ },
+ [0x1DA49]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA49,
+ },
+ [0x1DA4A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA4A,
+ },
+ [0x1DA4B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA4B,
+ },
+ [0x1DA4C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA4C,
+ },
+ [0x1DA4D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA4D,
+ },
+ [0x1DA4E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA4E,
+ },
+ [0x1DA4F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA4F,
+ },
+ [0x1DA50]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA50,
+ },
+ [0x1DA51]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA51,
+ },
+ [0x1DA52]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA52,
+ },
+ [0x1DA53]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA53,
+ },
+ [0x1DA54]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA54,
+ },
+ [0x1DA55]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA55,
+ },
+ [0x1DA56]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA56,
+ },
+ [0x1DA57]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA57,
+ },
+ [0x1DA58]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA58,
+ },
+ [0x1DA59]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA59,
+ },
+ [0x1DA5A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA5A,
+ },
+ [0x1DA5B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA5B,
+ },
+ [0x1DA5C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA5C,
+ },
+ [0x1DA5D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA5D,
+ },
+ [0x1DA5E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA5E,
+ },
+ [0x1DA5F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA5F,
+ },
+ [0x1DA60]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA60,
+ },
+ [0x1DA61]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA61,
+ },
+ [0x1DA62]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA62,
+ },
+ [0x1DA63]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA63,
+ },
+ [0x1DA64]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA64,
+ },
+ [0x1DA65]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA65,
+ },
+ [0x1DA66]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA66,
+ },
+ [0x1DA67]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA67,
+ },
+ [0x1DA68]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA68,
+ },
+ [0x1DA69]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA69,
+ },
+ [0x1DA6A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA6A,
+ },
+ [0x1DA6B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA6B,
+ },
+ [0x1DA6C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA6C,
+ },
+ [0x1DA6D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA6D,
+ },
+ [0x1DA6E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA6E,
+ },
+ [0x1DA6F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA6F,
+ },
+ [0x1DA70]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA70,
+ },
+ [0x1DA71]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA71,
+ },
+ [0x1DA72]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA72,
+ },
+ [0x1DA73]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA73,
+ },
+ [0x1DA74]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA74,
+ },
+ [0x1DA75]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA75,
+ },
+ [0x1DA76]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA76,
+ },
+ [0x1DA77]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA77,
+ },
+ [0x1DA78]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA78,
+ },
+ [0x1DA79]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA79,
+ },
+ [0x1DA7A]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA7A,
+ },
+ [0x1DA7B]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA7B,
+ },
+ [0x1DA7C]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA7C,
+ },
+ [0x1DA7D]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA7D,
+ },
+ [0x1DA7E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA7E,
+ },
+ [0x1DA7F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA7F,
+ },
+ [0x1DA80]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA80,
+ },
+ [0x1DA81]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA81,
+ },
+ [0x1DA82]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA82,
+ },
+ [0x1DA83]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA83,
+ },
+ [0x1DA84]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA84,
+ },
+ [0x1DA85]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA85,
+ },
+ [0x1DA86]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA86,
+ },
+ [0x1DA87]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1DA87,
+ },
+ [0x1DA88]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1DA88,
+ },
+ [0x1DA89]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1DA89,
+ },
+ [0x1DA8A]={
+ category="po",
+ direction="l",
+ linebreak="ba",
+ unicodeslot=0x1DA8A,
+ },
+ [0x1DA8B]={
+ category="po",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1DA8B,
+ },
+ [0x1DA9B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA9B,
+ },
+ [0x1DA9C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA9C,
+ },
+ [0x1DA9D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA9D,
+ },
+ [0x1DA9E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA9E,
+ },
+ [0x1DA9F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DA9F,
+ },
+ [0x1DAA1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA1,
+ },
+ [0x1DAA2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA2,
+ },
+ [0x1DAA3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA3,
+ },
+ [0x1DAA4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA4,
+ },
+ [0x1DAA5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA5,
+ },
+ [0x1DAA6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA6,
+ },
+ [0x1DAA7]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA7,
+ },
+ [0x1DAA8]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA8,
+ },
+ [0x1DAA9]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAA9,
+ },
+ [0x1DAAA]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAAA,
+ },
+ [0x1DAAB]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAAB,
+ },
+ [0x1DAAC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAAC,
+ },
+ [0x1DAAD]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAAD,
+ },
+ [0x1DAAE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAAE,
+ },
+ [0x1DAAF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1DAAF,
+ },
+ [0x1E000]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E000,
+ },
+ [0x1E001]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E001,
+ },
+ [0x1E002]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E002,
+ },
+ [0x1E003]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E003,
+ },
+ [0x1E004]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E004,
+ },
+ [0x1E005]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E005,
+ },
+ [0x1E006]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E006,
+ },
+ [0x1E008]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E008,
+ },
+ [0x1E009]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E009,
+ },
+ [0x1E00A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E00A,
+ },
+ [0x1E00B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E00B,
+ },
+ [0x1E00C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E00C,
+ },
+ [0x1E00D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E00D,
+ },
+ [0x1E00E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E00E,
+ },
+ [0x1E00F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E00F,
+ },
+ [0x1E010]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E010,
+ },
+ [0x1E011]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E011,
+ },
+ [0x1E012]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E012,
+ },
+ [0x1E013]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E013,
+ },
+ [0x1E014]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E014,
+ },
+ [0x1E015]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E015,
+ },
+ [0x1E016]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E016,
+ },
+ [0x1E017]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E017,
+ },
+ [0x1E018]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E018,
+ },
+ [0x1E01B]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E01B,
+ },
+ [0x1E01C]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E01C,
+ },
+ [0x1E01D]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E01D,
+ },
+ [0x1E01E]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E01E,
+ },
+ [0x1E01F]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E01F,
+ },
+ [0x1E020]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E020,
+ },
+ [0x1E021]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E021,
+ },
+ [0x1E023]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E023,
+ },
+ [0x1E024]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E024,
+ },
+ [0x1E026]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E026,
+ },
+ [0x1E027]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E027,
+ },
+ [0x1E028]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E028,
+ },
+ [0x1E029]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E029,
+ },
+ [0x1E02A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E02A,
+ },
+ [0x1E100]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E100,
+ },
+ [0x1E101]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E101,
+ },
+ [0x1E102]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E102,
+ },
+ [0x1E103]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E103,
+ },
+ [0x1E104]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E104,
+ },
+ [0x1E105]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E105,
+ },
+ [0x1E106]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E106,
+ },
+ [0x1E107]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E107,
+ },
+ [0x1E108]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E108,
+ },
+ [0x1E109]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E109,
+ },
+ [0x1E10A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E10A,
+ },
+ [0x1E10B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E10B,
+ },
+ [0x1E10C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E10C,
+ },
+ [0x1E10D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E10D,
+ },
+ [0x1E10E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E10E,
+ },
+ [0x1E10F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E10F,
+ },
+ [0x1E110]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E110,
+ },
+ [0x1E111]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E111,
+ },
+ [0x1E112]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E112,
+ },
+ [0x1E113]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E113,
+ },
+ [0x1E114]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E114,
+ },
+ [0x1E115]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E115,
+ },
+ [0x1E116]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E116,
+ },
+ [0x1E117]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E117,
+ },
+ [0x1E118]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E118,
+ },
+ [0x1E119]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E119,
+ },
+ [0x1E11A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E11A,
+ },
+ [0x1E11B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E11B,
+ },
+ [0x1E11C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E11C,
+ },
+ [0x1E11D]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E11D,
+ },
+ [0x1E11E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E11E,
+ },
+ [0x1E11F]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E11F,
+ },
+ [0x1E120]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E120,
+ },
+ [0x1E121]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E121,
+ },
+ [0x1E122]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E122,
+ },
+ [0x1E123]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E123,
+ },
+ [0x1E124]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E124,
+ },
+ [0x1E125]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E125,
+ },
+ [0x1E126]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E126,
+ },
+ [0x1E127]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E127,
+ },
+ [0x1E128]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E128,
+ },
+ [0x1E129]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E129,
+ },
+ [0x1E12A]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E12A,
+ },
+ [0x1E12B]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E12B,
+ },
+ [0x1E12C]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E12C,
+ },
+ [0x1E130]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E130,
+ },
+ [0x1E131]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E131,
+ },
+ [0x1E132]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E132,
+ },
+ [0x1E133]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E133,
+ },
+ [0x1E134]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E134,
+ },
+ [0x1E135]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E135,
+ },
+ [0x1E136]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E136,
+ },
+ [0x1E137]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E137,
+ },
+ [0x1E138]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E138,
+ },
+ [0x1E139]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E139,
+ },
+ [0x1E13A]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E13A,
+ },
+ [0x1E13B]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E13B,
+ },
+ [0x1E13C]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E13C,
+ },
+ [0x1E13D]={
+ category="lm",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E13D,
+ },
+ [0x1E140]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E140,
+ },
+ [0x1E141]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E141,
+ },
+ [0x1E142]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E142,
+ },
+ [0x1E143]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E143,
+ },
+ [0x1E144]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E144,
+ },
+ [0x1E145]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E145,
+ },
+ [0x1E146]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E146,
+ },
+ [0x1E147]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E147,
+ },
+ [0x1E148]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E148,
+ },
+ [0x1E149]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E149,
+ },
+ [0x1E14E]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E14E,
+ },
+ [0x1E14F]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E14F,
+ },
+ [0x1E2C0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C0,
+ },
+ [0x1E2C1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C1,
+ },
+ [0x1E2C2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C2,
+ },
+ [0x1E2C3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C3,
+ },
+ [0x1E2C4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C4,
+ },
+ [0x1E2C5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C5,
+ },
+ [0x1E2C6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C6,
+ },
+ [0x1E2C7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C7,
+ },
+ [0x1E2C8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C8,
+ },
+ [0x1E2C9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2C9,
+ },
+ [0x1E2CA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2CA,
+ },
+ [0x1E2CB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2CB,
+ },
+ [0x1E2CC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2CC,
+ },
+ [0x1E2CD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2CD,
+ },
+ [0x1E2CE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2CE,
+ },
+ [0x1E2CF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2CF,
+ },
+ [0x1E2D0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D0,
+ },
+ [0x1E2D1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D1,
+ },
+ [0x1E2D2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D2,
+ },
+ [0x1E2D3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D3,
+ },
+ [0x1E2D4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D4,
+ },
+ [0x1E2D5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D5,
+ },
+ [0x1E2D6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D6,
+ },
+ [0x1E2D7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D7,
+ },
+ [0x1E2D8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D8,
+ },
+ [0x1E2D9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2D9,
+ },
+ [0x1E2DA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2DA,
+ },
+ [0x1E2DB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2DB,
+ },
+ [0x1E2DC]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2DC,
+ },
+ [0x1E2DD]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2DD,
+ },
+ [0x1E2DE]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2DE,
+ },
+ [0x1E2DF]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2DF,
+ },
+ [0x1E2E0]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E0,
+ },
+ [0x1E2E1]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E1,
+ },
+ [0x1E2E2]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E2,
+ },
+ [0x1E2E3]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E3,
+ },
+ [0x1E2E4]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E4,
+ },
+ [0x1E2E5]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E5,
+ },
+ [0x1E2E6]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E6,
+ },
+ [0x1E2E7]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E7,
+ },
+ [0x1E2E8]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E8,
+ },
+ [0x1E2E9]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2E9,
+ },
+ [0x1E2EA]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2EA,
+ },
+ [0x1E2EB]={
+ category="lo",
+ direction="l",
+ linebreak="al",
+ unicodeslot=0x1E2EB,
+ },
+ [0x1E2EC]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E2EC,
+ },
+ [0x1E2ED]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E2ED,
+ },
+ [0x1E2EE]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E2EE,
+ },
+ [0x1E2EF]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E2EF,
+ },
+ [0x1E2F0]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F0,
+ },
+ [0x1E2F1]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F1,
+ },
+ [0x1E2F2]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F2,
+ },
+ [0x1E2F3]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F3,
+ },
+ [0x1E2F4]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F4,
+ },
+ [0x1E2F5]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F5,
+ },
+ [0x1E2F6]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F6,
+ },
+ [0x1E2F7]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F7,
+ },
+ [0x1E2F8]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F8,
+ },
+ [0x1E2F9]={
+ category="nd",
+ direction="l",
+ linebreak="nu",
+ unicodeslot=0x1E2F9,
+ },
+ [0x1E2FF]={
+ category="sc",
+ direction="et",
+ linebreak="pr",
+ unicodeslot=0x1E2FF,
+ },
+ [0x1E800]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E800,
+ },
+ [0x1E801]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E801,
+ },
+ [0x1E802]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E802,
+ },
+ [0x1E803]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E803,
+ },
+ [0x1E804]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E804,
+ },
+ [0x1E805]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E805,
+ },
+ [0x1E806]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E806,
+ },
+ [0x1E807]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E807,
+ },
+ [0x1E808]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E808,
+ },
+ [0x1E809]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E809,
+ },
+ [0x1E80A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E80A,
+ },
+ [0x1E80B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E80B,
+ },
+ [0x1E80C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E80C,
+ },
+ [0x1E80D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E80D,
+ },
+ [0x1E80E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E80E,
+ },
+ [0x1E80F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E80F,
+ },
+ [0x1E810]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E810,
+ },
+ [0x1E811]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E811,
+ },
+ [0x1E812]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E812,
+ },
+ [0x1E813]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E813,
+ },
+ [0x1E814]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E814,
+ },
+ [0x1E815]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E815,
+ },
+ [0x1E816]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E816,
+ },
+ [0x1E817]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E817,
+ },
+ [0x1E818]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E818,
+ },
+ [0x1E819]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E819,
+ },
+ [0x1E81A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E81A,
+ },
+ [0x1E81B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E81B,
+ },
+ [0x1E81C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E81C,
+ },
+ [0x1E81D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E81D,
+ },
+ [0x1E81E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E81E,
+ },
+ [0x1E81F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E81F,
+ },
+ [0x1E820]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E820,
+ },
+ [0x1E821]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E821,
+ },
+ [0x1E822]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E822,
+ },
+ [0x1E823]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E823,
+ },
+ [0x1E824]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E824,
+ },
+ [0x1E825]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E825,
+ },
+ [0x1E826]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E826,
+ },
+ [0x1E827]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E827,
+ },
+ [0x1E828]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E828,
+ },
+ [0x1E829]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E829,
+ },
+ [0x1E82A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E82A,
+ },
+ [0x1E82B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E82B,
+ },
+ [0x1E82C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E82C,
+ },
+ [0x1E82D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E82D,
+ },
+ [0x1E82E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E82E,
+ },
+ [0x1E82F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E82F,
+ },
+ [0x1E830]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E830,
+ },
+ [0x1E831]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E831,
+ },
+ [0x1E832]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E832,
+ },
+ [0x1E833]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E833,
+ },
+ [0x1E834]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E834,
+ },
+ [0x1E835]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E835,
+ },
+ [0x1E836]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E836,
+ },
+ [0x1E837]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E837,
+ },
+ [0x1E838]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E838,
+ },
+ [0x1E839]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E839,
+ },
+ [0x1E83A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E83A,
+ },
+ [0x1E83B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E83B,
+ },
+ [0x1E83C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E83C,
+ },
+ [0x1E83D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E83D,
+ },
+ [0x1E83E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E83E,
+ },
+ [0x1E83F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E83F,
+ },
+ [0x1E840]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E840,
+ },
+ [0x1E841]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E841,
+ },
+ [0x1E842]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E842,
+ },
+ [0x1E843]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E843,
+ },
+ [0x1E844]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E844,
+ },
+ [0x1E845]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E845,
+ },
+ [0x1E846]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E846,
+ },
+ [0x1E847]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E847,
+ },
+ [0x1E848]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E848,
+ },
+ [0x1E849]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E849,
+ },
+ [0x1E84A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E84A,
+ },
+ [0x1E84B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E84B,
+ },
+ [0x1E84C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E84C,
+ },
+ [0x1E84D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E84D,
+ },
+ [0x1E84E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E84E,
+ },
+ [0x1E84F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E84F,
+ },
+ [0x1E850]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E850,
+ },
+ [0x1E851]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E851,
+ },
+ [0x1E852]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E852,
+ },
+ [0x1E853]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E853,
+ },
+ [0x1E854]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E854,
+ },
+ [0x1E855]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E855,
+ },
+ [0x1E856]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E856,
+ },
+ [0x1E857]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E857,
+ },
+ [0x1E858]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E858,
+ },
+ [0x1E859]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E859,
+ },
+ [0x1E85A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E85A,
+ },
+ [0x1E85B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E85B,
+ },
+ [0x1E85C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E85C,
+ },
+ [0x1E85D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E85D,
+ },
+ [0x1E85E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E85E,
+ },
+ [0x1E85F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E85F,
+ },
+ [0x1E860]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E860,
+ },
+ [0x1E861]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E861,
+ },
+ [0x1E862]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E862,
+ },
+ [0x1E863]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E863,
+ },
+ [0x1E864]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E864,
+ },
+ [0x1E865]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E865,
+ },
+ [0x1E866]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E866,
+ },
+ [0x1E867]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E867,
+ },
+ [0x1E868]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E868,
+ },
+ [0x1E869]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E869,
+ },
+ [0x1E86A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E86A,
+ },
+ [0x1E86B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E86B,
+ },
+ [0x1E86C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E86C,
+ },
+ [0x1E86D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E86D,
+ },
+ [0x1E86E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E86E,
+ },
+ [0x1E86F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E86F,
+ },
+ [0x1E870]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E870,
+ },
+ [0x1E871]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E871,
+ },
+ [0x1E872]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E872,
+ },
+ [0x1E873]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E873,
+ },
+ [0x1E874]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E874,
+ },
+ [0x1E875]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E875,
+ },
+ [0x1E876]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E876,
+ },
+ [0x1E877]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E877,
+ },
+ [0x1E878]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E878,
+ },
+ [0x1E879]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E879,
+ },
+ [0x1E87A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E87A,
+ },
+ [0x1E87B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E87B,
+ },
+ [0x1E87C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E87C,
+ },
+ [0x1E87D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E87D,
+ },
+ [0x1E87E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E87E,
+ },
+ [0x1E87F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E87F,
+ },
+ [0x1E880]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E880,
+ },
+ [0x1E881]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E881,
+ },
+ [0x1E882]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E882,
+ },
+ [0x1E883]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E883,
+ },
+ [0x1E884]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E884,
+ },
+ [0x1E885]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E885,
+ },
+ [0x1E886]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E886,
+ },
+ [0x1E887]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E887,
+ },
+ [0x1E888]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E888,
+ },
+ [0x1E889]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E889,
+ },
+ [0x1E88A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E88A,
+ },
+ [0x1E88B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E88B,
+ },
+ [0x1E88C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E88C,
+ },
+ [0x1E88D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E88D,
+ },
+ [0x1E88E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E88E,
+ },
+ [0x1E88F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E88F,
+ },
+ [0x1E890]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E890,
+ },
+ [0x1E891]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E891,
+ },
+ [0x1E892]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E892,
+ },
+ [0x1E893]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E893,
+ },
+ [0x1E894]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E894,
+ },
+ [0x1E895]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E895,
+ },
+ [0x1E896]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E896,
+ },
+ [0x1E897]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E897,
+ },
+ [0x1E898]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E898,
+ },
+ [0x1E899]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E899,
+ },
+ [0x1E89A]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E89A,
+ },
+ [0x1E89B]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E89B,
+ },
+ [0x1E89C]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E89C,
+ },
+ [0x1E89D]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E89D,
+ },
+ [0x1E89E]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E89E,
+ },
+ [0x1E89F]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E89F,
+ },
+ [0x1E8A0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A0,
+ },
+ [0x1E8A1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A1,
+ },
+ [0x1E8A2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A2,
+ },
+ [0x1E8A3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A3,
+ },
+ [0x1E8A4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A4,
+ },
+ [0x1E8A5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A5,
+ },
+ [0x1E8A6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A6,
+ },
+ [0x1E8A7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A7,
+ },
+ [0x1E8A8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A8,
+ },
+ [0x1E8A9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8A9,
+ },
+ [0x1E8AA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8AA,
+ },
+ [0x1E8AB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8AB,
+ },
+ [0x1E8AC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8AC,
+ },
+ [0x1E8AD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8AD,
+ },
+ [0x1E8AE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8AE,
+ },
+ [0x1E8AF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8AF,
+ },
+ [0x1E8B0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B0,
+ },
+ [0x1E8B1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B1,
+ },
+ [0x1E8B2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B2,
+ },
+ [0x1E8B3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B3,
+ },
+ [0x1E8B4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B4,
+ },
+ [0x1E8B5]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B5,
+ },
+ [0x1E8B6]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B6,
+ },
+ [0x1E8B7]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B7,
+ },
+ [0x1E8B8]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B8,
+ },
+ [0x1E8B9]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8B9,
+ },
+ [0x1E8BA]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8BA,
+ },
+ [0x1E8BB]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8BB,
+ },
+ [0x1E8BC]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8BC,
+ },
+ [0x1E8BD]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8BD,
+ },
+ [0x1E8BE]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8BE,
+ },
+ [0x1E8BF]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8BF,
+ },
+ [0x1E8C0]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C0,
+ },
+ [0x1E8C1]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C1,
+ },
+ [0x1E8C2]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C2,
+ },
+ [0x1E8C3]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C3,
+ },
+ [0x1E8C4]={
+ category="lo",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C4,
+ },
+ [0x1E8C7]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C7,
+ },
+ [0x1E8C8]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C8,
+ },
+ [0x1E8C9]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8C9,
+ },
+ [0x1E8CA]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8CA,
+ },
+ [0x1E8CB]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8CB,
+ },
+ [0x1E8CC]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8CC,
+ },
+ [0x1E8CD]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8CD,
+ },
+ [0x1E8CE]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8CE,
+ },
+ [0x1E8CF]={
+ category="no",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E8CF,
+ },
+ [0x1E8D0]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D0,
+ },
+ [0x1E8D1]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D1,
+ },
+ [0x1E8D2]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D2,
+ },
+ [0x1E8D3]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D3,
+ },
+ [0x1E8D4]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D4,
+ },
+ [0x1E8D5]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D5,
+ },
+ [0x1E8D6]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E8D6,
+ },
+ [0x1E900]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E900,
+ },
+ [0x1E901]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E901,
+ },
+ [0x1E902]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E902,
+ },
+ [0x1E903]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E903,
+ },
+ [0x1E904]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E904,
+ },
+ [0x1E905]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E905,
+ },
+ [0x1E906]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E906,
+ },
+ [0x1E907]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E907,
+ },
+ [0x1E908]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E908,
+ },
+ [0x1E909]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E909,
+ },
+ [0x1E90A]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E90A,
+ },
+ [0x1E90B]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E90B,
+ },
+ [0x1E90C]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E90C,
+ },
+ [0x1E90D]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E90D,
+ },
+ [0x1E90E]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E90E,
+ },
+ [0x1E90F]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E90F,
+ },
+ [0x1E910]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E910,
+ },
+ [0x1E911]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E911,
+ },
+ [0x1E912]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E912,
+ },
+ [0x1E913]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E913,
+ },
+ [0x1E914]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E914,
+ },
+ [0x1E915]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E915,
+ },
+ [0x1E916]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E916,
+ },
+ [0x1E917]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E917,
+ },
+ [0x1E918]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E918,
+ },
+ [0x1E919]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E919,
+ },
+ [0x1E91A]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E91A,
+ },
+ [0x1E91B]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E91B,
+ },
+ [0x1E91C]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E91C,
+ },
+ [0x1E91D]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E91D,
+ },
+ [0x1E91E]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E91E,
+ },
+ [0x1E91F]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E91F,
+ },
+ [0x1E920]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E920,
+ },
+ [0x1E921]={
+ category="lu",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E921,
+ },
+ [0x1E922]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E922,
+ },
+ [0x1E923]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E923,
+ },
+ [0x1E924]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E924,
+ },
+ [0x1E925]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E925,
+ },
+ [0x1E926]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E926,
+ },
+ [0x1E927]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E927,
+ },
+ [0x1E928]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E928,
+ },
+ [0x1E929]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E929,
+ },
+ [0x1E92A]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E92A,
+ },
+ [0x1E92B]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E92B,
+ },
+ [0x1E92C]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E92C,
+ },
+ [0x1E92D]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E92D,
+ },
+ [0x1E92E]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E92E,
+ },
+ [0x1E92F]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E92F,
+ },
+ [0x1E930]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E930,
+ },
+ [0x1E931]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E931,
+ },
+ [0x1E932]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E932,
+ },
+ [0x1E933]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E933,
+ },
+ [0x1E934]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E934,
+ },
+ [0x1E935]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E935,
+ },
+ [0x1E936]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E936,
+ },
+ [0x1E937]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E937,
+ },
+ [0x1E938]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E938,
+ },
+ [0x1E939]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E939,
+ },
+ [0x1E93A]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E93A,
+ },
+ [0x1E93B]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E93B,
+ },
+ [0x1E93C]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E93C,
+ },
+ [0x1E93D]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E93D,
+ },
+ [0x1E93E]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E93E,
+ },
+ [0x1E93F]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E93F,
+ },
+ [0x1E940]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E940,
+ },
+ [0x1E941]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E941,
+ },
+ [0x1E942]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E942,
+ },
+ [0x1E943]={
+ category="ll",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E943,
+ },
+ [0x1E944]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E944,
+ },
+ [0x1E945]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E945,
+ },
+ [0x1E946]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E946,
+ },
+ [0x1E947]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E947,
+ },
+ [0x1E948]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E948,
+ },
+ [0x1E949]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E949,
+ },
+ [0x1E94A]={
+ category="mn",
+ direction="nsm",
+ linebreak="cm",
+ unicodeslot=0x1E94A,
+ },
+ [0x1E94B]={
+ category="lm",
+ direction="r",
+ linebreak="al",
+ unicodeslot=0x1E94B,
+ },
+ [0x1E950]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E950,
+ },
+ [0x1E951]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E951,
+ },
+ [0x1E952]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E952,
+ },
+ [0x1E953]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E953,
+ },
+ [0x1E954]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E954,
+ },
+ [0x1E955]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E955,
+ },
+ [0x1E956]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E956,
+ },
+ [0x1E957]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E957,
+ },
+ [0x1E958]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E958,
+ },
+ [0x1E959]={
+ category="nd",
+ direction="r",
+ linebreak="nu",
+ unicodeslot=0x1E959,
+ },
+ [0x1E95E]={
+ category="po",
+ direction="r",
+ linebreak="op",
+ unicodeslot=0x1E95E,
+ },
+ [0x1E95F]={
+ category="po",
+ direction="r",
+ linebreak="op",
+ unicodeslot=0x1E95F,
+ },
+ [0x1EC71]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC71,
+ },
+ [0x1EC72]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC72,
+ },
+ [0x1EC73]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC73,
+ },
+ [0x1EC74]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC74,
+ },
+ [0x1EC75]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC75,
+ },
+ [0x1EC76]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC76,
+ },
+ [0x1EC77]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC77,
+ },
+ [0x1EC78]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC78,
+ },
+ [0x1EC79]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC79,
+ },
+ [0x1EC7A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC7A,
+ },
+ [0x1EC7B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC7B,
+ },
+ [0x1EC7C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC7C,
+ },
+ [0x1EC7D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC7D,
+ },
+ [0x1EC7E]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC7E,
+ },
+ [0x1EC7F]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC7F,
+ },
+ [0x1EC80]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC80,
+ },
+ [0x1EC81]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC81,
+ },
+ [0x1EC82]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC82,
+ },
+ [0x1EC83]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC83,
+ },
+ [0x1EC84]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC84,
+ },
+ [0x1EC85]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC85,
+ },
+ [0x1EC86]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC86,
+ },
+ [0x1EC87]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC87,
+ },
+ [0x1EC88]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC88,
+ },
+ [0x1EC89]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC89,
+ },
+ [0x1EC8A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC8A,
+ },
+ [0x1EC8B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC8B,
+ },
+ [0x1EC8C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC8C,
+ },
+ [0x1EC8D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC8D,
+ },
+ [0x1EC8E]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC8E,
+ },
+ [0x1EC8F]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC8F,
+ },
+ [0x1EC90]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC90,
+ },
+ [0x1EC91]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC91,
+ },
+ [0x1EC92]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC92,
+ },
+ [0x1EC93]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC93,
+ },
+ [0x1EC94]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC94,
+ },
+ [0x1EC95]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC95,
+ },
+ [0x1EC96]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC96,
+ },
+ [0x1EC97]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC97,
+ },
+ [0x1EC98]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC98,
+ },
+ [0x1EC99]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC99,
+ },
+ [0x1EC9A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC9A,
+ },
+ [0x1EC9B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC9B,
+ },
+ [0x1EC9C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC9C,
+ },
+ [0x1EC9D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC9D,
+ },
+ [0x1EC9E]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC9E,
+ },
+ [0x1EC9F]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1EC9F,
+ },
+ [0x1ECA0]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA0,
+ },
+ [0x1ECA1]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA1,
+ },
+ [0x1ECA2]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA2,
+ },
+ [0x1ECA3]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA3,
+ },
+ [0x1ECA4]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA4,
+ },
+ [0x1ECA5]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA5,
+ },
+ [0x1ECA6]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA6,
+ },
+ [0x1ECA7]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA7,
+ },
+ [0x1ECA8]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA8,
+ },
+ [0x1ECA9]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECA9,
+ },
+ [0x1ECAA]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECAA,
+ },
+ [0x1ECAB]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECAB,
+ },
+ [0x1ECAC]={
+ category="so",
+ direction="al",
+ linebreak="po",
+ unicodeslot=0x1ECAC,
+ },
+ [0x1ECAD]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECAD,
+ },
+ [0x1ECAE]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECAE,
+ },
+ [0x1ECAF]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECAF,
+ },
+ [0x1ECB0]={
+ category="sc",
+ direction="al",
+ linebreak="po",
+ unicodeslot=0x1ECB0,
+ },
+ [0x1ECB1]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECB1,
+ },
+ [0x1ECB2]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECB2,
+ },
+ [0x1ECB3]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECB3,
+ },
+ [0x1ECB4]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ECB4,
+ },
+ [0x1ED01]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED01,
+ },
+ [0x1ED02]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED02,
+ },
+ [0x1ED03]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED03,
+ },
+ [0x1ED04]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED04,
+ },
+ [0x1ED05]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED05,
+ },
+ [0x1ED06]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED06,
+ },
+ [0x1ED07]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED07,
+ },
+ [0x1ED08]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED08,
+ },
+ [0x1ED09]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED09,
+ },
+ [0x1ED0A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED0A,
+ },
+ [0x1ED0B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED0B,
+ },
+ [0x1ED0C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED0C,
+ },
+ [0x1ED0D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED0D,
+ },
+ [0x1ED0E]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED0E,
+ },
+ [0x1ED0F]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED0F,
+ },
+ [0x1ED10]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED10,
+ },
+ [0x1ED11]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED11,
+ },
+ [0x1ED12]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED12,
+ },
+ [0x1ED13]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED13,
+ },
+ [0x1ED14]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED14,
+ },
+ [0x1ED15]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED15,
+ },
+ [0x1ED16]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED16,
+ },
+ [0x1ED17]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED17,
+ },
+ [0x1ED18]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED18,
+ },
+ [0x1ED19]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED19,
+ },
+ [0x1ED1A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED1A,
+ },
+ [0x1ED1B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED1B,
+ },
+ [0x1ED1C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED1C,
+ },
+ [0x1ED1D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED1D,
+ },
+ [0x1ED1E]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED1E,
+ },
+ [0x1ED1F]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED1F,
+ },
+ [0x1ED20]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED20,
+ },
+ [0x1ED21]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED21,
+ },
+ [0x1ED22]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED22,
+ },
+ [0x1ED23]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED23,
+ },
+ [0x1ED24]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED24,
+ },
+ [0x1ED25]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED25,
+ },
+ [0x1ED26]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED26,
+ },
+ [0x1ED27]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED27,
+ },
+ [0x1ED28]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED28,
+ },
+ [0x1ED29]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED29,
+ },
+ [0x1ED2A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED2A,
+ },
+ [0x1ED2B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED2B,
+ },
+ [0x1ED2C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED2C,
+ },
+ [0x1ED2D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED2D,
+ },
+ [0x1ED2E]={
+ category="so",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED2E,
+ },
+ [0x1ED2F]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED2F,
+ },
+ [0x1ED30]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED30,
+ },
+ [0x1ED31]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED31,
+ },
+ [0x1ED32]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED32,
+ },
+ [0x1ED33]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED33,
+ },
+ [0x1ED34]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED34,
+ },
+ [0x1ED35]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED35,
+ },
+ [0x1ED36]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED36,
+ },
+ [0x1ED37]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED37,
+ },
+ [0x1ED38]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED38,
+ },
+ [0x1ED39]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED39,
+ },
+ [0x1ED3A]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED3A,
+ },
+ [0x1ED3B]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED3B,
+ },
+ [0x1ED3C]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED3C,
+ },
+ [0x1ED3D]={
+ category="no",
+ direction="al",
+ linebreak="al",
+ unicodeslot=0x1ED3D,
+ },
+ [0x1EE00]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x627 },
+ unicodeslot=0x1EE00,
+ },
+ [0x1EE01]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x628 },
+ unicodeslot=0x1EE01,
+ },
+ [0x1EE02]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62C },
+ unicodeslot=0x1EE02,
+ },
+ [0x1EE03]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62F },
+ unicodeslot=0x1EE03,
+ },
+ [0x1EE05]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x648 },
+ unicodeslot=0x1EE05,
+ },
+ [0x1EE06]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x632 },
+ unicodeslot=0x1EE06,
+ },
+ [0x1EE07]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62D },
+ unicodeslot=0x1EE07,
+ },
+ [0x1EE08]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x637 },
+ unicodeslot=0x1EE08,
+ },
+ [0x1EE09]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x64A },
+ unicodeslot=0x1EE09,
+ },
+ [0x1EE0A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x643 },
+ unicodeslot=0x1EE0A,
+ },
+ [0x1EE0B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x644 },
+ unicodeslot=0x1EE0B,
+ },
+ [0x1EE0C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x645 },
+ unicodeslot=0x1EE0C,
+ },
+ [0x1EE0D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x646 },
+ unicodeslot=0x1EE0D,
+ },
+ [0x1EE0E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x633 },
+ unicodeslot=0x1EE0E,
+ },
+ [0x1EE0F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x639 },
+ unicodeslot=0x1EE0F,
+ },
+ [0x1EE10]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x641 },
+ unicodeslot=0x1EE10,
+ },
+ [0x1EE11]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x635 },
+ unicodeslot=0x1EE11,
+ },
+ [0x1EE12]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x642 },
+ unicodeslot=0x1EE12,
+ },
+ [0x1EE13]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x631 },
+ unicodeslot=0x1EE13,
+ },
+ [0x1EE14]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x634 },
+ unicodeslot=0x1EE14,
+ },
+ [0x1EE15]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62A },
+ unicodeslot=0x1EE15,
+ },
+ [0x1EE16]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62B },
+ unicodeslot=0x1EE16,
+ },
+ [0x1EE17]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62E },
+ unicodeslot=0x1EE17,
+ },
+ [0x1EE18]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x630 },
+ unicodeslot=0x1EE18,
+ },
+ [0x1EE19]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x636 },
+ unicodeslot=0x1EE19,
+ },
+ [0x1EE1A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x638 },
+ unicodeslot=0x1EE1A,
+ },
+ [0x1EE1B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x63A },
+ unicodeslot=0x1EE1B,
+ },
+ [0x1EE1C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x66E },
+ unicodeslot=0x1EE1C,
+ },
+ [0x1EE1D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x6BA },
+ unicodeslot=0x1EE1D,
+ },
+ [0x1EE1E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x6A1 },
+ unicodeslot=0x1EE1E,
+ },
+ [0x1EE1F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x66F },
+ unicodeslot=0x1EE1F,
+ },
+ [0x1EE21]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x628 },
+ unicodeslot=0x1EE21,
+ },
+ [0x1EE22]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62C },
+ unicodeslot=0x1EE22,
+ },
+ [0x1EE24]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x647 },
+ unicodeslot=0x1EE24,
+ },
+ [0x1EE27]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62D },
+ unicodeslot=0x1EE27,
+ },
+ [0x1EE29]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x64A },
+ unicodeslot=0x1EE29,
+ },
+ [0x1EE2A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x643 },
+ unicodeslot=0x1EE2A,
+ },
+ [0x1EE2B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x644 },
+ unicodeslot=0x1EE2B,
+ },
+ [0x1EE2C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x645 },
+ unicodeslot=0x1EE2C,
+ },
+ [0x1EE2D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x646 },
+ unicodeslot=0x1EE2D,
+ },
+ [0x1EE2E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x633 },
+ unicodeslot=0x1EE2E,
+ },
+ [0x1EE2F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x639 },
+ unicodeslot=0x1EE2F,
+ },
+ [0x1EE30]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x641 },
+ unicodeslot=0x1EE30,
+ },
+ [0x1EE31]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x635 },
+ unicodeslot=0x1EE31,
+ },
+ [0x1EE32]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x642 },
+ unicodeslot=0x1EE32,
+ },
+ [0x1EE34]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x634 },
+ unicodeslot=0x1EE34,
+ },
+ [0x1EE35]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62A },
+ unicodeslot=0x1EE35,
+ },
+ [0x1EE36]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62B },
+ unicodeslot=0x1EE36,
+ },
+ [0x1EE37]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62E },
+ unicodeslot=0x1EE37,
+ },
+ [0x1EE39]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x636 },
+ unicodeslot=0x1EE39,
+ },
+ [0x1EE3B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x63A },
+ unicodeslot=0x1EE3B,
+ },
+ [0x1EE42]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62C },
+ unicodeslot=0x1EE42,
+ },
+ [0x1EE47]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62D },
+ unicodeslot=0x1EE47,
+ },
+ [0x1EE49]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x64A },
+ unicodeslot=0x1EE49,
+ },
+ [0x1EE4B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x644 },
+ unicodeslot=0x1EE4B,
+ },
+ [0x1EE4D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x646 },
+ unicodeslot=0x1EE4D,
+ },
+ [0x1EE4E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x633 },
+ unicodeslot=0x1EE4E,
+ },
+ [0x1EE4F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x639 },
+ unicodeslot=0x1EE4F,
+ },
+ [0x1EE51]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x635 },
+ unicodeslot=0x1EE51,
+ },
+ [0x1EE52]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x642 },
+ unicodeslot=0x1EE52,
+ },
+ [0x1EE54]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x634 },
+ unicodeslot=0x1EE54,
+ },
+ [0x1EE57]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62E },
+ unicodeslot=0x1EE57,
+ },
+ [0x1EE59]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x636 },
+ unicodeslot=0x1EE59,
+ },
+ [0x1EE5B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x63A },
+ unicodeslot=0x1EE5B,
+ },
+ [0x1EE5D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x6BA },
+ unicodeslot=0x1EE5D,
+ },
+ [0x1EE5F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x66F },
+ unicodeslot=0x1EE5F,
+ },
+ [0x1EE61]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x628 },
+ unicodeslot=0x1EE61,
+ },
+ [0x1EE62]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62C },
+ unicodeslot=0x1EE62,
+ },
+ [0x1EE64]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x647 },
+ unicodeslot=0x1EE64,
+ },
+ [0x1EE67]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62D },
+ unicodeslot=0x1EE67,
+ },
+ [0x1EE68]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x637 },
+ unicodeslot=0x1EE68,
+ },
+ [0x1EE69]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x64A },
+ unicodeslot=0x1EE69,
+ },
+ [0x1EE6A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x643 },
+ unicodeslot=0x1EE6A,
+ },
+ [0x1EE6C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x645 },
+ unicodeslot=0x1EE6C,
+ },
+ [0x1EE6D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x646 },
+ unicodeslot=0x1EE6D,
+ },
+ [0x1EE6E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x633 },
+ unicodeslot=0x1EE6E,
+ },
+ [0x1EE6F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x639 },
+ unicodeslot=0x1EE6F,
+ },
+ [0x1EE70]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x641 },
+ unicodeslot=0x1EE70,
+ },
+ [0x1EE71]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x635 },
+ unicodeslot=0x1EE71,
+ },
+ [0x1EE72]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x642 },
+ unicodeslot=0x1EE72,
+ },
+ [0x1EE74]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x634 },
+ unicodeslot=0x1EE74,
+ },
+ [0x1EE75]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62A },
+ unicodeslot=0x1EE75,
+ },
+ [0x1EE76]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62B },
+ unicodeslot=0x1EE76,
+ },
+ [0x1EE77]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62E },
+ unicodeslot=0x1EE77,
+ },
+ [0x1EE79]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x636 },
+ unicodeslot=0x1EE79,
+ },
+ [0x1EE7A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x638 },
+ unicodeslot=0x1EE7A,
+ },
+ [0x1EE7B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x63A },
+ unicodeslot=0x1EE7B,
+ },
+ [0x1EE7C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x66E },
+ unicodeslot=0x1EE7C,
+ },
+ [0x1EE7E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x6A1 },
+ unicodeslot=0x1EE7E,
+ },
+ [0x1EE80]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x627 },
+ unicodeslot=0x1EE80,
+ },
+ [0x1EE81]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x628 },
+ unicodeslot=0x1EE81,
+ },
+ [0x1EE82]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62C },
+ unicodeslot=0x1EE82,
+ },
+ [0x1EE83]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62F },
+ unicodeslot=0x1EE83,
+ },
+ [0x1EE84]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x647 },
+ unicodeslot=0x1EE84,
+ },
+ [0x1EE85]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x648 },
+ unicodeslot=0x1EE85,
+ },
+ [0x1EE86]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x632 },
+ unicodeslot=0x1EE86,
+ },
+ [0x1EE87]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62D },
+ unicodeslot=0x1EE87,
+ },
+ [0x1EE88]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x637 },
+ unicodeslot=0x1EE88,
+ },
+ [0x1EE89]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x64A },
+ unicodeslot=0x1EE89,
+ },
+ [0x1EE8B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x644 },
+ unicodeslot=0x1EE8B,
+ },
+ [0x1EE8C]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x645 },
+ unicodeslot=0x1EE8C,
+ },
+ [0x1EE8D]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x646 },
+ unicodeslot=0x1EE8D,
+ },
+ [0x1EE8E]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x633 },
+ unicodeslot=0x1EE8E,
+ },
+ [0x1EE8F]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x639 },
+ unicodeslot=0x1EE8F,
+ },
+ [0x1EE90]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x641 },
+ unicodeslot=0x1EE90,
+ },
+ [0x1EE91]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x635 },
+ unicodeslot=0x1EE91,
+ },
+ [0x1EE92]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x642 },
+ unicodeslot=0x1EE92,
+ },
+ [0x1EE93]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x631 },
+ unicodeslot=0x1EE93,
+ },
+ [0x1EE94]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x634 },
+ unicodeslot=0x1EE94,
+ },
+ [0x1EE95]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62A },
+ unicodeslot=0x1EE95,
+ },
+ [0x1EE96]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62B },
+ unicodeslot=0x1EE96,
+ },
+ [0x1EE97]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62E },
+ unicodeslot=0x1EE97,
+ },
+ [0x1EE98]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x630 },
+ unicodeslot=0x1EE98,
+ },
+ [0x1EE99]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x636 },
+ unicodeslot=0x1EE99,
+ },
+ [0x1EE9A]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x638 },
+ unicodeslot=0x1EE9A,
+ },
+ [0x1EE9B]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x63A },
+ unicodeslot=0x1EE9B,
+ },
+ [0x1EEA1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x628 },
+ unicodeslot=0x1EEA1,
+ },
+ [0x1EEA2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62C },
+ unicodeslot=0x1EEA2,
+ },
+ [0x1EEA3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62F },
+ unicodeslot=0x1EEA3,
+ },
+ [0x1EEA5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x648 },
+ unicodeslot=0x1EEA5,
+ },
+ [0x1EEA6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x632 },
+ unicodeslot=0x1EEA6,
+ },
+ [0x1EEA7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62D },
+ unicodeslot=0x1EEA7,
+ },
+ [0x1EEA8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x637 },
+ unicodeslot=0x1EEA8,
+ },
+ [0x1EEA9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x64A },
+ unicodeslot=0x1EEA9,
+ },
+ [0x1EEAB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x644 },
+ unicodeslot=0x1EEAB,
+ },
+ [0x1EEAC]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x645 },
+ unicodeslot=0x1EEAC,
+ },
+ [0x1EEAD]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x646 },
+ unicodeslot=0x1EEAD,
+ },
+ [0x1EEAE]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x633 },
+ unicodeslot=0x1EEAE,
+ },
+ [0x1EEAF]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x639 },
+ unicodeslot=0x1EEAF,
+ },
+ [0x1EEB0]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x641 },
+ unicodeslot=0x1EEB0,
+ },
+ [0x1EEB1]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x635 },
+ unicodeslot=0x1EEB1,
+ },
+ [0x1EEB2]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x642 },
+ unicodeslot=0x1EEB2,
+ },
+ [0x1EEB3]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x631 },
+ unicodeslot=0x1EEB3,
+ },
+ [0x1EEB4]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x634 },
+ unicodeslot=0x1EEB4,
+ },
+ [0x1EEB5]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62A },
+ unicodeslot=0x1EEB5,
+ },
+ [0x1EEB6]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62B },
+ unicodeslot=0x1EEB6,
+ },
+ [0x1EEB7]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x62E },
+ unicodeslot=0x1EEB7,
+ },
+ [0x1EEB8]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x630 },
+ unicodeslot=0x1EEB8,
+ },
+ [0x1EEB9]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x636 },
+ unicodeslot=0x1EEB9,
+ },
+ [0x1EEBA]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x638 },
+ unicodeslot=0x1EEBA,
+ },
+ [0x1EEBB]={
+ category="lo",
+ direction="al",
+ linebreak="al",
+ specials={ "font", 0x63A },
+ unicodeslot=0x1EEBB,
+ },
+ [0x1EEF0]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1EEF0,
+ },
+ [0x1EEF1]={
+ category="sm",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1EEF1,
+ },
+ [0x1F000]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F000,
+ },
+ [0x1F001]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F001,
+ },
+ [0x1F002]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F002,
+ },
+ [0x1F003]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F003,
+ },
+ [0x1F004]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F004,
+ },
+ [0x1F005]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F005,
+ },
+ [0x1F006]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F006,
+ },
+ [0x1F007]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F007,
+ },
+ [0x1F008]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F008,
+ },
+ [0x1F009]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F009,
+ },
+ [0x1F00A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F00A,
+ },
+ [0x1F00B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F00B,
+ },
+ [0x1F00C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F00C,
+ },
+ [0x1F00D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F00D,
+ },
+ [0x1F00E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F00E,
+ },
+ [0x1F00F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F00F,
+ },
+ [0x1F010]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F010,
+ },
+ [0x1F011]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F011,
+ },
+ [0x1F012]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F012,
+ },
+ [0x1F013]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F013,
+ },
+ [0x1F014]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F014,
+ },
+ [0x1F015]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F015,
+ },
+ [0x1F016]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F016,
+ },
+ [0x1F017]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F017,
+ },
+ [0x1F018]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F018,
+ },
+ [0x1F019]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F019,
+ },
+ [0x1F01A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F01A,
+ },
+ [0x1F01B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F01B,
+ },
+ [0x1F01C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F01C,
+ },
+ [0x1F01D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F01D,
+ },
+ [0x1F01E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F01E,
+ },
+ [0x1F01F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F01F,
+ },
+ [0x1F020]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F020,
+ },
+ [0x1F021]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F021,
+ },
+ [0x1F022]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F022,
+ },
+ [0x1F023]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F023,
+ },
+ [0x1F024]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F024,
+ },
+ [0x1F025]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F025,
+ },
+ [0x1F026]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F026,
+ },
+ [0x1F027]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F027,
+ },
+ [0x1F028]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F028,
+ },
+ [0x1F029]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F029,
+ },
+ [0x1F02A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F02A,
+ },
+ [0x1F02B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F02B,
+ },
+ [0x1F030]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F030,
+ },
+ [0x1F031]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F031,
+ },
+ [0x1F032]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F032,
+ },
+ [0x1F033]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F033,
+ },
+ [0x1F034]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F034,
+ },
+ [0x1F035]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F035,
+ },
+ [0x1F036]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F036,
+ },
+ [0x1F037]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F037,
+ },
+ [0x1F038]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F038,
+ },
+ [0x1F039]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F039,
+ },
+ [0x1F03A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F03A,
+ },
+ [0x1F03B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F03B,
+ },
+ [0x1F03C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F03C,
+ },
+ [0x1F03D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F03D,
+ },
+ [0x1F03E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F03E,
+ },
+ [0x1F03F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F03F,
+ },
+ [0x1F040]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F040,
+ },
+ [0x1F041]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F041,
+ },
+ [0x1F042]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F042,
+ },
+ [0x1F043]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F043,
+ },
+ [0x1F044]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F044,
+ },
+ [0x1F045]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F045,
+ },
+ [0x1F046]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F046,
+ },
+ [0x1F047]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F047,
+ },
+ [0x1F048]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F048,
+ },
+ [0x1F049]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F049,
+ },
+ [0x1F04A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F04A,
+ },
+ [0x1F04B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F04B,
+ },
+ [0x1F04C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F04C,
+ },
+ [0x1F04D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F04D,
+ },
+ [0x1F04E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F04E,
+ },
+ [0x1F04F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F04F,
+ },
+ [0x1F050]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F050,
+ },
+ [0x1F051]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F051,
+ },
+ [0x1F052]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F052,
+ },
+ [0x1F053]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F053,
+ },
+ [0x1F054]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F054,
+ },
+ [0x1F055]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F055,
+ },
+ [0x1F056]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F056,
+ },
+ [0x1F057]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F057,
+ },
+ [0x1F058]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F058,
+ },
+ [0x1F059]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F059,
+ },
+ [0x1F05A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F05A,
+ },
+ [0x1F05B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F05B,
+ },
+ [0x1F05C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F05C,
+ },
+ [0x1F05D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F05D,
+ },
+ [0x1F05E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F05E,
+ },
+ [0x1F05F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F05F,
+ },
+ [0x1F060]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F060,
+ },
+ [0x1F061]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F061,
+ },
+ [0x1F062]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F062,
+ },
+ [0x1F063]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F063,
+ },
+ [0x1F064]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F064,
+ },
+ [0x1F065]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F065,
+ },
+ [0x1F066]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F066,
+ },
+ [0x1F067]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F067,
+ },
+ [0x1F068]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F068,
+ },
+ [0x1F069]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F069,
+ },
+ [0x1F06A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F06A,
+ },
+ [0x1F06B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F06B,
+ },
+ [0x1F06C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F06C,
+ },
+ [0x1F06D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F06D,
+ },
+ [0x1F06E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F06E,
+ },
+ [0x1F06F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F06F,
+ },
+ [0x1F070]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F070,
+ },
+ [0x1F071]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F071,
+ },
+ [0x1F072]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F072,
+ },
+ [0x1F073]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F073,
+ },
+ [0x1F074]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F074,
+ },
+ [0x1F075]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F075,
+ },
+ [0x1F076]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F076,
+ },
+ [0x1F077]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F077,
+ },
+ [0x1F078]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F078,
+ },
+ [0x1F079]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F079,
+ },
+ [0x1F07A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F07A,
+ },
+ [0x1F07B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F07B,
+ },
+ [0x1F07C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F07C,
+ },
+ [0x1F07D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F07D,
+ },
+ [0x1F07E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F07E,
+ },
+ [0x1F07F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F07F,
+ },
+ [0x1F080]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F080,
+ },
+ [0x1F081]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F081,
+ },
+ [0x1F082]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F082,
+ },
+ [0x1F083]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F083,
+ },
+ [0x1F084]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F084,
+ },
+ [0x1F085]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F085,
+ },
+ [0x1F086]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F086,
+ },
+ [0x1F087]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F087,
+ },
+ [0x1F088]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F088,
+ },
+ [0x1F089]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F089,
+ },
+ [0x1F08A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F08A,
+ },
+ [0x1F08B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F08B,
+ },
+ [0x1F08C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F08C,
+ },
+ [0x1F08D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F08D,
+ },
+ [0x1F08E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F08E,
+ },
+ [0x1F08F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F08F,
+ },
+ [0x1F090]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F090,
+ },
+ [0x1F091]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F091,
+ },
+ [0x1F092]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F092,
+ },
+ [0x1F093]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F093,
+ },
+ [0x1F0A0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A0,
+ },
+ [0x1F0A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A1,
+ },
+ [0x1F0A2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A2,
+ },
+ [0x1F0A3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A3,
+ },
+ [0x1F0A4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A4,
+ },
+ [0x1F0A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A5,
+ },
+ [0x1F0A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A6,
+ },
+ [0x1F0A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A7,
+ },
+ [0x1F0A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A8,
+ },
+ [0x1F0A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0A9,
+ },
+ [0x1F0AA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0AA,
+ },
+ [0x1F0AB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0AB,
+ },
+ [0x1F0AC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0AC,
+ },
+ [0x1F0AD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0AD,
+ },
+ [0x1F0AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0AE,
+ },
+ [0x1F0B1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B1,
+ },
+ [0x1F0B2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B2,
+ },
+ [0x1F0B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B3,
+ },
+ [0x1F0B4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B4,
+ },
+ [0x1F0B5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B5,
+ },
+ [0x1F0B6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B6,
+ },
+ [0x1F0B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B7,
+ },
+ [0x1F0B8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B8,
+ },
+ [0x1F0B9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0B9,
+ },
+ [0x1F0BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0BA,
+ },
+ [0x1F0BB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0BB,
+ },
+ [0x1F0BC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0BC,
+ },
+ [0x1F0BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0BD,
+ },
+ [0x1F0BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0BE,
+ },
+ [0x1F0BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0BF,
+ },
+ [0x1F0C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C1,
+ },
+ [0x1F0C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C2,
+ },
+ [0x1F0C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C3,
+ },
+ [0x1F0C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C4,
+ },
+ [0x1F0C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C5,
+ },
+ [0x1F0C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C6,
+ },
+ [0x1F0C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C7,
+ },
+ [0x1F0C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C8,
+ },
+ [0x1F0C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0C9,
+ },
+ [0x1F0CA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0CA,
+ },
+ [0x1F0CB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0CB,
+ },
+ [0x1F0CC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0CC,
+ },
+ [0x1F0CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0CD,
+ },
+ [0x1F0CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0CE,
+ },
+ [0x1F0CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0CF,
+ },
+ [0x1F0D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D1,
+ },
+ [0x1F0D2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D2,
+ },
+ [0x1F0D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D3,
+ },
+ [0x1F0D4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D4,
+ },
+ [0x1F0D5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D5,
+ },
+ [0x1F0D6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D6,
+ },
+ [0x1F0D7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D7,
+ },
+ [0x1F0D8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D8,
+ },
+ [0x1F0D9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0D9,
+ },
+ [0x1F0DA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0DA,
+ },
+ [0x1F0DB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0DB,
+ },
+ [0x1F0DC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0DC,
+ },
+ [0x1F0DD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0DD,
+ },
+ [0x1F0DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0DE,
+ },
+ [0x1F0DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0DF,
+ },
+ [0x1F0E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E0,
+ },
+ [0x1F0E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E1,
+ },
+ [0x1F0E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E2,
+ },
+ [0x1F0E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E3,
+ },
+ [0x1F0E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E4,
+ },
+ [0x1F0E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E5,
+ },
+ [0x1F0E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E6,
+ },
+ [0x1F0E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E7,
+ },
+ [0x1F0E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E8,
+ },
+ [0x1F0E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0E9,
+ },
+ [0x1F0EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0EA,
+ },
+ [0x1F0EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0EB,
+ },
+ [0x1F0EC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0EC,
+ },
+ [0x1F0ED]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0ED,
+ },
+ [0x1F0EE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0EE,
+ },
+ [0x1F0EF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0EF,
+ },
+ [0x1F0F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0F0,
+ },
+ [0x1F0F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0F1,
+ },
+ [0x1F0F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0F2,
+ },
+ [0x1F0F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0F3,
+ },
+ [0x1F0F4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0F4,
+ },
+ [0x1F0F5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F0F5,
+ },
+ [0x1F100]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x30, 0x2E },
+ unicodeslot=0x1F100,
+ },
+ [0x1F101]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x30, 0x2C },
+ unicodeslot=0x1F101,
+ },
+ [0x1F102]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x31, 0x2C },
+ unicodeslot=0x1F102,
+ },
+ [0x1F103]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x32, 0x2C },
+ unicodeslot=0x1F103,
+ },
+ [0x1F104]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x33, 0x2C },
+ unicodeslot=0x1F104,
+ },
+ [0x1F105]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x34, 0x2C },
+ unicodeslot=0x1F105,
+ },
+ [0x1F106]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x35, 0x2C },
+ unicodeslot=0x1F106,
+ },
+ [0x1F107]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x36, 0x2C },
+ unicodeslot=0x1F107,
+ },
+ [0x1F108]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x37, 0x2C },
+ unicodeslot=0x1F108,
+ },
+ [0x1F109]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x38, 0x2C },
+ unicodeslot=0x1F109,
+ },
+ [0x1F10A]={
+ category="no",
+ direction="en",
+ linebreak="ai",
+ specials={ "compat", 0x39, 0x2C },
+ unicodeslot=0x1F10A,
+ },
+ [0x1F10B]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x1F10B,
+ },
+ [0x1F10C]={
+ category="no",
+ direction="on",
+ linebreak="ai",
+ unicodeslot=0x1F10C,
+ },
+ [0x1F110]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x41, 0x29 },
+ unicodeslot=0x1F110,
+ },
+ [0x1F111]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x42, 0x29 },
+ unicodeslot=0x1F111,
+ },
+ [0x1F112]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x43, 0x29 },
+ unicodeslot=0x1F112,
+ },
+ [0x1F113]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x44, 0x29 },
+ unicodeslot=0x1F113,
+ },
+ [0x1F114]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x45, 0x29 },
+ unicodeslot=0x1F114,
+ },
+ [0x1F115]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x46, 0x29 },
+ unicodeslot=0x1F115,
+ },
+ [0x1F116]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x47, 0x29 },
+ unicodeslot=0x1F116,
+ },
+ [0x1F117]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x48, 0x29 },
+ unicodeslot=0x1F117,
+ },
+ [0x1F118]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x49, 0x29 },
+ unicodeslot=0x1F118,
+ },
+ [0x1F119]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x4A, 0x29 },
+ unicodeslot=0x1F119,
+ },
+ [0x1F11A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x4B, 0x29 },
+ unicodeslot=0x1F11A,
+ },
+ [0x1F11B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x4C, 0x29 },
+ unicodeslot=0x1F11B,
+ },
+ [0x1F11C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x4D, 0x29 },
+ unicodeslot=0x1F11C,
+ },
+ [0x1F11D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x4E, 0x29 },
+ unicodeslot=0x1F11D,
+ },
+ [0x1F11E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x4F, 0x29 },
+ unicodeslot=0x1F11E,
+ },
+ [0x1F11F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x50, 0x29 },
+ unicodeslot=0x1F11F,
+ },
+ [0x1F120]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x51, 0x29 },
+ unicodeslot=0x1F120,
+ },
+ [0x1F121]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x52, 0x29 },
+ unicodeslot=0x1F121,
+ },
+ [0x1F122]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x53, 0x29 },
+ unicodeslot=0x1F122,
+ },
+ [0x1F123]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x54, 0x29 },
+ unicodeslot=0x1F123,
+ },
+ [0x1F124]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x55, 0x29 },
+ unicodeslot=0x1F124,
+ },
+ [0x1F125]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x56, 0x29 },
+ unicodeslot=0x1F125,
+ },
+ [0x1F126]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x57, 0x29 },
+ unicodeslot=0x1F126,
+ },
+ [0x1F127]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x58, 0x29 },
+ unicodeslot=0x1F127,
+ },
+ [0x1F128]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x59, 0x29 },
+ unicodeslot=0x1F128,
+ },
+ [0x1F129]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x28, 0x5A, 0x29 },
+ unicodeslot=0x1F129,
+ },
+ [0x1F12A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "compat", 0x3014, 0x53, 0x3015 },
+ unicodeslot=0x1F12A,
+ },
+ [0x1F12B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x43 },
+ unicodeslot=0x1F12B,
+ },
+ [0x1F12C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x52 },
+ unicodeslot=0x1F12C,
+ },
+ [0x1F12D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "circle", 0x43, 0x44 },
+ unicodeslot=0x1F12D,
+ },
+ [0x1F12E]={
+ category="so",
+ direction="l",
+ linebreak="al",
+ specials={ "circle", 0x57, 0x5A },
+ unicodeslot=0x1F12E,
+ },
+ [0x1F12F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F12F,
+ },
+ [0x1F130]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x41 },
+ unicodeslot=0x1F130,
+ },
+ [0x1F131]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x42 },
+ unicodeslot=0x1F131,
+ },
+ [0x1F132]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x43 },
+ unicodeslot=0x1F132,
+ },
+ [0x1F133]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x44 },
+ unicodeslot=0x1F133,
+ },
+ [0x1F134]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x45 },
+ unicodeslot=0x1F134,
+ },
+ [0x1F135]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x46 },
+ unicodeslot=0x1F135,
+ },
+ [0x1F136]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x47 },
+ unicodeslot=0x1F136,
+ },
+ [0x1F137]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x48 },
+ unicodeslot=0x1F137,
+ },
+ [0x1F138]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x49 },
+ unicodeslot=0x1F138,
+ },
+ [0x1F139]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4A },
+ unicodeslot=0x1F139,
+ },
+ [0x1F13A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4B },
+ unicodeslot=0x1F13A,
+ },
+ [0x1F13B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4C },
+ unicodeslot=0x1F13B,
+ },
+ [0x1F13C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4D },
+ unicodeslot=0x1F13C,
+ },
+ [0x1F13D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4E },
+ unicodeslot=0x1F13D,
+ },
+ [0x1F13E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4F },
+ unicodeslot=0x1F13E,
+ },
+ [0x1F13F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x50 },
+ unicodeslot=0x1F13F,
+ },
+ [0x1F140]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x51 },
+ unicodeslot=0x1F140,
+ },
+ [0x1F141]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x52 },
+ unicodeslot=0x1F141,
+ },
+ [0x1F142]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x53 },
+ unicodeslot=0x1F142,
+ },
+ [0x1F143]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x54 },
+ unicodeslot=0x1F143,
+ },
+ [0x1F144]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x55 },
+ unicodeslot=0x1F144,
+ },
+ [0x1F145]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x56 },
+ unicodeslot=0x1F145,
+ },
+ [0x1F146]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x57 },
+ unicodeslot=0x1F146,
+ },
+ [0x1F147]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x58 },
+ unicodeslot=0x1F147,
+ },
+ [0x1F148]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x59 },
+ unicodeslot=0x1F148,
+ },
+ [0x1F149]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x5A },
+ unicodeslot=0x1F149,
+ },
+ [0x1F14A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x48, 0x56 },
+ unicodeslot=0x1F14A,
+ },
+ [0x1F14B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x4D, 0x56 },
+ unicodeslot=0x1F14B,
+ },
+ [0x1F14C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x53, 0x44 },
+ unicodeslot=0x1F14C,
+ },
+ [0x1F14D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x53, 0x53 },
+ unicodeslot=0x1F14D,
+ },
+ [0x1F14E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x50, 0x50, 0x56 },
+ unicodeslot=0x1F14E,
+ },
+ [0x1F14F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x57, 0x43 },
+ unicodeslot=0x1F14F,
+ },
+ [0x1F150]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F150,
+ },
+ [0x1F151]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F151,
+ },
+ [0x1F152]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F152,
+ },
+ [0x1F153]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F153,
+ },
+ [0x1F154]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F154,
+ },
+ [0x1F155]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F155,
+ },
+ [0x1F156]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F156,
+ },
+ [0x1F157]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F157,
+ },
+ [0x1F158]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F158,
+ },
+ [0x1F159]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F159,
+ },
+ [0x1F15A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F15A,
+ },
+ [0x1F15B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F15B,
+ },
+ [0x1F15C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F15C,
+ },
+ [0x1F15D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F15D,
+ },
+ [0x1F15E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F15E,
+ },
+ [0x1F15F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F15F,
+ },
+ [0x1F160]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F160,
+ },
+ [0x1F161]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F161,
+ },
+ [0x1F162]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F162,
+ },
+ [0x1F163]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F163,
+ },
+ [0x1F164]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F164,
+ },
+ [0x1F165]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F165,
+ },
+ [0x1F166]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F166,
+ },
+ [0x1F167]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F167,
+ },
+ [0x1F168]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F168,
+ },
+ [0x1F169]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F169,
+ },
+ [0x1F16A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "super", 0x4D, 0x43 },
+ unicodeslot=0x1F16A,
+ },
+ [0x1F16B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "super", 0x4D, 0x44 },
+ unicodeslot=0x1F16B,
+ },
+ [0x1F16C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ specials={ "super", 0x4D, 0x52 },
+ unicodeslot=0x1F16C,
+ },
+ [0x1F170]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F170,
+ },
+ [0x1F171]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F171,
+ },
+ [0x1F172]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F172,
+ },
+ [0x1F173]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F173,
+ },
+ [0x1F174]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F174,
+ },
+ [0x1F175]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F175,
+ },
+ [0x1F176]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F176,
+ },
+ [0x1F177]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F177,
+ },
+ [0x1F178]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F178,
+ },
+ [0x1F179]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F179,
+ },
+ [0x1F17A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F17A,
+ },
+ [0x1F17B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F17B,
+ },
+ [0x1F17C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F17C,
+ },
+ [0x1F17D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F17D,
+ },
+ [0x1F17E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F17E,
+ },
+ [0x1F17F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F17F,
+ },
+ [0x1F180]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F180,
+ },
+ [0x1F181]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F181,
+ },
+ [0x1F182]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F182,
+ },
+ [0x1F183]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F183,
+ },
+ [0x1F184]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F184,
+ },
+ [0x1F185]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F185,
+ },
+ [0x1F186]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F186,
+ },
+ [0x1F187]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F187,
+ },
+ [0x1F188]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F188,
+ },
+ [0x1F189]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F189,
+ },
+ [0x1F18A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F18A,
+ },
+ [0x1F18B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F18B,
+ },
+ [0x1F18C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F18C,
+ },
+ [0x1F18D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F18D,
+ },
+ [0x1F18E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F18E,
+ },
+ [0x1F18F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F18F,
+ },
+ [0x1F190]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ specials={ "square", 0x44, 0x4A },
+ unicodeslot=0x1F190,
+ },
+ [0x1F191]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F191,
+ },
+ [0x1F192]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F192,
+ },
+ [0x1F193]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F193,
+ },
+ [0x1F194]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F194,
+ },
+ [0x1F195]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F195,
+ },
+ [0x1F196]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F196,
+ },
+ [0x1F197]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F197,
+ },
+ [0x1F198]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F198,
+ },
+ [0x1F199]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F199,
+ },
+ [0x1F19A]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F19A,
+ },
+ [0x1F19B]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F19B,
+ },
+ [0x1F19C]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F19C,
+ },
+ [0x1F19D]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F19D,
+ },
+ [0x1F19E]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F19E,
+ },
+ [0x1F19F]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F19F,
+ },
+ [0x1F1A0]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A0,
+ },
+ [0x1F1A1]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A1,
+ },
+ [0x1F1A2]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A2,
+ },
+ [0x1F1A3]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A3,
+ },
+ [0x1F1A4]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A4,
+ },
+ [0x1F1A5]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A5,
+ },
+ [0x1F1A6]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A6,
+ },
+ [0x1F1A7]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A7,
+ },
+ [0x1F1A8]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A8,
+ },
+ [0x1F1A9]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1A9,
+ },
+ [0x1F1AA]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1AA,
+ },
+ [0x1F1AB]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1AB,
+ },
+ [0x1F1AC]={
+ category="so",
+ direction="l",
+ linebreak="ai",
+ unicodeslot=0x1F1AC,
+ },
+ [0x1F1E6]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1E6,
+ },
+ [0x1F1E7]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1E7,
+ },
+ [0x1F1E8]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1E8,
+ },
+ [0x1F1E9]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1E9,
+ },
+ [0x1F1EA]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1EA,
+ },
+ [0x1F1EB]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1EB,
+ },
+ [0x1F1EC]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1EC,
+ },
+ [0x1F1ED]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1ED,
+ },
+ [0x1F1EE]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1EE,
+ },
+ [0x1F1EF]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1EF,
+ },
+ [0x1F1F0]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F0,
+ },
+ [0x1F1F1]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F1,
+ },
+ [0x1F1F2]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F2,
+ },
+ [0x1F1F3]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F3,
+ },
+ [0x1F1F4]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F4,
+ },
+ [0x1F1F5]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F5,
+ },
+ [0x1F1F6]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F6,
+ },
+ [0x1F1F7]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F7,
+ },
+ [0x1F1F8]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F8,
+ },
+ [0x1F1F9]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1F9,
+ },
+ [0x1F1FA]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1FA,
+ },
+ [0x1F1FB]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1FB,
+ },
+ [0x1F1FC]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1FC,
+ },
+ [0x1F1FD]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1FD,
+ },
+ [0x1F1FE]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1FE,
+ },
+ [0x1F1FF]={
+ category="so",
+ direction="l",
+ linebreak="ri",
+ unicodeslot=0x1F1FF,
+ },
+ [0x1F200]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x307B, 0x304B },
+ unicodeslot=0x1F200,
+ },
+ [0x1F201]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B3, 0x30B3 },
+ unicodeslot=0x1F201,
+ },
+ [0x1F202]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30B5 },
+ unicodeslot=0x1F202,
+ },
+ [0x1F210]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x624B },
+ unicodeslot=0x1F210,
+ },
+ [0x1F211]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5B57 },
+ unicodeslot=0x1F211,
+ },
+ [0x1F212]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x53CC },
+ unicodeslot=0x1F212,
+ },
+ [0x1F213]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x30C7 },
+ unicodeslot=0x1F213,
+ },
+ [0x1F214]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4E8C },
+ unicodeslot=0x1F214,
+ },
+ [0x1F215]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x591A },
+ unicodeslot=0x1F215,
+ },
+ [0x1F216]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x89E3 },
+ unicodeslot=0x1F216,
+ },
+ [0x1F217]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5929 },
+ unicodeslot=0x1F217,
+ },
+ [0x1F218]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4EA4 },
+ unicodeslot=0x1F218,
+ },
+ [0x1F219]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6620 },
+ unicodeslot=0x1F219,
+ },
+ [0x1F21A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x7121 },
+ unicodeslot=0x1F21A,
+ },
+ [0x1F21B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6599 },
+ unicodeslot=0x1F21B,
+ },
+ [0x1F21C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x524D },
+ unicodeslot=0x1F21C,
+ },
+ [0x1F21D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5F8C },
+ unicodeslot=0x1F21D,
+ },
+ [0x1F21E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x518D },
+ unicodeslot=0x1F21E,
+ },
+ [0x1F21F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x65B0 },
+ unicodeslot=0x1F21F,
+ },
+ [0x1F220]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x521D },
+ unicodeslot=0x1F220,
+ },
+ [0x1F221]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x7D42 },
+ unicodeslot=0x1F221,
+ },
+ [0x1F222]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x751F },
+ unicodeslot=0x1F222,
+ },
+ [0x1F223]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x8CA9 },
+ unicodeslot=0x1F223,
+ },
+ [0x1F224]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x58F0 },
+ unicodeslot=0x1F224,
+ },
+ [0x1F225]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5439 },
+ unicodeslot=0x1F225,
+ },
+ [0x1F226]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6F14 },
+ unicodeslot=0x1F226,
+ },
+ [0x1F227]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6295 },
+ unicodeslot=0x1F227,
+ },
+ [0x1F228]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6355 },
+ unicodeslot=0x1F228,
+ },
+ [0x1F229]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4E00 },
+ unicodeslot=0x1F229,
+ },
+ [0x1F22A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4E09 },
+ unicodeslot=0x1F22A,
+ },
+ [0x1F22B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x904A },
+ unicodeslot=0x1F22B,
+ },
+ [0x1F22C]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5DE6 },
+ unicodeslot=0x1F22C,
+ },
+ [0x1F22D]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x4E2D },
+ unicodeslot=0x1F22D,
+ },
+ [0x1F22E]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x53F3 },
+ unicodeslot=0x1F22E,
+ },
+ [0x1F22F]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6307 },
+ unicodeslot=0x1F22F,
+ },
+ [0x1F230]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x8D70 },
+ unicodeslot=0x1F230,
+ },
+ [0x1F231]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6253 },
+ unicodeslot=0x1F231,
+ },
+ [0x1F232]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x7981 },
+ unicodeslot=0x1F232,
+ },
+ [0x1F233]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x7A7A },
+ unicodeslot=0x1F233,
+ },
+ [0x1F234]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5408 },
+ unicodeslot=0x1F234,
+ },
+ [0x1F235]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6E80 },
+ unicodeslot=0x1F235,
+ },
+ [0x1F236]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6709 },
+ unicodeslot=0x1F236,
+ },
+ [0x1F237]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x6708 },
+ unicodeslot=0x1F237,
+ },
+ [0x1F238]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x7533 },
+ unicodeslot=0x1F238,
+ },
+ [0x1F239]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x5272 },
+ unicodeslot=0x1F239,
+ },
+ [0x1F23A]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x55B6 },
+ unicodeslot=0x1F23A,
+ },
+ [0x1F23B]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "square", 0x914D },
+ unicodeslot=0x1F23B,
+ },
+ [0x1F240]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x672C, 0x3015 },
+ unicodeslot=0x1F240,
+ },
+ [0x1F241]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x4E09, 0x3015 },
+ unicodeslot=0x1F241,
+ },
+ [0x1F242]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x4E8C, 0x3015 },
+ unicodeslot=0x1F242,
+ },
+ [0x1F243]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x5B89, 0x3015 },
+ unicodeslot=0x1F243,
+ },
+ [0x1F244]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x70B9, 0x3015 },
+ unicodeslot=0x1F244,
+ },
+ [0x1F245]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x6253, 0x3015 },
+ unicodeslot=0x1F245,
+ },
+ [0x1F246]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x76D7, 0x3015 },
+ unicodeslot=0x1F246,
+ },
+ [0x1F247]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x52DD, 0x3015 },
+ unicodeslot=0x1F247,
+ },
+ [0x1F248]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "compat", 0x3014, 0x6557, 0x3015 },
+ unicodeslot=0x1F248,
+ },
+ [0x1F250]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x5F97 },
+ unicodeslot=0x1F250,
+ },
+ [0x1F251]={
+ category="so",
+ direction="l",
+ linebreak="id",
+ specials={ "circle", 0x53EF },
+ unicodeslot=0x1F251,
+ },
+ [0x1F260]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F260,
+ },
+ [0x1F261]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F261,
+ },
+ [0x1F262]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F262,
+ },
+ [0x1F263]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F263,
+ },
+ [0x1F264]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F264,
+ },
+ [0x1F265]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F265,
+ },
+ [0x1F300]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F300,
+ },
+ [0x1F301]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F301,
+ },
+ [0x1F302]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F302,
+ },
+ [0x1F303]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F303,
+ },
+ [0x1F304]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F304,
+ },
+ [0x1F305]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F305,
+ },
+ [0x1F306]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F306,
+ },
+ [0x1F307]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F307,
+ },
+ [0x1F308]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F308,
+ },
+ [0x1F309]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F309,
+ },
+ [0x1F30A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F30A,
+ },
+ [0x1F30B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F30B,
+ },
+ [0x1F30C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F30C,
+ },
+ [0x1F30D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F30D,
+ },
+ [0x1F30E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F30E,
+ },
+ [0x1F30F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F30F,
+ },
+ [0x1F310]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F310,
+ },
+ [0x1F311]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F311,
+ },
+ [0x1F312]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F312,
+ },
+ [0x1F313]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F313,
+ },
+ [0x1F314]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F314,
+ },
+ [0x1F315]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F315,
+ },
+ [0x1F316]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F316,
+ },
+ [0x1F317]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F317,
+ },
+ [0x1F318]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F318,
+ },
+ [0x1F319]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F319,
+ },
+ [0x1F31A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F31A,
+ },
+ [0x1F31B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F31B,
+ },
+ [0x1F31C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F31C,
+ },
+ [0x1F31D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F31D,
+ },
+ [0x1F31E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F31E,
+ },
+ [0x1F31F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F31F,
+ },
+ [0x1F320]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F320,
+ },
+ [0x1F321]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F321,
+ },
+ [0x1F322]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F322,
+ },
+ [0x1F323]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F323,
+ },
+ [0x1F324]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F324,
+ },
+ [0x1F325]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F325,
+ },
+ [0x1F326]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F326,
+ },
+ [0x1F327]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F327,
+ },
+ [0x1F328]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F328,
+ },
+ [0x1F329]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F329,
+ },
+ [0x1F32A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F32A,
+ },
+ [0x1F32B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F32B,
+ },
+ [0x1F32C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F32C,
+ },
+ [0x1F32D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F32D,
+ },
+ [0x1F32E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F32E,
+ },
+ [0x1F32F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F32F,
+ },
+ [0x1F330]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F330,
+ },
+ [0x1F331]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F331,
+ },
+ [0x1F332]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F332,
+ },
+ [0x1F333]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F333,
+ },
+ [0x1F334]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F334,
+ },
+ [0x1F335]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F335,
+ },
+ [0x1F336]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F336,
+ },
+ [0x1F337]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F337,
+ },
+ [0x1F338]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F338,
+ },
+ [0x1F339]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F339,
+ },
+ [0x1F33A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F33A,
+ },
+ [0x1F33B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F33B,
+ },
+ [0x1F33C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F33C,
+ },
+ [0x1F33D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F33D,
+ },
+ [0x1F33E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F33E,
+ },
+ [0x1F33F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F33F,
+ },
+ [0x1F340]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F340,
+ },
+ [0x1F341]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F341,
+ },
+ [0x1F342]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F342,
+ },
+ [0x1F343]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F343,
+ },
+ [0x1F344]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F344,
+ },
+ [0x1F345]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F345,
+ },
+ [0x1F346]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F346,
+ },
+ [0x1F347]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F347,
+ },
+ [0x1F348]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F348,
+ },
+ [0x1F349]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F349,
+ },
+ [0x1F34A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F34A,
+ },
+ [0x1F34B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F34B,
+ },
+ [0x1F34C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F34C,
+ },
+ [0x1F34D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F34D,
+ },
+ [0x1F34E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F34E,
+ },
+ [0x1F34F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F34F,
+ },
+ [0x1F350]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F350,
+ },
+ [0x1F351]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F351,
+ },
+ [0x1F352]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F352,
+ },
+ [0x1F353]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F353,
+ },
+ [0x1F354]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F354,
+ },
+ [0x1F355]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F355,
+ },
+ [0x1F356]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F356,
+ },
+ [0x1F357]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F357,
+ },
+ [0x1F358]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F358,
+ },
+ [0x1F359]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F359,
+ },
+ [0x1F35A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F35A,
+ },
+ [0x1F35B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F35B,
+ },
+ [0x1F35C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F35C,
+ },
+ [0x1F35D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F35D,
+ },
+ [0x1F35E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F35E,
+ },
+ [0x1F35F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F35F,
+ },
+ [0x1F360]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F360,
+ },
+ [0x1F361]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F361,
+ },
+ [0x1F362]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F362,
+ },
+ [0x1F363]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F363,
+ },
+ [0x1F364]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F364,
+ },
+ [0x1F365]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F365,
+ },
+ [0x1F366]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F366,
+ },
+ [0x1F367]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F367,
+ },
+ [0x1F368]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F368,
+ },
+ [0x1F369]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F369,
+ },
+ [0x1F36A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F36A,
+ },
+ [0x1F36B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F36B,
+ },
+ [0x1F36C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F36C,
+ },
+ [0x1F36D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F36D,
+ },
+ [0x1F36E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F36E,
+ },
+ [0x1F36F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F36F,
+ },
+ [0x1F370]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F370,
+ },
+ [0x1F371]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F371,
+ },
+ [0x1F372]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F372,
+ },
+ [0x1F373]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F373,
+ },
+ [0x1F374]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F374,
+ },
+ [0x1F375]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F375,
+ },
+ [0x1F376]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F376,
+ },
+ [0x1F377]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F377,
+ },
+ [0x1F378]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F378,
+ },
+ [0x1F379]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F379,
+ },
+ [0x1F37A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F37A,
+ },
+ [0x1F37B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F37B,
+ },
+ [0x1F37C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F37C,
+ },
+ [0x1F37D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F37D,
+ },
+ [0x1F37E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F37E,
+ },
+ [0x1F37F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F37F,
+ },
+ [0x1F380]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F380,
+ },
+ [0x1F381]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F381,
+ },
+ [0x1F382]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F382,
+ },
+ [0x1F383]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F383,
+ },
+ [0x1F384]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F384,
+ },
+ [0x1F385]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F385,
+ },
+ [0x1F386]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F386,
+ },
+ [0x1F387]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F387,
+ },
+ [0x1F388]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F388,
+ },
+ [0x1F389]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F389,
+ },
+ [0x1F38A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F38A,
+ },
+ [0x1F38B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F38B,
+ },
+ [0x1F38C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F38C,
+ },
+ [0x1F38D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F38D,
+ },
+ [0x1F38E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F38E,
+ },
+ [0x1F38F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F38F,
+ },
+ [0x1F390]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F390,
+ },
+ [0x1F391]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F391,
+ },
+ [0x1F392]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F392,
+ },
+ [0x1F393]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F393,
+ },
+ [0x1F394]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F394,
+ },
+ [0x1F395]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F395,
+ },
+ [0x1F396]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F396,
+ },
+ [0x1F397]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F397,
+ },
+ [0x1F398]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F398,
+ },
+ [0x1F399]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F399,
+ },
+ [0x1F39A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F39A,
+ },
+ [0x1F39B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F39B,
+ },
+ [0x1F39C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F39C,
+ },
+ [0x1F39D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F39D,
+ },
+ [0x1F39E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F39E,
+ },
+ [0x1F39F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F39F,
+ },
+ [0x1F3A0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A0,
+ },
+ [0x1F3A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A1,
+ },
+ [0x1F3A2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A2,
+ },
+ [0x1F3A3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A3,
+ },
+ [0x1F3A4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A4,
+ },
+ [0x1F3A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A5,
+ },
+ [0x1F3A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A6,
+ },
+ [0x1F3A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A7,
+ },
+ [0x1F3A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A8,
+ },
+ [0x1F3A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3A9,
+ },
+ [0x1F3AA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3AA,
+ },
+ [0x1F3AB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3AB,
+ },
+ [0x1F3AC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3AC,
+ },
+ [0x1F3AD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3AD,
+ },
+ [0x1F3AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3AE,
+ },
+ [0x1F3AF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3AF,
+ },
+ [0x1F3B0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B0,
+ },
+ [0x1F3B1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B1,
+ },
+ [0x1F3B2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B2,
+ },
+ [0x1F3B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B3,
+ },
+ [0x1F3B4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B4,
+ },
+ [0x1F3B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F3B5,
+ },
+ [0x1F3B6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F3B6,
+ },
+ [0x1F3B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B7,
+ },
+ [0x1F3B8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B8,
+ },
+ [0x1F3B9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3B9,
+ },
+ [0x1F3BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3BA,
+ },
+ [0x1F3BB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3BB,
+ },
+ [0x1F3BC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F3BC,
+ },
+ [0x1F3BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3BD,
+ },
+ [0x1F3BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3BE,
+ },
+ [0x1F3BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3BF,
+ },
+ [0x1F3C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3C0,
+ },
+ [0x1F3C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3C1,
+ },
+ [0x1F3C2]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3C2,
+ },
+ [0x1F3C3]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3C3,
+ },
+ [0x1F3C4]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3C4,
+ },
+ [0x1F3C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3C5,
+ },
+ [0x1F3C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3C6,
+ },
+ [0x1F3C7]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3C7,
+ },
+ [0x1F3C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3C8,
+ },
+ [0x1F3C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3C9,
+ },
+ [0x1F3CA]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3CA,
+ },
+ [0x1F3CB]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3CB,
+ },
+ [0x1F3CC]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F3CC,
+ },
+ [0x1F3CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3CD,
+ },
+ [0x1F3CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3CE,
+ },
+ [0x1F3CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3CF,
+ },
+ [0x1F3D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D0,
+ },
+ [0x1F3D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D1,
+ },
+ [0x1F3D2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D2,
+ },
+ [0x1F3D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D3,
+ },
+ [0x1F3D4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D4,
+ },
+ [0x1F3D5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D5,
+ },
+ [0x1F3D6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D6,
+ },
+ [0x1F3D7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D7,
+ },
+ [0x1F3D8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D8,
+ },
+ [0x1F3D9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3D9,
+ },
+ [0x1F3DA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3DA,
+ },
+ [0x1F3DB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3DB,
+ },
+ [0x1F3DC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3DC,
+ },
+ [0x1F3DD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3DD,
+ },
+ [0x1F3DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3DE,
+ },
+ [0x1F3DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3DF,
+ },
+ [0x1F3E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E0,
+ },
+ [0x1F3E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E1,
+ },
+ [0x1F3E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E2,
+ },
+ [0x1F3E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E3,
+ },
+ [0x1F3E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E4,
+ },
+ [0x1F3E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E5,
+ },
+ [0x1F3E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E6,
+ },
+ [0x1F3E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E7,
+ },
+ [0x1F3E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E8,
+ },
+ [0x1F3E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3E9,
+ },
+ [0x1F3EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3EA,
+ },
+ [0x1F3EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3EB,
+ },
+ [0x1F3EC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3EC,
+ },
+ [0x1F3ED]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3ED,
+ },
+ [0x1F3EE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3EE,
+ },
+ [0x1F3EF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3EF,
+ },
+ [0x1F3F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F0,
+ },
+ [0x1F3F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F1,
+ },
+ [0x1F3F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F2,
+ },
+ [0x1F3F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F3,
+ },
+ [0x1F3F4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F4,
+ },
+ [0x1F3F5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F5,
+ },
+ [0x1F3F6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F6,
+ },
+ [0x1F3F7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F7,
+ },
+ [0x1F3F8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F8,
+ },
+ [0x1F3F9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3F9,
+ },
+ [0x1F3FA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F3FA,
+ },
+ [0x1F3FB]={
+ category="sk",
+ direction="on",
+ linebreak="em",
+ unicodeslot=0x1F3FB,
+ },
+ [0x1F3FC]={
+ category="sk",
+ direction="on",
+ linebreak="em",
+ unicodeslot=0x1F3FC,
+ },
+ [0x1F3FD]={
+ category="sk",
+ direction="on",
+ linebreak="em",
+ unicodeslot=0x1F3FD,
+ },
+ [0x1F3FE]={
+ category="sk",
+ direction="on",
+ linebreak="em",
+ unicodeslot=0x1F3FE,
+ },
+ [0x1F3FF]={
+ category="sk",
+ direction="on",
+ linebreak="em",
+ unicodeslot=0x1F3FF,
+ },
+ [0x1F400]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F400,
+ },
+ [0x1F401]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F401,
+ },
+ [0x1F402]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F402,
+ },
+ [0x1F403]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F403,
+ },
+ [0x1F404]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F404,
+ },
+ [0x1F405]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F405,
+ },
+ [0x1F406]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F406,
+ },
+ [0x1F407]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F407,
+ },
+ [0x1F408]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F408,
+ },
+ [0x1F409]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F409,
+ },
+ [0x1F40A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F40A,
+ },
+ [0x1F40B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F40B,
+ },
+ [0x1F40C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F40C,
+ },
+ [0x1F40D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F40D,
+ },
+ [0x1F40E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F40E,
+ },
+ [0x1F40F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F40F,
+ },
+ [0x1F410]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F410,
+ },
+ [0x1F411]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F411,
+ },
+ [0x1F412]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F412,
+ },
+ [0x1F413]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F413,
+ },
+ [0x1F414]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F414,
+ },
+ [0x1F415]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F415,
+ },
+ [0x1F416]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F416,
+ },
+ [0x1F417]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F417,
+ },
+ [0x1F418]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F418,
+ },
+ [0x1F419]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F419,
+ },
+ [0x1F41A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F41A,
+ },
+ [0x1F41B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F41B,
+ },
+ [0x1F41C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F41C,
+ },
+ [0x1F41D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F41D,
+ },
+ [0x1F41E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F41E,
+ },
+ [0x1F41F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F41F,
+ },
+ [0x1F420]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F420,
+ },
+ [0x1F421]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F421,
+ },
+ [0x1F422]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F422,
+ },
+ [0x1F423]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F423,
+ },
+ [0x1F424]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F424,
+ },
+ [0x1F425]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F425,
+ },
+ [0x1F426]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F426,
+ },
+ [0x1F427]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F427,
+ },
+ [0x1F428]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F428,
+ },
+ [0x1F429]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F429,
+ },
+ [0x1F42A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F42A,
+ },
+ [0x1F42B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F42B,
+ },
+ [0x1F42C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F42C,
+ },
+ [0x1F42D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F42D,
+ },
+ [0x1F42E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F42E,
+ },
+ [0x1F42F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F42F,
+ },
+ [0x1F430]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F430,
+ },
+ [0x1F431]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F431,
+ },
+ [0x1F432]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F432,
+ },
+ [0x1F433]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F433,
+ },
+ [0x1F434]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F434,
+ },
+ [0x1F435]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F435,
+ },
+ [0x1F436]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F436,
+ },
+ [0x1F437]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F437,
+ },
+ [0x1F438]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F438,
+ },
+ [0x1F439]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F439,
+ },
+ [0x1F43A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F43A,
+ },
+ [0x1F43B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F43B,
+ },
+ [0x1F43C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F43C,
+ },
+ [0x1F43D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F43D,
+ },
+ [0x1F43E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F43E,
+ },
+ [0x1F43F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F43F,
+ },
+ [0x1F440]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F440,
+ },
+ [0x1F441]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F441,
+ },
+ [0x1F442]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F442,
+ },
+ [0x1F443]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F443,
+ },
+ [0x1F444]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F444,
+ },
+ [0x1F445]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F445,
+ },
+ [0x1F446]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F446,
+ },
+ [0x1F447]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F447,
+ },
+ [0x1F448]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F448,
+ },
+ [0x1F449]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F449,
+ },
+ [0x1F44A]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F44A,
+ },
+ [0x1F44B]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F44B,
+ },
+ [0x1F44C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F44C,
+ },
+ [0x1F44D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F44D,
+ },
+ [0x1F44E]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F44E,
+ },
+ [0x1F44F]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F44F,
+ },
+ [0x1F450]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F450,
+ },
+ [0x1F451]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F451,
+ },
+ [0x1F452]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F452,
+ },
+ [0x1F453]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F453,
+ },
+ [0x1F454]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F454,
+ },
+ [0x1F455]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F455,
+ },
+ [0x1F456]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F456,
+ },
+ [0x1F457]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F457,
+ },
+ [0x1F458]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F458,
+ },
+ [0x1F459]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F459,
+ },
+ [0x1F45A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F45A,
+ },
+ [0x1F45B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F45B,
+ },
+ [0x1F45C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F45C,
+ },
+ [0x1F45D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F45D,
+ },
+ [0x1F45E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F45E,
+ },
+ [0x1F45F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F45F,
+ },
+ [0x1F460]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F460,
+ },
+ [0x1F461]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F461,
+ },
+ [0x1F462]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F462,
+ },
+ [0x1F463]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F463,
+ },
+ [0x1F464]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F464,
+ },
+ [0x1F465]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F465,
+ },
+ [0x1F466]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F466,
+ },
+ [0x1F467]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F467,
+ },
+ [0x1F468]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F468,
+ },
+ [0x1F469]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F469,
+ },
+ [0x1F46A]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F46A,
+ },
+ [0x1F46B]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F46B,
+ },
+ [0x1F46C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F46C,
+ },
+ [0x1F46D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F46D,
+ },
+ [0x1F46E]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F46E,
+ },
+ [0x1F46F]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F46F,
+ },
+ [0x1F470]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F470,
+ },
+ [0x1F471]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F471,
+ },
+ [0x1F472]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F472,
+ },
+ [0x1F473]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F473,
+ },
+ [0x1F474]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F474,
+ },
+ [0x1F475]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F475,
+ },
+ [0x1F476]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F476,
+ },
+ [0x1F477]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F477,
+ },
+ [0x1F478]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F478,
+ },
+ [0x1F479]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F479,
+ },
+ [0x1F47A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F47A,
+ },
+ [0x1F47B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F47B,
+ },
+ [0x1F47C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F47C,
+ },
+ [0x1F47D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F47D,
+ },
+ [0x1F47E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F47E,
+ },
+ [0x1F47F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F47F,
+ },
+ [0x1F480]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F480,
+ },
+ [0x1F481]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F481,
+ },
+ [0x1F482]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F482,
+ },
+ [0x1F483]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F483,
+ },
+ [0x1F484]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F484,
+ },
+ [0x1F485]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F485,
+ },
+ [0x1F486]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F486,
+ },
+ [0x1F487]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F487,
+ },
+ [0x1F488]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F488,
+ },
+ [0x1F489]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F489,
+ },
+ [0x1F48A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F48A,
+ },
+ [0x1F48B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F48B,
+ },
+ [0x1F48C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F48C,
+ },
+ [0x1F48D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F48D,
+ },
+ [0x1F48E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F48E,
+ },
+ [0x1F48F]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F48F,
+ },
+ [0x1F490]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F490,
+ },
+ [0x1F491]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F491,
+ },
+ [0x1F492]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F492,
+ },
+ [0x1F493]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F493,
+ },
+ [0x1F494]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F494,
+ },
+ [0x1F495]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F495,
+ },
+ [0x1F496]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F496,
+ },
+ [0x1F497]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F497,
+ },
+ [0x1F498]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F498,
+ },
+ [0x1F499]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F499,
+ },
+ [0x1F49A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F49A,
+ },
+ [0x1F49B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F49B,
+ },
+ [0x1F49C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F49C,
+ },
+ [0x1F49D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F49D,
+ },
+ [0x1F49E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F49E,
+ },
+ [0x1F49F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F49F,
+ },
+ [0x1F4A0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F4A0,
+ },
+ [0x1F4A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A1,
+ },
+ [0x1F4A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F4A2,
+ },
+ [0x1F4A3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A3,
+ },
+ [0x1F4A4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F4A4,
+ },
+ [0x1F4A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A5,
+ },
+ [0x1F4A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A6,
+ },
+ [0x1F4A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A7,
+ },
+ [0x1F4A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A8,
+ },
+ [0x1F4A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4A9,
+ },
+ [0x1F4AA]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F4AA,
+ },
+ [0x1F4AB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4AB,
+ },
+ [0x1F4AC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4AC,
+ },
+ [0x1F4AD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4AD,
+ },
+ [0x1F4AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4AE,
+ },
+ [0x1F4AF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F4AF,
+ },
+ [0x1F4B0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B0,
+ },
+ [0x1F4B1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F4B1,
+ },
+ [0x1F4B2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F4B2,
+ },
+ [0x1F4B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B3,
+ },
+ [0x1F4B4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B4,
+ },
+ [0x1F4B5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B5,
+ },
+ [0x1F4B6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B6,
+ },
+ [0x1F4B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B7,
+ },
+ [0x1F4B8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B8,
+ },
+ [0x1F4B9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4B9,
+ },
+ [0x1F4BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4BA,
+ },
+ [0x1F4BB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4BB,
+ },
+ [0x1F4BC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4BC,
+ },
+ [0x1F4BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4BD,
+ },
+ [0x1F4BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4BE,
+ },
+ [0x1F4BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4BF,
+ },
+ [0x1F4C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C0,
+ },
+ [0x1F4C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C1,
+ },
+ [0x1F4C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C2,
+ },
+ [0x1F4C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C3,
+ },
+ [0x1F4C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C4,
+ },
+ [0x1F4C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C5,
+ },
+ [0x1F4C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C6,
+ },
+ [0x1F4C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C7,
+ },
+ [0x1F4C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C8,
+ },
+ [0x1F4C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4C9,
+ },
+ [0x1F4CA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4CA,
+ },
+ [0x1F4CB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4CB,
+ },
+ [0x1F4CC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4CC,
+ },
+ [0x1F4CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4CD,
+ },
+ [0x1F4CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4CE,
+ },
+ [0x1F4CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4CF,
+ },
+ [0x1F4D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D0,
+ },
+ [0x1F4D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D1,
+ },
+ [0x1F4D2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D2,
+ },
+ [0x1F4D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D3,
+ },
+ [0x1F4D4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D4,
+ },
+ [0x1F4D5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D5,
+ },
+ [0x1F4D6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D6,
+ },
+ [0x1F4D7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D7,
+ },
+ [0x1F4D8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D8,
+ },
+ [0x1F4D9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4D9,
+ },
+ [0x1F4DA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4DA,
+ },
+ [0x1F4DB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4DB,
+ },
+ [0x1F4DC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4DC,
+ },
+ [0x1F4DD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4DD,
+ },
+ [0x1F4DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4DE,
+ },
+ [0x1F4DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4DF,
+ },
+ [0x1F4E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E0,
+ },
+ [0x1F4E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E1,
+ },
+ [0x1F4E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E2,
+ },
+ [0x1F4E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E3,
+ },
+ [0x1F4E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E4,
+ },
+ [0x1F4E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E5,
+ },
+ [0x1F4E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E6,
+ },
+ [0x1F4E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E7,
+ },
+ [0x1F4E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E8,
+ },
+ [0x1F4E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4E9,
+ },
+ [0x1F4EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4EA,
+ },
+ [0x1F4EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4EB,
+ },
+ [0x1F4EC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4EC,
+ },
+ [0x1F4ED]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4ED,
+ },
+ [0x1F4EE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4EE,
+ },
+ [0x1F4EF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4EF,
+ },
+ [0x1F4F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F0,
+ },
+ [0x1F4F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F1,
+ },
+ [0x1F4F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F2,
+ },
+ [0x1F4F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F3,
+ },
+ [0x1F4F4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F4,
+ },
+ [0x1F4F5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F5,
+ },
+ [0x1F4F6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F6,
+ },
+ [0x1F4F7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F7,
+ },
+ [0x1F4F8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F8,
+ },
+ [0x1F4F9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4F9,
+ },
+ [0x1F4FA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4FA,
+ },
+ [0x1F4FB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4FB,
+ },
+ [0x1F4FC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4FC,
+ },
+ [0x1F4FD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4FD,
+ },
+ [0x1F4FE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4FE,
+ },
+ [0x1F4FF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F4FF,
+ },
+ [0x1F500]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F500,
+ },
+ [0x1F501]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F501,
+ },
+ [0x1F502]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F502,
+ },
+ [0x1F503]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F503,
+ },
+ [0x1F504]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F504,
+ },
+ [0x1F505]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F505,
+ },
+ [0x1F506]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F506,
+ },
+ [0x1F507]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F507,
+ },
+ [0x1F508]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F508,
+ },
+ [0x1F509]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F509,
+ },
+ [0x1F50A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F50A,
+ },
+ [0x1F50B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F50B,
+ },
+ [0x1F50C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F50C,
+ },
+ [0x1F50D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F50D,
+ },
+ [0x1F50E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F50E,
+ },
+ [0x1F50F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F50F,
+ },
+ [0x1F510]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F510,
+ },
+ [0x1F511]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F511,
+ },
+ [0x1F512]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F512,
+ },
+ [0x1F513]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F513,
+ },
+ [0x1F514]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F514,
+ },
+ [0x1F515]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F515,
+ },
+ [0x1F516]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F516,
+ },
+ [0x1F517]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F517,
+ },
+ [0x1F518]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F518,
+ },
+ [0x1F519]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F519,
+ },
+ [0x1F51A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F51A,
+ },
+ [0x1F51B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F51B,
+ },
+ [0x1F51C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F51C,
+ },
+ [0x1F51D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F51D,
+ },
+ [0x1F51E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F51E,
+ },
+ [0x1F51F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F51F,
+ },
+ [0x1F520]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F520,
+ },
+ [0x1F521]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F521,
+ },
+ [0x1F522]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F522,
+ },
+ [0x1F523]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F523,
+ },
+ [0x1F524]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F524,
+ },
+ [0x1F525]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F525,
+ },
+ [0x1F526]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F526,
+ },
+ [0x1F527]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F527,
+ },
+ [0x1F528]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F528,
+ },
+ [0x1F529]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F529,
+ },
+ [0x1F52A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F52A,
+ },
+ [0x1F52B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F52B,
+ },
+ [0x1F52C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F52C,
+ },
+ [0x1F52D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F52D,
+ },
+ [0x1F52E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F52E,
+ },
+ [0x1F52F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F52F,
+ },
+ [0x1F530]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F530,
+ },
+ [0x1F531]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F531,
+ },
+ [0x1F532]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F532,
+ },
+ [0x1F533]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F533,
+ },
+ [0x1F534]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F534,
+ },
+ [0x1F535]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F535,
+ },
+ [0x1F536]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F536,
+ },
+ [0x1F537]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F537,
+ },
+ [0x1F538]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F538,
+ },
+ [0x1F539]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F539,
+ },
+ [0x1F53A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F53A,
+ },
+ [0x1F53B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F53B,
+ },
+ [0x1F53C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F53C,
+ },
+ [0x1F53D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F53D,
+ },
+ [0x1F53E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F53E,
+ },
+ [0x1F53F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F53F,
+ },
+ [0x1F540]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F540,
+ },
+ [0x1F541]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F541,
+ },
+ [0x1F542]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F542,
+ },
+ [0x1F543]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F543,
+ },
+ [0x1F544]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F544,
+ },
+ [0x1F545]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F545,
+ },
+ [0x1F546]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F546,
+ },
+ [0x1F547]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F547,
+ },
+ [0x1F548]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F548,
+ },
+ [0x1F549]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F549,
+ },
+ [0x1F54A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F54A,
+ },
+ [0x1F54B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F54B,
+ },
+ [0x1F54C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F54C,
+ },
+ [0x1F54D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F54D,
+ },
+ [0x1F54E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F54E,
+ },
+ [0x1F54F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F54F,
+ },
+ [0x1F550]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F550,
+ },
+ [0x1F551]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F551,
+ },
+ [0x1F552]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F552,
+ },
+ [0x1F553]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F553,
+ },
+ [0x1F554]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F554,
+ },
+ [0x1F555]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F555,
+ },
+ [0x1F556]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F556,
+ },
+ [0x1F557]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F557,
+ },
+ [0x1F558]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F558,
+ },
+ [0x1F559]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F559,
+ },
+ [0x1F55A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F55A,
+ },
+ [0x1F55B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F55B,
+ },
+ [0x1F55C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F55C,
+ },
+ [0x1F55D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F55D,
+ },
+ [0x1F55E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F55E,
+ },
+ [0x1F55F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F55F,
+ },
+ [0x1F560]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F560,
+ },
+ [0x1F561]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F561,
+ },
+ [0x1F562]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F562,
+ },
+ [0x1F563]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F563,
+ },
+ [0x1F564]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F564,
+ },
+ [0x1F565]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F565,
+ },
+ [0x1F566]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F566,
+ },
+ [0x1F567]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F567,
+ },
+ [0x1F568]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F568,
+ },
+ [0x1F569]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F569,
+ },
+ [0x1F56A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F56A,
+ },
+ [0x1F56B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F56B,
+ },
+ [0x1F56C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F56C,
+ },
+ [0x1F56D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F56D,
+ },
+ [0x1F56E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F56E,
+ },
+ [0x1F56F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F56F,
+ },
+ [0x1F570]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F570,
+ },
+ [0x1F571]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F571,
+ },
+ [0x1F572]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F572,
+ },
+ [0x1F573]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F573,
+ },
+ [0x1F574]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F574,
+ },
+ [0x1F575]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F575,
+ },
+ [0x1F576]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F576,
+ },
+ [0x1F577]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F577,
+ },
+ [0x1F578]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F578,
+ },
+ [0x1F579]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F579,
+ },
+ [0x1F57A]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F57A,
+ },
+ [0x1F57B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F57B,
+ },
+ [0x1F57C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F57C,
+ },
+ [0x1F57D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F57D,
+ },
+ [0x1F57E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F57E,
+ },
+ [0x1F57F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F57F,
+ },
+ [0x1F580]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F580,
+ },
+ [0x1F581]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F581,
+ },
+ [0x1F582]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F582,
+ },
+ [0x1F583]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F583,
+ },
+ [0x1F584]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F584,
+ },
+ [0x1F585]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F585,
+ },
+ [0x1F586]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F586,
+ },
+ [0x1F587]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F587,
+ },
+ [0x1F588]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F588,
+ },
+ [0x1F589]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F589,
+ },
+ [0x1F58A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F58A,
+ },
+ [0x1F58B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F58B,
+ },
+ [0x1F58C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F58C,
+ },
+ [0x1F58D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F58D,
+ },
+ [0x1F58E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F58E,
+ },
+ [0x1F58F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F58F,
+ },
+ [0x1F590]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F590,
+ },
+ [0x1F591]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F591,
+ },
+ [0x1F592]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F592,
+ },
+ [0x1F593]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F593,
+ },
+ [0x1F594]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F594,
+ },
+ [0x1F595]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F595,
+ },
+ [0x1F596]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F596,
+ },
+ [0x1F597]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F597,
+ },
+ [0x1F598]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F598,
+ },
+ [0x1F599]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F599,
+ },
+ [0x1F59A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F59A,
+ },
+ [0x1F59B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F59B,
+ },
+ [0x1F59C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F59C,
+ },
+ [0x1F59D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F59D,
+ },
+ [0x1F59E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F59E,
+ },
+ [0x1F59F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F59F,
+ },
+ [0x1F5A0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A0,
+ },
+ [0x1F5A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A1,
+ },
+ [0x1F5A2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A2,
+ },
+ [0x1F5A3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A3,
+ },
+ [0x1F5A4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A4,
+ },
+ [0x1F5A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A5,
+ },
+ [0x1F5A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A6,
+ },
+ [0x1F5A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A7,
+ },
+ [0x1F5A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A8,
+ },
+ [0x1F5A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5A9,
+ },
+ [0x1F5AA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5AA,
+ },
+ [0x1F5AB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5AB,
+ },
+ [0x1F5AC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5AC,
+ },
+ [0x1F5AD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5AD,
+ },
+ [0x1F5AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5AE,
+ },
+ [0x1F5AF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5AF,
+ },
+ [0x1F5B0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B0,
+ },
+ [0x1F5B1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B1,
+ },
+ [0x1F5B2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B2,
+ },
+ [0x1F5B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B3,
+ },
+ [0x1F5B4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B4,
+ },
+ [0x1F5B5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B5,
+ },
+ [0x1F5B6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B6,
+ },
+ [0x1F5B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B7,
+ },
+ [0x1F5B8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B8,
+ },
+ [0x1F5B9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5B9,
+ },
+ [0x1F5BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5BA,
+ },
+ [0x1F5BB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5BB,
+ },
+ [0x1F5BC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5BC,
+ },
+ [0x1F5BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5BD,
+ },
+ [0x1F5BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5BE,
+ },
+ [0x1F5BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5BF,
+ },
+ [0x1F5C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C0,
+ },
+ [0x1F5C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C1,
+ },
+ [0x1F5C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C2,
+ },
+ [0x1F5C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C3,
+ },
+ [0x1F5C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C4,
+ },
+ [0x1F5C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C5,
+ },
+ [0x1F5C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C6,
+ },
+ [0x1F5C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C7,
+ },
+ [0x1F5C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C8,
+ },
+ [0x1F5C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5C9,
+ },
+ [0x1F5CA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5CA,
+ },
+ [0x1F5CB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5CB,
+ },
+ [0x1F5CC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5CC,
+ },
+ [0x1F5CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5CD,
+ },
+ [0x1F5CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5CE,
+ },
+ [0x1F5CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5CF,
+ },
+ [0x1F5D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5D0,
+ },
+ [0x1F5D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5D1,
+ },
+ [0x1F5D2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5D2,
+ },
+ [0x1F5D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5D3,
+ },
+ [0x1F5D4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5D4,
+ },
+ [0x1F5D5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5D5,
+ },
+ [0x1F5D6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5D6,
+ },
+ [0x1F5D7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5D7,
+ },
+ [0x1F5D8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5D8,
+ },
+ [0x1F5D9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5D9,
+ },
+ [0x1F5DA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5DA,
+ },
+ [0x1F5DB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5DB,
+ },
+ [0x1F5DC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5DC,
+ },
+ [0x1F5DD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5DD,
+ },
+ [0x1F5DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5DE,
+ },
+ [0x1F5DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5DF,
+ },
+ [0x1F5E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E0,
+ },
+ [0x1F5E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E1,
+ },
+ [0x1F5E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E2,
+ },
+ [0x1F5E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E3,
+ },
+ [0x1F5E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E4,
+ },
+ [0x1F5E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E5,
+ },
+ [0x1F5E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E6,
+ },
+ [0x1F5E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E7,
+ },
+ [0x1F5E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E8,
+ },
+ [0x1F5E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5E9,
+ },
+ [0x1F5EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5EA,
+ },
+ [0x1F5EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5EB,
+ },
+ [0x1F5EC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5EC,
+ },
+ [0x1F5ED]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5ED,
+ },
+ [0x1F5EE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5EE,
+ },
+ [0x1F5EF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5EF,
+ },
+ [0x1F5F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5F0,
+ },
+ [0x1F5F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5F1,
+ },
+ [0x1F5F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5F2,
+ },
+ [0x1F5F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5F3,
+ },
+ [0x1F5F4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5F4,
+ },
+ [0x1F5F5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5F5,
+ },
+ [0x1F5F6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5F6,
+ },
+ [0x1F5F7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5F7,
+ },
+ [0x1F5F8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5F8,
+ },
+ [0x1F5F9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F5F9,
+ },
+ [0x1F5FA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5FA,
+ },
+ [0x1F5FB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5FB,
+ },
+ [0x1F5FC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5FC,
+ },
+ [0x1F5FD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5FD,
+ },
+ [0x1F5FE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5FE,
+ },
+ [0x1F5FF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F5FF,
+ },
+ [0x1F600]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F600,
+ },
+ [0x1F601]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F601,
+ },
+ [0x1F602]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F602,
+ },
+ [0x1F603]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F603,
+ },
+ [0x1F604]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F604,
+ },
+ [0x1F605]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F605,
+ },
+ [0x1F606]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F606,
+ },
+ [0x1F607]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F607,
+ },
+ [0x1F608]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F608,
+ },
+ [0x1F609]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F609,
+ },
+ [0x1F60A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F60A,
+ },
+ [0x1F60B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F60B,
+ },
+ [0x1F60C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F60C,
+ },
+ [0x1F60D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F60D,
+ },
+ [0x1F60E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F60E,
+ },
+ [0x1F60F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F60F,
+ },
+ [0x1F610]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F610,
+ },
+ [0x1F611]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F611,
+ },
+ [0x1F612]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F612,
+ },
+ [0x1F613]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F613,
+ },
+ [0x1F614]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F614,
+ },
+ [0x1F615]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F615,
+ },
+ [0x1F616]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F616,
+ },
+ [0x1F617]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F617,
+ },
+ [0x1F618]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F618,
+ },
+ [0x1F619]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F619,
+ },
+ [0x1F61A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F61A,
+ },
+ [0x1F61B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F61B,
+ },
+ [0x1F61C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F61C,
+ },
+ [0x1F61D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F61D,
+ },
+ [0x1F61E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F61E,
+ },
+ [0x1F61F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F61F,
+ },
+ [0x1F620]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F620,
+ },
+ [0x1F621]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F621,
+ },
+ [0x1F622]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F622,
+ },
+ [0x1F623]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F623,
+ },
+ [0x1F624]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F624,
+ },
+ [0x1F625]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F625,
+ },
+ [0x1F626]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F626,
+ },
+ [0x1F627]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F627,
+ },
+ [0x1F628]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F628,
+ },
+ [0x1F629]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F629,
+ },
+ [0x1F62A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F62A,
+ },
+ [0x1F62B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F62B,
+ },
+ [0x1F62C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F62C,
+ },
+ [0x1F62D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F62D,
+ },
+ [0x1F62E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F62E,
+ },
+ [0x1F62F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F62F,
+ },
+ [0x1F630]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F630,
+ },
+ [0x1F631]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F631,
+ },
+ [0x1F632]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F632,
+ },
+ [0x1F633]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F633,
+ },
+ [0x1F634]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F634,
+ },
+ [0x1F635]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F635,
+ },
+ [0x1F636]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F636,
+ },
+ [0x1F637]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F637,
+ },
+ [0x1F638]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F638,
+ },
+ [0x1F639]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F639,
+ },
+ [0x1F63A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F63A,
+ },
+ [0x1F63B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F63B,
+ },
+ [0x1F63C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F63C,
+ },
+ [0x1F63D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F63D,
+ },
+ [0x1F63E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F63E,
+ },
+ [0x1F63F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F63F,
+ },
+ [0x1F640]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F640,
+ },
+ [0x1F641]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F641,
+ },
+ [0x1F642]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F642,
+ },
+ [0x1F643]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F643,
+ },
+ [0x1F644]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F644,
+ },
+ [0x1F645]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F645,
+ },
+ [0x1F646]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F646,
+ },
+ [0x1F647]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F647,
+ },
+ [0x1F648]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F648,
+ },
+ [0x1F649]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F649,
+ },
+ [0x1F64A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F64A,
+ },
+ [0x1F64B]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F64B,
+ },
+ [0x1F64C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F64C,
+ },
+ [0x1F64D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F64D,
+ },
+ [0x1F64E]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F64E,
+ },
+ [0x1F64F]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F64F,
+ },
+ [0x1F650]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F650,
+ },
+ [0x1F651]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F651,
+ },
+ [0x1F652]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F652,
+ },
+ [0x1F653]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F653,
+ },
+ [0x1F654]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F654,
+ },
+ [0x1F655]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F655,
+ },
+ [0x1F656]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F656,
+ },
+ [0x1F657]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F657,
+ },
+ [0x1F658]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F658,
+ },
+ [0x1F659]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F659,
+ },
+ [0x1F65A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F65A,
+ },
+ [0x1F65B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F65B,
+ },
+ [0x1F65C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F65C,
+ },
+ [0x1F65D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F65D,
+ },
+ [0x1F65E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F65E,
+ },
+ [0x1F65F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F65F,
+ },
+ [0x1F660]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F660,
+ },
+ [0x1F661]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F661,
+ },
+ [0x1F662]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F662,
+ },
+ [0x1F663]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F663,
+ },
+ [0x1F664]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F664,
+ },
+ [0x1F665]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F665,
+ },
+ [0x1F666]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F666,
+ },
+ [0x1F667]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F667,
+ },
+ [0x1F668]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F668,
+ },
+ [0x1F669]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F669,
+ },
+ [0x1F66A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F66A,
+ },
+ [0x1F66B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F66B,
+ },
+ [0x1F66C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F66C,
+ },
+ [0x1F66D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F66D,
+ },
+ [0x1F66E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F66E,
+ },
+ [0x1F66F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F66F,
+ },
+ [0x1F670]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F670,
+ },
+ [0x1F671]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F671,
+ },
+ [0x1F672]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F672,
+ },
+ [0x1F673]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F673,
+ },
+ [0x1F674]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F674,
+ },
+ [0x1F675]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F675,
+ },
+ [0x1F676]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x1F676,
+ },
+ [0x1F677]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x1F677,
+ },
+ [0x1F678]={
+ category="so",
+ direction="on",
+ linebreak="qu",
+ unicodeslot=0x1F678,
+ },
+ [0x1F679]={
+ category="so",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x1F679,
+ },
+ [0x1F67A]={
+ category="so",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x1F67A,
+ },
+ [0x1F67B]={
+ category="so",
+ direction="on",
+ linebreak="ns",
+ unicodeslot=0x1F67B,
+ },
+ [0x1F67C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F67C,
+ },
+ [0x1F67D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F67D,
+ },
+ [0x1F67E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F67E,
+ },
+ [0x1F67F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F67F,
+ },
+ [0x1F680]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F680,
+ },
+ [0x1F681]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F681,
+ },
+ [0x1F682]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F682,
+ },
+ [0x1F683]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F683,
+ },
+ [0x1F684]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F684,
+ },
+ [0x1F685]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F685,
+ },
+ [0x1F686]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F686,
+ },
+ [0x1F687]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F687,
+ },
+ [0x1F688]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F688,
+ },
+ [0x1F689]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F689,
+ },
+ [0x1F68A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F68A,
+ },
+ [0x1F68B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F68B,
+ },
+ [0x1F68C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F68C,
+ },
+ [0x1F68D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F68D,
+ },
+ [0x1F68E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F68E,
+ },
+ [0x1F68F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F68F,
+ },
+ [0x1F690]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F690,
+ },
+ [0x1F691]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F691,
+ },
+ [0x1F692]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F692,
+ },
+ [0x1F693]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F693,
+ },
+ [0x1F694]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F694,
+ },
+ [0x1F695]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F695,
+ },
+ [0x1F696]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F696,
+ },
+ [0x1F697]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F697,
+ },
+ [0x1F698]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F698,
+ },
+ [0x1F699]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F699,
+ },
+ [0x1F69A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F69A,
+ },
+ [0x1F69B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F69B,
+ },
+ [0x1F69C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F69C,
+ },
+ [0x1F69D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F69D,
+ },
+ [0x1F69E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F69E,
+ },
+ [0x1F69F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F69F,
+ },
+ [0x1F6A0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A0,
+ },
+ [0x1F6A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A1,
+ },
+ [0x1F6A2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A2,
+ },
+ [0x1F6A3]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F6A3,
+ },
+ [0x1F6A4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A4,
+ },
+ [0x1F6A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A5,
+ },
+ [0x1F6A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A6,
+ },
+ [0x1F6A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A7,
+ },
+ [0x1F6A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A8,
+ },
+ [0x1F6A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6A9,
+ },
+ [0x1F6AA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6AA,
+ },
+ [0x1F6AB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6AB,
+ },
+ [0x1F6AC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6AC,
+ },
+ [0x1F6AD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6AD,
+ },
+ [0x1F6AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6AE,
+ },
+ [0x1F6AF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6AF,
+ },
+ [0x1F6B0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B0,
+ },
+ [0x1F6B1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B1,
+ },
+ [0x1F6B2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B2,
+ },
+ [0x1F6B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B3,
+ },
+ [0x1F6B4]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F6B4,
+ },
+ [0x1F6B5]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F6B5,
+ },
+ [0x1F6B6]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F6B6,
+ },
+ [0x1F6B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B7,
+ },
+ [0x1F6B8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B8,
+ },
+ [0x1F6B9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6B9,
+ },
+ [0x1F6BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6BA,
+ },
+ [0x1F6BB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6BB,
+ },
+ [0x1F6BC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6BC,
+ },
+ [0x1F6BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6BD,
+ },
+ [0x1F6BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6BE,
+ },
+ [0x1F6BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6BF,
+ },
+ [0x1F6C0]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F6C0,
+ },
+ [0x1F6C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C1,
+ },
+ [0x1F6C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C2,
+ },
+ [0x1F6C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C3,
+ },
+ [0x1F6C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C4,
+ },
+ [0x1F6C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C5,
+ },
+ [0x1F6C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C6,
+ },
+ [0x1F6C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C7,
+ },
+ [0x1F6C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C8,
+ },
+ [0x1F6C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6C9,
+ },
+ [0x1F6CA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6CA,
+ },
+ [0x1F6CB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6CB,
+ },
+ [0x1F6CC]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F6CC,
+ },
+ [0x1F6CD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6CD,
+ },
+ [0x1F6CE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6CE,
+ },
+ [0x1F6CF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6CF,
+ },
+ [0x1F6D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6D0,
+ },
+ [0x1F6D1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6D1,
+ },
+ [0x1F6D2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6D2,
+ },
+ [0x1F6D3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6D3,
+ },
+ [0x1F6D4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6D4,
+ },
+ [0x1F6D5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6D5,
+ },
+ [0x1F6E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E0,
+ },
+ [0x1F6E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E1,
+ },
+ [0x1F6E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E2,
+ },
+ [0x1F6E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E3,
+ },
+ [0x1F6E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E4,
+ },
+ [0x1F6E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E5,
+ },
+ [0x1F6E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E6,
+ },
+ [0x1F6E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E7,
+ },
+ [0x1F6E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E8,
+ },
+ [0x1F6E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6E9,
+ },
+ [0x1F6EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6EA,
+ },
+ [0x1F6EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6EB,
+ },
+ [0x1F6EC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6EC,
+ },
+ [0x1F6F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F0,
+ },
+ [0x1F6F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F1,
+ },
+ [0x1F6F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F2,
+ },
+ [0x1F6F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F3,
+ },
+ [0x1F6F4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F4,
+ },
+ [0x1F6F5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F5,
+ },
+ [0x1F6F6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F6,
+ },
+ [0x1F6F7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F7,
+ },
+ [0x1F6F8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F8,
+ },
+ [0x1F6F9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6F9,
+ },
+ [0x1F6FA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F6FA,
+ },
+ [0x1F700]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F700,
+ },
+ [0x1F701]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F701,
+ },
+ [0x1F702]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F702,
+ },
+ [0x1F703]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F703,
+ },
+ [0x1F704]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F704,
+ },
+ [0x1F705]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F705,
+ },
+ [0x1F706]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F706,
+ },
+ [0x1F707]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F707,
+ },
+ [0x1F708]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F708,
+ },
+ [0x1F709]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F709,
+ },
+ [0x1F70A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F70A,
+ },
+ [0x1F70B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F70B,
+ },
+ [0x1F70C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F70C,
+ },
+ [0x1F70D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F70D,
+ },
+ [0x1F70E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F70E,
+ },
+ [0x1F70F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F70F,
+ },
+ [0x1F710]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F710,
+ },
+ [0x1F711]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F711,
+ },
+ [0x1F712]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F712,
+ },
+ [0x1F713]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F713,
+ },
+ [0x1F714]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F714,
+ },
+ [0x1F715]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F715,
+ },
+ [0x1F716]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F716,
+ },
+ [0x1F717]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F717,
+ },
+ [0x1F718]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F718,
+ },
+ [0x1F719]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F719,
+ },
+ [0x1F71A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F71A,
+ },
+ [0x1F71B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F71B,
+ },
+ [0x1F71C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F71C,
+ },
+ [0x1F71D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F71D,
+ },
+ [0x1F71E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F71E,
+ },
+ [0x1F71F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F71F,
+ },
+ [0x1F720]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F720,
+ },
+ [0x1F721]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F721,
+ },
+ [0x1F722]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F722,
+ },
+ [0x1F723]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F723,
+ },
+ [0x1F724]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F724,
+ },
+ [0x1F725]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F725,
+ },
+ [0x1F726]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F726,
+ },
+ [0x1F727]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F727,
+ },
+ [0x1F728]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F728,
+ },
+ [0x1F729]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F729,
+ },
+ [0x1F72A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F72A,
+ },
+ [0x1F72B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F72B,
+ },
+ [0x1F72C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F72C,
+ },
+ [0x1F72D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F72D,
+ },
+ [0x1F72E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F72E,
+ },
+ [0x1F72F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F72F,
+ },
+ [0x1F730]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F730,
+ },
+ [0x1F731]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F731,
+ },
+ [0x1F732]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F732,
+ },
+ [0x1F733]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F733,
+ },
+ [0x1F734]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F734,
+ },
+ [0x1F735]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F735,
+ },
+ [0x1F736]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F736,
+ },
+ [0x1F737]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F737,
+ },
+ [0x1F738]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F738,
+ },
+ [0x1F739]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F739,
+ },
+ [0x1F73A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F73A,
+ },
+ [0x1F73B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F73B,
+ },
+ [0x1F73C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F73C,
+ },
+ [0x1F73D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F73D,
+ },
+ [0x1F73E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F73E,
+ },
+ [0x1F73F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F73F,
+ },
+ [0x1F740]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F740,
+ },
+ [0x1F741]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F741,
+ },
+ [0x1F742]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F742,
+ },
+ [0x1F743]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F743,
+ },
+ [0x1F744]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F744,
+ },
+ [0x1F745]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F745,
+ },
+ [0x1F746]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F746,
+ },
+ [0x1F747]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F747,
+ },
+ [0x1F748]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F748,
+ },
+ [0x1F749]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F749,
+ },
+ [0x1F74A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F74A,
+ },
+ [0x1F74B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F74B,
+ },
+ [0x1F74C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F74C,
+ },
+ [0x1F74D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F74D,
+ },
+ [0x1F74E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F74E,
+ },
+ [0x1F74F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F74F,
+ },
+ [0x1F750]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F750,
+ },
+ [0x1F751]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F751,
+ },
+ [0x1F752]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F752,
+ },
+ [0x1F753]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F753,
+ },
+ [0x1F754]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F754,
+ },
+ [0x1F755]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F755,
+ },
+ [0x1F756]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F756,
+ },
+ [0x1F757]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F757,
+ },
+ [0x1F758]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F758,
+ },
+ [0x1F759]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F759,
+ },
+ [0x1F75A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F75A,
+ },
+ [0x1F75B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F75B,
+ },
+ [0x1F75C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F75C,
+ },
+ [0x1F75D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F75D,
+ },
+ [0x1F75E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F75E,
+ },
+ [0x1F75F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F75F,
+ },
+ [0x1F760]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F760,
+ },
+ [0x1F761]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F761,
+ },
+ [0x1F762]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F762,
+ },
+ [0x1F763]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F763,
+ },
+ [0x1F764]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F764,
+ },
+ [0x1F765]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F765,
+ },
+ [0x1F766]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F766,
+ },
+ [0x1F767]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F767,
+ },
+ [0x1F768]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F768,
+ },
+ [0x1F769]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F769,
+ },
+ [0x1F76A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F76A,
+ },
+ [0x1F76B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F76B,
+ },
+ [0x1F76C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F76C,
+ },
+ [0x1F76D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F76D,
+ },
+ [0x1F76E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F76E,
+ },
+ [0x1F76F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F76F,
+ },
+ [0x1F770]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F770,
+ },
+ [0x1F771]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F771,
+ },
+ [0x1F772]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F772,
+ },
+ [0x1F773]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F773,
+ },
+ [0x1F780]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F780,
+ },
+ [0x1F781]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F781,
+ },
+ [0x1F782]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F782,
+ },
+ [0x1F783]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F783,
+ },
+ [0x1F784]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F784,
+ },
+ [0x1F785]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F785,
+ },
+ [0x1F786]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F786,
+ },
+ [0x1F787]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F787,
+ },
+ [0x1F788]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F788,
+ },
+ [0x1F789]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F789,
+ },
+ [0x1F78A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F78A,
+ },
+ [0x1F78B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F78B,
+ },
+ [0x1F78C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F78C,
+ },
+ [0x1F78D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F78D,
+ },
+ [0x1F78E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F78E,
+ },
+ [0x1F78F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F78F,
+ },
+ [0x1F790]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F790,
+ },
+ [0x1F791]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F791,
+ },
+ [0x1F792]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F792,
+ },
+ [0x1F793]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F793,
+ },
+ [0x1F794]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F794,
+ },
+ [0x1F795]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F795,
+ },
+ [0x1F796]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F796,
+ },
+ [0x1F797]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F797,
+ },
+ [0x1F798]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F798,
+ },
+ [0x1F799]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F799,
+ },
+ [0x1F79A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F79A,
+ },
+ [0x1F79B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F79B,
+ },
+ [0x1F79C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F79C,
+ },
+ [0x1F79D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F79D,
+ },
+ [0x1F79E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F79E,
+ },
+ [0x1F79F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F79F,
+ },
+ [0x1F7A0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A0,
+ },
+ [0x1F7A1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A1,
+ },
+ [0x1F7A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A2,
+ },
+ [0x1F7A3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A3,
+ },
+ [0x1F7A4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A4,
+ },
+ [0x1F7A5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A5,
+ },
+ [0x1F7A6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A6,
+ },
+ [0x1F7A7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A7,
+ },
+ [0x1F7A8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A8,
+ },
+ [0x1F7A9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7A9,
+ },
+ [0x1F7AA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7AA,
+ },
+ [0x1F7AB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7AB,
+ },
+ [0x1F7AC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7AC,
+ },
+ [0x1F7AD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7AD,
+ },
+ [0x1F7AE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7AE,
+ },
+ [0x1F7AF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7AF,
+ },
+ [0x1F7B0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B0,
+ },
+ [0x1F7B1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B1,
+ },
+ [0x1F7B2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B2,
+ },
+ [0x1F7B3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B3,
+ },
+ [0x1F7B4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B4,
+ },
+ [0x1F7B5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B5,
+ },
+ [0x1F7B6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B6,
+ },
+ [0x1F7B7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B7,
+ },
+ [0x1F7B8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B8,
+ },
+ [0x1F7B9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7B9,
+ },
+ [0x1F7BA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7BA,
+ },
+ [0x1F7BB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7BB,
+ },
+ [0x1F7BC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7BC,
+ },
+ [0x1F7BD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7BD,
+ },
+ [0x1F7BE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7BE,
+ },
+ [0x1F7BF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7BF,
+ },
+ [0x1F7C0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C0,
+ },
+ [0x1F7C1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C1,
+ },
+ [0x1F7C2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C2,
+ },
+ [0x1F7C3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C3,
+ },
+ [0x1F7C4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C4,
+ },
+ [0x1F7C5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C5,
+ },
+ [0x1F7C6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C6,
+ },
+ [0x1F7C7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C7,
+ },
+ [0x1F7C8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C8,
+ },
+ [0x1F7C9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7C9,
+ },
+ [0x1F7CA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7CA,
+ },
+ [0x1F7CB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7CB,
+ },
+ [0x1F7CC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7CC,
+ },
+ [0x1F7CD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7CD,
+ },
+ [0x1F7CE]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7CE,
+ },
+ [0x1F7CF]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7CF,
+ },
+ [0x1F7D0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7D0,
+ },
+ [0x1F7D1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7D1,
+ },
+ [0x1F7D2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7D2,
+ },
+ [0x1F7D3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7D3,
+ },
+ [0x1F7D4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F7D4,
+ },
+ [0x1F7D5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7D5,
+ },
+ [0x1F7D6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7D6,
+ },
+ [0x1F7D7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7D7,
+ },
+ [0x1F7D8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7D8,
+ },
+ [0x1F7E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E0,
+ },
+ [0x1F7E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E1,
+ },
+ [0x1F7E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E2,
+ },
+ [0x1F7E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E3,
+ },
+ [0x1F7E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E4,
+ },
+ [0x1F7E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E5,
+ },
+ [0x1F7E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E6,
+ },
+ [0x1F7E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E7,
+ },
+ [0x1F7E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E8,
+ },
+ [0x1F7E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7E9,
+ },
+ [0x1F7EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7EA,
+ },
+ [0x1F7EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F7EB,
+ },
+ [0x1F800]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F800,
+ },
+ [0x1F801]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F801,
+ },
+ [0x1F802]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F802,
+ },
+ [0x1F803]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F803,
+ },
+ [0x1F804]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F804,
+ },
+ [0x1F805]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F805,
+ },
+ [0x1F806]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F806,
+ },
+ [0x1F807]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F807,
+ },
+ [0x1F808]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F808,
+ },
+ [0x1F809]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F809,
+ },
+ [0x1F80A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F80A,
+ },
+ [0x1F80B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F80B,
+ },
+ [0x1F810]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F810,
+ },
+ [0x1F811]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F811,
+ },
+ [0x1F812]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F812,
+ },
+ [0x1F813]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F813,
+ },
+ [0x1F814]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F814,
+ },
+ [0x1F815]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F815,
+ },
+ [0x1F816]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F816,
+ },
+ [0x1F817]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F817,
+ },
+ [0x1F818]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F818,
+ },
+ [0x1F819]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F819,
+ },
+ [0x1F81A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F81A,
+ },
+ [0x1F81B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F81B,
+ },
+ [0x1F81C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F81C,
+ },
+ [0x1F81D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F81D,
+ },
+ [0x1F81E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F81E,
+ },
+ [0x1F81F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F81F,
+ },
+ [0x1F820]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F820,
+ },
+ [0x1F821]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F821,
+ },
+ [0x1F822]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F822,
+ },
+ [0x1F823]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F823,
+ },
+ [0x1F824]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F824,
+ },
+ [0x1F825]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F825,
+ },
+ [0x1F826]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F826,
+ },
+ [0x1F827]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F827,
+ },
+ [0x1F828]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F828,
+ },
+ [0x1F829]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F829,
+ },
+ [0x1F82A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F82A,
+ },
+ [0x1F82B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F82B,
+ },
+ [0x1F82C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F82C,
+ },
+ [0x1F82D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F82D,
+ },
+ [0x1F82E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F82E,
+ },
+ [0x1F82F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F82F,
+ },
+ [0x1F830]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F830,
+ },
+ [0x1F831]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F831,
+ },
+ [0x1F832]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F832,
+ },
+ [0x1F833]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F833,
+ },
+ [0x1F834]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F834,
+ },
+ [0x1F835]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F835,
+ },
+ [0x1F836]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F836,
+ },
+ [0x1F837]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F837,
+ },
+ [0x1F838]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F838,
+ },
+ [0x1F839]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F839,
+ },
+ [0x1F83A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F83A,
+ },
+ [0x1F83B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F83B,
+ },
+ [0x1F83C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F83C,
+ },
+ [0x1F83D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F83D,
+ },
+ [0x1F83E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F83E,
+ },
+ [0x1F83F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F83F,
+ },
+ [0x1F840]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F840,
+ },
+ [0x1F841]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F841,
+ },
+ [0x1F842]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F842,
+ },
+ [0x1F843]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F843,
+ },
+ [0x1F844]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F844,
+ },
+ [0x1F845]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F845,
+ },
+ [0x1F846]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F846,
+ },
+ [0x1F847]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F847,
+ },
+ [0x1F850]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F850,
+ },
+ [0x1F851]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F851,
+ },
+ [0x1F852]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F852,
+ },
+ [0x1F853]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F853,
+ },
+ [0x1F854]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F854,
+ },
+ [0x1F855]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F855,
+ },
+ [0x1F856]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F856,
+ },
+ [0x1F857]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F857,
+ },
+ [0x1F858]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F858,
+ },
+ [0x1F859]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F859,
+ },
+ [0x1F860]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F860,
+ },
+ [0x1F861]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F861,
+ },
+ [0x1F862]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F862,
+ },
+ [0x1F863]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F863,
+ },
+ [0x1F864]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F864,
+ },
+ [0x1F865]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F865,
+ },
+ [0x1F866]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F866,
+ },
+ [0x1F867]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F867,
+ },
+ [0x1F868]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F868,
+ },
+ [0x1F869]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F869,
+ },
+ [0x1F86A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F86A,
+ },
+ [0x1F86B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F86B,
+ },
+ [0x1F86C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F86C,
+ },
+ [0x1F86D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F86D,
+ },
+ [0x1F86E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F86E,
+ },
+ [0x1F86F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F86F,
+ },
+ [0x1F870]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F870,
+ },
+ [0x1F871]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F871,
+ },
+ [0x1F872]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F872,
+ },
+ [0x1F873]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F873,
+ },
+ [0x1F874]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F874,
+ },
+ [0x1F875]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F875,
+ },
+ [0x1F876]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F876,
+ },
+ [0x1F877]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F877,
+ },
+ [0x1F878]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F878,
+ },
+ [0x1F879]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F879,
+ },
+ [0x1F87A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F87A,
+ },
+ [0x1F87B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F87B,
+ },
+ [0x1F87C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F87C,
+ },
+ [0x1F87D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F87D,
+ },
+ [0x1F87E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F87E,
+ },
+ [0x1F87F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F87F,
+ },
+ [0x1F880]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F880,
+ },
+ [0x1F881]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F881,
+ },
+ [0x1F882]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F882,
+ },
+ [0x1F883]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F883,
+ },
+ [0x1F884]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F884,
+ },
+ [0x1F885]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F885,
+ },
+ [0x1F886]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F886,
+ },
+ [0x1F887]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F887,
+ },
+ [0x1F890]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F890,
+ },
+ [0x1F891]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F891,
+ },
+ [0x1F892]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F892,
+ },
+ [0x1F893]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F893,
+ },
+ [0x1F894]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F894,
+ },
+ [0x1F895]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F895,
+ },
+ [0x1F896]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F896,
+ },
+ [0x1F897]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F897,
+ },
+ [0x1F898]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F898,
+ },
+ [0x1F899]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F899,
+ },
+ [0x1F89A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F89A,
+ },
+ [0x1F89B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F89B,
+ },
+ [0x1F89C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F89C,
+ },
+ [0x1F89D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F89D,
+ },
+ [0x1F89E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F89E,
+ },
+ [0x1F89F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F89F,
+ },
+ [0x1F8A0]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A0,
+ },
+ [0x1F8A1]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A1,
+ },
+ [0x1F8A2]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A2,
+ },
+ [0x1F8A3]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A3,
+ },
+ [0x1F8A4]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A4,
+ },
+ [0x1F8A5]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A5,
+ },
+ [0x1F8A6]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A6,
+ },
+ [0x1F8A7]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A7,
+ },
+ [0x1F8A8]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A8,
+ },
+ [0x1F8A9]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8A9,
+ },
+ [0x1F8AA]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8AA,
+ },
+ [0x1F8AB]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8AB,
+ },
+ [0x1F8AC]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8AC,
+ },
+ [0x1F8AD]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F8AD,
+ },
+ [0x1F900]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F900,
+ },
+ [0x1F901]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F901,
+ },
+ [0x1F902]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F902,
+ },
+ [0x1F903]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F903,
+ },
+ [0x1F904]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F904,
+ },
+ [0x1F905]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F905,
+ },
+ [0x1F906]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F906,
+ },
+ [0x1F907]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F907,
+ },
+ [0x1F908]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F908,
+ },
+ [0x1F909]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F909,
+ },
+ [0x1F90A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F90A,
+ },
+ [0x1F90B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1F90B,
+ },
+ [0x1F90D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F90D,
+ },
+ [0x1F90E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F90E,
+ },
+ [0x1F90F]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F90F,
+ },
+ [0x1F910]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F910,
+ },
+ [0x1F911]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F911,
+ },
+ [0x1F912]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F912,
+ },
+ [0x1F913]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F913,
+ },
+ [0x1F914]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F914,
+ },
+ [0x1F915]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F915,
+ },
+ [0x1F916]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F916,
+ },
+ [0x1F917]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F917,
+ },
+ [0x1F918]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F918,
+ },
+ [0x1F919]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F919,
+ },
+ [0x1F91A]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F91A,
+ },
+ [0x1F91B]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F91B,
+ },
+ [0x1F91C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F91C,
+ },
+ [0x1F91D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F91D,
+ },
+ [0x1F91E]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F91E,
+ },
+ [0x1F91F]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F91F,
+ },
+ [0x1F920]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F920,
+ },
+ [0x1F921]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F921,
+ },
+ [0x1F922]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F922,
+ },
+ [0x1F923]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F923,
+ },
+ [0x1F924]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F924,
+ },
+ [0x1F925]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F925,
+ },
+ [0x1F926]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F926,
+ },
+ [0x1F927]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F927,
+ },
+ [0x1F928]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F928,
+ },
+ [0x1F929]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F929,
+ },
+ [0x1F92A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F92A,
+ },
+ [0x1F92B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F92B,
+ },
+ [0x1F92C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F92C,
+ },
+ [0x1F92D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F92D,
+ },
+ [0x1F92E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F92E,
+ },
+ [0x1F92F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F92F,
+ },
+ [0x1F930]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F930,
+ },
+ [0x1F931]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F931,
+ },
+ [0x1F932]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F932,
+ },
+ [0x1F933]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F933,
+ },
+ [0x1F934]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F934,
+ },
+ [0x1F935]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F935,
+ },
+ [0x1F936]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F936,
+ },
+ [0x1F937]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F937,
+ },
+ [0x1F938]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F938,
+ },
+ [0x1F939]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F939,
+ },
+ [0x1F93A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F93A,
+ },
+ [0x1F93B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F93B,
+ },
+ [0x1F93C]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F93C,
+ },
+ [0x1F93D]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F93D,
+ },
+ [0x1F93E]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F93E,
+ },
+ [0x1F93F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F93F,
+ },
+ [0x1F940]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F940,
+ },
+ [0x1F941]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F941,
+ },
+ [0x1F942]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F942,
+ },
+ [0x1F943]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F943,
+ },
+ [0x1F944]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F944,
+ },
+ [0x1F945]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F945,
+ },
+ [0x1F946]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F946,
+ },
+ [0x1F947]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F947,
+ },
+ [0x1F948]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F948,
+ },
+ [0x1F949]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F949,
+ },
+ [0x1F94A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F94A,
+ },
+ [0x1F94B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F94B,
+ },
+ [0x1F94C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F94C,
+ },
+ [0x1F94D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F94D,
+ },
+ [0x1F94E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F94E,
+ },
+ [0x1F94F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F94F,
+ },
+ [0x1F950]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F950,
+ },
+ [0x1F951]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F951,
+ },
+ [0x1F952]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F952,
+ },
+ [0x1F953]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F953,
+ },
+ [0x1F954]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F954,
+ },
+ [0x1F955]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F955,
+ },
+ [0x1F956]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F956,
+ },
+ [0x1F957]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F957,
+ },
+ [0x1F958]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F958,
+ },
+ [0x1F959]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F959,
+ },
+ [0x1F95A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F95A,
+ },
+ [0x1F95B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F95B,
+ },
+ [0x1F95C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F95C,
+ },
+ [0x1F95D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F95D,
+ },
+ [0x1F95E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F95E,
+ },
+ [0x1F95F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F95F,
+ },
+ [0x1F960]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F960,
+ },
+ [0x1F961]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F961,
+ },
+ [0x1F962]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F962,
+ },
+ [0x1F963]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F963,
+ },
+ [0x1F964]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F964,
+ },
+ [0x1F965]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F965,
+ },
+ [0x1F966]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F966,
+ },
+ [0x1F967]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F967,
+ },
+ [0x1F968]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F968,
+ },
+ [0x1F969]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F969,
+ },
+ [0x1F96A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F96A,
+ },
+ [0x1F96B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F96B,
+ },
+ [0x1F96C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F96C,
+ },
+ [0x1F96D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F96D,
+ },
+ [0x1F96E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F96E,
+ },
+ [0x1F96F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F96F,
+ },
+ [0x1F970]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F970,
+ },
+ [0x1F971]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F971,
+ },
+ [0x1F973]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F973,
+ },
+ [0x1F974]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F974,
+ },
+ [0x1F975]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F975,
+ },
+ [0x1F976]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F976,
+ },
+ [0x1F97A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F97A,
+ },
+ [0x1F97B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F97B,
+ },
+ [0x1F97C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F97C,
+ },
+ [0x1F97D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F97D,
+ },
+ [0x1F97E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F97E,
+ },
+ [0x1F97F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F97F,
+ },
+ [0x1F980]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F980,
+ },
+ [0x1F981]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F981,
+ },
+ [0x1F982]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F982,
+ },
+ [0x1F983]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F983,
+ },
+ [0x1F984]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F984,
+ },
+ [0x1F985]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F985,
+ },
+ [0x1F986]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F986,
+ },
+ [0x1F987]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F987,
+ },
+ [0x1F988]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F988,
+ },
+ [0x1F989]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F989,
+ },
+ [0x1F98A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F98A,
+ },
+ [0x1F98B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F98B,
+ },
+ [0x1F98C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F98C,
+ },
+ [0x1F98D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F98D,
+ },
+ [0x1F98E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F98E,
+ },
+ [0x1F98F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F98F,
+ },
+ [0x1F990]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F990,
+ },
+ [0x1F991]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F991,
+ },
+ [0x1F992]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F992,
+ },
+ [0x1F993]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F993,
+ },
+ [0x1F994]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F994,
+ },
+ [0x1F995]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F995,
+ },
+ [0x1F996]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F996,
+ },
+ [0x1F997]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F997,
+ },
+ [0x1F998]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F998,
+ },
+ [0x1F999]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F999,
+ },
+ [0x1F99A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F99A,
+ },
+ [0x1F99B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F99B,
+ },
+ [0x1F99C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F99C,
+ },
+ [0x1F99D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F99D,
+ },
+ [0x1F99E]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F99E,
+ },
+ [0x1F99F]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F99F,
+ },
+ [0x1F9A0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A0,
+ },
+ [0x1F9A1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A1,
+ },
+ [0x1F9A2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A2,
+ },
+ [0x1F9A5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A5,
+ },
+ [0x1F9A6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A6,
+ },
+ [0x1F9A7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A7,
+ },
+ [0x1F9A8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A8,
+ },
+ [0x1F9A9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9A9,
+ },
+ [0x1F9AA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9AA,
+ },
+ [0x1F9AE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9AE,
+ },
+ [0x1F9AF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9AF,
+ },
+ [0x1F9B0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9B0,
+ },
+ [0x1F9B1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9B1,
+ },
+ [0x1F9B2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9B2,
+ },
+ [0x1F9B3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9B3,
+ },
+ [0x1F9B4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9B4,
+ },
+ [0x1F9B5]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9B5,
+ },
+ [0x1F9B6]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9B6,
+ },
+ [0x1F9B7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9B7,
+ },
+ [0x1F9B8]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9B8,
+ },
+ [0x1F9B9]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9B9,
+ },
+ [0x1F9BA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9BA,
+ },
+ [0x1F9BB]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9BB,
+ },
+ [0x1F9BC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9BC,
+ },
+ [0x1F9BD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9BD,
+ },
+ [0x1F9BE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9BE,
+ },
+ [0x1F9BF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9BF,
+ },
+ [0x1F9C0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C0,
+ },
+ [0x1F9C1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C1,
+ },
+ [0x1F9C2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C2,
+ },
+ [0x1F9C3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C3,
+ },
+ [0x1F9C4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C4,
+ },
+ [0x1F9C5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C5,
+ },
+ [0x1F9C6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C6,
+ },
+ [0x1F9C7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C7,
+ },
+ [0x1F9C8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C8,
+ },
+ [0x1F9C9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9C9,
+ },
+ [0x1F9CA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9CA,
+ },
+ [0x1F9CD]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9CD,
+ },
+ [0x1F9CE]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9CE,
+ },
+ [0x1F9CF]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9CF,
+ },
+ [0x1F9D0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9D0,
+ },
+ [0x1F9D1]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D1,
+ },
+ [0x1F9D2]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D2,
+ },
+ [0x1F9D3]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D3,
+ },
+ [0x1F9D4]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D4,
+ },
+ [0x1F9D5]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D5,
+ },
+ [0x1F9D6]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D6,
+ },
+ [0x1F9D7]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D7,
+ },
+ [0x1F9D8]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D8,
+ },
+ [0x1F9D9]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9D9,
+ },
+ [0x1F9DA]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9DA,
+ },
+ [0x1F9DB]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9DB,
+ },
+ [0x1F9DC]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9DC,
+ },
+ [0x1F9DD]={
+ category="so",
+ direction="on",
+ linebreak="eb",
+ unicodeslot=0x1F9DD,
+ },
+ [0x1F9DE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9DE,
+ },
+ [0x1F9DF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9DF,
+ },
+ [0x1F9E0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E0,
+ },
+ [0x1F9E1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E1,
+ },
+ [0x1F9E2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E2,
+ },
+ [0x1F9E3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E3,
+ },
+ [0x1F9E4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E4,
+ },
+ [0x1F9E5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E5,
+ },
+ [0x1F9E6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E6,
+ },
+ [0x1F9E7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E7,
+ },
+ [0x1F9E8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E8,
+ },
+ [0x1F9E9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9E9,
+ },
+ [0x1F9EA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9EA,
+ },
+ [0x1F9EB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9EB,
+ },
+ [0x1F9EC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9EC,
+ },
+ [0x1F9ED]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9ED,
+ },
+ [0x1F9EE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9EE,
+ },
+ [0x1F9EF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9EF,
+ },
+ [0x1F9F0]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F0,
+ },
+ [0x1F9F1]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F1,
+ },
+ [0x1F9F2]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F2,
+ },
+ [0x1F9F3]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F3,
+ },
+ [0x1F9F4]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F4,
+ },
+ [0x1F9F5]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F5,
+ },
+ [0x1F9F6]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F6,
+ },
+ [0x1F9F7]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F7,
+ },
+ [0x1F9F8]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F8,
+ },
+ [0x1F9F9]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9F9,
+ },
+ [0x1F9FA]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9FA,
+ },
+ [0x1F9FB]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9FB,
+ },
+ [0x1F9FC]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9FC,
+ },
+ [0x1F9FD]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9FD,
+ },
+ [0x1F9FE]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9FE,
+ },
+ [0x1F9FF]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1F9FF,
+ },
+ [0x1FA00]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA00,
+ },
+ [0x1FA01]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA01,
+ },
+ [0x1FA02]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA02,
+ },
+ [0x1FA03]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA03,
+ },
+ [0x1FA04]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA04,
+ },
+ [0x1FA05]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA05,
+ },
+ [0x1FA06]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA06,
+ },
+ [0x1FA07]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA07,
+ },
+ [0x1FA08]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA08,
+ },
+ [0x1FA09]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA09,
+ },
+ [0x1FA0A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA0A,
+ },
+ [0x1FA0B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA0B,
+ },
+ [0x1FA0C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA0C,
+ },
+ [0x1FA0D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA0D,
+ },
+ [0x1FA0E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA0E,
+ },
+ [0x1FA0F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA0F,
+ },
+ [0x1FA10]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA10,
+ },
+ [0x1FA11]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA11,
+ },
+ [0x1FA12]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA12,
+ },
+ [0x1FA13]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA13,
+ },
+ [0x1FA14]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA14,
+ },
+ [0x1FA15]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA15,
+ },
+ [0x1FA16]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA16,
+ },
+ [0x1FA17]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA17,
+ },
+ [0x1FA18]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA18,
+ },
+ [0x1FA19]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA19,
+ },
+ [0x1FA1A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA1A,
+ },
+ [0x1FA1B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA1B,
+ },
+ [0x1FA1C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA1C,
+ },
+ [0x1FA1D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA1D,
+ },
+ [0x1FA1E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA1E,
+ },
+ [0x1FA1F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA1F,
+ },
+ [0x1FA20]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA20,
+ },
+ [0x1FA21]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA21,
+ },
+ [0x1FA22]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA22,
+ },
+ [0x1FA23]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA23,
+ },
+ [0x1FA24]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA24,
+ },
+ [0x1FA25]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA25,
+ },
+ [0x1FA26]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA26,
+ },
+ [0x1FA27]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA27,
+ },
+ [0x1FA28]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA28,
+ },
+ [0x1FA29]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA29,
+ },
+ [0x1FA2A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA2A,
+ },
+ [0x1FA2B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA2B,
+ },
+ [0x1FA2C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA2C,
+ },
+ [0x1FA2D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA2D,
+ },
+ [0x1FA2E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA2E,
+ },
+ [0x1FA2F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA2F,
+ },
+ [0x1FA30]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA30,
+ },
+ [0x1FA31]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA31,
+ },
+ [0x1FA32]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA32,
+ },
+ [0x1FA33]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA33,
+ },
+ [0x1FA34]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA34,
+ },
+ [0x1FA35]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA35,
+ },
+ [0x1FA36]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA36,
+ },
+ [0x1FA37]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA37,
+ },
+ [0x1FA38]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA38,
+ },
+ [0x1FA39]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA39,
+ },
+ [0x1FA3A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA3A,
+ },
+ [0x1FA3B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA3B,
+ },
+ [0x1FA3C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA3C,
+ },
+ [0x1FA3D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA3D,
+ },
+ [0x1FA3E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA3E,
+ },
+ [0x1FA3F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA3F,
+ },
+ [0x1FA40]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA40,
+ },
+ [0x1FA41]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA41,
+ },
+ [0x1FA42]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA42,
+ },
+ [0x1FA43]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA43,
+ },
+ [0x1FA44]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA44,
+ },
+ [0x1FA45]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA45,
+ },
+ [0x1FA46]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA46,
+ },
+ [0x1FA47]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA47,
+ },
+ [0x1FA48]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA48,
+ },
+ [0x1FA49]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA49,
+ },
+ [0x1FA4A]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA4A,
+ },
+ [0x1FA4B]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA4B,
+ },
+ [0x1FA4C]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA4C,
+ },
+ [0x1FA4D]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA4D,
+ },
+ [0x1FA4E]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA4E,
+ },
+ [0x1FA4F]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA4F,
+ },
+ [0x1FA50]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA50,
+ },
+ [0x1FA51]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA51,
+ },
+ [0x1FA52]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA52,
+ },
+ [0x1FA53]={
+ category="so",
+ direction="on",
+ linebreak="al",
+ unicodeslot=0x1FA53,
+ },
+ [0x1FA60]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA60,
+ },
+ [0x1FA61]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA61,
+ },
+ [0x1FA62]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA62,
+ },
+ [0x1FA63]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA63,
+ },
+ [0x1FA64]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA64,
+ },
+ [0x1FA65]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA65,
+ },
+ [0x1FA66]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA66,
+ },
+ [0x1FA67]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA67,
+ },
+ [0x1FA68]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA68,
+ },
+ [0x1FA69]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA69,
+ },
+ [0x1FA6A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA6A,
+ },
+ [0x1FA6B]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA6B,
+ },
+ [0x1FA6C]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA6C,
+ },
+ [0x1FA6D]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA6D,
+ },
+ [0x1FA70]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA70,
+ },
+ [0x1FA71]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA71,
+ },
+ [0x1FA72]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA72,
+ },
+ [0x1FA73]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA73,
+ },
+ [0x1FA78]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA78,
+ },
+ [0x1FA79]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA79,
+ },
+ [0x1FA7A]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA7A,
+ },
+ [0x1FA80]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA80,
+ },
+ [0x1FA81]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA81,
+ },
+ [0x1FA82]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA82,
+ },
+ [0x1FA90]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA90,
+ },
+ [0x1FA91]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA91,
+ },
+ [0x1FA92]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA92,
+ },
+ [0x1FA93]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA93,
+ },
+ [0x1FA94]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA94,
+ },
+ [0x1FA95]={
+ category="so",
+ direction="on",
+ linebreak="id",
+ unicodeslot=0x1FA95,
+ },
+ [0x2F800]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E3D },
+ unicodeslot=0x2F800,
+ },
+ [0x2F801]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E38 },
+ unicodeslot=0x2F801,
+ },
+ [0x2F802]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4E41 },
+ unicodeslot=0x2F802,
+ },
+ [0x2F803]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x20122 },
+ unicodeslot=0x2F803,
+ },
+ [0x2F804]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4F60 },
+ unicodeslot=0x2F804,
+ },
+ [0x2F805]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4FAE },
+ unicodeslot=0x2F805,
+ },
+ [0x2F806]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4FBB },
+ unicodeslot=0x2F806,
+ },
+ [0x2F807]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5002 },
+ unicodeslot=0x2F807,
+ },
+ [0x2F808]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x507A },
+ unicodeslot=0x2F808,
+ },
+ [0x2F809]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5099 },
+ unicodeslot=0x2F809,
+ },
+ [0x2F80A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x50E7 },
+ unicodeslot=0x2F80A,
+ },
+ [0x2F80B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x50CF },
+ unicodeslot=0x2F80B,
+ },
+ [0x2F80C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x349E },
+ unicodeslot=0x2F80C,
+ },
+ [0x2F80D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2063A },
+ unicodeslot=0x2F80D,
+ },
+ [0x2F80E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x514D },
+ unicodeslot=0x2F80E,
+ },
+ [0x2F80F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5154 },
+ unicodeslot=0x2F80F,
+ },
+ [0x2F810]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5164 },
+ unicodeslot=0x2F810,
+ },
+ [0x2F811]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5177 },
+ unicodeslot=0x2F811,
+ },
+ [0x2F812]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2051C },
+ unicodeslot=0x2F812,
+ },
+ [0x2F813]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x34B9 },
+ unicodeslot=0x2F813,
+ },
+ [0x2F814]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5167 },
+ unicodeslot=0x2F814,
+ },
+ [0x2F815]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x518D },
+ unicodeslot=0x2F815,
+ },
+ [0x2F816]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2054B },
+ unicodeslot=0x2F816,
+ },
+ [0x2F817]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5197 },
+ unicodeslot=0x2F817,
+ },
+ [0x2F818]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51A4 },
+ unicodeslot=0x2F818,
+ },
+ [0x2F819]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4ECC },
+ unicodeslot=0x2F819,
+ },
+ [0x2F81A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51AC },
+ unicodeslot=0x2F81A,
+ },
+ [0x2F81B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51B5 },
+ unicodeslot=0x2F81B,
+ },
+ [0x2F81C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x291DF },
+ unicodeslot=0x2F81C,
+ },
+ [0x2F81D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x51F5 },
+ unicodeslot=0x2F81D,
+ },
+ [0x2F81E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5203 },
+ unicodeslot=0x2F81E,
+ },
+ [0x2F81F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x34DF },
+ unicodeslot=0x2F81F,
+ },
+ [0x2F820]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x523B },
+ unicodeslot=0x2F820,
+ },
+ [0x2F821]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5246 },
+ unicodeslot=0x2F821,
+ },
+ [0x2F822]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5272 },
+ unicodeslot=0x2F822,
+ },
+ [0x2F823]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5277 },
+ unicodeslot=0x2F823,
+ },
+ [0x2F824]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3515 },
+ unicodeslot=0x2F824,
+ },
+ [0x2F825]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52C7 },
+ unicodeslot=0x2F825,
+ },
+ [0x2F826]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52C9 },
+ unicodeslot=0x2F826,
+ },
+ [0x2F827]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52E4 },
+ unicodeslot=0x2F827,
+ },
+ [0x2F828]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52FA },
+ unicodeslot=0x2F828,
+ },
+ [0x2F829]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5305 },
+ unicodeslot=0x2F829,
+ },
+ [0x2F82A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5306 },
+ unicodeslot=0x2F82A,
+ },
+ [0x2F82B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5317 },
+ unicodeslot=0x2F82B,
+ },
+ [0x2F82C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5349 },
+ unicodeslot=0x2F82C,
+ },
+ [0x2F82D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5351 },
+ unicodeslot=0x2F82D,
+ },
+ [0x2F82E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x535A },
+ unicodeslot=0x2F82E,
+ },
+ [0x2F82F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5373 },
+ unicodeslot=0x2F82F,
+ },
+ [0x2F830]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x537D },
+ unicodeslot=0x2F830,
+ },
+ [0x2F831]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x537F },
+ unicodeslot=0x2F831,
+ },
+ [0x2F832]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x537F },
+ unicodeslot=0x2F832,
+ },
+ [0x2F833]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x537F },
+ unicodeslot=0x2F833,
+ },
+ [0x2F834]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x20A2C },
+ unicodeslot=0x2F834,
+ },
+ [0x2F835]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7070 },
+ unicodeslot=0x2F835,
+ },
+ [0x2F836]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x53CA },
+ unicodeslot=0x2F836,
+ },
+ [0x2F837]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x53DF },
+ unicodeslot=0x2F837,
+ },
+ [0x2F838]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x20B63 },
+ unicodeslot=0x2F838,
+ },
+ [0x2F839]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x53EB },
+ unicodeslot=0x2F839,
+ },
+ [0x2F83A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x53F1 },
+ unicodeslot=0x2F83A,
+ },
+ [0x2F83B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5406 },
+ unicodeslot=0x2F83B,
+ },
+ [0x2F83C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x549E },
+ unicodeslot=0x2F83C,
+ },
+ [0x2F83D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5438 },
+ unicodeslot=0x2F83D,
+ },
+ [0x2F83E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5448 },
+ unicodeslot=0x2F83E,
+ },
+ [0x2F83F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5468 },
+ unicodeslot=0x2F83F,
+ },
+ [0x2F840]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x54A2 },
+ unicodeslot=0x2F840,
+ },
+ [0x2F841]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x54F6 },
+ unicodeslot=0x2F841,
+ },
+ [0x2F842]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5510 },
+ unicodeslot=0x2F842,
+ },
+ [0x2F843]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5553 },
+ unicodeslot=0x2F843,
+ },
+ [0x2F844]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5563 },
+ unicodeslot=0x2F844,
+ },
+ [0x2F845]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5584 },
+ unicodeslot=0x2F845,
+ },
+ [0x2F846]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5584 },
+ unicodeslot=0x2F846,
+ },
+ [0x2F847]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5599 },
+ unicodeslot=0x2F847,
+ },
+ [0x2F848]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x55AB },
+ unicodeslot=0x2F848,
+ },
+ [0x2F849]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x55B3 },
+ unicodeslot=0x2F849,
+ },
+ [0x2F84A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x55C2 },
+ unicodeslot=0x2F84A,
+ },
+ [0x2F84B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5716 },
+ unicodeslot=0x2F84B,
+ },
+ [0x2F84C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5606 },
+ unicodeslot=0x2F84C,
+ },
+ [0x2F84D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5717 },
+ unicodeslot=0x2F84D,
+ },
+ [0x2F84E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5651 },
+ unicodeslot=0x2F84E,
+ },
+ [0x2F84F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5674 },
+ unicodeslot=0x2F84F,
+ },
+ [0x2F850]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5207 },
+ unicodeslot=0x2F850,
+ },
+ [0x2F851]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58EE },
+ unicodeslot=0x2F851,
+ },
+ [0x2F852]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x57CE },
+ unicodeslot=0x2F852,
+ },
+ [0x2F853]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x57F4 },
+ unicodeslot=0x2F853,
+ },
+ [0x2F854]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x580D },
+ unicodeslot=0x2F854,
+ },
+ [0x2F855]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x578B },
+ unicodeslot=0x2F855,
+ },
+ [0x2F856]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5832 },
+ unicodeslot=0x2F856,
+ },
+ [0x2F857]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5831 },
+ unicodeslot=0x2F857,
+ },
+ [0x2F858]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58AC },
+ unicodeslot=0x2F858,
+ },
+ [0x2F859]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x214E4 },
+ unicodeslot=0x2F859,
+ },
+ [0x2F85A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58F2 },
+ unicodeslot=0x2F85A,
+ },
+ [0x2F85B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x58F7 },
+ unicodeslot=0x2F85B,
+ },
+ [0x2F85C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5906 },
+ unicodeslot=0x2F85C,
+ },
+ [0x2F85D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x591A },
+ unicodeslot=0x2F85D,
+ },
+ [0x2F85E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5922 },
+ unicodeslot=0x2F85E,
+ },
+ [0x2F85F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5962 },
+ unicodeslot=0x2F85F,
+ },
+ [0x2F860]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x216A8 },
+ unicodeslot=0x2F860,
+ },
+ [0x2F861]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x216EA },
+ unicodeslot=0x2F861,
+ },
+ [0x2F862]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x59EC },
+ unicodeslot=0x2F862,
+ },
+ [0x2F863]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5A1B },
+ unicodeslot=0x2F863,
+ },
+ [0x2F864]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5A27 },
+ unicodeslot=0x2F864,
+ },
+ [0x2F865]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x59D8 },
+ unicodeslot=0x2F865,
+ },
+ [0x2F866]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5A66 },
+ unicodeslot=0x2F866,
+ },
+ [0x2F867]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x36EE },
+ unicodeslot=0x2F867,
+ },
+ [0x2F868]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x36FC },
+ unicodeslot=0x2F868,
+ },
+ [0x2F869]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5B08 },
+ unicodeslot=0x2F869,
+ },
+ [0x2F86A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5B3E },
+ unicodeslot=0x2F86A,
+ },
+ [0x2F86B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5B3E },
+ unicodeslot=0x2F86B,
+ },
+ [0x2F86C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x219C8 },
+ unicodeslot=0x2F86C,
+ },
+ [0x2F86D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BC3 },
+ unicodeslot=0x2F86D,
+ },
+ [0x2F86E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BD8 },
+ unicodeslot=0x2F86E,
+ },
+ [0x2F86F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BE7 },
+ unicodeslot=0x2F86F,
+ },
+ [0x2F870]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BF3 },
+ unicodeslot=0x2F870,
+ },
+ [0x2F871]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x21B18 },
+ unicodeslot=0x2F871,
+ },
+ [0x2F872]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5BFF },
+ unicodeslot=0x2F872,
+ },
+ [0x2F873]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C06 },
+ unicodeslot=0x2F873,
+ },
+ [0x2F874]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F53 },
+ unicodeslot=0x2F874,
+ },
+ [0x2F875]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C22 },
+ unicodeslot=0x2F875,
+ },
+ [0x2F876]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3781 },
+ unicodeslot=0x2F876,
+ },
+ [0x2F877]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C60 },
+ unicodeslot=0x2F877,
+ },
+ [0x2F878]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C6E },
+ unicodeslot=0x2F878,
+ },
+ [0x2F879]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5CC0 },
+ unicodeslot=0x2F879,
+ },
+ [0x2F87A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5C8D },
+ unicodeslot=0x2F87A,
+ },
+ [0x2F87B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x21DE4 },
+ unicodeslot=0x2F87B,
+ },
+ [0x2F87C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5D43 },
+ unicodeslot=0x2F87C,
+ },
+ [0x2F87D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x21DE6 },
+ unicodeslot=0x2F87D,
+ },
+ [0x2F87E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5D6E },
+ unicodeslot=0x2F87E,
+ },
+ [0x2F87F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5D6B },
+ unicodeslot=0x2F87F,
+ },
+ [0x2F880]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5D7C },
+ unicodeslot=0x2F880,
+ },
+ [0x2F881]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5DE1 },
+ unicodeslot=0x2F881,
+ },
+ [0x2F882]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5DE2 },
+ unicodeslot=0x2F882,
+ },
+ [0x2F883]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x382F },
+ unicodeslot=0x2F883,
+ },
+ [0x2F884]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5DFD },
+ unicodeslot=0x2F884,
+ },
+ [0x2F885]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5E28 },
+ unicodeslot=0x2F885,
+ },
+ [0x2F886]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5E3D },
+ unicodeslot=0x2F886,
+ },
+ [0x2F887]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5E69 },
+ unicodeslot=0x2F887,
+ },
+ [0x2F888]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3862 },
+ unicodeslot=0x2F888,
+ },
+ [0x2F889]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x22183 },
+ unicodeslot=0x2F889,
+ },
+ [0x2F88A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x387C },
+ unicodeslot=0x2F88A,
+ },
+ [0x2F88B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EB0 },
+ unicodeslot=0x2F88B,
+ },
+ [0x2F88C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EB3 },
+ unicodeslot=0x2F88C,
+ },
+ [0x2F88D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EB6 },
+ unicodeslot=0x2F88D,
+ },
+ [0x2F88E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5ECA },
+ unicodeslot=0x2F88E,
+ },
+ [0x2F88F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2A392 },
+ unicodeslot=0x2F88F,
+ },
+ [0x2F890]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5EFE },
+ unicodeslot=0x2F890,
+ },
+ [0x2F891]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x22331 },
+ unicodeslot=0x2F891,
+ },
+ [0x2F892]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x22331 },
+ unicodeslot=0x2F892,
+ },
+ [0x2F893]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8201 },
+ unicodeslot=0x2F893,
+ },
+ [0x2F894]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F22 },
+ unicodeslot=0x2F894,
+ },
+ [0x2F895]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F22 },
+ unicodeslot=0x2F895,
+ },
+ [0x2F896]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x38C7 },
+ unicodeslot=0x2F896,
+ },
+ [0x2F897]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x232B8 },
+ unicodeslot=0x2F897,
+ },
+ [0x2F898]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x261DA },
+ unicodeslot=0x2F898,
+ },
+ [0x2F899]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F62 },
+ unicodeslot=0x2F899,
+ },
+ [0x2F89A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F6B },
+ unicodeslot=0x2F89A,
+ },
+ [0x2F89B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x38E3 },
+ unicodeslot=0x2F89B,
+ },
+ [0x2F89C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5F9A },
+ unicodeslot=0x2F89C,
+ },
+ [0x2F89D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5FCD },
+ unicodeslot=0x2F89D,
+ },
+ [0x2F89E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5FD7 },
+ unicodeslot=0x2F89E,
+ },
+ [0x2F89F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5FF9 },
+ unicodeslot=0x2F89F,
+ },
+ [0x2F8A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6081 },
+ unicodeslot=0x2F8A0,
+ },
+ [0x2F8A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x393A },
+ unicodeslot=0x2F8A1,
+ },
+ [0x2F8A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x391C },
+ unicodeslot=0x2F8A2,
+ },
+ [0x2F8A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6094 },
+ unicodeslot=0x2F8A3,
+ },
+ [0x2F8A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x226D4 },
+ unicodeslot=0x2F8A4,
+ },
+ [0x2F8A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x60C7 },
+ unicodeslot=0x2F8A5,
+ },
+ [0x2F8A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6148 },
+ unicodeslot=0x2F8A6,
+ },
+ [0x2F8A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x614C },
+ unicodeslot=0x2F8A7,
+ },
+ [0x2F8A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x614E },
+ unicodeslot=0x2F8A8,
+ },
+ [0x2F8A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x614C },
+ unicodeslot=0x2F8A9,
+ },
+ [0x2F8AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x617A },
+ unicodeslot=0x2F8AA,
+ },
+ [0x2F8AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x618E },
+ unicodeslot=0x2F8AB,
+ },
+ [0x2F8AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61B2 },
+ unicodeslot=0x2F8AC,
+ },
+ [0x2F8AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61A4 },
+ unicodeslot=0x2F8AD,
+ },
+ [0x2F8AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61AF },
+ unicodeslot=0x2F8AE,
+ },
+ [0x2F8AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61DE },
+ unicodeslot=0x2F8AF,
+ },
+ [0x2F8B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61F2 },
+ unicodeslot=0x2F8B0,
+ },
+ [0x2F8B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x61F6 },
+ unicodeslot=0x2F8B1,
+ },
+ [0x2F8B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6210 },
+ unicodeslot=0x2F8B2,
+ },
+ [0x2F8B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x621B },
+ unicodeslot=0x2F8B3,
+ },
+ [0x2F8B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x625D },
+ unicodeslot=0x2F8B4,
+ },
+ [0x2F8B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62B1 },
+ unicodeslot=0x2F8B5,
+ },
+ [0x2F8B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62D4 },
+ unicodeslot=0x2F8B6,
+ },
+ [0x2F8B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6350 },
+ unicodeslot=0x2F8B7,
+ },
+ [0x2F8B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x22B0C },
+ unicodeslot=0x2F8B8,
+ },
+ [0x2F8B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x633D },
+ unicodeslot=0x2F8B9,
+ },
+ [0x2F8BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x62FC },
+ unicodeslot=0x2F8BA,
+ },
+ [0x2F8BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6368 },
+ unicodeslot=0x2F8BB,
+ },
+ [0x2F8BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6383 },
+ unicodeslot=0x2F8BC,
+ },
+ [0x2F8BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x63E4 },
+ unicodeslot=0x2F8BD,
+ },
+ [0x2F8BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x22BF1 },
+ unicodeslot=0x2F8BE,
+ },
+ [0x2F8BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6422 },
+ unicodeslot=0x2F8BF,
+ },
+ [0x2F8C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x63C5 },
+ unicodeslot=0x2F8C0,
+ },
+ [0x2F8C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x63A9 },
+ unicodeslot=0x2F8C1,
+ },
+ [0x2F8C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3A2E },
+ unicodeslot=0x2F8C2,
+ },
+ [0x2F8C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6469 },
+ unicodeslot=0x2F8C3,
+ },
+ [0x2F8C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x647E },
+ unicodeslot=0x2F8C4,
+ },
+ [0x2F8C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x649D },
+ unicodeslot=0x2F8C5,
+ },
+ [0x2F8C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6477 },
+ unicodeslot=0x2F8C6,
+ },
+ [0x2F8C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3A6C },
+ unicodeslot=0x2F8C7,
+ },
+ [0x2F8C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x654F },
+ unicodeslot=0x2F8C8,
+ },
+ [0x2F8C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x656C },
+ unicodeslot=0x2F8C9,
+ },
+ [0x2F8CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2300A },
+ unicodeslot=0x2F8CA,
+ },
+ [0x2F8CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x65E3 },
+ unicodeslot=0x2F8CB,
+ },
+ [0x2F8CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x66F8 },
+ unicodeslot=0x2F8CC,
+ },
+ [0x2F8CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6649 },
+ unicodeslot=0x2F8CD,
+ },
+ [0x2F8CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3B19 },
+ unicodeslot=0x2F8CE,
+ },
+ [0x2F8CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6691 },
+ unicodeslot=0x2F8CF,
+ },
+ [0x2F8D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3B08 },
+ unicodeslot=0x2F8D0,
+ },
+ [0x2F8D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3AE4 },
+ unicodeslot=0x2F8D1,
+ },
+ [0x2F8D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5192 },
+ unicodeslot=0x2F8D2,
+ },
+ [0x2F8D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5195 },
+ unicodeslot=0x2F8D3,
+ },
+ [0x2F8D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6700 },
+ unicodeslot=0x2F8D4,
+ },
+ [0x2F8D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x669C },
+ unicodeslot=0x2F8D5,
+ },
+ [0x2F8D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x80AD },
+ unicodeslot=0x2F8D6,
+ },
+ [0x2F8D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x43D9 },
+ unicodeslot=0x2F8D7,
+ },
+ [0x2F8D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6717 },
+ unicodeslot=0x2F8D8,
+ },
+ [0x2F8D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x671B },
+ unicodeslot=0x2F8D9,
+ },
+ [0x2F8DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6721 },
+ unicodeslot=0x2F8DA,
+ },
+ [0x2F8DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x675E },
+ unicodeslot=0x2F8DB,
+ },
+ [0x2F8DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6753 },
+ unicodeslot=0x2F8DC,
+ },
+ [0x2F8DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x233C3 },
+ unicodeslot=0x2F8DD,
+ },
+ [0x2F8DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3B49 },
+ unicodeslot=0x2F8DE,
+ },
+ [0x2F8DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x67FA },
+ unicodeslot=0x2F8DF,
+ },
+ [0x2F8E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6785 },
+ unicodeslot=0x2F8E0,
+ },
+ [0x2F8E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6852 },
+ unicodeslot=0x2F8E1,
+ },
+ [0x2F8E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6885 },
+ unicodeslot=0x2F8E2,
+ },
+ [0x2F8E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2346D },
+ unicodeslot=0x2F8E3,
+ },
+ [0x2F8E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x688E },
+ unicodeslot=0x2F8E4,
+ },
+ [0x2F8E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x681F },
+ unicodeslot=0x2F8E5,
+ },
+ [0x2F8E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6914 },
+ unicodeslot=0x2F8E6,
+ },
+ [0x2F8E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3B9D },
+ unicodeslot=0x2F8E7,
+ },
+ [0x2F8E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6942 },
+ unicodeslot=0x2F8E8,
+ },
+ [0x2F8E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x69A3 },
+ unicodeslot=0x2F8E9,
+ },
+ [0x2F8EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x69EA },
+ unicodeslot=0x2F8EA,
+ },
+ [0x2F8EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6AA8 },
+ unicodeslot=0x2F8EB,
+ },
+ [0x2F8EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x236A3 },
+ unicodeslot=0x2F8EC,
+ },
+ [0x2F8ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6ADB },
+ unicodeslot=0x2F8ED,
+ },
+ [0x2F8EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3C18 },
+ unicodeslot=0x2F8EE,
+ },
+ [0x2F8EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B21 },
+ unicodeslot=0x2F8EF,
+ },
+ [0x2F8F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x238A7 },
+ unicodeslot=0x2F8F0,
+ },
+ [0x2F8F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B54 },
+ unicodeslot=0x2F8F1,
+ },
+ [0x2F8F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3C4E },
+ unicodeslot=0x2F8F2,
+ },
+ [0x2F8F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B72 },
+ unicodeslot=0x2F8F3,
+ },
+ [0x2F8F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6B9F },
+ unicodeslot=0x2F8F4,
+ },
+ [0x2F8F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6BBA },
+ unicodeslot=0x2F8F5,
+ },
+ [0x2F8F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6BBB },
+ unicodeslot=0x2F8F6,
+ },
+ [0x2F8F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23A8D },
+ unicodeslot=0x2F8F7,
+ },
+ [0x2F8F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x21D0B },
+ unicodeslot=0x2F8F8,
+ },
+ [0x2F8F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23AFA },
+ unicodeslot=0x2F8F9,
+ },
+ [0x2F8FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6C4E },
+ unicodeslot=0x2F8FA,
+ },
+ [0x2F8FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23CBC },
+ unicodeslot=0x2F8FB,
+ },
+ [0x2F8FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6CBF },
+ unicodeslot=0x2F8FC,
+ },
+ [0x2F8FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6CCD },
+ unicodeslot=0x2F8FD,
+ },
+ [0x2F8FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6C67 },
+ unicodeslot=0x2F8FE,
+ },
+ [0x2F8FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D16 },
+ unicodeslot=0x2F8FF,
+ },
+ [0x2F900]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D3E },
+ unicodeslot=0x2F900,
+ },
+ [0x2F901]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D77 },
+ unicodeslot=0x2F901,
+ },
+ [0x2F902]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D41 },
+ unicodeslot=0x2F902,
+ },
+ [0x2F903]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D69 },
+ unicodeslot=0x2F903,
+ },
+ [0x2F904]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D78 },
+ unicodeslot=0x2F904,
+ },
+ [0x2F905]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D85 },
+ unicodeslot=0x2F905,
+ },
+ [0x2F906]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23D1E },
+ unicodeslot=0x2F906,
+ },
+ [0x2F907]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6D34 },
+ unicodeslot=0x2F907,
+ },
+ [0x2F908]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6E2F },
+ unicodeslot=0x2F908,
+ },
+ [0x2F909]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6E6E },
+ unicodeslot=0x2F909,
+ },
+ [0x2F90A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3D33 },
+ unicodeslot=0x2F90A,
+ },
+ [0x2F90B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6ECB },
+ unicodeslot=0x2F90B,
+ },
+ [0x2F90C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6EC7 },
+ unicodeslot=0x2F90C,
+ },
+ [0x2F90D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23ED1 },
+ unicodeslot=0x2F90D,
+ },
+ [0x2F90E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6DF9 },
+ unicodeslot=0x2F90E,
+ },
+ [0x2F90F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6F6E },
+ unicodeslot=0x2F90F,
+ },
+ [0x2F910]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23F5E },
+ unicodeslot=0x2F910,
+ },
+ [0x2F911]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23F8E },
+ unicodeslot=0x2F911,
+ },
+ [0x2F912]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x6FC6 },
+ unicodeslot=0x2F912,
+ },
+ [0x2F913]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7039 },
+ unicodeslot=0x2F913,
+ },
+ [0x2F914]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x701E },
+ unicodeslot=0x2F914,
+ },
+ [0x2F915]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x701B },
+ unicodeslot=0x2F915,
+ },
+ [0x2F916]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3D96 },
+ unicodeslot=0x2F916,
+ },
+ [0x2F917]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x704A },
+ unicodeslot=0x2F917,
+ },
+ [0x2F918]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x707D },
+ unicodeslot=0x2F918,
+ },
+ [0x2F919]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7077 },
+ unicodeslot=0x2F919,
+ },
+ [0x2F91A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x70AD },
+ unicodeslot=0x2F91A,
+ },
+ [0x2F91B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x20525 },
+ unicodeslot=0x2F91B,
+ },
+ [0x2F91C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7145 },
+ unicodeslot=0x2F91C,
+ },
+ [0x2F91D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24263 },
+ unicodeslot=0x2F91D,
+ },
+ [0x2F91E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x719C },
+ unicodeslot=0x2F91E,
+ },
+ [0x2F91F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x243AB },
+ unicodeslot=0x2F91F,
+ },
+ [0x2F920]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7228 },
+ unicodeslot=0x2F920,
+ },
+ [0x2F921]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7235 },
+ unicodeslot=0x2F921,
+ },
+ [0x2F922]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7250 },
+ unicodeslot=0x2F922,
+ },
+ [0x2F923]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24608 },
+ unicodeslot=0x2F923,
+ },
+ [0x2F924]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7280 },
+ unicodeslot=0x2F924,
+ },
+ [0x2F925]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7295 },
+ unicodeslot=0x2F925,
+ },
+ [0x2F926]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24735 },
+ unicodeslot=0x2F926,
+ },
+ [0x2F927]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24814 },
+ unicodeslot=0x2F927,
+ },
+ [0x2F928]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x737A },
+ unicodeslot=0x2F928,
+ },
+ [0x2F929]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x738B },
+ unicodeslot=0x2F929,
+ },
+ [0x2F92A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3EAC },
+ unicodeslot=0x2F92A,
+ },
+ [0x2F92B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x73A5 },
+ unicodeslot=0x2F92B,
+ },
+ [0x2F92C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3EB8 },
+ unicodeslot=0x2F92C,
+ },
+ [0x2F92D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3EB8 },
+ unicodeslot=0x2F92D,
+ },
+ [0x2F92E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7447 },
+ unicodeslot=0x2F92E,
+ },
+ [0x2F92F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x745C },
+ unicodeslot=0x2F92F,
+ },
+ [0x2F930]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7471 },
+ unicodeslot=0x2F930,
+ },
+ [0x2F931]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7485 },
+ unicodeslot=0x2F931,
+ },
+ [0x2F932]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x74CA },
+ unicodeslot=0x2F932,
+ },
+ [0x2F933]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3F1B },
+ unicodeslot=0x2F933,
+ },
+ [0x2F934]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7524 },
+ unicodeslot=0x2F934,
+ },
+ [0x2F935]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24C36 },
+ unicodeslot=0x2F935,
+ },
+ [0x2F936]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x753E },
+ unicodeslot=0x2F936,
+ },
+ [0x2F937]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24C92 },
+ unicodeslot=0x2F937,
+ },
+ [0x2F938]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7570 },
+ unicodeslot=0x2F938,
+ },
+ [0x2F939]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2219F },
+ unicodeslot=0x2F939,
+ },
+ [0x2F93A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7610 },
+ unicodeslot=0x2F93A,
+ },
+ [0x2F93B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24FA1 },
+ unicodeslot=0x2F93B,
+ },
+ [0x2F93C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x24FB8 },
+ unicodeslot=0x2F93C,
+ },
+ [0x2F93D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25044 },
+ unicodeslot=0x2F93D,
+ },
+ [0x2F93E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x3FFC },
+ unicodeslot=0x2F93E,
+ },
+ [0x2F93F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4008 },
+ unicodeslot=0x2F93F,
+ },
+ [0x2F940]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x76F4 },
+ unicodeslot=0x2F940,
+ },
+ [0x2F941]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x250F3 },
+ unicodeslot=0x2F941,
+ },
+ [0x2F942]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x250F2 },
+ unicodeslot=0x2F942,
+ },
+ [0x2F943]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25119 },
+ unicodeslot=0x2F943,
+ },
+ [0x2F944]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25133 },
+ unicodeslot=0x2F944,
+ },
+ [0x2F945]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x771E },
+ unicodeslot=0x2F945,
+ },
+ [0x2F946]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x771F },
+ unicodeslot=0x2F946,
+ },
+ [0x2F947]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x771F },
+ unicodeslot=0x2F947,
+ },
+ [0x2F948]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x774A },
+ unicodeslot=0x2F948,
+ },
+ [0x2F949]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4039 },
+ unicodeslot=0x2F949,
+ },
+ [0x2F94A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x778B },
+ unicodeslot=0x2F94A,
+ },
+ [0x2F94B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4046 },
+ unicodeslot=0x2F94B,
+ },
+ [0x2F94C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4096 },
+ unicodeslot=0x2F94C,
+ },
+ [0x2F94D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2541D },
+ unicodeslot=0x2F94D,
+ },
+ [0x2F94E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x784E },
+ unicodeslot=0x2F94E,
+ },
+ [0x2F94F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x788C },
+ unicodeslot=0x2F94F,
+ },
+ [0x2F950]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x78CC },
+ unicodeslot=0x2F950,
+ },
+ [0x2F951]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x40E3 },
+ unicodeslot=0x2F951,
+ },
+ [0x2F952]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25626 },
+ unicodeslot=0x2F952,
+ },
+ [0x2F953]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7956 },
+ unicodeslot=0x2F953,
+ },
+ [0x2F954]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2569A },
+ unicodeslot=0x2F954,
+ },
+ [0x2F955]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x256C5 },
+ unicodeslot=0x2F955,
+ },
+ [0x2F956]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x798F },
+ unicodeslot=0x2F956,
+ },
+ [0x2F957]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x79EB },
+ unicodeslot=0x2F957,
+ },
+ [0x2F958]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x412F },
+ unicodeslot=0x2F958,
+ },
+ [0x2F959]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7A40 },
+ unicodeslot=0x2F959,
+ },
+ [0x2F95A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7A4A },
+ unicodeslot=0x2F95A,
+ },
+ [0x2F95B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7A4F },
+ unicodeslot=0x2F95B,
+ },
+ [0x2F95C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2597C },
+ unicodeslot=0x2F95C,
+ },
+ [0x2F95D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25AA7 },
+ unicodeslot=0x2F95D,
+ },
+ [0x2F95E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25AA7 },
+ unicodeslot=0x2F95E,
+ },
+ [0x2F95F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7AEE },
+ unicodeslot=0x2F95F,
+ },
+ [0x2F960]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4202 },
+ unicodeslot=0x2F960,
+ },
+ [0x2F961]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25BAB },
+ unicodeslot=0x2F961,
+ },
+ [0x2F962]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7BC6 },
+ unicodeslot=0x2F962,
+ },
+ [0x2F963]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7BC9 },
+ unicodeslot=0x2F963,
+ },
+ [0x2F964]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4227 },
+ unicodeslot=0x2F964,
+ },
+ [0x2F965]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25C80 },
+ unicodeslot=0x2F965,
+ },
+ [0x2F966]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7CD2 },
+ unicodeslot=0x2F966,
+ },
+ [0x2F967]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x42A0 },
+ unicodeslot=0x2F967,
+ },
+ [0x2F968]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7CE8 },
+ unicodeslot=0x2F968,
+ },
+ [0x2F969]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7CE3 },
+ unicodeslot=0x2F969,
+ },
+ [0x2F96A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7D00 },
+ unicodeslot=0x2F96A,
+ },
+ [0x2F96B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x25F86 },
+ unicodeslot=0x2F96B,
+ },
+ [0x2F96C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7D63 },
+ unicodeslot=0x2F96C,
+ },
+ [0x2F96D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4301 },
+ unicodeslot=0x2F96D,
+ },
+ [0x2F96E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7DC7 },
+ unicodeslot=0x2F96E,
+ },
+ [0x2F96F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7E02 },
+ unicodeslot=0x2F96F,
+ },
+ [0x2F970]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7E45 },
+ unicodeslot=0x2F970,
+ },
+ [0x2F971]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4334 },
+ unicodeslot=0x2F971,
+ },
+ [0x2F972]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26228 },
+ unicodeslot=0x2F972,
+ },
+ [0x2F973]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26247 },
+ unicodeslot=0x2F973,
+ },
+ [0x2F974]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4359 },
+ unicodeslot=0x2F974,
+ },
+ [0x2F975]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x262D9 },
+ unicodeslot=0x2F975,
+ },
+ [0x2F976]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F7A },
+ unicodeslot=0x2F976,
+ },
+ [0x2F977]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2633E },
+ unicodeslot=0x2F977,
+ },
+ [0x2F978]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7F95 },
+ unicodeslot=0x2F978,
+ },
+ [0x2F979]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x7FFA },
+ unicodeslot=0x2F979,
+ },
+ [0x2F97A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8005 },
+ unicodeslot=0x2F97A,
+ },
+ [0x2F97B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x264DA },
+ unicodeslot=0x2F97B,
+ },
+ [0x2F97C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26523 },
+ unicodeslot=0x2F97C,
+ },
+ [0x2F97D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8060 },
+ unicodeslot=0x2F97D,
+ },
+ [0x2F97E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x265A8 },
+ unicodeslot=0x2F97E,
+ },
+ [0x2F97F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8070 },
+ unicodeslot=0x2F97F,
+ },
+ [0x2F980]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2335F },
+ unicodeslot=0x2F980,
+ },
+ [0x2F981]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x43D5 },
+ unicodeslot=0x2F981,
+ },
+ [0x2F982]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x80B2 },
+ unicodeslot=0x2F982,
+ },
+ [0x2F983]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8103 },
+ unicodeslot=0x2F983,
+ },
+ [0x2F984]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x440B },
+ unicodeslot=0x2F984,
+ },
+ [0x2F985]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x813E },
+ unicodeslot=0x2F985,
+ },
+ [0x2F986]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5AB5 },
+ unicodeslot=0x2F986,
+ },
+ [0x2F987]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x267A7 },
+ unicodeslot=0x2F987,
+ },
+ [0x2F988]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x267B5 },
+ unicodeslot=0x2F988,
+ },
+ [0x2F989]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x23393 },
+ unicodeslot=0x2F989,
+ },
+ [0x2F98A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2339C },
+ unicodeslot=0x2F98A,
+ },
+ [0x2F98B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8201 },
+ unicodeslot=0x2F98B,
+ },
+ [0x2F98C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8204 },
+ unicodeslot=0x2F98C,
+ },
+ [0x2F98D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F9E },
+ unicodeslot=0x2F98D,
+ },
+ [0x2F98E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x446B },
+ unicodeslot=0x2F98E,
+ },
+ [0x2F98F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8291 },
+ unicodeslot=0x2F98F,
+ },
+ [0x2F990]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x828B },
+ unicodeslot=0x2F990,
+ },
+ [0x2F991]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x829D },
+ unicodeslot=0x2F991,
+ },
+ [0x2F992]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x52B3 },
+ unicodeslot=0x2F992,
+ },
+ [0x2F993]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x82B1 },
+ unicodeslot=0x2F993,
+ },
+ [0x2F994]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x82B3 },
+ unicodeslot=0x2F994,
+ },
+ [0x2F995]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x82BD },
+ unicodeslot=0x2F995,
+ },
+ [0x2F996]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x82E6 },
+ unicodeslot=0x2F996,
+ },
+ [0x2F997]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26B3C },
+ unicodeslot=0x2F997,
+ },
+ [0x2F998]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x82E5 },
+ unicodeslot=0x2F998,
+ },
+ [0x2F999]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x831D },
+ unicodeslot=0x2F999,
+ },
+ [0x2F99A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8363 },
+ unicodeslot=0x2F99A,
+ },
+ [0x2F99B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83AD },
+ unicodeslot=0x2F99B,
+ },
+ [0x2F99C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8323 },
+ unicodeslot=0x2F99C,
+ },
+ [0x2F99D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83BD },
+ unicodeslot=0x2F99D,
+ },
+ [0x2F99E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83E7 },
+ unicodeslot=0x2F99E,
+ },
+ [0x2F99F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8457 },
+ unicodeslot=0x2F99F,
+ },
+ [0x2F9A0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8353 },
+ unicodeslot=0x2F9A0,
+ },
+ [0x2F9A1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83CA },
+ unicodeslot=0x2F9A1,
+ },
+ [0x2F9A2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83CC },
+ unicodeslot=0x2F9A2,
+ },
+ [0x2F9A3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x83DC },
+ unicodeslot=0x2F9A3,
+ },
+ [0x2F9A4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26C36 },
+ unicodeslot=0x2F9A4,
+ },
+ [0x2F9A5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26D6B },
+ unicodeslot=0x2F9A5,
+ },
+ [0x2F9A6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26CD5 },
+ unicodeslot=0x2F9A6,
+ },
+ [0x2F9A7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x452B },
+ unicodeslot=0x2F9A7,
+ },
+ [0x2F9A8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x84F1 },
+ unicodeslot=0x2F9A8,
+ },
+ [0x2F9A9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x84F3 },
+ unicodeslot=0x2F9A9,
+ },
+ [0x2F9AA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8516 },
+ unicodeslot=0x2F9AA,
+ },
+ [0x2F9AB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x273CA },
+ unicodeslot=0x2F9AB,
+ },
+ [0x2F9AC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8564 },
+ unicodeslot=0x2F9AC,
+ },
+ [0x2F9AD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26F2C },
+ unicodeslot=0x2F9AD,
+ },
+ [0x2F9AE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x455D },
+ unicodeslot=0x2F9AE,
+ },
+ [0x2F9AF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4561 },
+ unicodeslot=0x2F9AF,
+ },
+ [0x2F9B0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x26FB1 },
+ unicodeslot=0x2F9B0,
+ },
+ [0x2F9B1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x270D2 },
+ unicodeslot=0x2F9B1,
+ },
+ [0x2F9B2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x456B },
+ unicodeslot=0x2F9B2,
+ },
+ [0x2F9B3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8650 },
+ unicodeslot=0x2F9B3,
+ },
+ [0x2F9B4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x865C },
+ unicodeslot=0x2F9B4,
+ },
+ [0x2F9B5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8667 },
+ unicodeslot=0x2F9B5,
+ },
+ [0x2F9B6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8669 },
+ unicodeslot=0x2F9B6,
+ },
+ [0x2F9B7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x86A9 },
+ unicodeslot=0x2F9B7,
+ },
+ [0x2F9B8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8688 },
+ unicodeslot=0x2F9B8,
+ },
+ [0x2F9B9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x870E },
+ unicodeslot=0x2F9B9,
+ },
+ [0x2F9BA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x86E2 },
+ unicodeslot=0x2F9BA,
+ },
+ [0x2F9BB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8779 },
+ unicodeslot=0x2F9BB,
+ },
+ [0x2F9BC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8728 },
+ unicodeslot=0x2F9BC,
+ },
+ [0x2F9BD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x876B },
+ unicodeslot=0x2F9BD,
+ },
+ [0x2F9BE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8786 },
+ unicodeslot=0x2F9BE,
+ },
+ [0x2F9BF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x45D7 },
+ unicodeslot=0x2F9BF,
+ },
+ [0x2F9C0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x87E1 },
+ unicodeslot=0x2F9C0,
+ },
+ [0x2F9C1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8801 },
+ unicodeslot=0x2F9C1,
+ },
+ [0x2F9C2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x45F9 },
+ unicodeslot=0x2F9C2,
+ },
+ [0x2F9C3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8860 },
+ unicodeslot=0x2F9C3,
+ },
+ [0x2F9C4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8863 },
+ unicodeslot=0x2F9C4,
+ },
+ [0x2F9C5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x27667 },
+ unicodeslot=0x2F9C5,
+ },
+ [0x2F9C6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88D7 },
+ unicodeslot=0x2F9C6,
+ },
+ [0x2F9C7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88DE },
+ unicodeslot=0x2F9C7,
+ },
+ [0x2F9C8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4635 },
+ unicodeslot=0x2F9C8,
+ },
+ [0x2F9C9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x88FA },
+ unicodeslot=0x2F9C9,
+ },
+ [0x2F9CA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x34BB },
+ unicodeslot=0x2F9CA,
+ },
+ [0x2F9CB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x278AE },
+ unicodeslot=0x2F9CB,
+ },
+ [0x2F9CC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x27966 },
+ unicodeslot=0x2F9CC,
+ },
+ [0x2F9CD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x46BE },
+ unicodeslot=0x2F9CD,
+ },
+ [0x2F9CE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x46C7 },
+ unicodeslot=0x2F9CE,
+ },
+ [0x2F9CF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AA0 },
+ unicodeslot=0x2F9CF,
+ },
+ [0x2F9D0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8AED },
+ unicodeslot=0x2F9D0,
+ },
+ [0x2F9D1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8B8A },
+ unicodeslot=0x2F9D1,
+ },
+ [0x2F9D2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8C55 },
+ unicodeslot=0x2F9D2,
+ },
+ [0x2F9D3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x27CA8 },
+ unicodeslot=0x2F9D3,
+ },
+ [0x2F9D4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8CAB },
+ unicodeslot=0x2F9D4,
+ },
+ [0x2F9D5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8CC1 },
+ unicodeslot=0x2F9D5,
+ },
+ [0x2F9D6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8D1B },
+ unicodeslot=0x2F9D6,
+ },
+ [0x2F9D7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8D77 },
+ unicodeslot=0x2F9D7,
+ },
+ [0x2F9D8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x27F2F },
+ unicodeslot=0x2F9D8,
+ },
+ [0x2F9D9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x20804 },
+ unicodeslot=0x2F9D9,
+ },
+ [0x2F9DA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8DCB },
+ unicodeslot=0x2F9DA,
+ },
+ [0x2F9DB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8DBC },
+ unicodeslot=0x2F9DB,
+ },
+ [0x2F9DC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8DF0 },
+ unicodeslot=0x2F9DC,
+ },
+ [0x2F9DD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x208DE },
+ unicodeslot=0x2F9DD,
+ },
+ [0x2F9DE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8ED4 },
+ unicodeslot=0x2F9DE,
+ },
+ [0x2F9DF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x8F38 },
+ unicodeslot=0x2F9DF,
+ },
+ [0x2F9E0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x285D2 },
+ unicodeslot=0x2F9E0,
+ },
+ [0x2F9E1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x285ED },
+ unicodeslot=0x2F9E1,
+ },
+ [0x2F9E2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9094 },
+ unicodeslot=0x2F9E2,
+ },
+ [0x2F9E3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x90F1 },
+ unicodeslot=0x2F9E3,
+ },
+ [0x2F9E4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9111 },
+ unicodeslot=0x2F9E4,
+ },
+ [0x2F9E5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2872E },
+ unicodeslot=0x2F9E5,
+ },
+ [0x2F9E6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x911B },
+ unicodeslot=0x2F9E6,
+ },
+ [0x2F9E7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9238 },
+ unicodeslot=0x2F9E7,
+ },
+ [0x2F9E8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x92D7 },
+ unicodeslot=0x2F9E8,
+ },
+ [0x2F9E9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x92D8 },
+ unicodeslot=0x2F9E9,
+ },
+ [0x2F9EA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x927C },
+ unicodeslot=0x2F9EA,
+ },
+ [0x2F9EB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x93F9 },
+ unicodeslot=0x2F9EB,
+ },
+ [0x2F9EC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9415 },
+ unicodeslot=0x2F9EC,
+ },
+ [0x2F9ED]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x28BFA },
+ unicodeslot=0x2F9ED,
+ },
+ [0x2F9EE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x958B },
+ unicodeslot=0x2F9EE,
+ },
+ [0x2F9EF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4995 },
+ unicodeslot=0x2F9EF,
+ },
+ [0x2F9F0]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x95B7 },
+ unicodeslot=0x2F9F0,
+ },
+ [0x2F9F1]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x28D77 },
+ unicodeslot=0x2F9F1,
+ },
+ [0x2F9F2]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x49E6 },
+ unicodeslot=0x2F9F2,
+ },
+ [0x2F9F3]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x96C3 },
+ unicodeslot=0x2F9F3,
+ },
+ [0x2F9F4]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x5DB2 },
+ unicodeslot=0x2F9F4,
+ },
+ [0x2F9F5]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9723 },
+ unicodeslot=0x2F9F5,
+ },
+ [0x2F9F6]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x29145 },
+ unicodeslot=0x2F9F6,
+ },
+ [0x2F9F7]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2921A },
+ unicodeslot=0x2F9F7,
+ },
+ [0x2F9F8]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4A6E },
+ unicodeslot=0x2F9F8,
+ },
+ [0x2F9F9]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4A76 },
+ unicodeslot=0x2F9F9,
+ },
+ [0x2F9FA]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x97E0 },
+ unicodeslot=0x2F9FA,
+ },
+ [0x2F9FB]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2940A },
+ unicodeslot=0x2F9FB,
+ },
+ [0x2F9FC]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4AB2 },
+ unicodeslot=0x2F9FC,
+ },
+ [0x2F9FD]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x29496 },
+ unicodeslot=0x2F9FD,
+ },
+ [0x2F9FE]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x980B },
+ unicodeslot=0x2F9FE,
+ },
+ [0x2F9FF]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x980B },
+ unicodeslot=0x2F9FF,
+ },
+ [0x2FA00]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9829 },
+ unicodeslot=0x2FA00,
+ },
+ [0x2FA01]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x295B6 },
+ unicodeslot=0x2FA01,
+ },
+ [0x2FA02]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x98E2 },
+ unicodeslot=0x2FA02,
+ },
+ [0x2FA03]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4B33 },
+ unicodeslot=0x2FA03,
+ },
+ [0x2FA04]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9929 },
+ unicodeslot=0x2FA04,
+ },
+ [0x2FA05]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x99A7 },
+ unicodeslot=0x2FA05,
+ },
+ [0x2FA06]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x99C2 },
+ unicodeslot=0x2FA06,
+ },
+ [0x2FA07]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x99FE },
+ unicodeslot=0x2FA07,
+ },
+ [0x2FA08]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4BCE },
+ unicodeslot=0x2FA08,
+ },
+ [0x2FA09]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x29B30 },
+ unicodeslot=0x2FA09,
+ },
+ [0x2FA0A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9B12 },
+ unicodeslot=0x2FA0A,
+ },
+ [0x2FA0B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9C40 },
+ unicodeslot=0x2FA0B,
+ },
+ [0x2FA0C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9CFD },
+ unicodeslot=0x2FA0C,
+ },
+ [0x2FA0D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4CCE },
+ unicodeslot=0x2FA0D,
+ },
+ [0x2FA0E]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4CED },
+ unicodeslot=0x2FA0E,
+ },
+ [0x2FA0F]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9D67 },
+ unicodeslot=0x2FA0F,
+ },
+ [0x2FA10]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2A0CE },
+ unicodeslot=0x2FA10,
+ },
+ [0x2FA11]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4CF8 },
+ unicodeslot=0x2FA11,
+ },
+ [0x2FA12]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2A105 },
+ unicodeslot=0x2FA12,
+ },
+ [0x2FA13]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2A20E },
+ unicodeslot=0x2FA13,
+ },
+ [0x2FA14]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2A291 },
+ unicodeslot=0x2FA14,
+ },
+ [0x2FA15]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9EBB },
+ unicodeslot=0x2FA15,
+ },
+ [0x2FA16]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x4D56 },
+ unicodeslot=0x2FA16,
+ },
+ [0x2FA17]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9EF9 },
+ unicodeslot=0x2FA17,
+ },
+ [0x2FA18]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9EFE },
+ unicodeslot=0x2FA18,
+ },
+ [0x2FA19]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F05 },
+ unicodeslot=0x2FA19,
+ },
+ [0x2FA1A]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F0F },
+ unicodeslot=0x2FA1A,
+ },
+ [0x2FA1B]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F16 },
+ unicodeslot=0x2FA1B,
+ },
+ [0x2FA1C]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x9F3B },
+ unicodeslot=0x2FA1C,
+ },
+ [0x2FA1D]={
+ category="lo",
+ direction="l",
+ linebreak="id",
+ specials={ "char", 0x2A600 },
+ unicodeslot=0x2FA1D,
+ },
+ [0xE0001]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0001,
+ },
+ [0xE0020]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0020,
+ },
+ [0xE0021]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0021,
+ },
+ [0xE0022]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0022,
+ },
+ [0xE0023]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0023,
+ },
+ [0xE0024]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0024,
+ },
+ [0xE0025]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0025,
+ },
+ [0xE0026]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0026,
+ },
+ [0xE0027]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0027,
+ },
+ [0xE0028]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0028,
+ },
+ [0xE0029]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0029,
+ },
+ [0xE002A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE002A,
+ },
+ [0xE002B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE002B,
+ },
+ [0xE002C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE002C,
+ },
+ [0xE002D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE002D,
+ },
+ [0xE002E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE002E,
+ },
+ [0xE002F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE002F,
+ },
+ [0xE0030]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0030,
+ },
+ [0xE0031]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0031,
+ },
+ [0xE0032]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0032,
+ },
+ [0xE0033]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0033,
+ },
+ [0xE0034]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0034,
+ },
+ [0xE0035]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0035,
+ },
+ [0xE0036]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0036,
+ },
+ [0xE0037]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0037,
+ },
+ [0xE0038]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0038,
+ },
+ [0xE0039]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0039,
+ },
+ [0xE003A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE003A,
+ },
+ [0xE003B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE003B,
+ },
+ [0xE003C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE003C,
+ },
+ [0xE003D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE003D,
+ },
+ [0xE003E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE003E,
+ },
+ [0xE003F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE003F,
+ },
+ [0xE0040]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0040,
+ },
+ [0xE0041]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0041,
+ },
+ [0xE0042]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0042,
+ },
+ [0xE0043]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0043,
+ },
+ [0xE0044]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0044,
+ },
+ [0xE0045]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0045,
+ },
+ [0xE0046]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0046,
+ },
+ [0xE0047]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0047,
+ },
+ [0xE0048]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0048,
+ },
+ [0xE0049]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0049,
+ },
+ [0xE004A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE004A,
+ },
+ [0xE004B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE004B,
+ },
+ [0xE004C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE004C,
+ },
+ [0xE004D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE004D,
+ },
+ [0xE004E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE004E,
+ },
+ [0xE004F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE004F,
+ },
+ [0xE0050]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0050,
+ },
+ [0xE0051]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0051,
+ },
+ [0xE0052]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0052,
+ },
+ [0xE0053]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0053,
+ },
+ [0xE0054]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0054,
+ },
+ [0xE0055]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0055,
+ },
+ [0xE0056]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0056,
+ },
+ [0xE0057]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0057,
+ },
+ [0xE0058]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0058,
+ },
+ [0xE0059]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0059,
+ },
+ [0xE005A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE005A,
+ },
+ [0xE005B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE005B,
+ },
+ [0xE005C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE005C,
+ },
+ [0xE005D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE005D,
+ },
+ [0xE005E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE005E,
+ },
+ [0xE005F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE005F,
+ },
+ [0xE0060]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0060,
+ },
+ [0xE0061]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0061,
+ },
+ [0xE0062]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0062,
+ },
+ [0xE0063]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0063,
+ },
+ [0xE0064]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0064,
+ },
+ [0xE0065]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0065,
+ },
+ [0xE0066]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0066,
+ },
+ [0xE0067]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0067,
+ },
+ [0xE0068]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0068,
+ },
+ [0xE0069]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0069,
+ },
+ [0xE006A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE006A,
+ },
+ [0xE006B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE006B,
+ },
+ [0xE006C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE006C,
+ },
+ [0xE006D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE006D,
+ },
+ [0xE006E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE006E,
+ },
+ [0xE006F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE006F,
+ },
+ [0xE0070]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0070,
+ },
+ [0xE0071]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0071,
+ },
+ [0xE0072]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0072,
+ },
+ [0xE0073]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0073,
+ },
+ [0xE0074]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0074,
+ },
+ [0xE0075]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0075,
+ },
+ [0xE0076]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0076,
+ },
+ [0xE0077]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0077,
+ },
+ [0xE0078]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0078,
+ },
+ [0xE0079]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE0079,
+ },
+ [0xE007A]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE007A,
+ },
+ [0xE007B]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE007B,
+ },
+ [0xE007C]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE007C,
+ },
+ [0xE007D]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE007D,
+ },
+ [0xE007E]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE007E,
+ },
+ [0xE007F]={
+ category="cf",
+ direction="bn",
+ linebreak="cm",
+ unicodeslot=0xE007F,
+ },
+ [0xE0100]={
+ unicodeslot=0xE0100,
+ },
+ characters={},
+ classifiers={
+ [0x600]=0x4,
+ [0x601]=0x4,
+ [0x602]=0x4,
+ [0x603]=0x4,
+ [0x604]=0x4,
+ [0x605]=0x4,
+ [0x606]=0x6,
+ [0x607]=0x6,
+ [0x608]=0x4,
+ [0x609]=0x6,
+ [0x60A]=0x6,
+ [0x60B]=0x4,
+ [0x60C]=0x6,
+ [0x60D]=0x6,
+ [0x60E]=0x6,
+ [0x60F]=0x6,
+ [0x610]=0x5,
+ [0x611]=0x5,
+ [0x612]=0x5,
+ [0x613]=0x5,
+ [0x614]=0x5,
+ [0x615]=0x5,
+ [0x616]=0x5,
+ [0x617]=0x5,
+ [0x618]=0x5,
+ [0x619]=0x5,
+ [0x61A]=0x5,
+ [0x61B]=0x6,
+ [0x61C]=0x6,
+ [0x61E]=0x6,
+ [0x61F]=0x6,
+ [0x620]=0x2,
+ [0x621]=0x4,
+ [0x622]=0x3,
+ [0x623]=0x3,
+ [0x624]=0x3,
+ [0x625]=0x3,
+ [0x626]=0x2,
+ [0x627]=0x3,
+ [0x628]=0x2,
+ [0x629]=0x3,
+ [0x62A]=0x2,
+ [0x62B]=0x2,
+ [0x62C]=0x2,
+ [0x62D]=0x2,
+ [0x62E]=0x2,
+ [0x62F]=0x3,
+ [0x630]=0x3,
+ [0x631]=0x3,
+ [0x632]=0x3,
+ [0x633]=0x2,
+ [0x634]=0x2,
+ [0x635]=0x2,
+ [0x636]=0x2,
+ [0x637]=0x2,
+ [0x638]=0x2,
+ [0x639]=0x2,
+ [0x63A]=0x2,
+ [0x63B]=0x2,
+ [0x63C]=0x2,
+ [0x63D]=0x2,
+ [0x63E]=0x2,
+ [0x63F]=0x2,
+ [0x640]=0x2,
+ [0x641]=0x2,
+ [0x642]=0x2,
+ [0x643]=0x2,
+ [0x644]=0x2,
+ [0x645]=0x2,
+ [0x646]=0x2,
+ [0x647]=0x2,
+ [0x648]=0x3,
+ [0x649]=0x2,
+ [0x64A]=0x2,
+ [0x64B]=0x5,
+ [0x64C]=0x5,
+ [0x64D]=0x5,
+ [0x64E]=0x5,
+ [0x64F]=0x5,
+ [0x650]=0x5,
+ [0x651]=0x5,
+ [0x652]=0x5,
+ [0x653]=0x5,
+ [0x654]=0x5,
+ [0x655]=0x5,
+ [0x656]=0x5,
+ [0x657]=0x5,
+ [0x658]=0x5,
+ [0x659]=0x5,
+ [0x65A]=0x5,
+ [0x65B]=0x5,
+ [0x65C]=0x5,
+ [0x65D]=0x5,
+ [0x65E]=0x5,
+ [0x65F]=0x5,
+ [0x660]=0x6,
+ [0x661]=0x6,
+ [0x662]=0x6,
+ [0x663]=0x6,
+ [0x664]=0x6,
+ [0x665]=0x6,
+ [0x666]=0x6,
+ [0x667]=0x6,
+ [0x668]=0x6,
+ [0x669]=0x6,
+ [0x66A]=0x6,
+ [0x66B]=0x6,
+ [0x66C]=0x6,
+ [0x66D]=0x6,
+ [0x66E]=0x2,
+ [0x66F]=0x2,
+ [0x670]=0x5,
+ [0x671]=0x3,
+ [0x672]=0x3,
+ [0x673]=0x3,
+ [0x674]=0x4,
+ [0x675]=0x3,
+ [0x676]=0x3,
+ [0x677]=0x3,
+ [0x678]=0x2,
+ [0x679]=0x2,
+ [0x67A]=0x2,
+ [0x67B]=0x2,
+ [0x67C]=0x2,
+ [0x67D]=0x2,
+ [0x67E]=0x2,
+ [0x67F]=0x2,
+ [0x680]=0x2,
+ [0x681]=0x2,
+ [0x682]=0x2,
+ [0x683]=0x2,
+ [0x684]=0x2,
+ [0x685]=0x2,
+ [0x686]=0x2,
+ [0x687]=0x2,
+ [0x688]=0x3,
+ [0x689]=0x3,
+ [0x68A]=0x3,
+ [0x68B]=0x3,
+ [0x68C]=0x3,
+ [0x68D]=0x3,
+ [0x68E]=0x3,
+ [0x68F]=0x3,
+ [0x690]=0x3,
+ [0x691]=0x3,
+ [0x692]=0x3,
+ [0x693]=0x3,
+ [0x694]=0x3,
+ [0x695]=0x3,
+ [0x696]=0x3,
+ [0x697]=0x3,
+ [0x698]=0x3,
+ [0x699]=0x3,
+ [0x69A]=0x2,
+ [0x69B]=0x2,
+ [0x69C]=0x2,
+ [0x69D]=0x2,
+ [0x69E]=0x2,
+ [0x69F]=0x2,
+ [0x6A0]=0x2,
+ [0x6A1]=0x2,
+ [0x6A2]=0x2,
+ [0x6A3]=0x2,
+ [0x6A4]=0x2,
+ [0x6A5]=0x2,
+ [0x6A6]=0x2,
+ [0x6A7]=0x2,
+ [0x6A8]=0x2,
+ [0x6A9]=0x2,
+ [0x6AA]=0x2,
+ [0x6AB]=0x2,
+ [0x6AC]=0x2,
+ [0x6AD]=0x2,
+ [0x6AE]=0x2,
+ [0x6AF]=0x2,
+ [0x6B0]=0x2,
+ [0x6B1]=0x2,
+ [0x6B2]=0x2,
+ [0x6B3]=0x2,
+ [0x6B4]=0x2,
+ [0x6B5]=0x2,
+ [0x6B6]=0x2,
+ [0x6B7]=0x2,
+ [0x6B8]=0x2,
+ [0x6B9]=0x2,
+ [0x6BA]=0x2,
+ [0x6BB]=0x2,
+ [0x6BC]=0x2,
+ [0x6BD]=0x2,
+ [0x6BE]=0x2,
+ [0x6BF]=0x2,
+ [0x6C0]=0x3,
+ [0x6C1]=0x2,
+ [0x6C2]=0x2,
+ [0x6C3]=0x3,
+ [0x6C4]=0x3,
+ [0x6C5]=0x3,
+ [0x6C6]=0x3,
+ [0x6C7]=0x3,
+ [0x6C8]=0x3,
+ [0x6C9]=0x3,
+ [0x6CA]=0x3,
+ [0x6CB]=0x3,
+ [0x6CC]=0x2,
+ [0x6CD]=0x3,
+ [0x6CE]=0x2,
+ [0x6CF]=0x3,
+ [0x6D0]=0x2,
+ [0x6D1]=0x2,
+ [0x6D2]=0x3,
+ [0x6D3]=0x3,
+ [0x6D4]=0x6,
+ [0x6D5]=0x3,
+ [0x6D6]=0x5,
+ [0x6D7]=0x5,
+ [0x6D8]=0x5,
+ [0x6D9]=0x5,
+ [0x6DA]=0x5,
+ [0x6DB]=0x5,
+ [0x6DC]=0x5,
+ [0x6DD]=0x4,
+ [0x6DE]=0x6,
+ [0x6DF]=0x5,
+ [0x6E0]=0x5,
+ [0x6E1]=0x5,
+ [0x6E2]=0x5,
+ [0x6E3]=0x5,
+ [0x6E4]=0x5,
+ [0x6E5]=0x6,
+ [0x6E6]=0x6,
+ [0x6E7]=0x5,
+ [0x6E8]=0x5,
+ [0x6E9]=0x6,
+ [0x6EA]=0x5,
+ [0x6EB]=0x5,
+ [0x6EC]=0x5,
+ [0x6ED]=0x5,
+ [0x6EE]=0x3,
+ [0x6EF]=0x3,
+ [0x6F0]=0x6,
+ [0x6F1]=0x6,
+ [0x6F2]=0x6,
+ [0x6F3]=0x6,
+ [0x6F4]=0x6,
+ [0x6F5]=0x6,
+ [0x6F6]=0x6,
+ [0x6F7]=0x6,
+ [0x6F8]=0x6,
+ [0x6F9]=0x6,
+ [0x6FA]=0x2,
+ [0x6FB]=0x2,
+ [0x6FC]=0x2,
+ [0x6FD]=0x6,
+ [0x6FE]=0x6,
+ [0x6FF]=0x2,
+ [0x700]=0x6,
+ [0x701]=0x6,
+ [0x702]=0x6,
+ [0x703]=0x6,
+ [0x704]=0x6,
+ [0x705]=0x6,
+ [0x706]=0x6,
+ [0x707]=0x6,
+ [0x708]=0x6,
+ [0x709]=0x6,
+ [0x70A]=0x6,
+ [0x70B]=0x6,
+ [0x70C]=0x6,
+ [0x70D]=0x6,
+ [0x710]=0x3,
+ [0x711]=0x5,
+ [0x712]=0x2,
+ [0x713]=0x2,
+ [0x714]=0x2,
+ [0x715]=0x3,
+ [0x716]=0x3,
+ [0x717]=0x3,
+ [0x718]=0x3,
+ [0x719]=0x3,
+ [0x71A]=0x2,
+ [0x71B]=0x2,
+ [0x71C]=0x2,
+ [0x71D]=0x2,
+ [0x71E]=0x3,
+ [0x71F]=0x2,
+ [0x720]=0x2,
+ [0x721]=0x2,
+ [0x722]=0x2,
+ [0x723]=0x2,
+ [0x724]=0x2,
+ [0x725]=0x2,
+ [0x726]=0x2,
+ [0x727]=0x2,
+ [0x728]=0x3,
+ [0x729]=0x2,
+ [0x72A]=0x3,
+ [0x72B]=0x2,
+ [0x72C]=0x3,
+ [0x72D]=0x2,
+ [0x72E]=0x2,
+ [0x72F]=0x3,
+ [0x730]=0x5,
+ [0x731]=0x5,
+ [0x732]=0x5,
+ [0x733]=0x5,
+ [0x734]=0x5,
+ [0x735]=0x5,
+ [0x736]=0x5,
+ [0x737]=0x5,
+ [0x738]=0x5,
+ [0x739]=0x5,
+ [0x73A]=0x5,
+ [0x73B]=0x5,
+ [0x73C]=0x5,
+ [0x73D]=0x5,
+ [0x73E]=0x5,
+ [0x73F]=0x5,
+ [0x740]=0x5,
+ [0x741]=0x5,
+ [0x742]=0x5,
+ [0x743]=0x5,
+ [0x744]=0x5,
+ [0x745]=0x5,
+ [0x746]=0x5,
+ [0x747]=0x5,
+ [0x748]=0x5,
+ [0x749]=0x5,
+ [0x74A]=0x5,
+ [0x74D]=0x3,
+ [0x74E]=0x2,
+ [0x74F]=0x2,
+ [0x750]=0x2,
+ [0x751]=0x2,
+ [0x752]=0x2,
+ [0x753]=0x2,
+ [0x754]=0x2,
+ [0x755]=0x2,
+ [0x756]=0x2,
+ [0x757]=0x2,
+ [0x758]=0x2,
+ [0x759]=0x3,
+ [0x75A]=0x3,
+ [0x75B]=0x3,
+ [0x75C]=0x2,
+ [0x75D]=0x2,
+ [0x75E]=0x2,
+ [0x75F]=0x2,
+ [0x760]=0x2,
+ [0x761]=0x2,
+ [0x762]=0x2,
+ [0x763]=0x2,
+ [0x764]=0x2,
+ [0x765]=0x2,
+ [0x766]=0x2,
+ [0x767]=0x2,
+ [0x768]=0x2,
+ [0x769]=0x2,
+ [0x76A]=0x2,
+ [0x76B]=0x3,
+ [0x76C]=0x3,
+ [0x76D]=0x2,
+ [0x76E]=0x2,
+ [0x76F]=0x2,
+ [0x770]=0x2,
+ [0x771]=0x3,
+ [0x772]=0x2,
+ [0x773]=0x3,
+ [0x774]=0x3,
+ [0x775]=0x2,
+ [0x776]=0x2,
+ [0x777]=0x2,
+ [0x778]=0x3,
+ [0x779]=0x3,
+ [0x77A]=0x2,
+ [0x77B]=0x2,
+ [0x77C]=0x2,
+ [0x77D]=0x2,
+ [0x77E]=0x2,
+ [0x77F]=0x2,
+ [0x7C0]=0x6,
+ [0x7C1]=0x6,
+ [0x7C2]=0x6,
+ [0x7C3]=0x6,
+ [0x7C4]=0x6,
+ [0x7C5]=0x6,
+ [0x7C6]=0x6,
+ [0x7C7]=0x6,
+ [0x7C8]=0x6,
+ [0x7C9]=0x6,
+ [0x7CA]=0x2,
+ [0x7CB]=0x2,
+ [0x7CC]=0x2,
+ [0x7CD]=0x2,
+ [0x7CE]=0x2,
+ [0x7CF]=0x2,
+ [0x7D0]=0x2,
+ [0x7D1]=0x2,
+ [0x7D2]=0x2,
+ [0x7D3]=0x2,
+ [0x7D4]=0x2,
+ [0x7D5]=0x2,
+ [0x7D6]=0x2,
+ [0x7D7]=0x2,
+ [0x7D8]=0x2,
+ [0x7D9]=0x2,
+ [0x7DA]=0x2,
+ [0x7DB]=0x2,
+ [0x7DC]=0x2,
+ [0x7DD]=0x2,
+ [0x7DE]=0x2,
+ [0x7DF]=0x2,
+ [0x7E0]=0x2,
+ [0x7E1]=0x2,
+ [0x7E2]=0x2,
+ [0x7E3]=0x2,
+ [0x7E4]=0x2,
+ [0x7E5]=0x2,
+ [0x7E6]=0x2,
+ [0x7E7]=0x2,
+ [0x7E8]=0x2,
+ [0x7E9]=0x2,
+ [0x7EA]=0x2,
+ [0x7EB]=0x5,
+ [0x7EC]=0x5,
+ [0x7ED]=0x5,
+ [0x7EE]=0x5,
+ [0x7EF]=0x5,
+ [0x7F0]=0x5,
+ [0x7F1]=0x5,
+ [0x7F2]=0x5,
+ [0x7F3]=0x5,
+ [0x7F4]=0x6,
+ [0x7F5]=0x6,
+ [0x7F6]=0x6,
+ [0x7F7]=0x6,
+ [0x7F8]=0x6,
+ [0x7F9]=0x6,
+ [0x7FA]=0x2,
+ [0x7FD]=0x5,
+ [0x7FE]=0x6,
+ [0x7FF]=0x6,
+ [0x840]=0x3,
+ [0x841]=0x2,
+ [0x842]=0x2,
+ [0x843]=0x2,
+ [0x844]=0x2,
+ [0x845]=0x2,
+ [0x846]=0x3,
+ [0x847]=0x3,
+ [0x848]=0x2,
+ [0x849]=0x3,
+ [0x84A]=0x2,
+ [0x84B]=0x2,
+ [0x84C]=0x2,
+ [0x84D]=0x2,
+ [0x84E]=0x2,
+ [0x84F]=0x2,
+ [0x850]=0x2,
+ [0x851]=0x2,
+ [0x852]=0x2,
+ [0x853]=0x2,
+ [0x854]=0x3,
+ [0x855]=0x2,
+ [0x856]=0x4,
+ [0x857]=0x4,
+ [0x858]=0x4,
+ [0x860]=0x2,
+ [0x861]=0x4,
+ [0x862]=0x2,
+ [0x863]=0x2,
+ [0x864]=0x2,
+ [0x865]=0x2,
+ [0x866]=0x4,
+ [0x867]=0x3,
+ [0x868]=0x2,
+ [0x869]=0x3,
+ [0x86A]=0x3,
+ [0x8A0]=0x2,
+ [0x8A1]=0x2,
+ [0x8A2]=0x2,
+ [0x8A3]=0x2,
+ [0x8A4]=0x2,
+ [0x8A5]=0x2,
+ [0x8A6]=0x2,
+ [0x8A7]=0x2,
+ [0x8A8]=0x2,
+ [0x8A9]=0x2,
+ [0x8AA]=0x3,
+ [0x8AB]=0x3,
+ [0x8AC]=0x3,
+ [0x8AD]=0x4,
+ [0x8AE]=0x3,
+ [0x8AF]=0x2,
+ [0x8B0]=0x2,
+ [0x8B1]=0x3,
+ [0x8B2]=0x3,
+ [0x8B3]=0x2,
+ [0x8B4]=0x2,
+ [0x8B6]=0x2,
+ [0x8B7]=0x2,
+ [0x8B8]=0x2,
+ [0x8B9]=0x3,
+ [0x8BA]=0x2,
+ [0x8BB]=0x2,
+ [0x8BC]=0x2,
+ [0x8BD]=0x2,
+ [0x8E2]=0x4,
+ [0x1806]=0x4,
+ [0x1807]=0x2,
+ [0x180A]=0x2,
+ [0x180E]=0x4,
+ [0x1820]=0x2,
+ [0x1821]=0x2,
+ [0x1822]=0x2,
+ [0x1823]=0x2,
+ [0x1824]=0x2,
+ [0x1825]=0x2,
+ [0x1826]=0x2,
+ [0x1827]=0x2,
+ [0x1828]=0x2,
+ [0x1829]=0x2,
+ [0x182A]=0x2,
+ [0x182B]=0x2,
+ [0x182C]=0x2,
+ [0x182D]=0x2,
+ [0x182E]=0x2,
+ [0x182F]=0x2,
+ [0x1830]=0x2,
+ [0x1831]=0x2,
+ [0x1832]=0x2,
+ [0x1833]=0x2,
+ [0x1834]=0x2,
+ [0x1835]=0x2,
+ [0x1836]=0x2,
+ [0x1837]=0x2,
+ [0x1838]=0x2,
+ [0x1839]=0x2,
+ [0x183A]=0x2,
+ [0x183B]=0x2,
+ [0x183C]=0x2,
+ [0x183D]=0x2,
+ [0x183E]=0x2,
+ [0x183F]=0x2,
+ [0x1840]=0x2,
+ [0x1841]=0x2,
+ [0x1842]=0x2,
+ [0x1843]=0x2,
+ [0x1844]=0x2,
+ [0x1845]=0x2,
+ [0x1846]=0x2,
+ [0x1847]=0x2,
+ [0x1848]=0x2,
+ [0x1849]=0x2,
+ [0x184A]=0x2,
+ [0x184B]=0x2,
+ [0x184C]=0x2,
+ [0x184D]=0x2,
+ [0x184E]=0x2,
+ [0x184F]=0x2,
+ [0x1850]=0x2,
+ [0x1851]=0x2,
+ [0x1852]=0x2,
+ [0x1853]=0x2,
+ [0x1854]=0x2,
+ [0x1855]=0x2,
+ [0x1856]=0x2,
+ [0x1857]=0x2,
+ [0x1858]=0x2,
+ [0x1859]=0x2,
+ [0x185A]=0x2,
+ [0x185B]=0x2,
+ [0x185C]=0x2,
+ [0x185D]=0x2,
+ [0x185E]=0x2,
+ [0x185F]=0x2,
+ [0x1860]=0x2,
+ [0x1861]=0x2,
+ [0x1862]=0x2,
+ [0x1863]=0x2,
+ [0x1864]=0x2,
+ [0x1865]=0x2,
+ [0x1866]=0x2,
+ [0x1867]=0x2,
+ [0x1868]=0x2,
+ [0x1869]=0x2,
+ [0x186A]=0x2,
+ [0x186B]=0x2,
+ [0x186C]=0x2,
+ [0x186D]=0x2,
+ [0x186E]=0x2,
+ [0x186F]=0x2,
+ [0x1870]=0x2,
+ [0x1871]=0x2,
+ [0x1872]=0x2,
+ [0x1873]=0x2,
+ [0x1874]=0x2,
+ [0x1875]=0x2,
+ [0x1876]=0x2,
+ [0x1877]=0x2,
+ [0x1878]=0x2,
+ [0x1880]=0x4,
+ [0x1881]=0x4,
+ [0x1882]=0x4,
+ [0x1883]=0x4,
+ [0x1884]=0x4,
+ [0x1887]=0x2,
+ [0x1888]=0x2,
+ [0x1889]=0x2,
+ [0x188A]=0x2,
+ [0x188B]=0x2,
+ [0x188C]=0x2,
+ [0x188D]=0x2,
+ [0x188E]=0x2,
+ [0x188F]=0x2,
+ [0x1890]=0x2,
+ [0x1891]=0x2,
+ [0x1892]=0x2,
+ [0x1893]=0x2,
+ [0x1894]=0x2,
+ [0x1895]=0x2,
+ [0x1896]=0x2,
+ [0x1897]=0x2,
+ [0x1898]=0x2,
+ [0x1899]=0x2,
+ [0x189A]=0x2,
+ [0x189B]=0x2,
+ [0x189C]=0x2,
+ [0x189D]=0x2,
+ [0x189E]=0x2,
+ [0x189F]=0x2,
+ [0x18A0]=0x2,
+ [0x18A1]=0x2,
+ [0x18A2]=0x2,
+ [0x18A3]=0x2,
+ [0x18A4]=0x2,
+ [0x18A5]=0x2,
+ [0x18A6]=0x2,
+ [0x18A7]=0x2,
+ [0x18A8]=0x2,
+ [0x18AA]=0x2,
+ [0x200C]=0x4,
+ [0x200D]=0x2,
+ [0x202F]=0x4,
+ [0x2066]=0x4,
+ [0x2067]=0x4,
+ [0x2068]=0x4,
+ [0x2069]=0x4,
+ [0xA840]=0x2,
+ [0xA841]=0x2,
+ [0xA842]=0x2,
+ [0xA843]=0x2,
+ [0xA844]=0x2,
+ [0xA845]=0x2,
+ [0xA846]=0x2,
+ [0xA847]=0x2,
+ [0xA848]=0x2,
+ [0xA849]=0x2,
+ [0xA84A]=0x2,
+ [0xA84B]=0x2,
+ [0xA84C]=0x2,
+ [0xA84D]=0x2,
+ [0xA84E]=0x2,
+ [0xA84F]=0x2,
+ [0xA850]=0x2,
+ [0xA851]=0x2,
+ [0xA852]=0x2,
+ [0xA853]=0x2,
+ [0xA854]=0x2,
+ [0xA855]=0x2,
+ [0xA856]=0x2,
+ [0xA857]=0x2,
+ [0xA858]=0x2,
+ [0xA859]=0x2,
+ [0xA85A]=0x2,
+ [0xA85B]=0x2,
+ [0xA85C]=0x2,
+ [0xA85D]=0x2,
+ [0xA85E]=0x2,
+ [0xA85F]=0x2,
+ [0xA860]=0x2,
+ [0xA861]=0x2,
+ [0xA862]=0x2,
+ [0xA863]=0x2,
+ [0xA864]=0x2,
+ [0xA865]=0x2,
+ [0xA866]=0x2,
+ [0xA867]=0x2,
+ [0xA868]=0x2,
+ [0xA869]=0x2,
+ [0xA86A]=0x2,
+ [0xA86B]=0x2,
+ [0xA86C]=0x2,
+ [0xA86D]=0x2,
+ [0xA86E]=0x2,
+ [0xA86F]=0x2,
+ [0xA870]=0x2,
+ [0xA871]=0x2,
+ [0xA872]=0x1,
+ [0xA873]=0x4,
+ [0x10AC0]=0x2,
+ [0x10AC1]=0x2,
+ [0x10AC2]=0x2,
+ [0x10AC3]=0x2,
+ [0x10AC4]=0x2,
+ [0x10AC5]=0x3,
+ [0x10AC6]=0x4,
+ [0x10AC7]=0x3,
+ [0x10AC8]=0x4,
+ [0x10AC9]=0x3,
+ [0x10ACA]=0x3,
+ [0x10ACB]=0x4,
+ [0x10ACC]=0x4,
+ [0x10ACD]=0x1,
+ [0x10ACE]=0x3,
+ [0x10ACF]=0x3,
+ [0x10AD0]=0x3,
+ [0x10AD1]=0x3,
+ [0x10AD2]=0x3,
+ [0x10AD3]=0x2,
+ [0x10AD4]=0x2,
+ [0x10AD5]=0x2,
+ [0x10AD6]=0x2,
+ [0x10AD7]=0x1,
+ [0x10AD8]=0x2,
+ [0x10AD9]=0x2,
+ [0x10ADA]=0x2,
+ [0x10ADB]=0x2,
+ [0x10ADC]=0x2,
+ [0x10ADD]=0x3,
+ [0x10ADE]=0x2,
+ [0x10ADF]=0x2,
+ [0x10AE0]=0x2,
+ [0x10AE1]=0x3,
+ [0x10AE2]=0x4,
+ [0x10AE3]=0x4,
+ [0x10AE4]=0x3,
+ [0x10AEB]=0x2,
+ [0x10AEC]=0x2,
+ [0x10AED]=0x2,
+ [0x10AEE]=0x2,
+ [0x10AEF]=0x3,
+ [0x10B80]=0x2,
+ [0x10B81]=0x3,
+ [0x10B82]=0x2,
+ [0x10B83]=0x3,
+ [0x10B84]=0x3,
+ [0x10B85]=0x3,
+ [0x10B86]=0x2,
+ [0x10B87]=0x2,
+ [0x10B88]=0x2,
+ [0x10B89]=0x3,
+ [0x10B8A]=0x2,
+ [0x10B8B]=0x2,
+ [0x10B8C]=0x3,
+ [0x10B8D]=0x2,
+ [0x10B8E]=0x3,
+ [0x10B8F]=0x3,
+ [0x10B90]=0x2,
+ [0x10B91]=0x3,
+ [0x10BA9]=0x3,
+ [0x10BAA]=0x3,
+ [0x10BAB]=0x3,
+ [0x10BAC]=0x3,
+ [0x10BAD]=0x2,
+ [0x10BAE]=0x2,
+ [0x10BAF]=0x4,
+ [0x10D00]=0x1,
+ [0x10D01]=0x2,
+ [0x10D02]=0x2,
+ [0x10D03]=0x2,
+ [0x10D04]=0x2,
+ [0x10D05]=0x2,
+ [0x10D06]=0x2,
+ [0x10D07]=0x2,
+ [0x10D08]=0x2,
+ [0x10D09]=0x2,
+ [0x10D0A]=0x2,
+ [0x10D0B]=0x2,
+ [0x10D0C]=0x2,
+ [0x10D0D]=0x2,
+ [0x10D0E]=0x2,
+ [0x10D0F]=0x2,
+ [0x10D10]=0x2,
+ [0x10D11]=0x2,
+ [0x10D12]=0x2,
+ [0x10D13]=0x2,
+ [0x10D14]=0x2,
+ [0x10D15]=0x2,
+ [0x10D16]=0x2,
+ [0x10D17]=0x2,
+ [0x10D18]=0x2,
+ [0x10D19]=0x2,
+ [0x10D1A]=0x2,
+ [0x10D1B]=0x2,
+ [0x10D1C]=0x2,
+ [0x10D1D]=0x2,
+ [0x10D1E]=0x2,
+ [0x10D1F]=0x2,
+ [0x10D20]=0x2,
+ [0x10D21]=0x2,
+ [0x10D22]=0x3,
+ [0x10D23]=0x2,
+ [0x10F30]=0x2,
+ [0x10F31]=0x2,
+ [0x10F32]=0x2,
+ [0x10F33]=0x3,
+ [0x10F34]=0x2,
+ [0x10F35]=0x2,
+ [0x10F36]=0x2,
+ [0x10F37]=0x2,
+ [0x10F38]=0x2,
+ [0x10F39]=0x2,
+ [0x10F3A]=0x2,
+ [0x10F3B]=0x2,
+ [0x10F3C]=0x2,
+ [0x10F3D]=0x2,
+ [0x10F3E]=0x2,
+ [0x10F3F]=0x2,
+ [0x10F40]=0x2,
+ [0x10F41]=0x2,
+ [0x10F42]=0x2,
+ [0x10F43]=0x2,
+ [0x10F44]=0x2,
+ [0x10F45]=0x4,
+ [0x10F51]=0x2,
+ [0x10F52]=0x2,
+ [0x10F53]=0x2,
+ [0x10F54]=0x3,
+ [0x110BD]=0x4,
+ [0x110CD]=0x4,
+ [0x1E900]=0x2,
+ [0x1E901]=0x2,
+ [0x1E902]=0x2,
+ [0x1E903]=0x2,
+ [0x1E904]=0x2,
+ [0x1E905]=0x2,
+ [0x1E906]=0x2,
+ [0x1E907]=0x2,
+ [0x1E908]=0x2,
+ [0x1E909]=0x2,
+ [0x1E90A]=0x2,
+ [0x1E90B]=0x2,
+ [0x1E90C]=0x2,
+ [0x1E90D]=0x2,
+ [0x1E90E]=0x2,
+ [0x1E90F]=0x2,
+ [0x1E910]=0x2,
+ [0x1E911]=0x2,
+ [0x1E912]=0x2,
+ [0x1E913]=0x2,
+ [0x1E914]=0x2,
+ [0x1E915]=0x2,
+ [0x1E916]=0x2,
+ [0x1E917]=0x2,
+ [0x1E918]=0x2,
+ [0x1E919]=0x2,
+ [0x1E91A]=0x2,
+ [0x1E91B]=0x2,
+ [0x1E91C]=0x2,
+ [0x1E91D]=0x2,
+ [0x1E91E]=0x2,
+ [0x1E91F]=0x2,
+ [0x1E920]=0x2,
+ [0x1E921]=0x2,
+ [0x1E922]=0x2,
+ [0x1E923]=0x2,
+ [0x1E924]=0x2,
+ [0x1E925]=0x2,
+ [0x1E926]=0x2,
+ [0x1E927]=0x2,
+ [0x1E928]=0x2,
+ [0x1E929]=0x2,
+ [0x1E92A]=0x2,
+ [0x1E92B]=0x2,
+ [0x1E92C]=0x2,
+ [0x1E92D]=0x2,
+ [0x1E92E]=0x2,
+ [0x1E92F]=0x2,
+ [0x1E930]=0x2,
+ [0x1E931]=0x2,
+ [0x1E932]=0x2,
+ [0x1E933]=0x2,
+ [0x1E934]=0x2,
+ [0x1E935]=0x2,
+ [0x1E936]=0x2,
+ [0x1E937]=0x2,
+ [0x1E938]=0x2,
+ [0x1E939]=0x2,
+ [0x1E93A]=0x2,
+ [0x1E93B]=0x2,
+ [0x1E93C]=0x2,
+ [0x1E93D]=0x2,
+ [0x1E93E]=0x2,
+ [0x1E93F]=0x2,
+ [0x1E940]=0x2,
+ [0x1E941]=0x2,
+ [0x1E942]=0x2,
+ [0x1E943]=0x2,
+ },
+} \ No newline at end of file
diff --git a/macros/luatex/generic/luaotfload/luaotfload-colors.lua b/macros/luatex/generic/luaotfload/luaotfload-colors.lua
new file mode 100644
index 0000000000..d9dabd1c6c
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-colors.lua
@@ -0,0 +1,414 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-colors.lua
+-- DESCRIPTION: part of luaotfload / font colors
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-colors",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / color",
+ license = "GPL v2.0",
+ author = "Khaled Hosny, Elie Roux, Philipp Gesang, Dohyun Kim, David Carlisle",
+ copyright = "Luaotfload Development Team"
+ }
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+--[[doc--
+
+buggy coloring with the pre_output_filter when expansion is enabled
+ · tfmdata for different expansion values is split over different objects
+ · in ``initializeexpansion()``, chr.expansion_factor is set, and only
+ those characters that have it are affected
+ · in constructors.scale: chr.expansion_factor = ve*1000 if commented out
+ makes the bug vanish
+
+explanation: http://tug.org/pipermail/luatex/2013-May/004305.html
+
+--doc]]--
+
+local logreport = luaotfload and luaotfload.log.report or print
+
+local nodedirect = node.direct
+local newnode = nodedirect.new
+local insert_node_before = nodedirect.insert_before
+local insert_node_after = nodedirect.insert_after
+local todirect = nodedirect.todirect
+local tonode = nodedirect.tonode
+local setfield = nodedirect.setfield
+local getid = nodedirect.getid
+local getfont = nodedirect.getfont
+local getlist = nodedirect.getlist
+local getsubtype = nodedirect.getsubtype
+local getnext = nodedirect.getnext
+local nodetail = nodedirect.tail
+local getattribute = nodedirect.has_attribute
+local setattribute = nodedirect.set_attribute
+
+local stringformat = string.format
+local identifiers = fonts.hashes.identifiers
+
+local add_color_callback --[[ this used to be a global‽ ]]
+
+--[[doc--
+This converts a single octet into a decimal with three digits of
+precision. The optional second argument limits precision to a single
+digit.
+--doc]]--
+
+--- string -> bool? -> string
+local hex_to_dec = function (hex,one) --- one isn’t actually used anywhere ...
+ if one then
+ return stringformat("%.1g", tonumber(hex, 16)/255)
+ else
+ return stringformat("%.3g", tonumber(hex, 16)/255)
+ end
+end
+
+--[[doc--
+Color string validator / parser.
+--doc]]--
+
+local lpeg = require"lpeg"
+local lpegmatch = lpeg.match
+local C, Cg, Ct, P, R, S = lpeg.C, lpeg.Cg, lpeg.Ct, lpeg.P, lpeg.R, lpeg.S
+
+local digit16 = R("09", "af", "AF")
+local opaque = S("fF") * S("fF")
+local octet = C(digit16 * digit16)
+
+local p_rgb = octet * octet * octet
+local p_rgba = p_rgb * (octet - opaque)
+local valid_digits = C(p_rgba + p_rgb) -- matches eight or six hex digits
+
+local p_Crgb = Cg(octet/hex_to_dec, "red") --- for captures
+ * Cg(octet/hex_to_dec, "green")
+ * Cg(octet/hex_to_dec, "blue")
+local p_Crgba = p_Crgb * Cg(octet/hex_to_dec, "alpha")
+local extract_color = Ct(p_Crgba + p_Crgb)
+
+--- string -> (string | nil)
+local sanitize_color_expression = function (digits)
+ digits = tostring(digits)
+ local sanitized = lpegmatch(valid_digits, digits)
+ if not sanitized then
+ logreport("both", 0, "color",
+ "%q is not a valid rgb[a] color expression",
+ digits)
+ return nil
+ end
+ return sanitized
+end
+
+--- something is carried around in ``res``
+--- for later use by color_handler() --- but what?
+
+local res = nil
+
+--- float -> unit
+local function pageresources(alpha)
+ res = res or {}
+ res[alpha] = true
+end
+
+--- we store results of below color handler as tuples of
+--- push/pop strings
+local color_cache = { } --- (string, (string * string)) hash_t
+
+--- string -> (string * string)
+local hex_to_rgba = function (digits)
+ if not digits then
+ return
+ end
+
+ --- this is called like a thousand times, so some
+ --- memoizing is in order.
+ local cached = color_cache[digits]
+ if not cached then
+ local push, pop
+ local rgb = lpegmatch(extract_color, digits)
+ if rgb.alpha then
+ pageresources(rgb.alpha)
+ push = stringformat(
+ "/TransGs%g gs %s %s %s rg",
+ rgb.alpha,
+ rgb.red,
+ rgb.green,
+ rgb.blue)
+ pop = "0 g /TransGs1 gs"
+ else
+ push = stringformat(
+ "%s %s %s rg",
+ rgb.red,
+ rgb.green,
+ rgb.blue)
+ pop = "0 g"
+ end
+ color_cache[digits] = { push, pop }
+ return push, pop
+ end
+
+ return cached[1], cached[2]
+end
+
+--- Luatex internal types
+
+local nodetype = node.id
+local glyph_t = nodetype("glyph")
+local hlist_t = nodetype("hlist")
+local vlist_t = nodetype("vlist")
+local whatsit_t = nodetype("whatsit")
+local disc_t = nodetype("disc")
+local pdfliteral_t = node.subtype("pdf_literal")
+local colorstack_t = node.subtype("pdf_colorstack")
+local mlist_to_hlist = node.mlist_to_hlist
+
+local color_callback
+local color_attr = luatexbase.new_attribute("luaotfload_color_attribute")
+
+-- (node * node * string * bool * (bool | nil)) -> (node * node * (string | nil))
+local color_whatsit
+color_whatsit = function (head, curr, color, push, tail)
+ local pushdata = hex_to_rgba(color)
+ local colornode = newnode(whatsit_t, colorstack_t)
+ setfield(colornode, "stack", 0)
+ setfield(colornode, "command", push and 1 or 2) -- 1: push, 2: pop
+ setfield(colornode, "data", push and pushdata or nil)
+ if tail then
+ head, curr = insert_node_after (head, curr, colornode)
+ else
+ head = insert_node_before(head, curr, colornode)
+ end
+ if not push and color:len() > 6 then
+ local colornode = newnode(whatsit_t, pdfliteral_t)
+ setfield(colornode, "mode", 2)
+ setfield(colornode, "data", "/TransGs1 gs")
+ if tail then
+ head, curr = insert_node_after (head, curr, colornode)
+ else
+ head = insert_node_before(head, curr, colornode)
+ end
+ end
+ color = push and color or nil
+ return head, curr, color
+end
+
+-- number -> string | nil
+local get_font_color = function (font_id)
+ local tfmdata = identifiers[font_id]
+ local font_color = tfmdata and tfmdata.properties and tfmdata.properties.color
+ return font_color
+end
+
+--[[doc--
+While the second argument and second returned value are apparently
+always nil when the function is called, they temporarily take string
+values during the node list traversal.
+--doc]]--
+
+--- (node * (string | nil)) -> (node * (string | nil))
+local node_colorize
+node_colorize = function (head, toplevel, current_color)
+ local n = head
+ while n do
+ local n_id = getid(n)
+
+ if n_id == hlist_t or n_id == vlist_t then
+ local n_list = getlist(n)
+ if getattribute(n_list, color_attr) then
+ if current_color then
+ head, n, current_color = color_whatsit(head, n, current_color, false)
+ end
+ else
+ n_list, current_color = node_colorize(n_list, false, current_color)
+ if current_color and getsubtype(n) == 1 then -- created by linebreak
+ n_list, _, current_color = color_whatsit(n_list, nodetail(n_list), current_color, false, true)
+ end
+ setfield(n, "head", n_list)
+ end
+
+ elseif n_id == glyph_t then
+ --- colorization is restricted to those fonts
+ --- that received the “color” property upon
+ --- loading (see ``setcolor()`` above)
+ local font_color = get_font_color(getfont(n))
+ if font_color ~= current_color then
+ if current_color then
+ head, n, current_color = color_whatsit(head, n, current_color, false)
+ end
+ if font_color then
+ head, n, current_color = color_whatsit(head, n, font_color, true)
+ end
+ end
+
+ if current_color and color_callback == "pre_linebreak_filter" then
+ local nn = getnext(n)
+ while nn and getid(nn) == glyph_t do
+ local font_color = get_font_color(getfont(nn))
+ if font_color == current_color then
+ n = nn
+ else
+ break
+ end
+ nn = getnext(nn)
+ end
+ if getid(nn) == disc_t then
+ head, n, current_color = color_whatsit(head, nn, current_color, false, true)
+ else
+ head, n, current_color = color_whatsit(head, n, current_color, false, true)
+ end
+ end
+
+ elseif n_id == whatsit_t then
+ if current_color then
+ head, n, current_color = color_whatsit(head, n, current_color, false)
+ end
+
+ end
+
+ n = getnext(n)
+ end
+
+ if toplevel and current_color then
+ head, _, current_color = color_whatsit(head, nodetail(head), current_color, false, true)
+ end
+
+ setattribute(head, color_attr, 1)
+ return head, current_color
+end
+
+local getpageres = pdf.getpageresources or function() return pdf.pageresources end
+local setpageres = pdf.setpageresources or function(s) pdf.pageresources = s end
+local catat11 = luatexbase.registernumber("catcodetable@atletter")
+local gettoks, scantoks = tex.gettoks, tex.scantoks
+local pgf = { bye = "pgfutil@everybye", extgs = "\\pgf@sys@addpdfresource@extgs@plain" }
+
+--- node -> node
+local color_handler = function (head)
+ head = todirect(head)
+ head = node_colorize(head, true)
+ head = tonode(head)
+
+ -- now append our page resources
+ if res then
+ res["1"] = true
+ if scantoks and pgf.bye and not pgf.loaded then
+ pgf.loaded = token.create(pgf.bye).cmdname == "assign_toks"
+ pgf.bye = pgf.loaded and pgf.bye
+ end
+ local tpr = pgf.loaded and gettoks(pgf.bye) or getpageres() or ""
+
+ local t = ""
+ for k in pairs(res) do
+ local str = stringformat("/TransGs%s<</ca %s>>", k, k) -- don't touch stroking elements
+ if not tpr:find(str) then
+ t = t .. str
+ end
+ end
+ if t ~= "" then
+ if pgf.loaded then
+ scantoks("global", pgf.bye, catat11, stringformat("%s{%s}%s", pgf.extgs, t, tpr))
+ else
+ local tpr, n = tpr:gsub("/ExtGState<<", "%1"..t)
+ if n == 0 then
+ tpr = stringformat("%s/ExtGState<<%s>>", tpr, t)
+ end
+ setpageres(tpr)
+ end
+ end
+ res = nil -- reset res
+ end
+ return head
+end
+
+local color_callback_name = "luaotfload.color_handler"
+local color_callback_activated = 0
+local add_to_callback = luatexbase.add_to_callback
+
+--- unit -> bool
+local mlist_to_hlist_initial = function ()
+ local cdesc = luatexbase.callback_descriptions "mlist_to_hlist"
+ return cdesc and cdesc[1] == color_callback_name
+end
+
+--- unit -> unit
+add_color_callback = function ( )
+ color_callback = config.luaotfload.run.color_callback
+ if not color_callback then
+ color_callback = "post_linebreak_filter"
+ end
+
+ if color_callback_activated == 0 then
+ add_to_callback(color_callback,
+ color_handler,
+ color_callback_name)
+ add_to_callback("hpack_filter",
+ function (head, groupcode)
+ if groupcode == "hbox" or
+ groupcode == "adjusted_hbox" or
+ groupcode == "align_set" then
+ head = color_handler(head)
+ end
+ return head
+ end,
+ color_callback_name)
+ add_to_callback("mlist_to_hlist",
+ function (head, display_type, need_penalties)
+ if mlist_to_hlist_initial () then
+ head = mlist_to_hlist(head, display_type, need_penalties)
+ end
+ if display_type == "text" then
+ return head
+ end
+ return color_handler(head)
+ end,
+ color_callback_name)
+ color_callback_activated = 1
+ end
+end
+
+--[[doc--
+``setcolor`` modifies tfmdata.properties.color in place
+--doc]]--
+
+--- fontobj -> string -> unit
+---
+--- (where “string” is a rgb value as three octet
+--- hexadecimal, with an optional fourth transparency
+--- value)
+---
+local setcolor = function (tfmdata, value)
+ local sanitized = sanitize_color_expression(value)
+ local properties = tfmdata.properties
+
+ if sanitized then
+ properties.color = sanitized
+ add_color_callback()
+ end
+end
+
+return function ()
+ logreport = luaotfload.log.report
+ if not fonts then
+ logreport ("log", 0, "color",
+ "OTF mechanisms missing -- did you forget to \z
+ load a font loader?")
+ return false
+ end
+ fonts.handlers.otf.features.register {
+ name = "color",
+ description = "color",
+ initializers = {
+ base = setcolor,
+ node = setcolor,
+ }
+ }
+ return true
+end
+
+-- vim:tw=71:sw=4:ts=4:expandtab
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload-conf.pdf b/macros/luatex/generic/luaotfload/luaotfload-conf.pdf
new file mode 100644
index 0000000000..7ea1cd2882
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-conf.pdf
Binary files differ
diff --git a/macros/luatex/generic/luaotfload/luaotfload-configuration.lua b/macros/luatex/generic/luaotfload/luaotfload-configuration.lua
new file mode 100644
index 0000000000..12fc63e0d5
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-configuration.lua
@@ -0,0 +1,1034 @@
+-------------------------------------------------------------------------------
+-- FILE: luaotfload-configuration.lua
+-- DESCRIPTION: part of luaotfload / luaotfload-tool / config file reader
+-- AUTHOR: Philipp Gesang, <phg@phi-gamma.net>
+-- AUTHOR: Dohyun Kim <nomosnomos@gmail.com>
+-------------------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-configuration",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / config file reader",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+------------------------------
+
+local status_file = "luaotfload-status"
+local luaotfloadstatus = require (status_file)
+
+local string = string
+local stringfind = string.find
+local stringformat = string.format
+local stringstrip = string.strip
+local stringsub = string.sub
+
+local tableappend = table.append
+local tableconcat = table.concat
+local tablecopy = table.copy
+local table = table
+local tabletohash = table.tohash
+
+local math = math
+local mathfloor = math.floor
+
+local io = io
+local ioloaddata = io.loaddata
+local iopopen = io.popen
+local iowrite = io.write
+
+local os = os
+local osdate = os.date
+local osgetenv = os.getenv
+
+local lpeg = require "lpeg"
+local lpegmatch = lpeg.match
+local commasplitter = lpeg.splitat ","
+local equalssplitter = lpeg.splitat "="
+
+local kpseexpand_path = kpse.expand_path
+
+local lfs = lfs
+local lfsisfile = lfs.isfile
+local lfsisdir = lfs.isdir
+
+local file = file
+local filejoin = file.join
+local filereplacesuffix = file.replacesuffix
+
+local logreport = print -- overloaded later
+local getwritablepath = caches.getwritablepath
+
+
+local config_parser -- set later during init
+local stripslashes -- set later during init
+
+-------------------------------------------------------------------------------
+--- SETTINGS
+-------------------------------------------------------------------------------
+
+local path_t = 0
+local kpse_t = 1
+
+local val_home = kpseexpand_path "~"
+local val_xdg_config_home = kpseexpand_path "$XDG_CONFIG_HOME"
+
+if val_xdg_config_home == "" then val_xdg_config_home = "~/.config" end
+
+local config_paths = {
+ --- needs adapting for those other OS
+ { path_t, "./luaotfload.conf" },
+ { path_t, "./luaotfloadrc" },
+ { path_t, filejoin (val_xdg_config_home, "luaotfload/luaotfload.conf") },
+ { path_t, filejoin (val_xdg_config_home, "luaotfload/luaotfloadrc") },
+ { path_t, filejoin (val_home, ".luaotfloadrc") },
+ { kpse_t, "luaotfloadrc" },
+ { kpse_t, "luaotfload.conf" },
+}
+
+local valid_formats = tabletohash {
+ "otf", "ttc", "ttf", "afm", "pfb"
+}
+
+local default_anon_sequence = {
+ "tex", "path", "name"
+}
+
+local valid_resolvers = tabletohash {
+ "tex", "path", "name", "file", "my"
+}
+
+local feature_presets = {
+ arab = tabletohash {
+ "ccmp", "locl", "isol", "fina", "fin2",
+ "fin3", "medi", "med2", "init", "rlig",
+ "calt", "liga", "cswh", "mset", "curs",
+ "kern", "mark", "mkmk",
+ },
+ deva = tabletohash {
+ "ccmp", "locl", "init", "nukt", "akhn",
+ "rphf", "blwf", "half", "pstf", "vatu",
+ "pres", "blws", "abvs", "psts", "haln",
+ "calt", "blwm", "abvm", "dist", "kern",
+ "mark", "mkmk",
+ },
+ khmr = tabletohash {
+ "ccmp", "locl", "pref", "blwf", "abvf",
+ "pstf", "pres", "blws", "abvs", "psts",
+ "clig", "calt", "blwm", "abvm", "dist",
+ "kern", "mark", "mkmk",
+ },
+ thai = tabletohash {
+ "ccmp", "locl", "liga", "kern", "mark",
+ "mkmk",
+ },
+}
+
+--[[doc--
+
+ We allow loading of arbitrary fontloaders. Nevertheless we maintain a
+ list of the “official” ones shipped with Luaotfload so we can emit a
+ different log message.
+
+--doc]]--
+
+local default_fontloader = function ()
+ return luaotfloadstatus and luaotfloadstatus.notes.loader or "reference"
+end
+
+local registered_loaders = {
+ default = default_fontloader (),
+ reference = "reference",
+ unpackaged = "unpackaged",
+ context = "context",
+}
+
+local pick_fontloader = function (s)
+ local ldr = registered_loaders[s]
+ if ldr ~= nil and type (ldr) == "string" then
+ logreport ("log", 2, "conf", "Using predefined fontloader \"%s\".", ldr)
+ return ldr
+ end
+ local idx = stringfind (s, ":")
+ if idx and idx > 2 then
+ if stringsub (s, 1, idx - 1) == "context" then
+ local pth = stringsub (s, idx + 1)
+ pth = stringstrip (pth)
+ logreport ("log", 2, "conf", "Context base path specified at \"%s\".", pth)
+ if lfsisdir (pth) then
+ logreport ("log", 5, "conf", "Context base path exists at \"%s\".", pth)
+ return pth
+ end
+ pth = kpseexpand_path (pth)
+ if lfsisdir (pth) then
+ logreport ("log", 5, "conf", "Context base path exists at \"%s\".", pth)
+ return pth
+ end
+ logreport ("both", 0, "conf", "Context base path not found at \"%s\".", pth)
+ end
+ end
+ return nil
+end
+
+--[[doc--
+
+ The ``post_linebreak_filter`` has been made the default callback for
+ hooking the colorizer into. This helps with the linebreaking whose
+ inserted hyphens would remain unaffected by the coloring otherwise.
+
+ http://tex.stackexchange.com/q/238539/14066
+
+--doc]]--
+
+local permissible_color_callbacks = {
+ default = "post_linebreak_filter",
+ pre_linebreak_filter = "pre_linebreak_filter",
+ post_linebreak_filter = "post_linebreak_filter",
+ pre_output_filter = "pre_output_filter",
+}
+
+
+-------------------------------------------------------------------------------
+--- DEFAULTS
+-------------------------------------------------------------------------------
+
+local default_config = {
+ db = {
+ formats = "otf,ttf,ttc",
+ scan_local = false,
+ skip_read = false,
+ strip = true,
+ update_live = true,
+ compress = true,
+ max_fonts = 2^51,
+ designsize_dimen= "bp",
+ },
+ run = {
+ anon_sequence = default_anon_sequence,
+ resolver = "cached",
+ definer = "patch",
+ log_level = 0,
+ color_callback = "post_linebreak_filter",
+ fontloader = default_fontloader (),
+ },
+ misc = {
+ bisect = false,
+ version = luaotfload.version,
+ statistics = false,
+ termwidth = nil,
+ },
+ paths = {
+ names_dir = "names",
+ cache_dir = "fonts",
+ index_file = "luaotfload-names.lua",
+ lookups_file = "luaotfload-lookup-cache.lua",
+ lookup_path_lua = nil,
+ lookup_path_luc = nil,
+ index_path_lua = nil,
+ index_path_luc = nil,
+ },
+ default_features = {
+ global = { mode = "node" },
+ dflt = tabletohash {
+ "ccmp", "locl", "rlig", "liga", "clig",
+ "kern", "mark", "mkmk", 'itlc',
+ },
+
+ arab = feature_presets.arab,
+ syrc = feature_presets.arab,
+ mong = feature_presets.arab,
+ nko = feature_presets.arab,
+
+ deva = feature_presets.deva,
+ beng = feature_presets.deva,
+ guru = feature_presets.deva,
+ gujr = feature_presets.deva,
+ orya = feature_presets.deva,
+ taml = feature_presets.deva,
+ telu = feature_presets.deva,
+ knda = feature_presets.deva,
+ mlym = feature_presets.deva,
+ sinh = feature_presets.deva,
+
+ khmr = feature_presets.khmr,
+ tibt = feature_presets.khmr,
+ thai = feature_presets.thai,
+ lao = feature_presets.thai,
+
+ hang = tabletohash { "ccmp", "ljmo", "vjmo", "tjmo", },
+ },
+}
+
+-------------------------------------------------------------------------------
+--- RECONFIGURATION TASKS
+-------------------------------------------------------------------------------
+
+--[[doc--
+
+ Procedures to be executed in order to put the new configuration into effect.
+
+--doc]]--
+
+local reconf_tasks = nil
+
+local min_terminal_width = 40
+
+--- The “termwidth” value is only considered when printing
+--- short status messages, e.g. when building the database
+--- online.
+local check_termwidth = function ()
+ if config.luaotfload.misc.termwidth == nil then
+ local tw = 79
+ if not ( os.type == "windows" --- Assume broken terminal.
+ or osgetenv "TERM" == "dumb")
+ then
+ local p = iopopen "tput cols"
+ if p then
+ result = tonumber (p:read "*all")
+ p:close ()
+ if result then
+ tw = result
+ else
+ logreport ("log", 2, "db", "tput returned non-number.")
+ end
+ else
+ logreport ("log", 2, "db", "Shell escape disabled or tput executable missing.")
+ logreport ("log", 2, "db", "Assuming 79 cols terminal width.")
+ end
+ end
+ config.luaotfload.misc.termwidth = tw
+ end
+ return true
+end
+
+local set_font_filter = function ()
+ local names = fonts.names
+ if names and names.set_font_filter then
+ local formats = config.luaotfload.db.formats
+ if not formats or formats == "" then
+ formats = default_config.db.formats
+ end
+ names.set_font_filter (formats)
+ end
+ return true
+end
+
+local set_size_dimension = function ()
+ local names = fonts.names
+ if names and names.set_size_dimension then
+ local dim = config.luaotfload.db.designsize_dimen
+ if not dim or dim == "" then
+ dim = default_config.db.designsize_dimen
+ end
+ names.set_size_dimension (dim)
+ end
+ return true
+end
+
+local set_name_resolver = function ()
+ local names = fonts.names
+ if names and names.resolve_cached then
+ --- replace the resolver from luatex-fonts
+ if config.luaotfload.db.resolver == "cached" then
+ logreport ("both", 2, "cache", "Caching of name: lookups active.")
+ names.resolvespec = fonts.names.lookup_font_name_cached
+ else
+ names.resolvespec = fonts.names.lookup_font_name
+ end
+ end
+ return true
+end
+
+local set_loglevel = function ()
+ if luaotfload then
+ luaotfload.log.set_loglevel (config.luaotfload.run.log_level)
+ return true
+ end
+ return false
+end
+
+local build_cache_paths = function ()
+ local paths = config.luaotfload.paths
+ local prefix = getwritablepath (paths.names_dir, "")
+
+ if not prefix then
+ luaotfload.error ("Impossible to find a suitable writeable cache...")
+ return false
+ end
+
+ prefix = lpegmatch (stripslashes, prefix)
+ logreport ("log", 0, "conf", "Root cache directory is %s.", prefix)
+
+ local index_file = filejoin (prefix, paths.index_file)
+ local lookups_file = filejoin (prefix, paths.lookups_file)
+
+ paths.prefix = prefix
+ paths.index_path_lua = filereplacesuffix (index_file, "lua")
+ paths.index_path_luc = filereplacesuffix (index_file, "luc")
+ paths.lookup_path_lua = filereplacesuffix (lookups_file, "lua")
+ paths.lookup_path_luc = filereplacesuffix (lookups_file, "luc")
+ return true
+end
+
+
+local set_default_features = function ()
+ local default_features = config.luaotfload.default_features
+ luaotfload.features = luaotfload.features or {
+ global = { },
+ defaults = { },
+ }
+ current_features = luaotfload.features
+ for var, val in next, default_features do
+ if var == "global" then
+ current_features.global = val
+ else
+ current_features.defaults[var] = val
+ end
+ end
+ return true
+end
+
+reconf_tasks = {
+ { "Set the log level" , set_loglevel },
+ { "Build cache paths" , build_cache_paths },
+ { "Check terminal dimensions" , check_termwidth },
+ { "Set the font filter" , set_font_filter },
+ { "Set design size dimension" , set_size_dimension },
+ { "Install font name resolver", set_name_resolver },
+ { "Set default features" , set_default_features },
+}
+
+-------------------------------------------------------------------------------
+--- OPTION SPECIFICATION
+-------------------------------------------------------------------------------
+
+local string_t = "string"
+local table_t = "table"
+local number_t = "number"
+local boolean_t = "boolean"
+local function_t = "function"
+
+local tointeger = function (n)
+ n = tonumber (n)
+ if n then
+ return mathfloor (n + 0.5)
+ end
+end
+
+local toarray = function (s)
+ local fields = { lpegmatch (commasplitter, s) }
+ local ret = { }
+ for i = 1, #fields do
+ local field = stringstrip (fields[i])
+ if field and field ~= "" then
+ ret[#ret + 1] = field
+ end
+ end
+ return ret
+end
+
+local tohash = function (s)
+ local result = { }
+ local fields = toarray (s)
+ for _, field in next, fields do
+ local var, val
+ if stringfind (field, "=") then
+ local tmp
+ var, tmp = lpegmatch (equalssplitter, field)
+ if tmp == "true" or tmp == "yes" then val = true else val = tmp end
+ else
+ var, val = field, true
+ end
+ result[var] = val
+ end
+ return result
+end
+
+local option_spec = {
+ db = {
+ formats = {
+ in_t = string_t,
+ out_t = string_t,
+ transform = function (f)
+ local fields = toarray (f)
+
+ --- check validity
+ if not fields then
+ logreport ("both", 0, "conf",
+ "Expected list of identifiers, got %q.", f)
+ return nil
+ end
+
+ --- strip dupes
+ local known = { }
+ local result = { }
+ for i = 1, #fields do
+ local field = fields[i]
+ if known[field] ~= true then
+ --- yet unknown, tag as seen
+ known[field] = true
+ --- include in output if valid
+ if valid_formats[field] == true then
+ result[#result + 1] = field
+ else
+ logreport ("both", 4, "conf",
+ "Invalid font format identifier %q, ignoring.",
+ field)
+ end
+ end
+ end
+ if #result == 0 then
+ --- force defaults
+ return nil
+ end
+ return tableconcat (result, ",")
+ end
+ },
+ scan_local = { in_t = boolean_t, },
+ skip_read = { in_t = boolean_t, },
+ strip = { in_t = boolean_t, },
+ update_live = { in_t = boolean_t, },
+ compress = { in_t = boolean_t, },
+ max_fonts = {
+ in_t = number_t,
+ out_t = number_t, --- TODO int_t from 5.3.x on
+ transform = tointeger,
+ },
+ designsize_dimen = {
+ in_t = string_t,
+ out_t = string_t,
+ },
+ },
+ run = {
+ anon_sequence = {
+ in_t = string_t,
+ out_t = table_t,
+ transform = function (s)
+ if s ~= "default" then
+ local bits = { lpegmatch (commasplitter, s) }
+ if next (bits) then
+ local seq = { }
+ local done = { }
+ for i = 1, #bits do
+ local bit = bits [i]
+ if valid_resolvers [bit] then
+ if not done [bit] then
+ done [bit] = true
+ seq [#seq + 1] = bit
+ else
+ logreport ("both", 0, "conf",
+ "ignoring duplicate resolver %s at position %d \z
+ in lookup sequence",
+ bit, i)
+ end
+ else
+ logreport ("both", 0, "conf",
+ "lookup sequence contains invalid item %s \z
+ at position %d.",
+ bit, i)
+ end
+ end
+ if next (seq) then
+ logreport ("both", 2, "conf",
+ "overriding anon lookup sequence %s.",
+ tableconcat (seq, ","))
+ return seq
+ end
+ end
+ end
+ return default_anon_sequence
+ end
+ },
+ live = { in_t = boolean_t, }, --- false for the tool, true for TeX run
+ resolver = {
+ in_t = string_t,
+ out_t = string_t,
+ transform = function (r) return r == "normal" and r or "cached" end,
+ },
+ definer = {
+ in_t = string_t,
+ out_t = string_t,
+ transform = function (d)
+ if d == "generic" or d == "patch"
+ or d == "info_generic" or d == "info_patch"
+ then
+ return d
+ end
+ return "patch"
+ end,
+ },
+ fontloader = {
+ in_t = string_t,
+ out_t = string_t,
+ transform = function (id)
+ local ldr = pick_fontloader (id)
+ if ldr ~= nil then
+ return ldr
+ end
+ logreport ("log", 0, "conf",
+ "Requested fontloader \"%s\" not defined, "
+ .. "use at your own risk.",
+ id)
+ return id
+ end,
+ },
+ log_level = {
+ in_t = number_t,
+ out_t = number_t, --- TODO int_t from 5.3.x on
+ transform = tointeger,
+ },
+ color_callback = {
+ in_t = string_t,
+ out_t = string_t,
+ transform = function (cb_spec)
+ --- These are the two that make sense.
+ local cb = permissible_color_callbacks[cb_spec]
+ if cb then
+ logreport ("log", 3, "conf",
+ "Using callback \"%s\" for font colorization.",
+ cb)
+ return cb
+ end
+ logreport ("log", 0, "conf",
+ "Requested callback identifier \"%s\" invalid, "
+ .. "falling back to default.",
+ cb_spec)
+ return permissible_color_callbacks.default
+ end,
+ },
+ },
+ misc = {
+ bisect = { in_t = boolean_t, }, --- doesn’t make sense in a config file
+ version = { in_t = string_t, },
+ statistics = { in_t = boolean_t, },
+ termwidth = {
+ in_t = number_t,
+ out_t = number_t,
+ transform = function (w)
+ w = tointeger (w)
+ if w < min_terminal_width then
+ return min_terminal_width
+ end
+ return w
+ end,
+ },
+ },
+ paths = {
+ names_dir = { in_t = string_t, },
+ cache_dir = { in_t = string_t, },
+ index_file = { in_t = string_t, },
+ lookups_file = { in_t = string_t, },
+ lookup_path_lua = { in_t = string_t, },
+ lookup_path_luc = { in_t = string_t, },
+ index_path_lua = { in_t = string_t, },
+ index_path_luc = { in_t = string_t, },
+ },
+ default_features = {
+ __default = { in_t = string_t, out_t = table_t, transform = tohash, },
+ },
+}
+
+-------------------------------------------------------------------------------
+--- FORMATTERS
+-------------------------------------------------------------------------------
+
+local commented = function (str)
+ return ";" .. str
+end
+
+local underscore_replacer = lpeg.replacer ("_", "-", true)
+
+local dashed = function (var)
+ --- INI spec dictates that dashes are valid in variable names, not
+ --- underscores.
+ return underscore_replacer (var) or var
+end
+
+local indent = " "
+local format_string = function (var, val)
+ return stringformat (indent .. "%s = %s", var, val)
+end
+
+local format_integer = function (var, val)
+ return stringformat (indent .. "%s = %d", var, val)
+end
+
+local format_boolean = function (var, val)
+ return stringformat (indent .. "%s = %s", var, val == true and "true" or "false")
+end
+
+local format_keyval = function (var, val)
+ local list = { }
+ local keys = table.sortedkeys (val)
+ for i = 1, #keys do
+ local key = keys[i]
+ local subval = val[key]
+ if subval == true then
+ list[#list + 1] = stringformat ("%s", key)
+ else
+ list[#list + 1] = stringformat ("%s=%s", key, val[key])
+ end
+ end
+ if next (list) then
+ return stringformat (indent .. "%s = %s",
+ var,
+ tableconcat (list, ","))
+ end
+end
+
+local format_list = function (var, val)
+ local elts = { }
+ for i = 1, #val do elts [i] = val [i] end
+ if next (elts) then
+ return stringformat (indent .. "%s = %s",
+ var, tableconcat (elts, ","))
+ end
+end
+
+local format_section = function (title)
+ return stringformat ("[%s]", dashed (title))
+end
+
+local conf_header = [==[
+;;-----------------------------------------------------------------------------
+;; Luaotfload Configuration
+;;-----------------------------------------------------------------------------
+;;
+;; This file was generated by luaotfload-tool
+;; on %s. Configuration variables
+;; are documented in the manual to luaotfload.conf(5).
+;;
+;;-----------------------------------------------------------------------------
+
+]==]
+
+local conf_footer = [==[
+
+;; vim:filetype=dosini:expandtab:shiftwidth=2
+]==]
+
+--- Each dumpable variable (the ones mentioned in the man page) receives a
+--- formatter that will be used in dumping the variable. Each value receives a
+--- “commented” flag that indicates whether or not the line should be printed
+--- as a comment.
+
+local formatters = {
+ db = {
+ compress = { false, format_boolean },
+ designsize_dimen = { false, format_string },
+ formats = { false, format_string },
+ max_fonts = { false, format_integer },
+ scan_local = { false, format_boolean },
+ skip_read = { false, format_boolean },
+ strip = { false, format_boolean },
+ update_live = { false, format_boolean },
+ },
+ default_features = {
+ __default = { true, format_keyval },
+ },
+ misc = {
+ bisect = { false, format_boolean },
+ statistics = { false, format_boolean },
+ termwidth = { true , format_integer },
+ version = { true , format_string },
+ },
+ paths = {
+ cache_dir = { false, format_string },
+ names_dir = { false, format_string },
+ index_file = { false, format_string },
+ lookups_file = { false, format_string },
+ },
+ run = {
+ anon_sequence = { false, format_list },
+ color_callback = { false, format_string },
+ definer = { false, format_string },
+ fontloader = { false, format_string },
+ log_level = { false, format_integer },
+ resolver = { false, format_string },
+ },
+}
+
+-------------------------------------------------------------------------------
+--- MAIN FUNCTIONALITY
+-------------------------------------------------------------------------------
+
+--[[doc--
+
+ tilde_expand -- Rudimentary tilde expansion; covers just the “substitute ‘~’
+ by the current users’s $HOME” part.
+
+--doc]]--
+
+local tilde_expand = function (p)
+ if #p > 2 then
+ if stringsub (p, 1, 2) == "~/" then
+ local homedir = osgetenv "HOME"
+ if homedir and lfsisdir (homedir) then
+ p = filejoin (homedir, stringsub (p, 3))
+ end
+ end
+ end
+ return p
+end
+
+local resolve_config_path = function ()
+ for i = 1, #config_paths do
+ local t, p = unpack (config_paths[i])
+ local fullname
+ if t == kpse_t then
+ fullname = kpse.find_file (p)
+ logreport ("both", 6, "conf", "kpse lookup: %s -> %s.", p, fullname)
+ elseif t == path_t then
+ local expanded = tilde_expand (p)
+ if lfsisfile (expanded) then
+ fullname = expanded
+ end
+ logreport ("both", 6, "conf", "path lookup: %s -> %s.", p, fullname)
+ end
+ if fullname then
+ logreport ("both", 3, "conf", "Reading configuration file at %q.", fullname)
+ return fullname
+ end
+ end
+ logreport ("both", 2, "conf", "No configuration file found.")
+ return false
+end
+
+local add_config_paths = function (t)
+ if not next (t) then
+ return
+ end
+ local result = { }
+ for i = 1, #t do
+ local path = t[i]
+ result[#result + 1] = { path_t, path }
+ end
+ config_paths = tableappend (result, config_paths)
+end
+
+local process_options = function (opts)
+ local new = { }
+ for i = 1, #opts do
+ local section = opts[i]
+ local title = section.section.title
+ local vars = section.variables
+
+ if not title then --- trigger warning: arrow code ahead
+ logreport ("both", 2, "conf", "Section %d lacks a title; skipping.", i)
+ elseif not vars then
+ logreport ("both", 2, "conf", "Section %d (%s) lacks a variable section; skipping.", i, title)
+ else
+ local spec = option_spec[title]
+ if not spec then
+ logreport ("both", 2, "conf", "Section %d (%s) unknown; skipping.", i, title)
+ else
+ local newsection = new[title]
+ if not newsection then
+ newsection = { }
+ new[title] = newsection
+ end
+
+ for var, val in next, vars do
+ local vspec = spec[var] or spec.__default
+ local t_val = type (val)
+ if not vspec then
+ logreport ("both", 2, "conf",
+ "Section %d (%s): invalid configuration variable %q (%q); ignoring.",
+ i, title,
+ var, tostring (val))
+ elseif t_val ~= vspec.in_t then
+ logreport ("both", 2, "conf",
+ "Section %d (%s): type mismatch of input value %q (%q, %s != %s); ignoring.",
+ i, title,
+ var, tostring (val), t_val, vspec.in_t)
+ else --- type matches
+ local transform = vspec.transform
+ if transform then
+ local dval
+ local t_transform = type (transform)
+ if t_transform == function_t then
+ dval = transform (val)
+ elseif t_transform == table_t then
+ dval = transform[val]
+ end
+ if dval then
+ local out_t = vspec.out_t
+ if out_t then
+ local t_dval = type (dval)
+ if t_dval == out_t then
+ newsection[var] = dval
+ else
+ logreport ("both", 2, "conf",
+ "Section %d (%s): type mismatch of derived value of %q (%q, %s != %s); ignoring.",
+ i, title,
+ var, tostring (dval), t_dval, out_t)
+ end
+ else
+ newsection[var] = dval
+ end
+ else
+ logreport ("both", 2, "conf",
+ "Section %d (%s): value of %q could not be derived via %s from input %q; ignoring.",
+ i, title, var, t_transform, tostring (val))
+ end
+ else --- insert as is
+ newsection[var] = val
+ end
+ end
+ end
+ end
+ end
+ end
+ return new
+end
+
+local apply
+apply = function (old, new)
+ if not new then
+ if not old then
+ return false
+ end
+ return tablecopy (old)
+ elseif not old then
+ return tablecopy (new)
+ end
+ local result = tablecopy (old)
+ for name, section in next, new do
+ local t_section = type (section)
+ if t_section ~= table_t then
+ logreport ("both", 1, "conf",
+ "Error applying configuration: entry %s is %s, expected table.",
+ section, t_section)
+ --- ignore
+ else
+ local currentsection = result[name]
+ for var, val in next, section do
+ currentsection[var] = val
+ end
+ end
+ end
+ result.status = luaotfloadstatus
+ return result
+end
+
+local reconfigure = function ()
+ for i = 1, #reconf_tasks do
+ local name, task = unpack (reconf_tasks[i])
+ logreport ("both", 3, "conf", "Launch post-configuration task %q.", name)
+ if not task () then
+ logreport ("both", 0, "conf", "Post-configuration task %q failed.", name)
+ return false
+ end
+ end
+ return true
+end
+
+local read = function (extra)
+ if extra then
+ add_config_paths (extra)
+ end
+
+ local readme = resolve_config_path ()
+ if readme == false then
+ logreport ("both", 2, "conf", "No configuration file.")
+ return false
+ end
+
+ local raw = ioloaddata (readme)
+ if not raw then
+ logreport ("both", 2, "conf", "Error reading the configuration file %q.", readme)
+ return false
+ end
+
+ local parsed = lpegmatch (config_parser, raw)
+ if not parsed then
+ logreport ("both", 2, "conf", "Error parsing configuration file %q.", readme)
+ return false
+ end
+
+ local ret, msg = process_options (parsed)
+ if not ret then
+ logreport ("both", 2, "conf", "File %q is not a valid configuration file.", readme)
+ logreport ("both", 2, "conf", "Error: %s", msg)
+ return false
+ end
+ return ret
+end
+
+local apply_defaults = function ()
+ local defaults = default_config
+ local vars = read ()
+ --- Side-effects galore ...
+ config.luaotfload = apply (defaults, vars)
+ return reconfigure ()
+end
+
+local dump = function ()
+ local sections = table.sortedkeys (config.luaotfload)
+ local confdata = { }
+ for i = 1, #sections do
+ local section = sections[i]
+ local vars = config.luaotfload[section]
+ local varnames = table.sortedkeys (vars)
+ local sformats = formatters[section]
+ if sformats then
+ confdata[#confdata + 1] = format_section (section)
+ for j = 1, #varnames do
+ local var = varnames[j]
+ local val = vars[var]
+ local comment, sformat = unpack (sformats[var] or { })
+ if not sformat then
+ comment, sformat = unpack (sformats.__default or { })
+ end
+
+ if sformat then
+ local dashedvar = dashed (var)
+ if comment then
+ confdata[#confdata + 1] = commented (sformat (dashedvar, val))
+ else
+ confdata[#confdata + 1] = sformat (dashedvar, val)
+ end
+ end
+
+ end
+ confdata[#confdata + 1] = ""
+ end
+ end
+ if next(confdata) then
+ iowrite (stringformat (conf_header,
+ osdate ("%Y-%m-d %H:%M:%S", os.time ())))
+ iowrite (tableconcat (confdata, "\n"))
+ iowrite (conf_footer)
+ end
+end
+
+-------------------------------------------------------------------------------
+--- EXPORTS
+-------------------------------------------------------------------------------
+
+return function ()
+ config.luaotfload = { }
+ logreport = luaotfload.log.report
+ local parsers = luaotfload.parsers
+ config_parser = parsers.config
+ stripslashes = parsers.stripslashes
+
+ luaotfload.default_config = default_config
+ config.actions = {
+ read = read,
+ apply = apply,
+ apply_defaults = apply_defaults,
+ reconfigure = reconfigure,
+ dump = dump,
+ }
+ if not apply_defaults () then
+ logreport ("log", 0, "load",
+ "Configuration unsuccessful: error loading default settings.")
+ end
+ return true
+end
diff --git a/macros/luatex/generic/luaotfload/luaotfload-database.lua b/macros/luatex/generic/luaotfload/luaotfload-database.lua
new file mode 100644
index 0000000000..a932456b6a
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-database.lua
@@ -0,0 +1,3764 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-database.lua
+-- DESCRIPTION: part of luaotfload / luaotfload-tool / font database
+-----------------------------------------------------------------------
+do -- block to avoid to many local variables error
+ local ProvidesLuaModule = {
+ name = "luaotfload-database",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / database",
+ license = "GPL v2.0",
+ author = "Khaled Hosny, Elie Roux, Philipp Gesang, Marcel Krüger",
+ copyright = "Luaotfload Development Team",
+ }
+
+ if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+ end
+end
+
+--[[doc--
+
+ With version 2.7 we killed of the Fontforge libraries in favor of
+ the Lua implementation of the OT format reader. There were many
+ reasons to do this on top of the fact that FF won’t be around at
+ version 1.0 anymore: In addition to maintainability, memory safety
+ and general code hygiene, the new reader shows an amazing
+ performance: Scanning of the 3200 font files on my system takes
+ around 23 s now, as opposed to 74 s with the Fontforge libs. Memory
+ usage has improved drastically as well, as illustrated by these
+ profiles:
+
+ GB
+ 1.324^ #
+ | #
+ | ::#
+ | : #::
+ | @: #:
+ | @: #:
+ | @@@: #:
+ | @@@ @: #:
+ | @@ @ @ @: #:
+ | @ @@:@ @ @: #: :
+ | @@ : @ :@ @ @: #: :
+ | @@: ::@@ :@@ ::@ :@ @ @: #: : :::
+ | @@ : :: @@ :@ : @ :@ @ @: #: : :: :
+ | @@ : ::: @@ :@ ::: @ :@ @ @: #: :: :: :
+ | @@@@ :: :::: @@ :@ : : @ :@ @ @: #: :: :::: ::
+ | :@ @@ :: :::: @@ :@ : :: : @ :@ @ @: #: :: :: :: ::
+ | @:@ @@ :: ::::: @@ :@ : :::: : @ :@ @ @: #: :::: :::: :: ::
+ | @@:@ @@ :: ::::::: @@ :@ : : :: : @ :@ @ @: #: ::: @: :: :: ::@
+ | @@@:@ @@ :: :: ::::: @@ :@ ::: :: : @ :@ @ @: #: ::: @: :: :: ::@
+ | @@@@@:@ @@ ::::::: ::::: @@ :@ ::: :: : @ :@ @ @: #: ::: ::@: :: :: ::@
+ 0 +----------------------------------------------------------------------->GB
+ 0 16.29
+
+ This is the memory usage during a complete database rebuild with
+ the Fontforge libraries. The same action using the new
+ ``getinfo()`` method gives a different picture:
+
+ MB
+ 43.37^ #
+ | @ @ @#
+ | @@ @ @ @# :
+ | @@@ : @: @ @ @# :
+ | @ @@@ : : @: @ @: :@# :
+ | @ @ @@@ : : @: @ @: :@# :
+ | @ : : :@ @@@:::: @::@ @: :@#:: :
+ | :: : @ : @ : :::@ @ :@@@:::::@::@ @:::@#::::
+ | : @ : :: : :@:: :@: :::::@ @ :@@@:::::@::@:@:::@#::::
+ | :: :@ : @ ::@:@:::@:: :@: :::::@: :@ :@@@:::::@::@:@:::@#::::
+ | :: :@::: :@ ::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::::@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | ::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ | :::: :@::::@::: :@:::@:@: :@::::@::::::::@:::@::@@@:::::@::@:@:::@#::::
+ 0 +----------------------------------------------------------------------->GB
+ 0 3.231
+
+ FF peaks at around 1.4 GB after 12.5 GB worth of allocations,
+ whereas the Lua implementation arrives at around 45 MB after 3.2 GB
+ total:
+
+ impl time(B) total(B) useful-heap(B) extra-heap(B)
+ fontforge 12,496,407,184 1,421,150,144 1,327,888,638 93,261,506
+ lua 3,263,698,960 45,478,640 37,231,892 8,246,748
+
+ Much of the inefficiency of Fontforge is a direct consequence of
+ having to parse the entire font to extract what essentially boils
+ down to a couple hundred bytes of metadata per font. Since some
+ information like design sizes (oh, Adobe!) is stuffed away in
+ Opentype tables, the vastly more efficient approach of
+ fontloader.info() proves insufficient for indexing. Thus, we ended
+ up using fontloader.open() which causes even the character tables
+ to be parsed, which incidentally are responsible for most of the
+ allocations during that peak of 1.4 GB measured above, along with
+ the encodings:
+
+ 20.67% (293,781,048B) 0x6A8F72: SplineCharCreate (splineutil.c:3878)
+ 09.82% (139,570,318B) 0x618ACD: _FontViewBaseCreate (fontviewbase.c:84)
+ 08.77% (124,634,384B) 0x6A8FB3: SplineCharCreate (splineutil.c:3885)
+ 04.53% (64,436,904B) in 80 places, all below massif's threshold (1.00%)
+ 02.68% (38,071,520B) 0x64E14E: addKernPair (parsettfatt.c:493)
+ 01.04% (14,735,320B) 0x64DE7D: addPairPos (parsettfatt.c:452)
+ 39.26% (557,942,484B) 0x64A4E0: PsuedoEncodeUnencoded (parsettf.c:5706)
+
+ What gives? For 2.7 we expect a rougher transition than a year back
+ due to the complete revamp of the OT loading code. Breakage of
+ fragile aspects like font and style names has been anticipated and
+ addressed prior to the 2016 pretest release. In contrast to the
+ earlier approach of letting FF do a complete dump and then harvest
+ identifiers from the output we now have to coordinate with upstream
+ as to which fields are actually needed in order to provide a
+ similarly acceptable name → file lookup. On the bright side, these
+ things are a lot simpler to fix than the rather tedious work of
+ having users update their Luatex binary =)
+
+--doc]]--
+
+local lpeg = require "lpeg"
+local P, lpegmatch = lpeg.P, lpeg.match
+
+local log = luaotfload.log
+local logreport = log and log.report or print -- overriden later on
+local report_status = log.names_status
+local report_status_start = log.names_status_start
+local report_status_stop = log.names_status_stop
+
+
+--- Luatex builtins
+local load = load
+local next = next
+local require = require
+local tonumber = tonumber
+local unpack = table.unpack
+
+local fonts = fonts or { }
+local fontshandlers = fonts.handlers or { }
+local otfhandler = fonts.handlers.otf or { }
+fonts.handlers = fontshandlers
+
+local gzipload = gzip.load
+local gzipsave = gzip.save
+local iolines = io.lines
+local ioopen = io.open
+local iopopen = io.popen
+local kpseexpand_path = kpse.expand_path
+local kpsefind_file = kpse.find_file
+local kpselookup = kpse.lookup
+local kpsereadable_file = kpse.readable_file
+local lfsattributes = lfs.attributes
+local lfschdir = lfs.chdir
+local lfscurrentdir = lfs.currentdir
+local lfsdir = lfs.dir
+local mathabs = math.abs
+local mathmin = math.min
+local osgetenv = os.getenv
+local osgettimeofday = os.gettimeofday
+local osremove = os.remove
+local stringfind = string.find
+local stringformat = string.format
+local stringgmatch = string.gmatch
+local stringgsub = string.gsub
+local stringlower = string.lower
+local stringsub = string.sub
+local stringupper = string.upper
+local tableconcat = table.concat
+local tablesort = table.sort
+local utf8len = utf8.len
+local utf8offset = utf8.offset
+
+--- these come from Lualibs/Context
+local filebasename = file.basename
+local filecollapsepath = file.collapsepath or file.collapse_path
+local filedirname = file.dirname
+local fileextname = file.extname
+local fileiswritable = file.iswritable
+local filejoin = file.join
+local filenameonly = file.nameonly
+local filereplacesuffix = file.replacesuffix
+local filesplitpath = file.splitpath or file.split_path
+local filesuffix = file.suffix
+local getwritablepath = caches.getwritablepath
+local lfsisdir = lfs.isdir
+local lfsisfile = lfs.isfile
+local lfsmkdirs = lfs.mkdirs
+local lpegsplitat = lpeg.splitat
+local stringis_empty = string.is_empty
+local stringsplit = string.split
+local stringstrip = string.strip
+local tableappend = table.append
+local tablecontains = table.contains
+local tablecopy = table.copy
+local tablefastcopy = table.fastcopy
+local tabletofile = table.tofile
+local tabletohash = table.tohash
+local tableserialize = table.serialize
+local names = fonts and fonts.names or { }
+
+--- some of our own
+local unicode = require'luaotfload-unicode'
+local casefold = unicode.casefold
+local alphnum_only = unicode.alphnum_only
+
+local name_index = nil --> upvalue for names.data
+local lookup_cache = nil --> for names.lookups
+
+--- string -> (string * string)
+local make_luanames = function (path)
+ return filereplacesuffix(path, "lua"),
+ filereplacesuffix(path, "luc")
+end
+
+local format_precedence = {
+ "otf", "ttc", "ttf", "afm", "pfb"
+}
+
+local location_precedence = {
+ "local", "system", "texmf",
+}
+
+local set_location_precedence = function (precedence)
+ location_precedence = precedence
+end
+
+--[[doc--
+
+ Auxiliary functions
+
+--doc]]--
+
+--- fontnames contain all kinds of garbage; as a precaution we
+--- lowercase and strip them of non alphanumerical characters
+
+--- string -> string
+
+local invalidchars = "[^%a%d]"
+
+local sanitize_fontname = function (str)
+ if str ~= nil then
+ if utf8len(str) then
+ str = alphnum_only(casefold(str, true))
+ else
+ str = stringgsub(stringlower(str), invalidchars, "")
+ end
+ return str
+ end
+ return nil
+end
+
+local sanitize_fontnames = function (rawnames)
+ local result = { }
+ for category, namedata in next, rawnames do
+
+ if type (namedata) == "string" then
+ if utf8len(namedata) then
+ result [category] = alphnum_only(casefold(namedata, true))
+ else
+ result [category] = stringgsub(stringlower(namedata), invalidchars, "")
+ end
+ else
+ local target = { }
+ for field, name in next, namedata do
+ if utf8len(name) then
+ target [field] = alphnum_only(casefold(name, true))
+ else
+ target [field] = stringgsub(stringlower(name), invalidchars, "")
+ end
+ end
+ result [category] = target
+ end
+ end
+ return result
+end
+
+local find_files_indeed
+find_files_indeed = function (acc, dirs, filter)
+ if not next (dirs) then --- done
+ return acc
+ end
+
+ local pwd = lfscurrentdir ()
+ local dir = dirs[#dirs]
+ dirs[#dirs] = nil
+
+ if lfschdir (dir) then
+ lfschdir (pwd)
+
+ local newfiles = { }
+ for ent in lfsdir (dir) do
+ if ent ~= "." and ent ~= ".." then
+ local fullpath = dir .. "/" .. ent
+ if filter (fullpath) == true then
+ if lfsisdir (fullpath) then
+ dirs[#dirs+1] = fullpath
+ elseif lfsisfile (fullpath) then
+ newfiles[#newfiles+1] = fullpath
+ end
+ end
+ end
+ end
+ return find_files_indeed (tableappend (acc, newfiles),
+ dirs, filter)
+ end
+ --- could not cd into, so we skip it
+ return find_files_indeed (acc, dirs, filter)
+end
+
+local dummyfilter = function () return true end
+
+--- the optional filter function receives the full path of a file
+--- system entity. a filter applies if the first argument it returns is
+--- true.
+
+--- string -> function? -> string list
+local find_files = function (root, filter)
+ if lfsisdir (root) then
+ return find_files_indeed ({}, { root }, filter or dummyfilter)
+ end
+end
+
+
+--[[doc--
+This is a sketch of the luaotfload db:
+
+ type dbobj = {
+ families : familytable;
+ files : filemap;
+ status : filestatus;
+ mappings : fontentry list;
+ meta : metadata;
+ }
+ and familytable = {
+ local : (format, familyentry) hash; // specified with include dir
+ texmf : (format, familyentry) hash;
+ system : (format, familyentry) hash;
+ }
+ and familyentry = {
+ r : sizes; // regular
+ i : sizes; // italic
+ b : sizes; // bold
+ bi : sizes; // bold italic
+ }
+ and sizes = {
+ default : int; // points into mappings or names
+ optical : (int, int) list; // design size -> index entry
+ }
+ and metadata = {
+ created : string // creation time
+ formats : string list; // { "otf", "ttf", "ttc" }
+ local : bool; (* set if local fonts were added to the db *)
+ modified : string // modification time
+ statistics : TODO; // created when built with "--stats"
+ version : float; // index version
+ }
+ and filemap = { // created by generate_filedata()
+ base : {
+ local : (string, int) hash; // basename -> idx
+ system : (string, int) hash;
+ texmf : (string, int) hash;
+ };
+ bare : {
+ local : (string, (string, int) hash) hash; // location -> (barename -> idx)
+ system : (string, (string, int) hash) hash;
+ texmf : (string, (string, int) hash) hash;
+ };
+ full : (int, string) hash; // idx -> full path
+ }
+ and fontentry = { // finalized by collect_families()
+ basename : string; // file name without path "foo.otf"
+ conflicts : { barename : int; basename : int }; // filename conflict with font at index; happens with subfonts
+ familyname : string; // sanitized name of the font family the font belongs to, usually from the names table
+ fontname : string; // sanitized name of the font
+ format : string; // "otf" | "ttf" | "afm" (* | "pfb" *)
+ fullname : string; // sanitized full name of the font including style modifiers
+ fullpath : string; // path to font in filesystem
+ index : int; // index in the mappings table
+ italicangle : float; // italic angle; non-zero with oblique faces
+ location : string; // "texmf" | "system" | "local"
+ plainname : string; // unsanitized font name
+ typographicsubfamily : string; // sanitized preferred subfamily (names table 14)
+ psname : string; // PostScript name
+ size : (false | float * float * float); // if available, size info from the size table converted from decipoints
+ subfamily : string; // sanitized subfamily (names table 2)
+ subfont : (int | bool); // integer if font is part of a TrueType collection ("ttc")
+ version : string; // font version string
+ weight : int; // usWeightClass
+ }
+ and filestatus = (string, // fullname
+ { index : int list; // pointer into mappings
+ timestamp : int; }) dict
+
+beware that this is a reconstruction and may be incomplete or out of
+date. Last update: 2014-04-06, describing version 2.51.
+
+mtx-fonts has in names.tma:
+
+ type names = {
+ cache_uuid : uuid;
+ cache_version : float;
+ datastate : uuid list;
+ fallbacks : (filetype, (basename, int) hash) hash;
+ families : (basename, int list) hash;
+ files : (filename, fullname) hash;
+ indices : (fullname, int) hash;
+ mappings : (filetype, (basename, int) hash) hash;
+ names : ? (empty hash) ?;
+ rejected : (basename, int) hash;
+ specifications: fontentry list;
+ }
+ and fontentry = {
+ designsize : int;
+ familyname : string;
+ filename : string;
+ fontname : string;
+ format : string;
+ fullname : string;
+ maxsize : int;
+ minsize : int;
+ modification : int;
+ rawname : string;
+ style : string;
+ subfamily : string;
+ variant : string;
+ weight : string;
+ width : string;
+ }
+
+--doc]]--
+
+--- string list -> string option -> dbobj
+
+local initialize_namedata = function (formats, created)
+ local now = os.date "%Y-%m-%d %H:%M:%S" --- i. e. "%F %T" on POSIX systems
+ return {
+ status = { }, -- was: status; map abspath -> mapping
+ mappings = { }, -- TODO: check if still necessary after rewrite
+ files = { }, -- created later
+ meta = {
+ created = created or now,
+ formats = formats,
+ ["local"] = false,
+ modified = now,
+ statistics = { },
+ version = names.version,
+ },
+ }
+end
+
+--- When loading a lua file we try its binary complement first, which
+--- is assumed to be located at an identical path, carrying the suffix
+--- .luc.
+
+--- string -> (string * table)
+local load_lua_file = function (path)
+ local foundname = filereplacesuffix (path, "luc")
+ local code = nil
+
+ local fh = ioopen (foundname, "rb") -- try bin first
+ if fh then
+ local chunk = fh:read"*all"
+ fh:close()
+ code = load (chunk, "b")
+ end
+
+ if not code then --- fall back to text file
+ foundname = filereplacesuffix (path, "lua")
+ fh = ioopen(foundname, "rb")
+ if fh then
+ local chunk = fh:read"*all"
+ fh:close()
+ code = load (chunk, "t")
+ end
+ end
+
+ if not code then --- probe gzipped file
+ foundname = filereplacesuffix (path, "lua.gz")
+ local chunk = gzipload (foundname)
+ if chunk then
+ code = load (chunk, "t")
+ end
+ end
+
+ if not code then return nil, nil end
+ return foundname, code ()
+end
+
+--- define locals in scope
+local access_font_index
+local find_closest
+local flush_lookup_cache
+local generate_filedata
+local get_font_filter
+local group_modifiers
+local load_names
+local lookup_font_name
+local getmetadata
+local order_design_sizes
+local ot_fullinfo
+local read_blacklist
+local reload_db
+local lookup_fullpath
+local save_lookups
+local save_names
+local set_font_filter
+local t1_fullinfo
+local update_names
+
+--- state of the database
+local fonts_reloaded = false
+
+--- limit output when approximate font matching (luaotfload-tool -F)
+local fuzzy_limit = 1 --- display closest only
+
+--- bool? -> -> bool? -> dbobj option
+load_names = function (dry_run, no_rebuild)
+ local starttime = osgettimeofday ()
+ local foundname, data = load_lua_file (config.luaotfload.paths.index_path_lua)
+
+ if data then
+ logreport ("log", 0, "db",
+ "Font names database loaded from %s", foundname)
+ logreport ("term", 3, "db",
+ "Font names database loaded from %s", foundname)
+ logreport ("info", 3, "db", "Loading took %0.f ms.",
+ 1000 * (osgettimeofday () - starttime))
+
+ local db_version, names_version
+ if data.meta then
+ db_version = data.meta.version
+ else
+ --- Compatibility branch; the version info used to be
+ --- stored in the table root which is why updating from
+ --- an earlier index version broke.
+ db_version = data.version or -42 --- invalid
+ end
+ names_version = names.version
+ if db_version ~= names_version then
+ if math.tointeger(db_version) then
+ logreport ("both", 0, "db",
+ [[Version mismatch; expected %d, got %d.]],
+ names_version, db_version)
+ else
+ logreport ("both", 0, "db",
+ [[Version mismatch; expected %d, got invalid data.]],
+ names_version, db_version)
+ end
+ if not fonts_reloaded then
+ logreport ("both", 0, "db", [[Force rebuild.]])
+ data = update_names (initialize_namedata (get_font_filter ()),
+ true, false)
+ if not data then
+ logreport ("both", 0, "db",
+ "Database creation unsuccessful.")
+ end
+ end
+ end
+ else
+ if no_rebuild == true then
+ logreport ("both", 2, "db",
+ [[Database does not exist, skipping rebuild though.]])
+ return false
+ end
+ logreport ("both", 0, "db",
+ [[Font names database not found, generating new one.]])
+ logreport ("both", 0, "db",
+ [[This can take several minutes; please be patient.]])
+ data = update_names (initialize_namedata (get_font_filter ()),
+ nil, dry_run)
+ if not data then
+ logreport ("both", 0, "db", "Database creation unsuccessful.")
+ end
+ end
+ return data
+end
+
+--[[doc--
+
+ access_font_index -- Provide a reference of the index table. Will
+ cause the index to be loaded if not present.
+
+--doc]]--
+
+access_font_index = function ()
+ if not name_index then name_index = load_names () end
+ return name_index
+end
+
+getmetadata = function ()
+ if not name_index then
+ name_index = load_names (false, true)
+ if name_index then return tablefastcopy (name_index.meta) end
+ end
+ return false
+end
+
+--- unit -> unit
+local load_lookups
+load_lookups = function ( )
+ local foundname, data = load_lua_file(config.luaotfload.paths.lookup_path_lua)
+ if data then
+ logreport ("log", 0, "cache", "Lookup cache loaded from %s.", foundname)
+ logreport ("term", 3, "cache",
+ "Lookup cache loaded from %s.", foundname)
+ else
+ logreport ("both", 1, "cache",
+ "No lookup cache, creating empty.")
+ data = { }
+ end
+ lookup_cache = data
+end
+
+local regular_synonym = {
+ book = true,
+ normal = true,
+ plain = true,
+ regular = true,
+ roman = true,
+}
+
+local style_synonym = {
+ oblique = 'i',
+ slanted = 'i',
+ italic = 'i',
+ boldoblique = 'bi',
+ boldslanted = 'bi',
+ bolditalic = 'bi',
+ bold = 'b',
+}
+
+-- MK Determine if casefold search is requested
+local casefold_search =
+ not ({['0'] = true, ['f'] = true, [''] = true})
+ [(kpse.var_value'texmf_casefold_search' or '1'):sub(1,1)]
+-- /MK
+
+local lookup_filename = function (filename)
+ if not name_index then name_index = load_names () end
+ local files = name_index.files
+ local basedata = files.base
+ local baredata = files.bare
+ for i = 1, #location_precedence do
+ local location = location_precedence [i]
+ local basenames = basedata [location]
+ local barenames = baredata [location]
+ local idx
+ if basenames ~= nil then
+ -- MK Added fallback
+ idx = basenames [filename]
+ or casefold_search and basenames [stringlower(filename)]
+ -- /MK
+ if idx then
+ goto done
+ end
+ end
+ if barenames ~= nil then
+ for j = 1, #format_precedence do
+ local format = format_precedence [j]
+ local filemap = barenames [format]
+ if filemap then
+ -- MK Added fallback
+ idx = barenames [format] [filename]
+ or casefold_search and barenames [format] [stringlower(filename)]
+ -- /MK
+ if idx then
+ break
+ end
+ end
+ end
+ end
+::done::
+ if idx then
+ return files.full [idx]
+ end
+ end
+end
+
+--[[doc--
+
+ lookup_font_file -- The ``file:`` are ultimately delegated here.
+ The lookups are kind of a blunt instrument since they try locating
+ the file using every conceivable method, which is quite
+ inefficient. Nevertheless, resolving files that way is rarely the
+ bottleneck.
+
+--doc]]--
+
+--- string -> string * string * bool
+local lookup_font_file
+
+-- MK Added mini scope to avoid variable limit
+do
+local type1_metrics = { "tfm", "ofm", }
+-- /MK
+
+lookup_font_file = function (filename)
+ local found = lookup_filename (filename)
+
+ if not found then
+ local type = file.suffix(filename)
+ if type ~= "" then
+ found = resolvers.findfile(filename, type)
+ end
+ end
+
+ if found then
+ return found, nil, true
+ end
+
+ for i=1, #type1_metrics do
+ local format = type1_metrics[i]
+ if resolvers.findfile(filename, format) then
+ return file.addsuffix(filename, format), format, true
+ end
+ end
+
+ if not fonts_reloaded and config.luaotfload.db.update_live == true then
+ return reload_db (stringformat ("File not found: %s.", filename),
+ lookup_font_file,
+ filename)
+ end
+ return filename, nil, false
+end
+-- MK
+end
+-- /MK
+
+--[[doc--
+
+ get_font_file -- Look up the file of an entry in the mappings
+ table. If the index is valid, pass on the name and subfont index
+ after verifing the existence of the resolved file. This
+ verification differs depending the index entry’s ``location``
+ field:
+
+ * ``texmf`` fonts are verified using the (slow) function
+ ``kpse.lookup()``;
+ * other locations are tested by resolving the full path and
+ checking for the presence of a file there.
+
+--doc]]--
+
+--- int -> bool * (string * int) option
+local get_font_file = function (index)
+ local entry = name_index.mappings [index]
+ if not entry then
+ return false
+ end
+ local basename = entry.basename
+ if entry.location == "texmf" then
+ local fullname = resolvers.findfile(basename, entry.format)
+ if fullname then
+ return true, fullname, entry.subfont
+ end
+ else --- system, local
+ local fullname = name_index.files.full [index]
+ if lfsisfile (fullname) then
+ return true, fullname, entry.subfont
+ end
+ end
+ return false
+end
+
+--[[doc--
+We need to verify if the result of a cached lookup actually exists in
+the texmf or filesystem. Again, due to the schizoprenic nature of the
+font managment we have to check both the system path and the texmf.
+--doc]]--
+
+local verify_font_file = function (basename)
+ local path = lookup_fullpath (basename)
+ if path and lfsisfile(path) then
+ return true
+ end
+ if resolvers.findfile(basename) then
+ return true
+ end
+ return false
+end
+
+--[[doc--
+Lookups can be quite costly, more so the less specific they are.
+Even if we find a matching font eventually, the next time the
+user compiles Eir document E will have to stand through the delay
+again.
+Thus, some caching of results -- even between runs -- is in order.
+We’ll just store successful name: lookups in a separate cache file.
+
+type lookup_cache = (string, (string * num)) dict
+
+The spec is expected to be modified in place (ugh), so we’ll have to
+catalogue what fields actually influence its behavior.
+
+Idk what the “spec” resolver is for.
+
+ lookup inspects modifies
+ ---------- ----------------- ---------------------------
+ file: name forced, name
+ name:[*] name, style, sub, resolved, sub, name, forced
+ optsize, size
+ spec: name, sub resolved, sub, name, forced
+
+[*] name: contains both the name resolver from luatex-fonts and
+ lookup_font_name () below
+
+From my reading of font-def.lua, what a resolver does is
+basically rewrite the “name” field of the specification record
+with the resolution.
+Also, the fields “resolved”, “sub”, “force” etc. influence the outcome.
+
+--doc]]--
+
+local concat_char = "#"
+local hash_fields = {
+ --- order is important
+ "specification", "style", "sub", "optsize", "size",
+}
+local n_hash_fields = #hash_fields
+
+--- spec -> string
+local hash_request = function (specification)
+ local key = { } --- segments of the hash
+ for i=1, n_hash_fields do
+ local field = specification[hash_fields[i]]
+ if field then
+ key[#key+1] = field
+ end
+ end
+ return tableconcat(key, concat_char)
+end
+
+--- 'a -> 'a -> table -> (string * int|boolean * boolean)
+local lookup_font_name_cached
+lookup_font_name_cached = function (specification)
+ if not lookup_cache then load_lookups () end
+ local request = hash_request(specification)
+ logreport ("both", 4, "cache", "Looking for %q in cache ...",
+ request)
+
+ local found = lookup_cache [request]
+
+ --- case 1) cache positive ----------------------------------------
+ if found then --- replay fields from cache hit
+ logreport ("info", 4, "cache", "Found!")
+ local basename = found[1]
+ --- check the presence of the file in case it’s been removed
+ local success = verify_font_file (basename)
+ if success == true then
+ return basename, found[2], true
+ end
+ logreport ("both", 4, "cache",
+ "Cached file not found; resolving again.")
+ else
+ logreport ("both", 4, "cache", "Not cached; resolving.")
+ end
+
+ --- case 2) cache negative ----------------------------------------
+ --- first we resolve normally ...
+ local filename, subfont = lookup_font_name (specification)
+ if not filename then
+ return nil, nil
+ end
+ --- ... then we add the fields to the cache ... ...
+ local entry = { filename, subfont }
+ logreport ("both", 4, "cache", "New entry: %s.", request)
+ lookup_cache [request] = entry
+
+ --- obviously, the updated cache needs to be stored.
+ --- TODO this should trigger a save only once the
+ --- document is compiled (finish_pdffile callback?)
+ logreport ("both", 5, "cache", "Saving updated cache.")
+ local success = save_lookups ()
+ if not success then --- sad, but not critical
+ logreport ("both", 0, "cache", "Error writing cache.")
+ end
+ return filename, subfont
+end
+
+--- this used to be inlined; with the lookup cache we don’t
+--- have to be parsimonious wrt function calls anymore
+--- “found” is the match accumulator
+local add_to_match = function (found, size, face)
+
+ local continue = true
+
+ local optsize = face.size
+
+ if optsize and next (optsize) then
+ local dsnsize, maxsize, minsize
+ dsnsize = optsize[1]
+ maxsize = optsize[2]
+ minsize = optsize[3]
+
+ if size ~= nil
+ and (dsnsize == size or (size > minsize and size <= maxsize))
+ then
+ found[1] = face
+ continue = false ---> break
+ else
+ found[#found+1] = face
+ end
+ else
+ found[1] = face
+ continue = false ---> break
+ end
+
+ return found, continue
+end
+
+local choose_closest = function (distances)
+ local closest = 2^51
+ local match
+ for i = 1, #distances do
+ local d, index = unpack (distances [i])
+ if d < closest then
+ closest = d
+ match = index
+ end
+ end
+ return match
+end
+
+--[[doc--
+
+ choose_size -- Pick a font face of appropriate size (in sp) from
+ the list of family members with matching style. There are three
+ categories:
+
+ 1. exact matches: if there is a face whose design size equals
+ the asked size, it is returned immediately and no further
+ candidates are inspected.
+
+ 2. range matches: of all faces in whose design range the
+ requested size falls the one whose center the requested
+ size is closest to is returned.
+
+ 3. out-of-range matches: of all other faces (i. e. whose range
+ is above or below the asked size) the one is chosen whose
+ boundary (upper or lower) is closest to the requested size.
+
+ 4. default matches: if no design size or a design size of zero
+ is requested, the face with the default size is returned.
+
+--doc]]--
+
+--- int * int * int * int list -> int -> int
+local function choose_size (sizes, askedsize)
+ local mappings = name_index.mappings
+ local exact
+ local inrange = { } --- distance * index list
+ local norange = { } --- distance * index list
+ local fontname, subfont
+ if askedsize ~= 0 then
+ --- firstly, look for an exactly matching design size or
+ --- matching range
+ for i = 1, #sizes do
+ local dsnsize, high, low, index = unpack (sizes [i])
+ if dsnsize == askedsize then
+ --- exact match, this is what we were looking for
+ return index
+ elseif askedsize <= low then
+ --- below range, add to the norange table
+ local d = low - askedsize
+ norange [#norange + 1] = { d, index }
+ elseif askedsize > high then
+ --- beyond range, add to the norange table
+ local d = askedsize - high
+ norange [#norange + 1] = { d, index }
+ else
+ --- range match
+ local d = 0
+
+ -- should always be true. Just in case there's some
+ -- weried fonts out there
+ if dsnsize > low and dsnsize < high then
+ d = dsnsize - askedsize
+ else
+ d = ((low + high) / 2) - askedsize
+ end
+ if d < 0 then
+ d = -d
+ end
+
+ inrange [#inrange + 1] = { d, index }
+ end
+ end
+ end
+::skip::
+ if #inrange > 0 then
+ return choose_closest (inrange)
+ elseif #norange > 0 then
+ return choose_closest (norange)
+ elseif sizes.default then
+ return sizes.default
+ elseif askedsize == 0 then
+ return choose_size(sizes, 655360) -- If there is no default size and no size specified, just guess
+ end
+end
+
+--[[doc--
+
+ lookup_familyname -- Query the families table for an entry
+ matching the specification.
+ The parameters “name” and “style” are pre-sanitized.
+
+--doc]]--
+--- spec -> string -> string -> int -> string * int * bool
+local lookup_familyname = function (specification, name, style, askedsize)
+ local families = name_index.families
+ local mappings = name_index.mappings
+ local candidates = nil
+ local fallback = true
+ --- arrow code alert
+ for i = 1, #location_precedence do
+ local location = location_precedence [i]
+ local locgroup = families [location]
+ for j = 1, #format_precedence do
+ local format = format_precedence [j]
+ local fmtgroup = locgroup [format]
+ if fmtgroup then
+ local familygroup = fmtgroup [name]
+ if familygroup then
+ local stylegroup = familygroup [style]
+ if stylegroup then --- suitable match
+ candidates = stylegroup
+ fallback = false
+ goto done
+ elseif not candidates then
+ candidates = familygroup.r
+ end
+ end
+ end
+ end
+ end
+ if not candidates then
+ return nil, nil
+ end
+::done::
+ index = choose_size (candidates, askedsize)
+ local success, resolved, subfont = get_font_file (index)
+ if not success then
+ return nil, nil
+ end
+ logreport ("info", 2, "db", "Match found: %s(%d).",
+ resolved, subfont or 0)
+ return resolved, subfont, fallback
+end
+
+local lookup_fontname = function (specification, name)
+ local mappings = name_index.mappings
+ local fallback = nil
+ local lastresort = nil
+ for i = 1, #mappings do
+ local face = mappings [i]
+ local typographicsubfamily = face.typographicsubfamily
+ local subfamily = face.subfamily
+ if face.fontname == name
+ or face.fullname == name
+ or face.psname == name
+ then
+ return face.fullpath, face.subfont
+ end
+ end
+ return nil, nil
+end
+
+local design_size_dimension --- scale asked size if not using bp
+local set_size_dimension --- called from config
+do
+
+ --- cf. TeXbook p. 57; the index stores sizes pre-scaled from bp to
+ --- sp. This allows requesting sizes we got from the TeX end
+ --- without further conversion. For the other options *pt* and *dd*
+ --- we scale the requested size as though the value in the font was
+ --- specified in the requested unit.
+
+ --- From @zhouyan:
+
+ --- Let P be the asked size in pt, and Aᵤ = CᵤP, where u is the
+ --- designed unit, pt, bp, or dd, and
+ ---
+ --- Cpt = 1, Cbp = 7200/7227, Cdd = 1157/1238.
+ ---
+ --- That is, Aᵤ is the asked size in the desired unit. Let D be the
+ --- de-sign size (assumed to be in the unit of bp) as reported by
+ --- the font (divided by 10; in all the following we ignore the
+ --- factor 2^16 ).
+ ---
+ --- For simplicity, consider only the case of exact match to the
+ --- design size. That is, we would like to have Aᵤ = D. Let A′ᵤ = αᵤP
+ --- and D′ = βD be the scaled values used in comparisons. For the
+ --- comparison to work correctly, we need,
+ ---
+ --- Aᵤ = D ⟺ A′ᵤ = D′ ,
+ ---
+ --- and thus αᵤ = βCᵤ. The fix in PR 400 is the case of β = 1. The
+ --- fix for review is β = 7227/7200, and the value of αᵤ is thus
+ --- correct for pt, bp, but not for dd.
+
+ local dimens = {
+ bp = false,
+ pt = 7227 / 7200,
+ dd = (7227 / 7200) * (1157 / 1238),
+ }
+
+ design_size_dimension = dimens.bp
+
+ set_size_dimension = function (dim)
+ local conv = dimens [dim]
+ if conv ~= nil then
+ logreport ("both", 4, "db",
+ "Interpreting design sizes as %q, factor %.6f.",
+ dim, conv or 1)
+ design_size_dimension = conv
+ return
+ end
+ logreport ("both", 0, "db",
+ "Invalid dimension %q requested for design sizes; \z
+ ignoring.")
+ end
+end
+
+
+--[[doc--
+
+ lookup_font_name -- Perform a name: lookup. This first queries the
+ font families table and, if there is no match for the spec, the
+ font names table.
+ The return value is a pair consisting of the file name and the
+ subfont index if appropriate..
+
+ the request specification has the fields:
+
+ · features: table
+ · normal: set of { ccmp clig itlc kern liga locl mark mkmk rlig }
+ · ???
+ · forced: string
+ · lookup: "name"
+ · method: string
+ · name: string
+ · resolved: string
+ · size: int
+ · specification: string (== <lookup> ":" <name>)
+ · sub: string
+
+ The “size” field deserves special attention: if its value is
+ negative, then it actually specifies a scalefactor of the
+ design size of the requested font. This happens e.g. if a font is
+ requested without an explicit “at size”. If the font is part of a
+ larger collection with different design sizes, this complicates
+ matters a bit: Normally, the resolver prefers fonts that have a
+ design size as close as possible to the requested size. If no
+ size specified, then the design size is implied. But which design
+ size should that be? Xetex appears to pick the “normal” (unmarked)
+ size: with Adobe fonts this would be the one that is neither
+ “caption” nor “subhead” nor “display” &c ... For fonts by Adobe this
+ seems to be the one that does not receive a “typographicsubfamily”
+ field. (IOW Adobe uses the “typographicsubfamily” field to encode
+ the design size in more or less human readable format.) However,
+ this is not true of LM and EB Garamond. As this matters only where
+ there are multiple design sizes to a given font/style combination,
+ we put a workaround in place that chooses that unmarked version.
+
+ The first return value of “lookup_font_name” is the file name of the
+ requested font (string). It can be passed to the fullname resolver
+ get_font_file().
+ The second value is either “false” or an integer indicating the
+ subfont index in a TTC.
+
+--doc]]--
+
+--- table -> string * (int | bool)
+lookup_font_name = function (specification)
+ if not name_index then name_index = load_names () end
+ local name = sanitize_fontname (specification.name)
+ local style = sanitize_fontname (specification.style) or "r"
+ local askedsize = specification.optsize
+
+ if askedsize then
+ askedsize = tonumber (askedsize) * 65536
+ else
+ askedsize = specification.size
+ if not askedsize or askedsize < 0 then
+ askedsize = 0
+ end
+ end
+
+ if design_size_dimension ~= false then
+ askedsize = design_size_dimension * askedsize
+ end
+
+ local resolved, subfont, fallback = lookup_familyname (specification,
+ name,
+ style,
+ askedsize)
+ if not resolved or fallback then
+ local new_resolved, new_subfont = lookup_fontname (specification,
+ name,
+ style)
+ if new_resolved then
+ resolved, subfont = new_resolved, new_subfont
+ end
+ end
+
+ if not resolved then
+ if not fonts_reloaded and config.luaotfload.db.update_live == true then
+ return reload_db (stringformat ("Font %s not found.",
+ specification.name or "<?>"),
+ lookup_font_name,
+ specification)
+ end
+ end
+ return resolved, subfont
+end
+
+lookup_fullpath = function (fontname, ext) --- getfilename()
+ if not name_index then name_index = load_names () end
+ local files = name_index.files
+ local basedata = files.base
+ local baredata = files.bare
+ for i = 1, #location_precedence do
+ local location = location_precedence [i]
+ local basenames = basedata [location]
+ local idx
+ if basenames ~= nil then
+ -- MK Added fallback
+ idx = basenames [fontname]
+ or casefold_search and basenames [stringlower(fontname)]
+ -- /MK
+ end
+ if ext then
+ local barenames = baredata [location] [ext]
+ if not idx and barenames ~= nil then
+ -- MK Added fallback
+ idx = barenames [fontname]
+ or casefold_search and barenames [stringlower(fontname)]
+ -- /MK
+ end
+ end
+ if idx then
+ return files.full [idx]
+ end
+ end
+ return ""
+end
+
+--- when reload is triggered we update the database
+--- and then re-run the caller with the arg list
+
+--- string -> ('a -> 'a) -> 'a list -> 'a
+reload_db = function (why, caller, ...)
+ local namedata = name_index
+ local formats = tableconcat (namedata.meta.formats, ",")
+
+ logreport ("both", 0, "db",
+ "Reload initiated (formats: %s); reason: %q.",
+ formats, why)
+
+ set_font_filter (formats)
+ namedata = update_names (namedata, false, false)
+
+ if namedata then
+ fonts_reloaded = true
+ name_index = namedata
+ return caller (...)
+ end
+
+ logreport ("both", 0, "db", "Database update unsuccessful.")
+end
+
+--- string -> string -> int
+local iterative_levenshtein = function (s1, s2)
+
+ local costs = { }
+ local len1, len2 = #s1, #s2
+
+ for i = 0, len1 do
+ local last = i
+ for j = 0, len2 do
+ if i == 0 then
+ costs[j] = j
+ else
+ if j > 0 then
+ local current = costs[j-1]
+ if stringsub(s1, i, i) ~= stringsub(s2, j, j) then
+ current = mathmin(current, last, costs[j]) + 1
+ end
+ costs[j-1] = last
+ last = current
+ end
+ end
+ end
+ if i > 0 then costs[len2] = last end
+ end
+
+ return costs[len2]--- lower right has the distance
+end
+
+--- string list -> string list
+local delete_dupes = function (lst)
+ local n0 = #lst
+ if n0 == 0 then return lst end
+ tablesort (lst)
+ local ret = { }
+ local last
+ for i = 1, n0 do
+ local cur = lst[i]
+ if cur ~= last then
+ last = cur
+ ret[#ret + 1] = cur
+ end
+ end
+ logreport (false, 8, "query",
+ "Removed %d duplicate names.", n0 - #ret)
+ return ret
+end
+
+--- string -> int -> bool
+find_closest = function (name, limit)
+ local name = sanitize_fontname (name)
+ limit = limit or fuzzy_limit
+
+ if not name_index then name_index = load_names () end
+ if not name_index or type (name_index) ~= "table" then
+ if not fonts_reloaded then
+ return reload_db("Font index missing.", find_closest, name)
+ end
+ return false
+ end
+
+ local by_distance = { } --- (int, string list) dict
+ local distances = { } --- int list
+ local cached = { } --- (string, int) dict
+ local mappings = name_index.mappings
+ local n_fonts = #mappings
+
+ for n = 1, n_fonts do
+ local current = mappings[n]
+ --[[
+ This is simplistic but surpisingly fast.
+ Matching is performed against the “fullname” field
+ of a db record in preprocessed form. We then store the
+ raw “fullname” at its edit distance.
+ We should probably do some weighting over all the
+ font name categories as well as whatever agrep
+ does.
+ --]]
+ local fullname = current.plainname
+ local sfullname = current.fullname
+ local dist = cached[sfullname]--- maybe already calculated
+
+ if not dist then
+ dist = iterative_levenshtein(name, sfullname)
+ cached[sfullname] = dist
+ end
+ local namelst = by_distance[dist]
+ if not namelst then --- first entry
+ namelst = { fullname }
+ distances[#distances+1] = dist
+ else --- append
+ namelst[#namelst+1] = fullname
+ end
+
+ by_distance[dist] = namelst
+ end
+
+ --- print the matches according to their distance
+ local n_distances = #distances
+ if n_distances > 0 then --- got some data
+ tablesort(distances)
+ limit = mathmin(n_distances, limit)
+ logreport (false, 1, "query",
+ "Displaying %d distance levels.", limit)
+
+ for i = 1, limit do
+ local dist = distances[i]
+ local namelst = delete_dupes (by_distance[dist])
+ logreport (false, 0, "query",
+ "Distance from \"%s\": %s\n "
+ .. tableconcat (namelst, "\n "),
+ name, dist)
+ end
+
+ return true
+ end
+ return false
+end --- find_closest()
+
+--- string -> uint -> bool * (string | rawdata)
+local read_font_file = function (filename, subfont)
+ local fontdata = otfhandler.readers.getinfo (filename,
+ { subfont = subfont
+ , platformnames = true
+ , rawfamilynames = true
+ })
+ local msg = fontdata.comment
+ if msg then
+ return false, msg
+ end
+ return true, fontdata
+end
+
+local load_font_file = function (filename, subfont)
+ local err, ret = read_font_file (filename, subfont)
+ if err == false then
+ logreport ("both", 1, "db", "ERROR: failed to open %q: %q.",
+ tostring (filename), tostring (ret))
+ return
+ end
+ return ret
+end
+
+--- Design sizes in the fonts are specified in decipoints. For the
+--- index these values are prescaled to sp which is what we’re dealing
+--- with at the TeX end.
+
+local get_size_info do --- too many upvalues :/
+ --- rawdata -> (int * int * int | bool)
+
+ local sp = 2^16 -- pt
+ local bp = 7227 / 7200 -- pt
+
+ get_size_info = function (rawinfo)
+ local design_size = rawinfo.design_size
+ local design_range_top = rawinfo.design_range_top
+ local design_range_bottom = rawinfo.design_range_bottom
+
+ local fallback_size = design_size ~= 0 and design_size
+ or design_range_bottom ~= 0 and design_range_bottom
+ or design_range_top ~= 0 and design_range_top
+
+ if fallback_size then
+ design_size = ((design_size or fallback_size) * sp) / 10
+ design_range_top = ((design_range_top or fallback_size) * sp) / 10
+ design_range_bottom = ((design_range_bottom or fallback_size) * sp) / 10
+
+ design_size = design_size * bp
+ design_range_top = design_range_top * bp
+ design_range_bottom = design_range_bottom * bp
+
+ return {
+ design_size, design_range_top, design_range_bottom,
+ }
+ end
+
+ return false
+ end
+end ---[local get_size_info]
+
+--[[doc--
+ map_enlish_names -- Names-table for Lua fontloader objects. This
+ may vanish eventually once we ditch Fontforge completely. Only
+ subset of entries of that table are actually relevant so we’ll
+ stick to that part.
+--doc]]--
+
+local get_english_names = function (metadata)
+ local namesource
+ local platformnames = metadata.platformnames
+ --[[--
+ Hans added the “platformnames” option for us to access parts of
+ the original name table. The names are unreliable and
+ completely disorganized, sure, but the Windows variant of the
+ field often contains the superior information. Case in point:
+
+ ["platformnames"]={
+ ["macintosh"]={
+ ["compatiblefullname"]="Garamond Premr Pro Smbd It",
+ ["family"]="Garamond Premier Pro",
+ ["fullname"]="Garamond Premier Pro Semibold Italic",
+ ["postscriptname"]="GaramondPremrPro-SmbdIt",
+ ["subfamily"]="Semibold Italic",
+ },
+ ["windows"]={
+ ["family"]="Garamond Premr Pro Smbd",
+ ["fullname"]="GaramondPremrPro-SmbdIt",
+ ["postscriptname"]="GaramondPremrPro-SmbdIt",
+ ["subfamily"]="Italic",
+ ["typographicfamily"]="Garamond Premier Pro",
+ ["typographicsubfamily"]="Semibold Italic",
+ },
+ },
+
+ The essential bit is contained as “typographicfamily” (which we
+ call for historical reasons the “preferred family”) and the
+ “subfamily”. Only Why this is the case, only Adobe knows for
+ certain.
+ --]]--
+ if platformnames then
+ if platformnames.windows and platformnames.macintosh then
+ return table.merge(platformnames.macintosh, platformnames.windows)
+ end
+ namesource = platformnames.windows or platformnames.macintosh
+ end
+ return namesource or metadata
+end
+
+--[[--
+ In case of broken PS names we set some dummies.
+
+ For this reason we copy what is necessary whilst keeping the table
+ structure the same as in the tfmdata.
+--]]--
+local get_raw_info = function (metadata, basename)
+ local fontname = metadata.fontname
+ local fullname = metadata.fullname
+
+ if not fontname or not fullname then
+ --- Broken names table, e.g. avkv.ttf with UTF-16 strings;
+ --- we put some dummies in place like the fontloader
+ --- (font-otf.lua) does.
+ logreport ("both", 3, "db",
+ "Invalid names table of font %s, using dummies. \z
+ Reported: fontname=%q, fullname=%q.",
+ tostring (basename), tostring (fontname),
+ tostring (fullname))
+ fontname = "bad-fontname-" .. basename
+ fullname = "bad-fullname-" .. basename
+ end
+
+ return {
+ familyname = metadata.familyname,
+ fontname = fontname,
+ fullname = fullname,
+ italicangle = metadata.italicangle,
+ names = metadata.names,
+ units_per_em = metadata.units_per_em,
+ version = metadata.version,
+ design_size = metadata.design_size or metadata.designsize,
+ design_range_top = metadata.design_range_top or metadata.maxsize,
+ design_range_bottom = metadata.design_range_bottom or metadata.minsize,
+ }
+end
+
+local organize_namedata = function (rawinfo,
+ nametable,
+ basename,
+ info)
+ local default_name = nametable.compatiblefullname
+ or nametable.fullname
+ or nametable.postscriptname
+ or rawinfo.fullname
+ or rawinfo.fontname
+ or info.fullname
+ or info.fontname
+ local default_family = nametable.typographicfamily
+ or nametable.family
+ or rawinfo.familyname
+ or info.familyname
+-- local default_modifier = nametable.typographicsubfamily
+-- or nametable.subfamily
+ local fontnames = {
+ --- see
+ --- https://developer.apple.com/fonts/TTRefMan/RM06/Chap6name.html
+ --- http://www.microsoft.com/typography/OTSPEC/name.htm#NameIDs
+ english = {
+ --- where a “compatiblefullname” field is given, the value
+ --- of “fullname” is either identical or differs by
+ --- separating the style with a hyphen and omitting spaces.
+ --- (According to the spec, “compatiblefullname” is
+ --- “Macintosh only”.) Of the three “fullname” fields, this
+ --- one appears to be the one with the entire name given in
+ --- a legible, non-abbreviated fashion, for most fonts at
+ --- any rate. However, in some fonts (e.g. CMU) all three
+ --- fields are identical.
+ fullname = --[[ 18 ]] nametable.compatiblefullname
+ or --[[ 4 ]] nametable.fullname
+ or default_name,
+ --- we keep both the “preferred family” and the “family”
+ --- values around since both are valid but can turn out
+ --- quite differently, e.g. with Latin Modern:
+ --- typographicfamily: “Latin Modern Sans”,
+ --- family: “LM Sans 10”
+ family = --[[ 1 ]] nametable.family or default_family,
+ subfamily = --[[ 2 ]] nametable.subfamily or rawinfo.subfamilyname,
+ psname = --[[ 6 ]] nametable.postscriptname,
+ typographicfamily = --[[ 16 ]] nametable.typographicfamily,
+ typographicsubfamily = --[[ 17 ]] nametable.typographicsubfamily,
+ },
+
+ metadata = {
+ fullname = rawinfo.fullname,
+ fontname = rawinfo.fontname,
+ familyname = rawinfo.familyname,
+ },
+
+ info = {
+ fullname = info.fullname,
+ familyname = info.familyname,
+ fontname = info.fontname,
+ },
+ }
+
+ return {
+ sanitized = sanitize_fontnames (fontnames),
+ fontname = rawinfo.fontname,
+ fullname = rawinfo.fullname,
+ familyname = rawinfo.familyname,
+ }
+end
+
+
+local dashsplitter = lpegsplitat "-"
+
+local split_fontname = function (fontname)
+ --- sometimes the style hides in the latter part of the
+ --- fontname, separated by a dash, e.g. “Iwona-Regular”,
+ --- “GFSSolomos-Regular”
+ local splitted = { lpegmatch (dashsplitter, fontname) }
+ if next (splitted) then
+ return sanitize_fontname (splitted [#splitted])
+ end
+end
+
+local organize_styledata = function (metadata, rawinfo, info)
+ local pfminfo = metadata.pfminfo
+ local names = rawinfo.names
+ return {
+ --- see http://www.microsoft.com/typography/OTSPEC/features_pt.htm#size
+ size = get_size_info (rawinfo),
+ pfmweight = pfminfo and pfminfo.weight or metadata.pfmweight or 400,
+ weight = rawinfo.weight or metadata.weight or "unspecified",
+ split = split_fontname (rawinfo.fontname),
+ width = pfminfo and pfminfo.width or metadata.pfmwidth,
+ italicangle = metadata.italicangle,
+ --- this is for querying, see www.ntg.nl/maps/40/07.pdf for details
+ units_per_em = metadata.units_per_em or metadata.units,
+ version = metadata.version,
+ }
+end
+
+--[[doc--
+The data inside an Opentype font file can be quite heterogeneous.
+Thus in order to get the relevant information, parts of the original
+table as returned by the font file reader need to be relocated.
+--doc]]--
+
+--- string -> int -> bool -> string -> fontentry
+
+ot_fullinfo = function (filename,
+ subfont,
+ location,
+ basename,
+ format,
+ info)
+
+ local metadata = load_font_file (filename, subfont)
+ if not metadata then
+ return nil
+ end
+
+ local rawinfo = get_raw_info (metadata, basename)
+ local nametable = get_english_names (metadata)
+ local namedata = organize_namedata (rawinfo,
+ nametable,
+ basename,
+ info)
+ local style = organize_styledata (metadata,
+ rawinfo,
+ info)
+ local res = {
+ file = { base = basename,
+ full = filename,
+ subfont = subfont,
+ location = location or "system" },
+ format = format,
+ names = namedata,
+ style = style,
+ version = rawinfo.version,
+ }
+ return res
+end
+
+--[[doc--
+
+ Type1 font inspector. In comparison with OTF, PFB’s contain a good
+ deal less name fields which makes it tricky in some parts to find a
+ meaningful representation for the database.
+
+ Good read: http://www.adobe.com/devnet/font/pdfs/5004.AFM_Spec.pdf
+
+--doc]]--
+
+--- string -> int -> bool -> string -> fontentry
+
+t1_fullinfo = function (filename, _subfont, location, basename, format)
+ local sanitized
+ local metadata = load_font_file (filename)
+ local fontname = metadata.fontname
+ local fullname = metadata.fullname
+ local familyname = metadata.familyname
+ local italicangle = metadata.italicangle
+ local style = ""
+ local weight
+
+ sanitized = sanitize_fontnames ({
+ fontname = fontname,
+ psname = fullname,
+ familyname = familyname,
+ weight = metadata.weight, --- string identifier
+ typographicsubfamily = style,
+ })
+
+ weight = sanitized.weight
+
+ if weight == "bold" then
+ style = weight
+ end
+
+ if italicangle ~= 0 then
+ style = style .. "italic"
+ end
+
+ return {
+ basename = basename,
+ fullpath = filename,
+ subfont = false,
+ location = location or "system",
+ format = format,
+ fullname = sanitized.fullname,
+ fontname = sanitized.fontname,
+ familyname = sanitized.familyname,
+ plainname = fullname,
+ psname = sanitized.fontname,
+ version = metadata.version,
+ size = false,
+ typographicsubfamily = style ~= "" and style or weight,
+ weight = metadata.pfminfo and pfminfo.weight or 400,
+ italicangle = italicangle,
+ }
+end
+
+local loaders = {
+ otf = ot_fullinfo,
+ ttc = ot_fullinfo,
+ ttf = ot_fullinfo,
+ afm = t1_fullinfo,
+ pfb = t1_fullinfo,
+}
+
+--- not side-effect free!
+
+local compare_timestamps = function (fullname,
+ currentstatus,
+ currententrystatus,
+ currentmappings,
+ targetstatus,
+ targetentrystatus,
+ targetmappings)
+
+ local currenttimestamp = currententrystatus
+ and currententrystatus.timestamp
+ local targettimestamp = lfsattributes (fullname, "modification")
+
+ if targetentrystatus ~= nil
+ and targetentrystatus.timestamp == targettimestamp then
+ logreport ("log", 3, "db", "Font %q already read.", fullname)
+ return false
+ end
+
+ targetentrystatus.timestamp = targettimestamp
+ targetentrystatus.index = targetentrystatus.index or { }
+
+ if currenttimestamp == targettimestamp
+ and not targetentrystatus.index [1]
+ then
+ --- copy old namedata into new
+
+ for _, currentindex in next, currententrystatus.index do
+
+ local targetindex = #targetentrystatus.index
+ local fullinfo = currentmappings [currentindex]
+ local location = #targetmappings + 1
+
+ targetmappings [location] = fullinfo
+ targetentrystatus.index [targetindex + 1] = location
+ end
+
+ logreport ("log", 3, "db", "Font %q already indexed.", fullname)
+
+ return false
+ end
+
+ return true
+end
+
+local insert_fullinfo = function (fullname,
+ basename,
+ n_font,
+ loader,
+ format,
+ location,
+ targetmappings,
+ targetentrystatus,
+ info)
+
+ local fullinfo = loader (fullname, n_font,
+ location, basename,
+ format, info)
+
+ if not fullinfo then
+ return false
+ end
+
+ local index = targetentrystatus.index [n_font]
+
+ if not index then
+ index = #targetmappings + 1
+ end
+
+ targetmappings [index] = fullinfo
+ targetentrystatus.index [n_font] = index
+
+ return true
+end
+
+
+
+--- we return true if the font is new or re-indexed
+--- string -> dbobj -> dbobj -> bool
+
+local read_font_names = function (fullname,
+ currentnames,
+ targetnames,
+ location)
+
+ local targetmappings = targetnames.mappings
+ local targetstatus = targetnames.status --- by full path
+ local targetentrystatus = targetstatus [fullname]
+
+ if targetentrystatus == nil then
+ targetentrystatus = { }
+ targetstatus [fullname] = targetentrystatus
+ end
+
+ local currentmappings = currentnames.mappings
+ local currentstatus = currentnames.status
+ local currententrystatus = currentstatus [fullname]
+
+ local basename = filebasename (fullname)
+ local barename = filenameonly (fullname)
+ local entryname = fullname
+
+ if location == "texmf" then
+ entryname = basename
+ end
+
+ --- 1) skip if blacklisted
+
+ if names.blacklist[fullname] or names.blacklist[basename] then
+ logreport ("log", 2, "db",
+ "Ignoring blacklisted font %q.", fullname)
+ return false
+ end
+
+ --- 2) skip if known with same timestamp
+
+ if not compare_timestamps (fullname,
+ currentstatus,
+ currententrystatus,
+ currentmappings,
+ targetstatus,
+ targetentrystatus,
+ targetmappings)
+ then
+ return false
+ end
+
+ --- 3) new font; choose a loader, abort if unknown
+
+ local format = stringlower (filesuffix (basename))
+ local loader = loaders [format] --- ot_fullinfo, t1_fullinfo
+
+ if not loader then
+ logreport ("both", 0, "db",
+ "Unknown format: %q, skipping.", format)
+ return false
+ end
+
+ --- 4) get basic info, abort if fontloader can’t read it
+
+ local err, info = read_font_file (fullname)
+
+ if err == false then
+ logreport ("log", 1, "db",
+ "Failed to read basic information from %q: %q",
+ basename, tostring (info))
+ return false
+ end
+
+
+ --- 5) check for subfonts and process each of them
+
+ if type (info) == "table" and #info >= 1 then --- ttc
+
+ local success = false --- true if at least one subfont got read
+
+ for n_font = 1, #info do
+ if insert_fullinfo (fullname, basename, n_font,
+ loader, format, location,
+ targetmappings, targetentrystatus,
+ info)
+ then
+ success = true
+ end
+ end
+
+ return success
+ end
+
+ return insert_fullinfo (fullname, basename, false,
+ loader, format, location,
+ targetmappings, targetentrystatus,
+ info)
+end
+
+local path_normalize
+do
+ --- os.type and os.name are constants so we
+ --- choose a normalization function in advance
+ --- instead of testing with every call
+ local os_type, os_name = os.type, os.name
+ local filecollapsepath = filecollapsepath
+ local lfsreadlink = lfs.readlink
+
+ --- windows and dos
+ if os_type == "windows" or os_type == "msdos" then
+ --- ms platfom specific stuff
+ path_normalize = function (path)
+ path = stringgsub(path, '\\', '/')
+ path = stringlower(path)
+ path = filecollapsepath(path)
+ return path
+ end
+--[[doc--
+ The special treatment for cygwin was removed with a patch submitted
+ by Ken Brown.
+ Reference: http://cygwin.com/ml/cygwin/2013-05/msg00006.html
+--doc]]--
+
+ else -- posix
+ path_normalize = function (path)
+ local dest = lfsreadlink(path)
+ if dest then
+ if kpsereadable_file(dest) then
+ path = dest
+ elseif kpsereadable_file(filejoin(filedirname(path), dest)) then
+ path = filejoin(file.dirname(path), dest)
+ else
+ -- broken symlink?
+ end
+ end
+ path = filecollapsepath(path)
+ return path
+ end
+ end
+end
+
+local blacklist = { }
+local p_blacklist --- prefixes of dirs
+
+--- string list -> string list
+local collapse_prefixes = function (lst)
+ --- avoid redundancies in blacklist
+ if #lst < 2 then
+ return lst
+ end
+
+ tablesort(lst)
+ local cur = lst[1]
+ local result = { cur }
+ for i=2, #lst do
+ local elm = lst[i]
+ if stringsub(elm, 1, #cur) ~= cur then
+ --- different prefix
+ cur = elm
+ result[#result+1] = cur
+ end
+ end
+ return result
+end
+
+--- string list -> string list -> (string, bool) hash_t
+local create_blacklist = function (blacklist, whitelist)
+ local result = { }
+ local dirs = { }
+
+ logreport ("info", 2, "db", "Blacklisting %d files and directories.",
+ #blacklist)
+ for i=1, #blacklist do
+ local entry = blacklist[i]
+ if lfsisdir(entry) then
+ dirs[#dirs+1] = entry
+ else
+ result[blacklist[i]] = true
+ end
+ end
+
+ logreport ("info", 2, "db", "Whitelisting %d files.", #whitelist)
+ for i=1, #whitelist do
+ result[whitelist[i]] = nil
+ end
+
+ dirs = collapse_prefixes(dirs)
+
+ --- build the disjunction of the blacklisted directories
+ for i=1, #dirs do
+ local p_dir = P(dirs[i])
+ if p_blacklist then
+ p_blacklist = p_blacklist + p_dir
+ else
+ p_blacklist = p_dir
+ end
+ end
+
+ if p_blacklist == nil then
+ --- always return false
+ p_blacklist = lpeg.Cc(false)
+ end
+
+ return result
+end
+
+--- unit -> unit
+read_blacklist = function ()
+ local files = {
+ kpselookup ("luaotfload-blacklist.cnf",
+ {all=true, format="tex"})
+ }
+ local blacklist = { }
+ local whitelist = { }
+
+ if files and type(files) == "table" then
+ for _, path in next, files do
+ for line in iolines (path) do
+ line = stringstrip(line) -- to get rid of lines like " % foo"
+ local first_chr = stringsub(line, 1, 1)
+ if first_chr == "%" or stringis_empty(line) then
+ -- comment or empty line
+ elseif first_chr == "-" then
+ logreport ("both", 3, "db",
+ "Whitelisted file %q via %q.",
+ line, path)
+ whitelist[#whitelist+1] = stringsub(line, 2, -1)
+ else
+ local cmt = stringfind(line, "%%")
+ if cmt then
+ line = stringsub(line, 1, cmt - 1)
+ end
+ line = stringstrip(line)
+ logreport ("both", 3, "db",
+ "Blacklisted file %q via %q.",
+ line, path)
+ blacklist[#blacklist+1] = line
+ end
+ end
+ end
+ end
+ names.blacklist = create_blacklist(blacklist, whitelist)
+end
+
+local p_font_filter
+
+do
+ local extension_pattern = function (list)
+ if type (list) ~= "table" or #list == 0 then return P(-1) end
+ local pat
+ for i=#list, 1, -1 do
+ local e = list[i]
+ if not pat then
+ pat = P(e)
+ else
+ pat = pat + P(e)
+ end
+ end
+ pat = pat * P(-1)
+ return (1 - pat)^1 * pat
+ end
+
+ --- small helper to adjust the font filter pattern (--formats
+ --- option)
+
+ local current_formats = { }
+
+ set_font_filter = function (formats)
+
+ if not formats or type (formats) ~= "string" then
+ return
+ end
+
+ if splitcomma == nil then
+ splitcomma = luaotfload.parsers and luaotfload.parsers.splitcomma
+ end
+ if stringsub (formats, 1, 1) == "+" then -- add
+ formats = lpegmatch (splitcomma, stringsub (formats, 2))
+ if formats then
+ current_formats = tableappend (current_formats, formats)
+ end
+ elseif stringsub (formats, 1, 1) == "-" then -- add
+ formats = lpegmatch (splitcomma, stringsub (formats, 2))
+ if formats then
+ local newformats = { }
+ for i = 1, #current_formats do
+ local fmt = current_formats[i]
+ local include = true
+ for j = 1, #formats do
+ if current_formats[i] == formats[j] then
+ include = false
+ goto skip
+ end
+ end
+ newformats[#newformats+1] = fmt
+ ::skip::
+ end
+ current_formats = newformats
+ end
+ else -- set
+ formats = lpegmatch (splitcomma, formats)
+ if formats then
+ current_formats = formats
+ end
+ end
+
+ p_font_filter = extension_pattern (current_formats)
+ end
+
+ get_font_filter = function (formats)
+ return tablefastcopy (current_formats)
+ end
+end
+
+local locate_matching_pfb = function (afmfile, dir)
+ local pfbname = filereplacesuffix (afmfile, "pfb")
+ local pfbpath = dir .. "/" .. pfbname
+ if lfsisfile (pfbpath) then
+ return pfbpath
+ end
+ --- Check for match in texmf too
+ return kpsefind_file (pfbname, "type1 fonts")
+end
+
+local process_dir_tree
+process_dir_tree = function (acc, dirs, done)
+ if not next (dirs) then --- done
+ return acc
+ end
+
+ local pwd = lfscurrentdir ()
+ local dir = dirs[#dirs]
+ dirs[#dirs] = nil
+
+ if not lfschdir (dir) then
+ --- Cannot cd; skip.
+ return process_dir_tree (acc, dirs, done)
+ end
+
+ dir = lfscurrentdir () --- resolve symlinks
+ lfschdir (pwd)
+ if tablecontains (done, dir) then
+ --- Already traversed. Note that it’d be unsafe to rely on the
+ --- hash part above due to Lua only processing up to 32 bytes
+ --- of string data. The lookup shouldn’t impact performance too
+ --- much but we could check the performance of alternative data
+ --- structures at some point.
+ return process_dir_tree (acc, dirs, done)
+ end
+
+ local newfiles = { }
+ local blacklist = names.blacklist
+ for ent in lfsdir (dir) do
+ --- filter right away
+ if ent ~= "." and ent ~= ".." and not blacklist[ent] then
+ local fullpath = dir .. "/" .. ent
+ if lfsisdir (fullpath)
+ and not lpegmatch (p_blacklist, fullpath)
+ then
+ dirs[#dirs+1] = fullpath
+ elseif lfsisfile (fullpath) then
+ ent = stringlower (ent)
+ if lpegmatch (p_font_filter, ent) then
+ if filesuffix (ent) == "afm" then
+ local pfbpath = locate_matching_pfb (ent, dir)
+ if pfbpath then
+ newfiles[#newfiles+1] = pfbpath
+ end
+ end
+ newfiles[#newfiles+1] = fullpath
+ end
+ end
+ end
+ end
+ done [#done + 1] = dir
+ return process_dir_tree (tableappend (acc, newfiles), dirs, done)
+end
+
+local process_dir = function (dir)
+ local pwd = lfscurrentdir ()
+ if lfschdir (dir) then
+ dir = lfscurrentdir () --- resolve symlinks
+ lfschdir (pwd)
+
+ local files = { }
+ local blacklist = names.blacklist
+ for ent in lfsdir (dir) do
+ if ent ~= "." and ent ~= ".." and not blacklist[ent] then
+ local fullpath = dir .. "/" .. ent
+ if lfsisfile (fullpath) then
+ ent = stringlower (ent)
+ if lpegmatch (p_font_filter, ent)
+ then
+ if filesuffix (ent) == "afm" then
+ local pfbpath = locate_matching_pfb (ent, dir)
+ if pfbpath then
+ files[#files+1] = pfbpath
+ end
+ else
+ files[#files+1] = fullpath
+ end
+ end
+ end
+ end
+ end
+ return files
+ end
+ return { }
+end
+
+--- string -> bool -> string list
+local find_font_files = function (root, recurse)
+ if lfsisdir (root) then
+ if recurse == true then
+ return process_dir_tree ({}, { root }, {})
+ else --- kpathsea already delivered the necessary subdirs
+ return process_dir (root)
+ end
+ end
+end
+
+--- truncate_string -- Cut the first part of a string to fit it
+--- into a given terminal width. The parameter “restrict” (int)
+--- indicates the number of characters already consumed on the
+--- line.
+local truncate_string = function (str, restrict)
+ local tw = config.luaotfload.misc.termwidth
+ local wd = tw - restrict
+ local len = utf8len (str)
+ if wd - len < 0 then
+ --- combined length exceeds terminal,
+ str = ".." .. stringsub(str, utf8offset(str, - wd + 2))
+ end
+ return str
+end
+
+
+--[[doc--
+
+ collect_font_filenames_dir -- Traverse the directory root at
+ ``dirname`` looking for font files. Returns a list of {*filename*;
+ *location*} pairs.
+
+--doc]]--
+
+--- string -> string -> string * string list
+local collect_font_filenames_dir = function (dirname, location)
+ if lpegmatch (p_blacklist, dirname) then
+ logreport ("both", 4, "db",
+ "Skipping blacklisted directory %s.", dirname)
+ --- ignore
+ return { }
+ end
+ local found = find_font_files (dirname, location ~= "texmf" and location ~= "local")
+ if not found then
+ logreport ("both", 4, "db",
+ "No such directory: %q; skipping.", dirname)
+ return { }
+ end
+
+ local nfound = #found
+ local files = { }
+
+ logreport ("both", 4, "db",
+ "%d font files detected in %s.",
+ nfound, dirname)
+ for j = 1, nfound do
+ local fullname = found[j]
+ files[#files + 1] = { path_normalize (fullname), location }
+ end
+ return files
+end
+
+--- string list -> string list
+local filter_out_pwd = function (dirs)
+ local result = { }
+ if stripslashes == nil then
+ stripslashes = luaotfload.parsers and luaotfload.parsers.stripslashes
+ end
+ local pwd = path_normalize (lpegmatch (stripslashes,
+ lfscurrentdir ()))
+ for i = 1, #dirs do
+ --- better safe than sorry
+ local dir = path_normalize (lpegmatch (stripslashes, dirs[i]))
+ if dir == "." or dir == pwd then
+ logreport ("both", 3, "db",
+ "Path “%s” matches $PWD (“%s”), skipping.",
+ dir, pwd)
+ else
+ result[#result+1] = dir
+ end
+ end
+ return result
+end
+
+local path_separator = os.type == "windows" and ";" or ":"
+
+--[[doc--
+
+ collect_font_filenames_texmf -- Scan texmf tree for font files
+ relying on the kpathsea variables $OPENTYPEFONTS and $TTFONTS of
+ texmf.cnf.
+ The current working directory comes as “.” (texlive) or absolute
+ path (miktex) and will always be filtered out.
+
+ Returns a list of { *filename*; *location* } pairs.
+
+--doc]]--
+
+--- unit -> string * string list
+local collect_font_filenames_texmf = function ()
+
+ local osfontdir = kpseexpand_path "$OSFONTDIR"
+
+ if stringis_empty (osfontdir) then
+ logreport ("both", 1, "db", "Scanning TEXMF for fonts...")
+ else
+ logreport ("both", 1, "db", "Scanning TEXMF and $OSFONTDIR for fonts...")
+ if log.get_loglevel () > 3 then
+ local osdirs = filesplitpath (osfontdir)
+ logreport ("both", 0, "db", "$OSFONTDIR has %d entries:", #osdirs)
+ for i = 1, #osdirs do
+ logreport ("both", 0, "db", "[%d] %s", i, osdirs[i])
+ end
+ end
+ end
+
+ fontdirs = kpseexpand_path "$OPENTYPEFONTS"
+ fontdirs = fontdirs .. path_separator .. kpseexpand_path "$TTFONTS"
+ fontdirs = fontdirs .. path_separator .. kpseexpand_path "$T1FONTS"
+ fontdirs = fontdirs .. path_separator .. kpseexpand_path "$AFMFONTS"
+
+ if stringis_empty (fontdirs) then
+ return { }
+ end
+
+ local tasks = filter_out_pwd (filesplitpath (fontdirs))
+ logreport ("both", 3, "db",
+ "Initiating scan of %d directories.", #tasks)
+
+ local files = { }
+ for _, dir in next, tasks do
+ files = tableappend (files, collect_font_filenames_dir (dir, "texmf"))
+ end
+ logreport ("both", 3, "db", "Collected %d files.", #files)
+ return files
+end
+
+--- unit -> string list
+local function get_os_dirs ()
+ if os.name == 'macosx' then
+ return {
+ filejoin(kpseexpand_path('~'), "Library/Fonts"),
+ "/Library/Fonts",
+ "/System/Library/Fonts",
+ "/Network/Library/Fonts",
+ }
+ elseif os.type == "windows" or os.type == "msdos" then
+ local windir = osgetenv("WINDIR")
+ return { filejoin(windir, 'Fonts') }
+ else
+ local fonts_conves = { --- plural, much?
+ "/usr/local/etc/fonts/fonts.conf",
+ "/etc/fonts/fonts.conf",
+ }
+ if not luaotfload.parsers then
+ logreport ("log", 0, "db", "Fatal: no fonts.conf parser.")
+ end
+ local os_dirs = luaotfload.parsers.read_fonts_conf(fonts_conves, find_files)
+ return os_dirs
+ end
+ return {}
+end
+
+--[[doc--
+
+ count_removed -- Count paths that do not exist in the file system.
+
+--doc]]--
+
+--- string list -> size_t
+local count_removed = function (files)
+ if not files or not files.full then
+ logreport ("log", 4, "db", "Empty file store; no data to work with.")
+ return 0
+ end
+ local old = files.full
+ logreport ("log", 4, "db", "Checking removed files.")
+ local nrem = 0
+ local nold = #old
+ for i = 1, nold do
+ local f = old[i]
+ if not kpsereadable_file (f) then
+ logreport ("log", 2, "db",
+ "File %s does not exist in file system.")
+ nrem = nrem + 1
+ end
+ end
+ return nrem
+end
+
+--[[doc--
+
+ retrieve_namedata -- Scan the list of collected fonts and populate
+ the list of namedata.
+
+ · dirname : name of the directory to scan
+ · currentnames : current font db object
+ · targetnames : font db object to fill
+ · dry_run : don’t touch anything
+
+ Returns the number of fonts that were actually added to the index.
+
+--doc]]--
+
+--- string * string list -> dbobj -> dbobj -> bool? -> int * int
+local retrieve_namedata = function (files, currentnames, targetnames, dry_run)
+
+ local nfiles = #files
+ local nnew = 0
+
+ logreport ("info", 1, "db", "Scanning %d collected font files ...", nfiles)
+
+ local bylocation = { texmf = { 0, 0 }
+ , ["local"] = { 0, 0 }
+ , system = { 0, 0 }
+ }
+ report_status_start (2, 4)
+ for i = 1, nfiles do
+ local fullname, location = unpack (files[i])
+ local count = bylocation[location]
+ count[1] = count[1] + 1
+ if dry_run == true then
+ local truncated = truncate_string (fullname, 43)
+ logreport ("log", 2, "db", "Would have been loading %s.", fullname)
+ report_status ("term", "db", "Would have been loading %s", truncated)
+ --- skip the read_font_names part
+ else
+ local truncated = truncate_string (fullname, 32)
+ logreport ("log", 2, "db", "Loading font %s.", fullname)
+ report_status ("term", "db", "Loading font %s", truncated)
+ local new = read_font_names (fullname, currentnames,
+ targetnames, location)
+ if new == true then
+ nnew = nnew + 1
+ count[2] = count[2] + 1
+ end
+ end
+ end
+ report_status_stop ("term", "db", "Scanned %d files, %d new.", nfiles, nnew)
+ for location, count in next, bylocation do
+ logreport ("term", 4, "db", " * %s: %d files, %d new",
+ location, count[1], count[2])
+ end
+ return nnew
+end
+
+--- unit -> string * string list
+local collect_font_filenames_system = function ()
+
+ local n_scanned, n_new = 0, 0
+ logreport ("info", 1, "db", "Scanning system fonts...")
+ logreport ("info", 2, "db",
+ "Searching in static system directories...")
+
+ local files = { }
+ for _, dir in next, get_os_dirs () do
+ tableappend (files, collect_font_filenames_dir (dir, "system"))
+ end
+ logreport ("term", 3, "db", "Collected %d files.", #files)
+ return files
+end
+
+--- unit -> bool
+flush_lookup_cache = function ()
+ lookup_cache = { }
+ collectgarbage "collect"
+ return true
+end
+
+--[[doc--
+
+ collect_font_filenames_local -- Scan $PWD (during a TeX run)
+ for font files.
+
+ Side effect: This sets the “local” flag in the subtable “meta” to
+ prevent the merged table from being saved to disk.
+
+ TODO the local tree could be cached in $PWD.
+
+--doc]]--
+
+--- unit -> string * string list
+local collect_font_filenames_local = function ()
+ local pwd = lfscurrentdir ()
+ logreport ("both", 1, "db", "Scanning for fonts in $PWD (%q) ...", pwd)
+
+ local files = collect_font_filenames_dir (pwd, "local")
+ local nfiles = #files
+ if nfiles > 0 then
+ targetnames.meta["local"] = true --- prevent saving to disk
+ logreport ("term", 1, "db", "Found %d files.", pwd)
+ else
+ logreport ("term", 1, "db",
+ "Couldn’t find a thing here. What a waste.", pwd)
+ end
+ logreport ("term", 3, "db", "Collected %d files.", #files)
+ return files
+end
+
+--- fontentry list -> filemap
+generate_filedata = function (mappings)
+
+ logreport ("both", 2, "db", "Creating filename map.")
+
+ local nmappings = #mappings
+
+ local files = {
+ bare = {
+ ["local"] = { },
+ system = { }, --- mapped to mapping format -> index in full
+ texmf = { }, --- mapped to mapping format -> “true”
+ },
+ base = {
+ ["local"] = { },
+ system = { }, --- mapped to index in “full”
+ texmf = { }, --- set; all values are “true”
+ },
+ full = { }, --- non-texmf
+ }
+
+ local base = files.base
+ local bare = files.bare
+ local full = files.full
+
+ local conflicts = {
+ basenames = 0,
+ barenames = 0,
+ }
+
+ for index = 1, nmappings do
+ local entry = mappings [index]
+ local filedata = entry.file
+ local format
+ local location
+ local fullpath
+ local basename
+ local barename
+ local subfont
+
+ if filedata then --- new entry
+ format = entry.format --- otf, afm, ...
+ location = filedata.location --- texmf, system, ...
+ fullpath = filedata.full
+ basename = filedata.base
+ barename = filenameonly (fullpath)
+ subfont = filedata.subfont
+ else
+ format = entry.format --- otf, afm, ...
+ location = entry.location --- texmf, system, ...
+ fullpath = entry.fullpath
+ basename = entry.basename
+ barename = filenameonly (fullpath)
+ subfont = entry.subfont
+ end
+
+ entry.index = index
+
+ --- 1) add to basename table
+
+ local inbase = base [location] --- no format since the suffix is known
+
+ -- MK Added lowercase versions for case-insensitive fallback
+ if inbase then
+ local present = inbase [basename]
+ if present then
+ logreport ("both", 4, "db",
+ "Conflicting basename: %q already indexed \z
+ in category %s, ignoring.",
+ barename, location)
+ conflicts.basenames = conflicts.basenames + 1
+
+ --- track conflicts per font
+ local conflictdata = entry.conflicts
+
+ if not conflictdata then
+ entry.conflicts = { basename = present }
+ else -- some conflicts already detected
+ conflictdata.basename = present
+ end
+
+ else
+ local lowerbasename = stringlower (basename)
+ if basename ~= lowerbasename then
+ present = inbase [lowerbasename]
+ if present then
+ logreport ("both", 4, "db",
+ "Conflicting basename: %q already indexed \z
+ as %s.",
+ barename, mappings[present].basename)
+ conflicts.basenames = conflicts.basenames + 1
+
+ --- track conflicts per font
+ local conflictdata = entry.conflicts
+
+ if not conflictdata then
+ entry.conflicts = { basename = present }
+ else -- some conflicts already detected
+ conflictdata.basename = present
+ end
+
+ else
+ inbase [lowerbasename] = index
+ end
+ end
+ inbase [basename] = index
+ end
+ else
+ inbase = { basename = index }
+ base [location] = inbase
+ local lowerbasename = stringlower (basename)
+ if basename ~= lowerbasename then
+ inbase [lowerbasename] = index
+ end
+ end
+
+ --- 2) add to barename table
+
+ local inbare = bare [location] [format]
+
+ if inbare then
+ local present = inbare [barename]
+ if present then
+ logreport ("both", 4, "db",
+ "Conflicting barename: %q already indexed \z
+ in category %s/%s, ignoring.",
+ barename, location, format)
+ conflicts.barenames = conflicts.barenames + 1
+
+ --- track conflicts per font
+ local conflictdata = entry.conflicts
+
+ if not conflictdata then
+ entry.conflicts = { barename = present }
+ else -- some conflicts already detected
+ conflictdata.barename = present
+ end
+ else
+ local lowerbarename = stringlower (barename)
+ if barename ~= lowerbarename then
+ present = inbare [lowerbarename]
+ if present then
+ logreport ("both", 4, "db",
+ "Conflicting barename: %q already indexed \z
+ as %s.",
+ barename, mappings[present].basename)
+ conflicts.barenames = conflicts.barenames + 1
+
+ --- track conflicts per font
+ local conflictdata = entry.conflicts
+
+ if not conflictdata then
+ entry.conflicts = { barename = present }
+ else -- some conflicts already detected
+ conflictdata.barename = present
+ end
+ else
+ inbare [lowerbarename] = index
+ end
+ end
+ inbare [barename] = index
+ end
+ else
+ inbare = { [barename] = index }
+ bare [location] [format] = inbare
+ local lowerbarename = stringlower (barename)
+ if barename ~= lowerbarename then
+ inbare [lowerbarename] = index
+ end
+ end
+ -- /MK
+
+ --- 3) add to fullpath map
+
+ full [index] = fullpath
+ end --- mapping traversal
+
+ return files
+end
+
+local bold_spectrum_low = 501 --- 500 is medium, 900 heavy/black
+local normal_weight = 400
+local bold_weight = 700
+local normal_width = 5
+
+local pick_style
+local pick_fallback_style
+local check_regular
+
+do
+ pick_style = function (typographicsubfamily, subfamily)
+ return style_synonym [typographicsubfamily or subfamily or ""]
+ end
+
+ pick_fallback_style = function (italicangle, pfmweight, width)
+ --[[--
+ More aggressive, but only to determine bold faces.
+ Note: Before you make this test more inclusive, ensure
+ no fonts are matched in the bold synonym spectrum over
+ a literally “bold[italic]” one. In the past, heuristics
+ been tried but ultimately caused unwanted modifiers
+ polluting the lookup table. What doesn’t work is, e. g.
+ treating weights > 500 as bold or allowing synonyms like
+ “heavy”, “black”.
+ --]]--
+ if width == normal_width then
+ if pfmweight == bold_weight then
+ --- bold spectrum matches
+ if italicangle == 0 then
+ return "b"
+ end
+ return "bi"
+ elseif pfmweight == normal_weight then
+ if italicangle ~= 0 then
+ return "i"
+ end
+ end
+ return tostring(pfmweight) .. (italicangle == 0 and "" or "i")
+ end
+ return false
+ end
+
+ --- we use only exact matches here since there are constructs
+ --- like “regularitalic” (Cabin, Bodoni Old Fashion)
+
+ check_regular = function (typographicsubfamily,
+ subfamily,
+ italicangle,
+ weight,
+ width,
+ pfmweight)
+ local plausible_weight = false
+ --[[--
+ This filters out undesirable candidates that specify their
+ typographicsubfamily or subfamily as “regular” but are actually of
+ “semibold” or other weight—another drawback of the
+ oversimplifying classification into only three styles (r, i,
+ b, bi).
+ --]]--
+ if italicangle == 0 then
+ if pfmweight == 400 then
+ --[[--
+ Some fonts like Dejavu advertise an undistinguished
+ regular and a “condensed” version with the same
+ weight whilst also providing the style info in the
+ typographic subfamily instead of the subfamily (i. e.
+ the converse of what Adobe’s doing). The only way to
+ weed out the undesired pseudo-regular shape is to
+ peek at its advertised width (4 vs. 5).
+ --]]--
+ if width then
+ plausible_weight = width == normal_width
+ else
+ plausible_weight = true
+ end
+ elseif weight and regular_synonym [weight] then
+ plausible_weight = true
+ end
+ end
+
+ if plausible_weight then
+ if subfamily then
+ if regular_synonym [subfamily] then return "r" end
+ elseif typographicsubfamily then
+ if regular_synonym [typographicsubfamily] then return "r" end
+ end
+ end
+ return false
+ end
+end
+
+local pull_values = function (entry)
+ local file = entry.file
+ local names = entry.names
+ local style = entry.style
+ local sanitized = names.sanitized
+ local english = sanitized.english
+ local info = sanitized.info
+ local metadata = sanitized.metadata
+
+ --- pull file info ...
+ entry.basename = file.base
+ entry.fullpath = file.full
+ entry.location = file.location
+ entry.subfont = file.subfont
+
+ --- pull name info ...
+ entry.psname = english.psname
+ entry.fontname = info.fontname or metadata.fontname
+ entry.fullname = english.fullname or info.fullname
+ entry.typographicsubfamily = english.typographicsubfamily
+ entry.familyname = metadata.familyname or english.typographicfamily or english.family
+ entry.plainname = names.fullname
+ entry.subfamily = english.subfamily
+
+ --- pull style info ...
+ entry.italicangle = style.italicangle
+ entry.size = style.size
+ entry.weight = style.weight
+ entry.width = style.width
+ entry.pfmweight = style.pfmweight
+
+ if config.luaotfload.db.strip == true then
+ entry.file = nil
+ entry.names = nil
+ entry.style = nil
+ end
+end
+
+local add_family = function (name, subtable, modifier, entry)
+ if not name then --- probably borked font
+ return
+ end
+ local familytable = subtable [name]
+ if not familytable then
+ familytable = { }
+ subtable [name] = familytable
+ end
+
+ familytable [#familytable + 1] = {
+ index = entry.index,
+ modifier = modifier,
+ }
+end
+
+local add_lastresort_regular = function (name, subtable, entry)
+ if not name then --- probably borked font
+ return
+ end
+ local familytable = subtable [name]
+ if not familytable then
+ familytable = { }
+ subtable [name] = familytable
+ end
+ familytable.fallback = entry.index
+end
+
+local get_subtable = function (families, entry)
+ local location = entry.location
+ local format = entry.format
+ local subtable = families [location] [format]
+ if not subtable then
+ subtable = { }
+ families [location] [format] = subtable
+ end
+ return subtable
+end
+
+local collect_families = function (mappings)
+
+ logreport ("info", 2, "db", "Analyzing families.")
+
+ local families = {
+ ["local"] = { },
+ system = { },
+ texmf = { },
+ }
+
+ for i = 1, #mappings do
+
+ local entry = mappings [i]
+
+ if entry.file then
+ pull_values (entry)
+ end
+
+ local subtable = get_subtable (families, entry)
+ local familyname = entry.familyname
+ local typographicsubfamily = entry.typographicsubfamily
+ local subfamily = entry.subfamily
+ local weight = entry.weight
+ local width = entry.width
+ local pfmweight = entry.pfmweight
+ local italicangle = entry.italicangle
+ local modifier = pick_style (typographicsubfamily, subfamily)
+
+ if not modifier then --- regular, exact only
+ modifier = check_regular (typographicsubfamily,
+ subfamily,
+ italicangle,
+ weight,
+ width,
+ pfmweight)
+ end
+
+ if not modifier then
+ modifier = pick_fallback_style (italicangle, pfmweight, width)
+ end
+
+ if modifier then
+ add_family (familyname, subtable, modifier, entry)
+ end
+ if modifier ~= 'r' and regular_synonym[typographicsubfamily or subfamily or ''] then
+ add_lastresort_regular (familyname, subtable, entry)
+ end
+ end
+
+ collectgarbage "collect"
+ return families
+end
+
+--[[doc--
+
+ group_modifiers -- For not-quite-bold faces, determine whether
+ they can fill in for a missing bold face slot in a matching family.
+
+ Some families like Lucida do not contain real bold / bold italic
+ members. Instead, they have semibold variants at weight 600 which
+ we must add in a separate pass.
+
+--doc]]--
+
+local style_categories = { "r", "b", "i", "bi" }
+local bold_categories = { "b", "bi" }
+
+group_modifiers = function (mappings, families)
+ logreport ("info", 2, "db", "Analyzing shapes, weights, and styles.")
+ for location, location_data in next, families do
+ for format, format_data in next, location_data do
+ for familyname, collected in next, format_data do
+ local styledata = { } --- will replace the “collected” table
+ local lastresort_regular = collected.fallback
+ collected.fallback = nil
+ --- First, fill in the ordinary style data that
+ --- fits neatly into the four relevant modifier
+ --- categories.
+ for _, modifier in next, style_categories do
+ local entries
+ for key, info in next, collected do
+ if info.modifier == modifier then
+ if not entries then
+ entries = { }
+ end
+ local index = info.index
+ local entry = mappings [index]
+ local size = entry.size
+ if size then
+ entries [#entries + 1] = {
+ size [1],
+ size [2],
+ size [3],
+ index,
+ }
+ else
+ entries.default = index
+ end
+ collected [key] = nil
+ end
+ styledata [modifier] = entries
+ end
+ end
+ if not styledata.r and lastresort_regular then
+ styledata.r = {default = lastresort_regular}
+ end
+
+ --- At this point the family set may still lack
+ --- entries for bold or bold italic. We will fill
+ --- those in using the modifier with the numeric
+ --- weight that is closest to bold (700).
+ if next (collected) then --- there are uncategorized entries
+ for _, modifier in next, bold_categories do
+ if not styledata [modifier] then
+ local closest
+ local minimum = 2^51
+ for key, info in next, collected do
+ local info_modifier = tonumber (info.modifier) and "b" or "bi"
+ if modifier == info_modifier then
+ local index = info.index
+ local entry = mappings [index]
+ local weight = entry.pfmweight
+ local diff = weight < 700 and 700 - weight or weight - 700
+ if weight > 500 and diff < minimum then
+ minimum = diff
+ closest = weight
+ end
+ end
+ end
+ if closest then
+ --- We know there is a substitute face for the modifier.
+ --- Now we scan the list again to extract the size data
+ --- in case the shape is available at multiple sizes.
+ local entries = { }
+ for key, info in next, collected do
+ local info_modifier = tonumber (info.modifier) and "b" or "bi"
+ if modifier == info_modifier then
+ local index = info.index
+ local entry = mappings [index]
+ local size = entry.size
+ if entry.pfmweight == closest then
+ if size then
+ entries [#entries + 1] = {
+ size [1],
+ size [2],
+ size [3],
+ index,
+ }
+ else
+ entries.default = index
+ end
+ end
+ end
+ end
+ styledata [modifier] = entries
+ end
+ end
+ end
+ end
+ format_data [familyname] = styledata
+ end
+ end
+ end
+ return families
+end
+
+local cmp_sizes = function (a, b)
+ return a [1] < b [1]
+end
+
+order_design_sizes = function (families)
+
+ logreport ("info", 2, "db", "Ordering design sizes.")
+
+ for location, data in next, families do
+ for format, data in next, data do
+ for familyname, data in next, data do
+ for style, data in next, data do
+ tablesort (data, cmp_sizes)
+ end
+ end
+ end
+ end
+
+ return families
+end
+
+--[[doc--
+
+ collect_font_filenames -- Scan the three search path categories for
+ font files. This constitutes the first pass of the update mode.
+
+--doc]]--
+
+--- unit -> string * string list
+local collect_font_filenames = function ()
+
+ logreport ("info", 4, "db", "Scanning the filesystem for font files.")
+
+ local filenames = { }
+ local bisect = config.luaotfload.misc.bisect
+ local max_fonts = config.luaotfload.db.max_fonts --- XXX revisit for lua 5.3 wrt integers
+
+ tableappend (filenames, collect_font_filenames_texmf ())
+ tableappend (filenames, collect_font_filenames_system ())
+ if config.luaotfload.db.scan_local == true then
+ tableappend (filenames, collect_font_filenames_local ())
+ end
+ --- Now drop everything above max_fonts.
+ if max_fonts < #filenames then
+ filenames = { unpack (filenames, 1, max_fonts) }
+ end
+ --- And choose the requested slice if in bisect mode.
+ if bisect then
+ return { unpack (filenames, bisect[1], bisect[2]) }
+ end
+ return filenames
+end
+
+--[[doc--
+
+ nth_font_file -- Return the filename of the nth font.
+
+--doc]]--
+
+--- int -> string
+local nth_font_filename = function (n)
+ logreport ("info", 4, "db", "Picking font file no. %d.", n)
+ if not p_blacklist then
+ read_blacklist ()
+ end
+ local filenames = collect_font_filenames ()
+ return filenames[n] and filenames[n][1] or "<error>"
+end
+
+--[[doc--
+
+ font_slice -- Return the fonts in the range from lo to hi.
+
+--doc]]--
+
+local font_slice = function (lo, hi)
+ logreport ("info", 4, "db", "Retrieving font files nos. %d--%d.", lo, hi)
+ if not p_blacklist then
+ read_blacklist ()
+ end
+ local filenames = collect_font_filenames ()
+ local result = { }
+ for i = lo, hi do
+ result[#result + 1] = filenames[i][1]
+ end
+ return result
+end
+
+--[[doc
+
+ count_font_files -- Return the number of files found by
+ collect_font_filenames. This function is exported primarily
+ for use with luaotfload-tool.lua in bisect mode.
+
+--doc]]--
+
+--- unit -> int
+local count_font_files = function ()
+ logreport ("info", 4, "db", "Counting font files.")
+ if not p_blacklist then
+ read_blacklist ()
+ end
+ return #collect_font_filenames ()
+end
+
+--- dbobj -> stats
+
+local collect_statistics = function (mappings)
+ local sum_dsnsize, n_dsnsize = 0, 0
+
+ local fullname, family, families = { }, { }, { }
+ local subfamily, typographicsubfamily = { }, { }
+
+ local addtohash = function (hash, item)
+ if item then
+ local times = hash [item]
+ if times then
+ hash [item] = times + 1
+ else
+ hash [item] = 1
+ end
+ end
+ end
+
+ local appendtohash = function (hash, key, value)
+ if key and value then
+ local entry = hash [key]
+ if entry then
+ entry [#entry + 1] = value
+ else
+ hash [key] = { value }
+ end
+ end
+ end
+
+ local addtoset = function (hash, key, value)
+ if key and value then
+ local set = hash [key]
+ if set then
+ set [value] = true
+ else
+ hash [key] = { [value] = true }
+ end
+ end
+ end
+
+ local setsize = function (set)
+ local n = 0
+ for _, _ in next, set do
+ n = n + 1
+ end
+ return n
+ end
+
+ local hashsum = function (hash)
+ local n = 0
+ for _, m in next, hash do
+ n = n + m
+ end
+ return n
+ end
+
+ for _, entry in next, mappings do
+ local style = entry.style
+ local names = entry.names.sanitized
+ local englishnames = names.english
+
+ addtohash (fullname, englishnames.fullname)
+ addtohash (family, englishnames.family)
+ addtohash (subfamily, englishnames.subfamily)
+ addtohash (typographicsubfamily, englishnames.typographicsubfamily)
+
+ addtoset (families, englishnames.family, englishnames.fullname)
+
+ local sizeinfo = entry.style.size
+ if sizeinfo then
+ sum_dsnsize = sum_dsnsize + sizeinfo [1]
+ n_dsnsize = n_dsnsize + 1
+ end
+ end
+
+ --inspect (families)
+
+ local n_fullname = setsize (fullname)
+ local n_family = setsize (family)
+
+ if log.get_loglevel () > 1 then
+ local pprint_top = function (hash, n, set)
+
+ local freqs = { }
+ local items = { }
+
+ for item, value in next, hash do
+ if set then
+ freq = setsize (value)
+ else
+ freq = value
+ end
+ local ifreq = items [freq]
+ if ifreq then
+ ifreq [#ifreq + 1] = item
+ else
+ items [freq] = { item }
+ freqs [#freqs + 1] = freq
+ end
+ end
+
+ tablesort (freqs)
+
+ local from = #freqs
+ local to = from - (n - 1)
+ if to < 1 then
+ to = 1
+ end
+
+ for i = from, to, -1 do
+ local freq = freqs [i]
+ local itemlist = items [freq]
+
+ if type (itemlist) == "table" then
+ itemlist = tableconcat (itemlist, ", ")
+ end
+
+ logreport ("both", 0, "db",
+ " · %4d × %s.",
+ freq, itemlist)
+ end
+ end
+
+ logreport ("both", 0, "", "~~~~ font index statistics ~~~~")
+ logreport ("both", 0, "db",
+ " · Collected %d fonts (%d names) in %d families.",
+ #mappings, n_fullname, n_family)
+ pprint_top (families, 4, true)
+
+ logreport ("both", 0, "db",
+ " · %d different “subfamily” kinds.",
+ setsize (subfamily))
+ pprint_top (subfamily, 4)
+
+ logreport ("both", 0, "db",
+ " · %d different “typographicsubfamily” kinds.",
+ setsize (typographicsubfamily))
+ pprint_top (typographicsubfamily, 4)
+
+ end
+
+ local mean_dsnsize = 0
+ if n_dsnsize > 0 then
+ mean_dsnsize = sum_dsnsize / n_dsnsize
+ end
+
+ return {
+ mean_dsnsize = mean_dsnsize,
+ names = {
+ fullname = n_fullname,
+ families = n_family,
+ },
+-- style = {
+-- subfamily = subfamily,
+-- typographicsubfamily = typographicsubfamily,
+-- },
+ }
+end
+
+--- force: dictate rebuild from scratch
+--- dry_dun: don’t write to the db, just scan dirs
+
+--- dbobj? -> bool? -> bool? -> dbobj
+update_names = function (currentnames, force, dry_run)
+ local targetnames
+ local n_new = 0
+ local n_rem = 0
+
+ local conf = config.luaotfload
+ if conf.run.live ~= false and conf.db.update_live == false then
+ logreport ("info", 2, "db", "Skipping database update.")
+ --- skip all db updates
+ return currentnames or name_index
+ end
+
+ local starttime = osgettimeofday ()
+
+ --[[
+ The main function, scans everything
+ - “targetnames” is the final table to return
+ - force is whether we rebuild it from scratch or not
+ ]]
+ logreport ("both", 1, "db",
+ "Updating the font names database"
+ .. (force and " forcefully." or "."))
+
+ if config.luaotfload.db.skip_read == true then
+ --- the difference to a “dry run” is that we don’t search
+ --- for font files entirely. we also ignore the “force”
+ --- parameter since it concerns only the font files.
+ logreport ("info", 2, "db",
+ "Ignoring font files, reusing old data.")
+ currentnames = load_names (false)
+ targetnames = currentnames
+ else
+ if force then
+ currentnames = initialize_namedata (get_font_filter ())
+ else
+ if not currentnames or not next (currentnames) then
+ currentnames = load_names (dry_run)
+ end
+ if currentnames.meta.version ~= names.version then
+ logreport ("both", 1, "db",
+ "No font names database or old \z
+ one found; generating new one.")
+ currentnames = initialize_namedata (get_font_filter ())
+ end
+ end
+
+ targetnames = initialize_namedata (get_font_filter (),
+ currentnames.meta and currentnames.meta.created)
+
+ read_blacklist ()
+
+ --- pass 1: Collect the names of all fonts we are going to process.
+ local font_filenames = collect_font_filenames ()
+
+ --- pass 2: read font files (normal case) or reuse information
+ --- present in index
+
+ n_rem = count_removed (currentnames.files)
+
+ n_new = retrieve_namedata (font_filenames,
+ currentnames,
+ targetnames,
+ dry_run)
+
+ logreport ("info", 3, "db",
+ "Found %d font files; %d new, %d stale entries.",
+ #font_filenames, n_new, n_rem)
+ end
+
+ --- pass 3 (optional): collect some stats about the raw font info
+ if config.luaotfload.misc.statistics == true then
+ targetnames.meta.statistics = collect_statistics
+ (targetnames.mappings)
+ end
+
+ --- we always generate the file lookup tables because
+ --- non-texmf entries are redirected there and the mapping
+ --- needs to be 100% consistent
+
+ --- pass 4: build filename table
+ targetnames.files = generate_filedata (targetnames.mappings)
+
+ --- pass 5: build family lookup table
+ targetnames.families = collect_families (targetnames.mappings)
+
+ --- pass 6: arrange style and size info
+ targetnames.families = group_modifiers (targetnames.mappings,
+ targetnames.families)
+
+ --- pass 7: order design size tables
+ targetnames.families = order_design_sizes (targetnames.families)
+
+ logreport ("info", 3, "db",
+ "Rebuilt in %0.f ms.",
+ 1000 * (osgettimeofday () - starttime))
+ name_index = targetnames
+
+ if dry_run ~= true then
+
+ if n_new + n_rem == 0 then
+ logreport ("info", 2, "db",
+ "No new or removed fonts, skip saving to disk.")
+ else
+ local success, reason = save_names ()
+ if not success then
+ logreport ("both", 0, "db",
+ "Failed to save database to disk: %s",
+ reason)
+ end
+ end
+
+ if flush_lookup_cache () and save_lookups () then
+ logreport ("both", 2, "cache", "Lookup cache emptied.")
+ return targetnames
+ end
+ end
+ return targetnames
+end
+
+--- unit -> bool
+save_lookups = function ( )
+ local paths = config.luaotfload.paths
+ local luaname, lucname = paths.lookup_path_lua, paths.lookup_path_luc
+ if fileiswritable (luaname) and fileiswritable (lucname) then
+ tabletofile (luaname, lookup_cache, true)
+ osremove (lucname)
+ caches.compile (lookup_cache, luaname, lucname)
+ --- double check ...
+ if lfsisfile (luaname) and lfsisfile (lucname) then
+ logreport ("both", 3, "cache", "Lookup cache saved.")
+ return true
+ end
+ logreport ("info", 0, "cache", "Could not compile lookup cache.")
+ return false
+ end
+ logreport ("info", 0, "cache", "Lookup cache file not writable.")
+ if not fileiswritable (luaname) then
+ logreport ("info", 0, "cache", "Failed to write %s.", luaname)
+ end
+ if not fileiswritable (lucname) then
+ logreport ("info", 0, "cache", "Failed to write %s.", lucname)
+ end
+ return false
+end
+
+--- save_names() is usually called without the argument
+--- dbobj? -> bool * string option
+save_names = function (currentnames)
+ if not currentnames then
+ currentnames = name_index
+ end
+ if not currentnames or type (currentnames) ~= "table" then
+ return false, "invalid names table"
+ elseif currentnames.meta and currentnames.meta["local"] then
+ return false, "table contains local entries"
+ end
+ local paths = config.luaotfload.paths
+ local luaname, lucname = paths.index_path_lua, paths.index_path_luc
+ if fileiswritable (luaname) and fileiswritable (lucname) then
+ osremove (lucname)
+ local gzname = luaname .. ".gz"
+ if config.luaotfload.db.compress then
+ local serialized = tableserialize (currentnames, true)
+ gzipsave (gzname, serialized)
+ caches.compile (currentnames, "", lucname)
+ else
+ tabletofile (luaname, currentnames, true)
+ caches.compile (currentnames, luaname, lucname)
+ end
+ logreport ("info", 2, "db", "Font index saved at ...")
+ local success = false
+ if lfsisfile (luaname) then
+ logreport ("info", 2, "db", "Text: " .. luaname)
+ success = true
+ end
+ if lfsisfile (gzname) then
+ logreport ("info", 2, "db", "Gzip: " .. gzname)
+ success = true
+ end
+ if lfsisfile (lucname) then
+ logreport ("info", 2, "db", "Byte: " .. lucname)
+ success = true
+ end
+ if success then
+ return true
+ else
+ logreport ("info", 0, "db", "Could not compile font index.")
+ return false
+ end
+ end
+ logreport ("info", 0, "db", "Index file not writable")
+ if not fileiswritable (luaname) then
+ logreport ("info", 0, "db", "Failed to write %s.", luaname)
+ end
+ if not fileiswritable (lucname) then
+ logreport ("info", 0, "db", "Failed to write %s.", lucname)
+ end
+ return false
+end
+
+--[[doc--
+
+ Below set of functions is modeled after mtx-cache.
+
+--doc]]--
+
+--- string -> string -> string list -> string list -> string list -> unit
+local print_cache = function (category, path, luanames, lucnames, rest)
+ local report_indeed = function (...)
+ logreport ("info", 0, "cache", ...)
+ end
+ report_indeed("Luaotfload cache: %s", category)
+ report_indeed("location: %s", path)
+ report_indeed("[raw] %4i", #luanames)
+ report_indeed("[compiled] %4i", #lucnames)
+ report_indeed("[other] %4i", #rest)
+ report_indeed("[total] %4i", #luanames + #lucnames + #rest)
+end
+
+--- string -> string -> string list -> bool -> bool
+local purge_from_cache = function (category, path, list, all)
+ logreport ("info", 1, "cache", "Luaotfload cache: %s %s",
+ (all and "erase" or "purge"), category)
+ logreport ("info", 1, "cache", "location: %s", path)
+ local n = 0
+ for i=1,#list do
+ local filename = list[i]
+ if stringfind(filename,"luatex%-cache") then -- safeguard
+ if all then
+ logreport ("info", 5, "cache", "Removing %s.", filename)
+ osremove(filename)
+ n = n + 1
+ else
+ local suffix = filesuffix(filename)
+ if suffix == "lua" then
+ local checkname = file.replacesuffix(
+ filename, "lua", "luc")
+ if lfsisfile(checkname) then
+ logreport ("info", 5, "cache", "Removing %s.", filename)
+ osremove(filename)
+ n = n + 1
+ end
+ end
+ end
+ end
+ end
+ logreport ("info", 1, "cache", "Removed lua files : %i", n)
+ return true
+end
+
+--- string -> string list -> int -> string list -> string list -> string list ->
+--- (string list * string list * string list * string list)
+local collect_cache collect_cache = function (path, all, n, luanames,
+ lucnames, rest)
+ if not all then
+ local all = find_files (path)
+
+ local luanames, lucnames, rest = { }, { }, { }
+ return collect_cache(nil, all, 1, luanames, lucnames, rest)
+ end
+
+ local filename = all[n]
+ if filename then
+ local suffix = filesuffix(filename)
+ if suffix == "lua" then
+ luanames[#luanames+1] = filename
+ elseif suffix == "luc" then
+ lucnames[#lucnames+1] = filename
+ else
+ rest[#rest+1] = filename
+ end
+ return collect_cache(nil, all, n+1, luanames, lucnames, rest)
+ end
+ return luanames, lucnames, rest, all
+end
+
+local getwritablecachepath = function ( )
+ --- fonts.handlers.otf doesn’t exist outside a Luatex run,
+ --- so we have to improvise
+ local writable = getwritablepath (config.luaotfload.paths.cache_dir, "")
+ if writable then
+ return writable
+ end
+end
+
+local getreadablecachepaths = function ( )
+ local readables = caches.getreadablepaths
+ (config.luaotfload.paths.cache_dir)
+ local result = { }
+ if readables then
+ for i=1, #readables do
+ local readable = readables[i]
+ if lfsisdir (readable) then
+ result[#result+1] = readable
+ end
+ end
+ end
+ return result
+end
+
+--- unit -> unit
+local purge_cache = function ( )
+ local writable_path = getwritablecachepath ()
+ local luanames, lucnames, rest = collect_cache(writable_path)
+ if log.get_loglevel() > 1 then
+ print_cache("writable path", writable_path, luanames, lucnames, rest)
+ end
+ local success = purge_from_cache("writable path", writable_path, luanames, false)
+ return success
+end
+
+--- unit -> unit
+local erase_cache = function ( )
+ local writable_path = getwritablecachepath ()
+ local luanames, lucnames, rest, all = collect_cache(writable_path)
+ if log.get_loglevel() > 1 then
+ print_cache("writable path", writable_path, luanames, lucnames, rest)
+ end
+ local success = purge_from_cache("writable path", writable_path, all, true)
+ return success
+end
+
+local separator = function ( )
+ logreport ("info", 0, string.rep("-", 67))
+end
+
+--- unit -> unit
+local show_cache = function ( )
+ local readable_paths = getreadablecachepaths ()
+ local writable_path = getwritablecachepath ()
+ local luanames, lucnames, rest = collect_cache(writable_path)
+
+ separator ()
+ print_cache ("writable path", writable_path,
+ luanames, lucnames, rest)
+ texio.write_nl""
+ for i=1,#readable_paths do
+ local readable_path = readable_paths[i]
+ if readable_path ~= writable_path then
+ local luanames, lucnames = collect_cache (readable_path)
+ print_cache ("readable path",
+ readable_path, luanames, lucnames, rest)
+ end
+ end
+ separator()
+ return true
+end
+
+-----------------------------------------------------------------------
+--- API assumptions of the fontloader
+-----------------------------------------------------------------------
+--- PHG: we need to investigate these, maybe they’re useful as early
+--- hooks
+
+local ignoredfile = function () return false end
+
+local reportmissingbase = function ()
+ logreport ("info", 0, "db", --> bug‽
+ "Font name database not found but expected by fontloader.")
+ fonts.names.reportmissingbase = nil
+end
+
+local reportmissingname = function ()
+ logreport ("info", 0, "db", --> bug‽
+ "Fontloader attempted to lookup name before Luaotfload \z
+ was initialized.")
+ fonts.names.reportmissingname = nil
+end
+
+local getfilename = function (a1, a2)
+ logreport ("info", 6, "db", --> bug‽
+ "Fontloader looked up font file (%s, %s) before Luaotfload \z
+ was initialized.", tostring(a1), tostring(a2))
+ return lookup_fullpath (a1, a2)
+end
+
+local resolve = function (name, subfont)
+ logreport ("info", 6, "db", --> bug‽
+ "Fontloader attempted to resolve name (%s, %s) before \z
+ Luaotfload was initialized.", tostring(name), tostring(subfont))
+ return lookup_font_name { name = name, sub = subfont }
+end
+
+local api = {
+ ignoredfile = ignoredfile,
+ reportmissingbase = reportmissingbase,
+ reportmissingname = reportmissingname,
+ getfilename = getfilename,
+ resolve = resolve,
+}
+
+-----------------------------------------------------------------------
+--- export functionality to the namespace “fonts.names”
+-----------------------------------------------------------------------
+
+local export = {
+ set_font_filter = set_font_filter,
+ set_size_dimension = set_size_dimension,
+ flush_lookup_cache = flush_lookup_cache,
+ save_lookups = save_lookups,
+ load = load_names,
+ access_font_index = access_font_index,
+ data = function () return name_index end,
+ save = save_names,
+ update = update_names,
+ lookup_font_file = lookup_font_file,
+ lookup_font_name = lookup_font_name,
+ lookup_font_name_cached = lookup_font_name_cached,
+ getfilename = lookup_fullpath,
+ lookup_fullpath = lookup_fullpath,
+ read_blacklist = read_blacklist,
+ sanitize_fontname = sanitize_fontname,
+ getmetadata = getmetadata,
+ set_location_precedence = set_location_precedence,
+ count_font_files = count_font_files,
+ nth_font_filename = nth_font_filename,
+ font_slice = font_slice,
+ --- font cache
+ purge_cache = purge_cache,
+ erase_cache = erase_cache,
+ show_cache = show_cache,
+ find_closest = find_closest,
+}
+
+return function ()
+ --- the font loader namespace is “fonts”, same as in Context
+ --- we need to put some fallbacks into place for when running
+ --- as a script
+ if not fonts then return false end
+ logreport = luaotfload.log.report
+ local fonts = fonts
+ fonts.names = fonts.names or names
+ fonts.formats = fonts.formats or { }
+ fonts.definers = fonts.definers or { resolvers = { } }
+
+ names.blacklist = blacklist
+ -- MK Changed to rebuild with case insensitive fallback.
+ -- Negative version to indicate generation by modified code.
+ names.version = -1 --- decrease monotonically
+ -- /MK
+ names.data = nil --- contains the loaded database
+ names.lookups = nil --- contains the lookup cache
+
+ for sym, ref in next, export do names[sym] = ref end
+ for sym, ref in next, api do names[sym] = names[sym] or ref end
+ return true
+end
+
+-- vim:tw=71:sw=4:ts=4:expandtab
diff --git a/macros/luatex/generic/luaotfload/luaotfload-diagnostics.lua b/macros/luatex/generic/luaotfload/luaotfload-diagnostics.lua
new file mode 100644
index 0000000000..8ef443aedc
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-diagnostics.lua
@@ -0,0 +1,698 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-diagnostics.lua
+-- DESCRIPTION: part of luaotfload-tool / functionality accessible by the --diagnose option
+-- REQUIREMENTS: luaotfload-tool.lua
+-- AUTHOR: Philipp Gesang <phg@phi-gamma.net>
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-diagnostics",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload-tool submodule / diagnostics",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+local names = fonts.names
+
+local kpse = require "kpse"
+local kpseexpand_path = kpse.expand_path
+local kpseexpand_var = kpse.expand_var
+local kpsefind_file = kpse.find_file
+
+local lfs = require "lfs"
+local lfsattributes = lfs.attributes
+local lfsisfile = lfs.isfile
+local lfsreadlink = lfs.readlink
+
+local md5 = require "md5"
+local md5sumhexa = md5.sumhexa
+
+local ioopen = io.open
+
+local osgetenv = os.getenv
+local osname = os.name
+local osremove = os.remove
+local ostype = os.type
+local stringformat = string.format
+local stringlower = string.lower
+local stringsub = string.sub
+
+local fileisreadable = file.isreadable
+local fileiswritable = file.iswritable
+local filesplitpath = file.splitpath
+local filesuffix = file.suffix
+local ioloaddata = io.loaddata
+local lua_of_json = utilities.json.tolua
+local tableconcat = table.concat
+local tablesortedkeys = table.sortedkeys
+local tabletohash = table.tohash
+
+local lpeg = require "lpeg"
+local C, Cg, Ct = lpeg.C, lpeg.Cg, lpeg.Ct
+local lpegmatch = lpeg.match
+
+local report = luaotfload.log.report
+local out = function (...)
+ report (false, 0, "diagnose", ...)
+end
+
+local parsers = luaotfload.parsers
+local stripslashes = parsers.stripslashes
+local splitcomma = parsers.splitcomma
+
+local check_index = function (errcnt)
+
+ out "================= font names =================="
+ local namedata = names.data()
+
+ if not namedata then
+ namedata = names.load ()
+ end
+
+ local mappings = namedata.mappings
+
+ if not namedata and namedata.formats and namedata.version then
+ out "Database corrupt."
+ return errcnt + 1
+ end
+
+ out ("Database version: %.3f.", namedata.meta.version)
+ out ("Font formats indexed: %s.",
+ tableconcat (namedata.meta.formats, ", "))
+ out ("%d font files indexed.", #mappings)
+
+ local by_format = { }
+ for i = 1, #mappings do
+ local record = mappings[i]
+ local format = stringlower (filesuffix (record.filename))
+ local count = by_format[format]
+ if count then
+ by_format[format] = count + 1
+ else
+ by_format[format] = 1
+ end
+ end
+
+ local formats = tablesortedkeys (by_format)
+ for i = 1, #formats do
+ local format = formats[i]
+ out ("%20s: %5d", format, by_format[format])
+ end
+ return errcnt
+end
+
+local verify_files = function (errcnt)
+ out "================ verify files ================="
+ local status = config.luaotfload.status
+ local hashes = status.hashes
+ local notes = status.notes
+ if not hashes or #hashes == 0 then
+ out ("FAILED: cannot read checksums from %s.", status_file)
+ return 1/0
+ elseif not notes then
+ out ("FAILED: cannot read commit metadata from %s.",
+ status_file)
+ return 1/0
+ end
+
+ out ("Luaotfload revision %s.", notes.revision)
+ out ("Committed by %s.", notes.committer)
+ out ("Timestamp %s.", notes.timestamp)
+
+ local nhashes = #hashes
+ out ("Testing %d files for integrity.", nhashes)
+ for i = 1, nhashes do
+ local fname, canonicalsum = unpack (hashes[i])
+ local location = kpsefind_file (fname)
+ or kpsefind_file (fname, "texmfscripts")
+ if not location then
+ errcnt = errcnt + 1
+ out ("FAILED: file %s missing.", fname)
+ else
+ out ("File: %s.", location)
+ local raw = ioloaddata (location)
+ if not raw then
+ errcnt = errcnt + 1
+ out ("FAILED: file %d not readable.", fname)
+ else
+ local sum = md5sumhexa (raw)
+ if sum ~= canonicalsum then
+ errcnt = errcnt + 1
+ out ("FAILED: checksum mismatch for file %s.",
+ fname)
+ out ("Expected %s.", canonicalsum)
+ out ("Got %s.", sum)
+ else
+ out ("Ok, %s passed.", fname)
+ end
+ end
+ end
+ end
+ return errcnt
+end
+
+local get_tentative_attributes = function (file)
+ if not lfsisfile (file) then
+ local chan = ioopen (file, "w")
+ if chan then
+ chan:close ()
+ local attributes = lfsattributes (file)
+ os.remove (file)
+ return attributes
+ end
+ end
+end
+
+local p_permissions = Ct(Cg(Ct(C(1) * C(1) * C(1)), "u")
+ * Cg(Ct(C(1) * C(1) * C(1)), "g")
+ * Cg(Ct(C(1) * C(1) * C(1)), "o"))
+
+local analyze_permissions = function (raw)
+ return lpegmatch (p_permissions, raw)
+end
+
+local get_permissions = function (t, location)
+ if stringsub (location, #location) == "/" then
+ --- strip trailing slashes (lfs idiosyncrasy on Win)
+ location = lpegmatch (stripslashes, location)
+ end
+ local attributes = lfsattributes (location)
+ if not attributes then
+ print""
+ print("attr", location, attributes)
+ os.exit()
+ end
+
+ if not attributes and t == "f" then
+ attributes = get_tentative_attributes (location)
+ if not attributes then
+ return false
+ end
+ end
+
+ local permissions
+
+ if fileisreadable (location) then
+ --- link handling appears to be unnecessary because
+ --- lfs.attributes() will return the information on
+ --- the link target.
+ if mode == "link" then --follow and repeat
+ location = lfsreadlink (location)
+ attributes = lfsattributes (location)
+ end
+ end
+
+ permissions = analyze_permissions (attributes.permissions)
+
+ return {
+ location = location,
+ mode = attributes.mode,
+ owner = attributes.uid, --- useless on windows
+ permissions = permissions,
+ attributes = attributes,
+ }
+end
+
+local check_conformance = function (spec, permissions, errcnt)
+ local uid = permissions.attributes.uid
+ local gid = permissions.attributes.gid
+ local raw = permissions.attributes.permissions
+
+ out ("Owner: %d, group %d, permissions %s.", uid, gid, raw)
+ if ostype == "unix" then
+ if uid == 0 or gid == 0 then
+ out "Owned by the superuser, permission conflict likely."
+ errcnt = errcnt + 1
+ end
+ end
+
+ local user = permissions.permissions.u
+ if spec.r == true then
+ if user[1] == "r" then
+ out "Readable: ok."
+ else
+ out "Not readable: permissions need fixing."
+ errcnt = errcnt + 1
+ end
+ end
+
+ if spec.w == true then
+ if user[2] == "w"
+ or fileiswritable (permissions.location) then
+ out "Writable: ok."
+ else
+ out "Not writable: permissions need fixing."
+ errcnt = errcnt + 1
+ end
+ end
+
+ return errcnt
+end
+
+local init_desired_permissions = function ()
+ local paths = config.luaotfload.paths
+ return {
+ { "d", {"r","w"}, function () return caches.getwritablepath ("", "") end },
+ { "d", {"r","w"}, paths.prefix },
+ { "f", {"r","w"}, paths.index_path_lua .. ".gz" },
+ { "f", {"r","w"}, paths.index_path_luc },
+ { "f", {"r","w"}, paths.lookup_path_lua },
+ { "f", {"r","w"}, paths.lookup_path_luc },
+ }
+end
+
+local check_permissions = function (errcnt)
+ out [[=============== file permissions ==============]]
+ local desired_permissions = init_desired_permissions ()
+ for i = 1, #desired_permissions do
+ local t, spec, path = unpack (desired_permissions[i])
+ if type (path) == "function" then
+ path = path ()
+ end
+
+ spec = tabletohash (spec)
+
+ out ("Checking permissions of %s.", path)
+
+ local permissions = get_permissions (t, path)
+ if permissions then
+ --inspect (permissions)
+ errcnt = check_conformance (spec, permissions, errcnt)
+ else
+ errcnt = errcnt + 1
+ end
+ end
+ return errcnt
+end
+
+local check_upstream
+
+if kpsefind_file ("https.lua", "lua") == nil then
+ check_upstream = function (errcnt)
+ out [[============= upstream repository =============
+ WARNING: Cannot retrieve repository data.
+ Github API access requires the luasec library.
+ Grab it from <https://github.com/brunoos/luasec>
+ and retry.]]
+ return errcnt
+ end
+else
+--- github api stuff begin
+ local https = require "ssl.https"
+
+ local gh_api_root = [[https://api.github.com]]
+ local release_url = [[https://github.com/lualatex/luaotfload/releases]]
+ local luaotfload_repo = [[lualatex/luaotfload]]
+ local user_agent = [[lualatex/luaotfload integrity check]]
+ local shortbytes = 8
+
+ local gh_shortrevision = function (rev)
+ return stringsub (rev, 1, shortbytes)
+ end
+
+ local gh_encode_parameters = function (parameters)
+ local acc = {}
+ for field, value in next, parameters do
+ --- unsafe, non-urlencoded coz it’s all ascii chars
+ acc[#acc+1] = field .. "=" .. value
+ end
+ return "?" .. tableconcat (acc, "&")
+ end
+
+ local gh_make_url = function (components, parameters)
+ local url = tableconcat ({ gh_api_root,
+ unpack (components) },
+ "/")
+ if parameters then
+ url = url .. gh_encode_parameters (parameters)
+ end
+ return url
+ end
+
+ local alright = [[HTTP/1.1 200 OK]]
+
+ local gh_api_request = function (...)
+ local args = {...}
+ local nargs = #args
+ local final = args[nargs]
+ local request = {
+ url = "",
+ headers = { ["user-agent"] = user_agent },
+ }
+ if type (final) == "table" then
+ args[nargs] = nil
+ request = gh_make_url (args, final)
+ else
+ request = gh_make_url (args)
+ end
+
+ out ("Requesting <%s>.", request)
+ local response, code, headers, status = https.request (request)
+ if status ~= alright then
+ out "Request failed!"
+ return false
+ end
+ return response
+ end
+
+ local gh_api_checklimit = function (headers)
+ local rawlimit = gh_api_request "rate_limit"
+ local limitdata = lua_of_json (rawlimit)
+ if not limitdata and limitdata.rate then
+ out "Cannot parse API rate limit."
+ return false
+ end
+ limitdata = limitdata.rate
+
+ local limit = tonumber (limitdata.limit)
+ local left = tonumber (limitdata.remaining)
+ local reset = tonumber (limitdata.reset)
+
+ out ("%d of %d Github API requests left.", left, limit)
+ if left == 0 then
+ out ("Cannot make any more API requests.")
+ if ostype == "unix" then
+ out ("Try again later at %s.", osdate ("%F %T", reset))
+ else --- windows doesn’t C99
+ out ("Try again later at %s.",
+ osdate ("%Y-%m-d %H:%M:%S", reset))
+ end
+ end
+ return true
+ end
+
+ local gh_tags = function ()
+ out "Fetching tags from repository, please stand by."
+ local rawtags = gh_api_request ("repos",
+ luaotfload_repo,
+ "tags")
+ local taglist = lua_of_json (rawtags)
+ if not taglist or #taglist == 0 then
+ out "Cannot parse response."
+ return false
+ end
+
+ local ntags = #taglist
+ out ("Repository contains %d tags.", ntags)
+ local _idx, latest = next (taglist)
+ out ("The most recent release is %s (revision %s).",
+ latest.name,
+ gh_shortrevision (latest.commit.sha))
+ return latest
+ end
+
+ local gh_compare = function (head, base)
+ if base == nil then
+ base = "HEAD"
+ end
+ out ("Fetching comparison between %s and %s, \z
+ please stand by.",
+ gh_shortrevision (head),
+ gh_shortrevision (base))
+ local comparison = base .. "..." .. head
+ local rawstatus = gh_api_request ("repos",
+ luaotfload_repo,
+ "compare",
+ comparison)
+ local status = lua_of_json (rawstatus)
+ if not status then
+ out "Cannot parse response for status request."
+ return false
+ end
+ return status
+ end
+
+ local gh_news = function (since)
+ local compared = gh_compare (since)
+ if not compared then
+ return false
+ end
+ local behind_by = compared.behind_by
+ local ahead_by = compared.ahead_by
+ local status = compared.status
+ out ("Comparison state: %s.", status)
+ if behind_by > 0 then
+ out ("Your Luaotfload is %d \z
+ revisions behind upstream.",
+ behind_by)
+ return behind_by
+ elseif status == "ahead" then
+ out "Since you are obviously from the future \z
+ I assume you already know the repository state."
+ else
+ out "Everything up to date. \z
+ Luaotfload is in sync with upstream."
+ end
+ return false
+ end
+
+ local gh_catchup = function (current, latest)
+ local compared = gh_compare (latest, current)
+ local ahead_by = tonumber (compared.ahead_by)
+ if ahead_by > 0 then
+ local permalink_url = compared.permalink_url
+ out ("Your Luaotfload is %d revisions \z
+ behind the most recent release.",
+ ahead_by)
+ out ("To view the commit log, visit <%s>.",
+ permalink_url)
+ out ("You can grab an up to date tarball at <%s>.",
+ release_url)
+ return true
+ else
+ out "There weren't any new releases in the meantime."
+ out "Luaotfload is up to date."
+ end
+ return false
+ end
+
+ check_upstream = function (current)
+ out "============= upstream repository ============="
+ local _succ = gh_api_checklimit ()
+ local behind = gh_news (current)
+ if behind then
+ local latest = gh_tags ()
+ local _behind = gh_catchup (current,
+ latest.commit.sha,
+ latest.name)
+ end
+ end
+
+ --- trivium: diff since the first revision as pushed by Élie
+ --- in 2009
+ --- local firstrevision = "c3ccb3ee07e0a67171c24960966ae974e0dd8e98"
+ --- check_upstream (firstrevision)
+end
+--- github api stuff end
+
+local print_envvar = function (var)
+ local val = osgetenv (var)
+ if val then
+ out ("%20s: %q", stringformat ("$%s", var), val)
+ return val
+ else
+ out ("%20s: <unset>", stringformat ("$%s", var))
+ end
+end
+
+local print_path = function (var)
+ local val = osgetenv (var)
+ if val then
+ local paths = filesplitpath (val)
+ if paths then
+ local npaths = #paths
+ if npaths == 1 then
+ out ("%20s: %q", stringformat ("$%s", var), val)
+ elseif npaths > 1 then
+ out ("%20s: <%d items>", stringformat ("$%s", var), npaths)
+ for i = 1, npaths do
+ out (" +: %q", paths[i])
+ end
+ else
+ out ("%20s: <empty>")
+ end
+ end
+ else
+ out ("%20s: <unset>", stringformat ("$%s", var))
+ end
+end
+
+local print_kpsevar = function (var)
+ var = "$" .. var
+ local val = kpseexpand_var (var)
+ if val and val ~= var then
+ out ("%20s: %q", var, val)
+ return val
+ else
+ out ("%20s: <empty or unset>", var)
+ end
+end
+
+local print_kpsepath = function (var)
+ var = "$" .. var
+ local val = kpseexpand_path (var)
+ if val and val ~= "" then
+ local paths = filesplitpath (val)
+ if paths then
+ local npaths = #paths
+ if npaths == 1 then
+ out ("%20s: %q", var, paths[1])
+ elseif npaths > 1 then
+ out ("%20s: <%d items>", var, npaths)
+ for i = 1, npaths do
+ out (" +: %q", paths[i])
+ end
+ else
+ out ("%20s: <empty>")
+ end
+ end
+ else
+ out ("%20s: <empty or unset>", var)
+ end
+end
+
+--- this test first if a variable is set and then expands the
+--- paths; this is necessitated by the fact that expand-path will
+--- return the empty string both if the variable is unset and if
+--- the directory does not exist
+
+local print_kpsepathvar = function (var)
+ local vvar = "$" .. var
+ local val = kpseexpand_var (vvar)
+ if val and val ~= vvar then
+ out ("%20s: %q", vvar, val)
+ print_kpsepath (var)
+ else
+ out ("%20s: <empty or unset>", var)
+ end
+end
+
+local check_environment = function (errcnt)
+ out "============ environment settings ============="
+ out ("system: %s/%s", ostype, osname)
+ if ostype == "unix" and io.popen then
+ local chan = io.popen ("uname -a", "r")
+ if chan then
+ out ("info: %s", chan:read "*all")
+ chan:close ()
+ end
+ end
+
+ out "1) *shell environment*"
+ print_envvar "SHELL"
+ print_path "PATH"
+ print_path "OSFONTDIR"
+ print_envvar "USER"
+ if ostype == "windows" then
+ print_envvar "WINDIR"
+ print_envvar "CD"
+ print_path "TEMP"
+ elseif ostype == "unix" then
+ print_envvar "HOME"
+ print_envvar "PWD"
+ print_path "TMPDIR"
+ end
+
+ out "2) *kpathsea*"
+ print_kpsepathvar "OPENTYPEFONTS"
+ print_kpsepathvar "TTFONTS"
+
+ print_kpsepathvar "TEXMFCACHE"
+ print_kpsepathvar "TEXMFVAR"
+
+ --- the expansion of these can be quite large; as they aren’t
+ --- usually essential to luaotfload, we won’t dump every single
+ --- path
+ print_kpsevar "LUAINPUTS"
+ print_kpsevar "CLUAINPUTS"
+
+ return errcnt
+end
+
+local anamneses = {
+ "environment",
+ "files",
+ "index",
+ "repository",
+ "permissions"
+}
+
+local diagnose = function (job)
+ local errcnt = 0
+ local asked = job.asked_diagnostics
+ if asked == "all" or asked == "thorough" then
+ asked = tabletohash (anamneses, true)
+ else
+ asked = lpegmatch (splitcomma, asked)
+ asked = tabletohash (asked, true)
+ end
+
+ if asked.index == true then
+ errcnt = check_index (errcnt)
+ asked.index = nil
+ end
+
+ if asked.environment == true then
+ errcnt = check_environment (errcnt)
+ asked.environment = nil
+ end
+
+ if asked.files == true then
+ errcnt = verify_files (errcnt)
+ asked.files = nil
+ end
+
+ if asked.permissions == true then
+ errcnt = check_permissions (errcnt)
+ asked.permissions = nil
+ end
+
+ if asked.repository == true then
+ local status = config.luaotfload.status
+ check_upstream (status.notes.revision)
+ asked.repository = nil
+ end
+
+ local rest = next (asked)
+ if rest ~= nil then --> something unknown
+ out ("Unknown diagnostic %q.", rest)
+ end
+ if errcnt == 0 then --> success
+ out ("Everything appears to be in order, \z
+ you may sleep well.")
+ return true, false
+ end
+ out ( [[===============================================
+ WARNING
+ ===============================================
+
+ The diagnostic detected %d errors.
+
+ This version of luaotfload may have been
+ tampered with. Modified versions of the
+ luaotfload source are unsupported. Read the log
+ carefully and get a clean version from CTAN or
+ github:
+
+ × http://www.ctan.org/pkg/luaotfload
+ × https://github.com/lualatex/luaotfload/releases
+
+ If you are uncertain as to how to proceed, then
+ ask on the lualatex mailing list:
+
+ http://www.tug.org/mailman/listinfo/lualatex-dev
+
+ ===============================================
+]], errcnt)
+ return true, false
+end
+
+return diagnose
+
+-- vim:tw=71:sw=4:ts=4:expandtab
diff --git a/macros/luatex/generic/luaotfload/luaotfload-embolden.lua b/macros/luatex/generic/luaotfload/luaotfload-embolden.lua
new file mode 100644
index 0000000000..5229c009f7
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-embolden.lua
@@ -0,0 +1,42 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-embolden.lua
+-- DESCRIPTION: part of luaotfload / embolden
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-embolden",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / color",
+ license = "GPL v2.0",
+ author = "Marcel Krüger"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+local otffeatures = fonts.constructors.newfeatures "otf"
+
+local function setembolden(tfmdata, factor)
+ tfmdata.embolden = factor
+end
+
+local function enableembolden(tfmdata)
+ tfmdata.mode, tfmdata.width = 2, tfmdata.size*tfmdata.unscaled.embolden/6578.176
+end
+
+otffeatures.register {
+ name = "embolden",
+ description = "embolden",
+ initializers = {
+ base = setembolden,
+ node = setembolden,
+ },
+ manipulators = {
+ base = enableembolden,
+ node = enableembolden,
+ }
+}
+
+--- vim:sw=2:ts=2:expandtab:tw=71
diff --git a/macros/luatex/generic/luaotfload/luaotfload-features.lua b/macros/luatex/generic/luaotfload/luaotfload-features.lua
new file mode 100644
index 0000000000..1d41cfd192
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-features.lua
@@ -0,0 +1,596 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-features.lua
+-- DESCRIPTION: part of luaotfload / font features
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-features",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / features",
+ license = "GPL v2.0",
+ author = "Hans Hagen, Khaled Hosny, Elie Roux, Philipp Gesang, Marcel Krüger",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+local type = type
+local next = next
+local tonumber = tonumber
+
+local lpeg = require "lpeg"
+local lpegmatch = lpeg.match
+local P = lpeg.P
+local R = lpeg.R
+local C = lpeg.C
+
+local table = table
+local tabletohash = table.tohash
+local tablesort = table.sort
+
+--- this appears to be based in part on luatex-fonts-def.lua
+
+local fonts = fonts
+local definers = fonts.definers
+local handlers = fonts.handlers
+local fontidentifiers = fonts.hashes and fonts.hashes.identifiers
+local otf = handlers.otf
+
+local config = config or { luaotfload = { run = { } } }
+
+local as_script = true
+local normalize = function () end
+
+if config.luaotfload.run.live ~= false then
+ normalize = otf.features.normalize
+ as_script = false
+end
+
+--[[HH (font-xtx) --
+ tricky: we sort of bypass the parser and directly feed all into
+ the sub parser
+--HH]]--
+
+function definers.getspecification(str)
+ return "", str, "", ":", str
+end
+
+local log = luaotfload.log
+local report = log.report
+
+local stringgsub = string.gsub
+local stringformat = string.format
+local stringis_empty = string.is_empty
+
+local cmp_by_idx = function (a, b) return a.idx < b.idx end
+
+local defined_combos = 0
+
+local handle_combination = function (combo, spec)
+ defined_combos = defined_combos + 1
+ if not combo [1] then
+ report ("both", 0, "features",
+ "combo %d: Empty font combination requested.",
+ defined_combos)
+ return false
+ end
+
+ if not fontidentifiers then
+ fontidentifiers = fonts.hashes and fonts.hashes.identifiers
+ end
+
+ local chain = { }
+ local fontids = { }
+ local n = #combo
+
+ tablesort (combo, cmp_by_idx)
+
+ --- pass 1: skim combo and resolve fonts
+ report ("both", 2, "features", "combo %d: combining %d fonts.",
+ defined_combos, n)
+ for i = 1, n do
+ local cur = combo [i]
+ local id = cur.id
+ local idx = cur.idx
+ local fnt = fontidentifiers [id]
+ if fnt then
+ local chars = cur.chars
+ if chars == true then
+ report ("both", 2, "features",
+ " *> %.2d: fallback font %d at rank %d.",
+ i, id, idx)
+ else
+ report ("both", 2, "features",
+ " *> %.2d: include font %d at rank %d (%d items).",
+ i, id, idx, (chars and #chars or 0))
+ end
+ chain [#chain + 1] = { fnt, chars, idx = idx }
+ fontids [#fontids + 1] = { id = id }
+ else
+ report ("both", 0, "features",
+ " *> %.2d: font %d at rank %d unknown, skipping.",
+ n, id, idx)
+ --- TODO might instead attempt to define the font at this point
+ --- but that’d require some modifications to the syntax
+ end
+ end
+
+ local nc = #chain
+ if nc == 0 then
+ report ("both", 0, "features",
+ " *> no valid font (of %d) in combination.", n)
+ return false
+ end
+
+ local basefnt = chain [1] [1]
+ if nc == 1 then
+ report ("both", 0, "features",
+ " *> combination boils down to a single font (%s) \z
+ of %d initially specified; not pursuing this any \z
+ further.", basefnt.fullname, n)
+ return basefnt
+ end
+
+ local basechar = basefnt.characters
+ local baseprop = basefnt.properties
+ baseprop.name = spec.name
+ baseprop.virtualized = true
+ basefnt.fonts = fontids
+
+ for i = 2, nc do
+ local cur = chain [i]
+ local fnt = cur [1]
+ local def = cur [2]
+ local src = fnt.characters
+ local cnt = 0
+
+ local pickchr = function (uc, unavailable)
+ local chr = src [uc]
+ if unavailable == true and basechar [uc] then
+ --- fallback mode: already known
+ return
+ end
+ if chr then
+ chr.commands = { { "slot", i, uc } }
+ basechar [uc] = chr
+ cnt = cnt + 1
+ end
+ end
+
+ if def == true then --> fallback; grab all currently unavailable
+ for uc, _chr in next, src do pickchr (uc, true) end
+ else --> grab only defined range
+ for j = 1, #def do
+ local this = def [j]
+ if type (this) == "number" then
+ report ("both", 2, "features",
+ " *> [%d][%d]: import codepoint U+%.4X",
+ i, j, this)
+ pickchr (this)
+ elseif type (this) == "table" then
+ local lo, hi = unpack (this)
+ report ("both", 2, "features",
+ " *> [%d][%d]: import codepoint range U+%.4X--U+%.4X",
+ i, j, lo, hi)
+ for uc = lo, hi do pickchr (uc) end
+ else
+ report ("both", 0, "features",
+ " *> item no. %d of combination definition \z
+ %d not processable.", j, i)
+ end
+ end
+ end
+ report ("both", 2, "features",
+ " *> font %d / %d: imported %d glyphs into combo.",
+ i, nc, cnt)
+ end
+ spec.lookup = "combo"
+ spec.file = basefnt.filename
+ spec.name = stringformat ("luaotfload<%d>", defined_combos)
+ spec.features = { normal = { spec.specification } }
+ spec.forced = "evl"
+ spec.eval = function () return basefnt end
+ return spec
+end
+
+---[[ begin excerpt from font-ott.lua ]]
+
+local swapped = function (h)
+ local r = { }
+ for k, v in next, h do
+ r[stringgsub(v,"[^a-z0-9]","")] = k -- is already lower
+ end
+ return r
+end
+
+local tables = otf.tables
+local scripts = tables.scripts
+local languages = tables.languages
+local verbosescripts = swapped(scripts )
+local verboselanguages = swapped(languages)
+
+---[[ end excerpt from font-ott.lua ]]
+
+--[[doc--
+
+ As discussed, we will issue a warning because of incomplete support
+ when one of the scripts below is requested.
+
+ Reference: https://github.com/lualatex/luaotfload/issues/31
+
+--doc]]--
+
+local support_incomplete = tabletohash({
+ -- "deva",
+ "beng", "guru", "gujr",
+ "orya", "taml", "telu", "knda",
+ "mlym", "sinh",
+}, true)
+
+--[[doc--
+
+ Which features are active by default depends on the script
+ requested.
+
+--doc]]--
+
+--- (string, string) dict -> (string, string) dict
+local apply_default_features = function (speclist)
+ local default_features = luaotfload.features
+
+ speclist = speclist or { }
+ speclist[""] = nil --- invalid options stub
+
+ --- handle language tag
+ local language = speclist.language
+ if language then --- already lowercase at this point
+ language = stringgsub(language, "[^a-z0-9]", "")
+ language = rawget(verboselanguages, language) -- srsly, rawget?
+ or (languages[language] and language)
+ or "dflt"
+ else
+ language = "dflt"
+ end
+ speclist.language = language
+
+ --- handle script tag
+ local script = speclist.script
+ if script then
+ script = stringgsub(script, "[^a-z0-9]","")
+ script = rawget(verbosescripts, script)
+ or (scripts[script] and script)
+ or "dflt"
+ if support_incomplete[script] then
+ report("log", 0, "features",
+ "Support for the requested script: "
+ .. "%q may be incomplete.", script)
+ end
+ else
+ script = "dflt"
+ end
+ speclist.script = script
+
+ report("log", 2, "features",
+ "Auto-selecting default features for script: %s.",
+ script)
+
+ local requested = default_features.defaults[script]
+ if not requested then
+ report("log", 2, "features",
+ "No default features for script %q, falling back to \"dflt\".",
+ script)
+ requested = default_features.defaults.dflt
+ end
+
+ for feat, state in next, requested do
+ if speclist[feat] == nil then speclist[feat] = state end
+ end
+
+ for feat, state in next, default_features.global do
+ --- This is primarily intended for setting node
+ --- mode unless “base” is requested, as stated
+ --- in the manual.
+ if speclist[feat] == nil then speclist[feat] = state end
+ end
+ return speclist
+end
+
+local import_values = {
+ --- That’s what the 1.x parser did, not quite as graciously,
+ --- with an array of branch expressions.
+ -- "style", "optsize",--> from slashed notation; handled otherwise
+ { "lookup", false },
+ { "sub", false },
+}
+
+local supported = {
+ b = "b",
+ i = "i",
+ bi = "bi",
+ aat = false,
+ icu = false,
+ gr = false,
+}
+
+--- (string | (string * string) | bool) list -> (string * number)
+local handle_slashed = function (modifiers)
+ local style, optsize
+ for i=1, #modifiers do
+ local mod = modifiers[i]
+ if type(mod) == "table" and mod[1] == "optsize" then --> optical size
+ optsize = tonumber(mod[2])
+ elseif mod == false then
+ --- ignore
+ report("log", 0, "features", "unsupported font option: %s", v)
+ elseif supported[mod] then
+ style = supported[mod]
+ elseif not stringis_empty(mod) then
+ style = stringgsub(mod, "[^%a%d]", "")
+ end
+ end
+ return style, optsize
+end
+
+local extract_subfont
+do
+ local eof = P(-1)
+ local digit = R"09"
+ --- Theoretically a valid subfont address can be up to ten
+ --- digits long.
+ local sub_expr = P"(" * C(digit^1) * P")" * eof
+ local full_path = C(P(1 - sub_expr)^1)
+ extract_subfont = full_path * sub_expr
+end
+
+--- spec -> spec
+local handle_request = function (specification)
+ local request = lpegmatch(luaotfload.parsers.font_request,
+ specification.specification)
+----inspect(request)
+ if not request then
+ --- happens when called with an absolute path
+ --- in an anonymous lookup;
+ --- we try to behave as friendly as possible
+ --- just go with it ...
+ report("log", 1, "features", "invalid request %q of type anon",
+ specification.specification)
+ report("log", 1, "features",
+ "use square bracket syntax or consult the documentation.")
+ --- The result of \fontname must be re-feedable into \font
+ --- which is expected by the Latex font mechanism. Now this
+ --- is complicated with TTC fonts that need to pass the
+ --- number of the requested subfont along with the file name.
+ --- Thus we test whether the request is a bare path only or
+ --- ends in a subfont expression (decimal digits inside
+ --- parentheses).
+ --- https://github.com/lualatex/luaotfload/issues/57
+ local fullpath, sub = lpegmatch(extract_subfont,
+ specification.specification)
+ if fullpath and sub then
+ specification.sub = tonumber(sub)
+ specification.name = fullpath
+ else
+ specification.name = specification.specification
+ end
+ specification.lookup = "path"
+ return specification
+ end
+
+ local lookup, name = request.lookup, request.name
+ if lookup == "combo" then
+ return handle_combination (name, specification)
+ end
+
+ local features = specification.features
+ if not features then
+ features = { }
+ specification.features = features
+ end
+
+ features.raw = request.features or {}
+ request.features = {}
+ for k, v in pairs(features.raw) do
+ if type(v) == 'string' then
+ v = string.lower(v)
+ v = ({['true'] = true, ['false'] = false})[v] or v
+ end
+ request.features[k] = v
+ end
+ request.features = apply_default_features(request.features)
+
+ if name then
+ specification.name = name
+ specification.lookup = lookup or specification.lookup
+ end
+
+ if request.modifiers then
+ local style, optsize = handle_slashed(request.modifiers)
+ specification.style, specification.optsize = style, optsize
+ end
+
+ for n=1, #import_values do
+ local feat = import_values[n][1]
+ local keep = import_values[n][2]
+ local newvalue = request.features[feat]
+ if newvalue then
+ specification[feat] = request.features[feat]
+ if not keep then
+ request.features[feat] = nil
+ end
+ end
+ end
+
+ --- The next line sets the “rand” feature to “random”; I haven’t
+ --- investigated it any further (luatex-fonts-ext), so it will
+ --- just stay here.
+ features.normal = normalize (request.features)
+ local subfont = tonumber (request.sub)
+ if subfont and subfont >= 0 then
+ specification.sub = subfont + 1
+ else
+ specification.sub = false
+ end
+
+ if request.features and request.features.mode
+ and fonts.readers[request.features.mode] then
+ specification.forced = request.features.mode
+ end
+
+ return specification
+end
+
+fonts.names.handle_request = handle_request
+
+
+if as_script == true then --- skip the remainder of the file
+ report ("log", 5, "features",
+ "Exiting early from luaotfload-features.lua.")
+ return
+end
+
+-- MK: Added
+function fonts.definers.analyze (spec_string, size)
+ return handle_request {
+ size = size,
+ specification = spec_string,
+ }
+end
+-- /MK
+
+-- We assume that the other otf stuff is loaded already; though there’s
+-- another check below during the initialization phase.
+
+
+local tlig_specification = {
+ {
+ type = "substitution",
+ features = everywhere,
+ data = {
+ --- quotedblright:
+ --- " (QUOTATION MARK) → ” (RIGHT DOUBLE QUOTATION MARK)
+ [0x0022] = 0x201D,
+
+ --- quoteleft:
+ --- ' (APOSTROPHE) → ’ (RIGHT SINGLE QUOTATION MARK)
+ [0x0027] = 0x2019,
+
+ --- quoteright:
+ --- ` (GRAVE ACCENT) → ‘ (LEFT SINGLE QUOTATION MARK)
+ [0x0060] = 0x2018,
+ },
+ flags = noflags,
+ order = { "tlig" },
+ prepend = true,
+ },
+ {
+ type = "ligature",
+ features = everywhere,
+ data = {
+
+ --- endash:
+ --- [--] (HYPHEN-MINUS, HYPHEN-MINUS) → – (EN DASH)
+ [0x2013] = {0x002D, 0x002D},
+
+ --- emdash:
+ --- [---] (HYPHEN-MINUS, HYPHEN-MINUS, HYPHEN-MINUS) → — (EM DASH)
+ [0x2014] = {0x002D, 0x002D, 0x002D},
+
+ --- quotedblleft:
+ --- [''] (GRAVE ACCENT, GRAVE ACCENT) → “ (LEFT DOUBLE QUOTATION MARK)
+ [0x201C] = {0x0060, 0x0060},
+
+ --- quotedblright:
+ --- [``] (APOSTROPHE, APOSTROPHE) → ” (RIGHT DOUBLE QUOTATION MARK)
+ [0x201D] = {0x0027, 0x0027},
+
+ --- exclamdown:
+ --- [!'] (EXCLAMATION MARK, GRAVE ACCENT) → ¡ (INVERTED EXCLAMATION MARK)
+ [0x00A1] = {0x0021, 0x0060},
+
+ --- questiondown:
+ --- [?'] (QUESTION MARK, GRAVE ACCENT) → ¡ (INVERTED EXCLAMATION MARK)
+ [0x00BF] = {0x003F, 0x0060},
+
+ --- next three originate in T1 encoding (Xetex applies them too)
+ --- quotedblbase:
+ --- [,,] (COMMA, COMMA) → ¡ (DOUBLE LOW-9 QUOTATION MARK)
+ [0x201E] = {0x002C, 0x002C},
+
+ --- LEFT-POINTING DOUBLE ANGLE QUOTATION MARK:
+ --- [,,] (LESS-THAN SIGN, LESS-THAN SIGN) → ¡ (LEFT-POINTING ANGLE QUOTATION MARK)
+ [0x00AB] = {0x003C, 0x003C},
+
+ --- RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK:
+ --- [,,] (GREATER-THAN SIGN, GREATER-THAN SIGN) → ¡ (RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK)
+ [0x00BB] = {0x003E, 0x003E},
+ },
+ flags = noflags,
+ order = { "tlig" },
+ prepend = true,
+ },
+}
+
+local rot13_specification = {
+ type = "substitution",
+ features = everywhere,
+ data = {
+ [65] = 78, [ 97] = 110, [78] = 65, [110] = 97,
+ [66] = 79, [ 98] = 111, [79] = 66, [111] = 98,
+ [67] = 80, [ 99] = 112, [80] = 67, [112] = 99,
+ [68] = 81, [100] = 113, [81] = 68, [113] = 100,
+ [69] = 82, [101] = 114, [82] = 69, [114] = 101,
+ [70] = 83, [102] = 115, [83] = 70, [115] = 102,
+ [71] = 84, [103] = 116, [84] = 71, [116] = 103,
+ [72] = 85, [104] = 117, [85] = 72, [117] = 104,
+ [73] = 86, [105] = 118, [86] = 73, [118] = 105,
+ [74] = 87, [106] = 119, [87] = 74, [119] = 106,
+ [75] = 88, [107] = 120, [88] = 75, [120] = 107,
+ [76] = 89, [108] = 121, [89] = 76, [121] = 108,
+ [77] = 90, [109] = 122, [90] = 77, [122] = 109,
+ },
+ flags = noflags,
+ order = { "rot13" },
+ prepend = true,
+}
+
+local interrolig_specification = {
+ { type = "ligature", data = { [0x203d] = {0x21, 0x3f}, [0x2e18] = {0xa1, 0xbf}, }, },
+ { type = "ligature", data = { [0x203d] = {0x3f, 0x21}, [0x2e18] = {0xbf, 0xa1}, }, },
+}
+
+local autofeatures = {
+ --- always present with Luaotfload; anum for Arabic and Persian is
+ --- predefined in font-otc.
+ { "tlig" , tlig_specification , "tex ligatures and substitutions" },
+ { "rot13", rot13_specification, "rot13" },
+ { "!!??", interrolig_specification, "interrobang substitutions" },
+}
+
+local add_auto_features = function ()
+ local nfeats = #autofeatures
+ logreport ("both", 5, "features",
+ "auto-installing %d feature definitions", nfeats)
+ for i = 1, nfeats do
+ local name, spec, desc = unpack (autofeatures [i])
+ spec.description = desc
+ otf.addfeature (name, spec)
+ end
+end
+
+return function ()
+ logreport = luaotfload.log.report
+
+ if not fonts and fonts.handlers then
+ logreport ("log", 0, "features",
+ "OTF mechanisms missing -- did you forget to \z
+ load a font loader?")
+ return false
+ end
+ add_auto_features ()
+ return true
+end
+-- vim:tw=79:sw=4:ts=4:expandtab
diff --git a/macros/luatex/generic/luaotfload/luaotfload-filelist.lua b/macros/luatex/generic/luaotfload/luaotfload-filelist.lua
new file mode 100644
index 0000000000..612822440f
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-filelist.lua
@@ -0,0 +1,430 @@
+-------------------------------------------------------------------------------
+-- FILE: luaotfload-filelist.lua
+-- DESCRIPTION: part of luaotfload / list of files
+-- AUTHOR: Ulrike Fischer, <fischer@troubleshooting-tex.de>
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-filelist",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / filelist",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+
+--[[doc--
+
+luaotfload has tables with files list in many places: In the import scripts,
+in the init file, in the documentation. This makes maintenance difficult.
+This here is a try to get everything in one place. As the order how files are
+loaded during the merge matters the table is an array. Lists with other
+sorting should be created with functions. Ditto for subtables.
+
+Some redundancy can not be avoided for now if one want to avoid to have to change all sort of functions.
+
+## locations
+files can reside in up to three location (with perhaps different names)
+- context ctxdir
+- git gitdir
+- texmf texdir
+
+files don't need to exist in all locations but the direction of the flow is
+always from context over git to texmf:
+ context-> git -> texmf
+so the "stations" of a file and its source can be deduced by the dirs recorded in the entries
+
+
+## "kind"
+the first four entries are from the original mkimport code and are important for the imports.
+the others are new.
+
+ · *essential*: Files required at runtime.
+ · *merged*: Files merged into the fontloader package.
+ · *ignored*: Lua files not merged, but part of the format.
+ · *tex*: TeX code, i.e. format and examples.
+ · *lualibs*: Files imported, but also provided by the Lualibs package.
+ · *library*: native luaotfload-files of type library
+ · *core*: native core luaotfload files
+ · *generated*: generated luaotfload files
+ · *scripts*: scripts (mk-...)
+ · *docu*: documentation (should perhaps be more refined
+
+## names
+
+The "real" name of a file in a location can be build
+
+- in the context location: ctxpref + name + ext
+- in the git location: (gitpref or "fontloader-") + (ours or name ) + ext
+- in the tex location: (gitpref or "fontloader-") + (texname or ours or name ) + ext
+
+## fields
+ mkstatus: used to ignore some files in mkstatus
+
+
+## files which use the file names
+
+### mkimport
+
+ mkimports needs an
+ --> "import" table with two subtables:
+ --> fontloader, with the files to get from generic, cond: ctxtype = "ctxgene"
+ --> context, with the files to get from context, cond: ctxtype = "ctxbase"
+ entries are subtables with {name=, ours=, kind= }
+
+and a
+ --> "package" table with
+ --> optional (probably unused)
+ --> required = files of type kind_merged
+ entries are the values of name
+
+### mkstatus
+
+this script has been already changed to use luaotfload-filelist.lua
+
+### luaotfload-init.lua
+
+luaotfload-init.lua needs a table
+--> context_modules
+with the (ordered) entries
+
+{false, "name"} -- kind_lualibs
+{ctxdir,"ctxprefix+name"} -- kind_essential or kind_merged
+
+The same list should be used in local init_main = function ()
+but only without the prefix.
+it is unclear how fonts_syn should be handled!!!!
+
+### filegraph.tex
+has been already adapted
+
+### luaotfload-latex.tex/luaotfload-main.tex
+has been already adapted
+
+### build.lua
+???
+
+--doc]]--
+
+
+local kind_essential = 0
+local kind_merged = 1
+local kind_tex = 2
+local kind_ignored = 3
+local kind_lualibs = 4
+local kind_library = 5
+local kind_core = 6
+local kind_generated = 7
+local kind_script = 8
+local kind_docu = 9
+
+local kind_name = {
+ [0] = "essential",
+ [1] = "merged" ,
+ [2] = "tex" ,
+ [3] = "ignored" ,
+ [4] = "lualibs" ,
+ [5] = "library" ,
+ [6] = "core",
+ [7] = "generated",
+ [8] = "script",
+ [9] = "docu"
+}
+
+
+local ctxdirbas = "tex/context/base/mkiv/"
+local ctxdirgen = "tex/generic/context/luatex/"
+
+local gitdirimp = "src/fontloader/misc/" -- imp=imported
+local gitdirsrc = "src/"
+local gitdiress = "src/fontloader/runtime/"
+local gitdirgen = "src/fontloader/auto/"
+local gitdirdoc = "doc/"
+local gitdirscr = "scripts/"
+local gitdirmain = "./"
+
+-- these here a not really pathes
+local texdirtex = "tex"
+local texdirscr = "scripts"
+local texdirdoc = "doc"
+local texdirman = "man"
+
+luaotfload = luaotfload or {}
+luaotfload.filelist = luaotfload.filelist or {}
+
+luaotfload.filelist.data =
+ {
+ -- at first the source files from context
+ { name = "l-lua" , ours = "l-lua" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-lpeg" , ours = "l-lpeg" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-function" , ours = "l-function" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-string" , ours = "l-string" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-table" , ours = "l-table" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-io" , ours = "l-io" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-file" , ours = "l-file" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-boolean" , ours = "l-boolean" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-math" , ours = "l-math" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "l-unicode" , ours = "l-unicode" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+
+ { name = "util-str" , ours = "util-str" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "util-fil" , ours = "util-fil" , ext = ".lua", kind = kind_lualibs , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+
+ { name = "basics-gen" , ours = nil , ext = ".lua", kind = kind_essential , gitdir=gitdiress, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+-- files merged in the fontloader. One file is ignored
+ { name = "data-con" , ours = "data-con" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "basics-nod" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "basics-chr" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "font-ini" , ours = "font-ini" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "fonts-mis" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "font-con" , ours = "font-con" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "fonts-enc" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "font-cid" , ours = "font-cid" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-map" , ours = "font-map" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "fonts-syn" , ours = nil , ext = ".lua", kind = kind_ignored , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "font-vfc" , ours = "font-vfc" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-otr" , ours = "font-otr" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-oti" , ours = "font-oti" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-ott" , ours = "font-ott" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-cff" , ours = "font-cff" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-ttf" , ours = "font-ttf" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-dsp" , ours = "font-dsp" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-oup" , ours = "font-oup" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-otl" , ours = "font-otl" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-oto" , ours = "font-oto" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-otj" , ours = "font-otj" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-ota" , ours = "font-ota" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-ots" , ours = "font-ots" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-osd" , ours = "font-osd" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-ocl" , ours = "font-ocl" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-otc" , ours = "font-otc" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-onr" , ours = "font-onr" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-one" , ours = "font-one" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-afk" , ours = "font-afk" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "fonts-tfm" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "font-lua" , ours = "font-lua" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-def" , ours = "font-def" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "fonts-def" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "fonts-ext" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "font-imp-tex" , ours = "font-imp-tex" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-imp-ligatures", ours = "font-imp-ligatures", ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-imp-italics" , ours = "font-imp-italics" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "font-imp-effects" , ours = "font-imp-effects" , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirbas, ctxtype = "ctxbase" },
+ { name = "fonts-lig" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "fonts-gbn" , ours = nil , ext = ".lua", kind = kind_merged , gitdir=gitdirimp, texdir = texdirtex , ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+-- end of files merged
+
+ { name = "fonts-merged" , ours = "reference" , ext = ".lua", kind = kind_essential , gitdir=gitdiress, texdir = texdirtex , ctxdir= ctxdirgen ,ctxtype = "ctxgene" , ctxpref = "luatex-" },
+
+
+
+-- this two files are useful as reference for the load order but should not be installed
+ { name = "fonts" , ours = "load-order-reference", ext = ".lua", kind = kind_ignored , gitdir=gitdirimp, ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+ { name = "fonts" , ours = "load-order-reference", ext = ".tex", kind = kind_tex , gitdir=gitdirimp, ctxdir= ctxdirgen, ctxtype = "ctxgene" , ctxpref = "luatex-" },
+
+-- the default fontloader. How to code the name??
+ { name = "YYYY-MM-DD" , ext = ".lua", kind = kind_generated , gitdir = gitdirgen, texdir = texdirtex,mkstatus="auto" },
+
+-- the luaotfload files
+ { name = "luaotfload" ,kind = kind_core, ext =".sty", gitdir=gitdirsrc, texdir=texdirtex, gitpref="",},
+ { name = "main" ,kind = kind_core, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "init" ,kind = kind_core, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "log" ,kind = kind_core, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "diagnostics" ,kind = kind_core, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+
+ { name = "tool" ,kind = kind_core, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "blacklist" ,kind = kind_core, ext =".cnf", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+
+ { name = "filelist" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "auxiliary" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "colors" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "configuration" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "database" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "features" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "letterspace" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "embolden" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "notdef" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "loaders" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "parsers" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "resolvers" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+ { name = "unicode" ,kind = kind_library, ext =".lua", gitdir=gitdirsrc, texdir=texdirtex, gitpref = "luaotfload-" },
+
+ { name = "characters" ,kind = kind_generated, ext =".lua", gitdir=gitdirgen, texdir=texdirtex, gitpref = "luaotfload-", script="mkcharacter" },
+ { name = "glyphlist" ,kind = kind_generated, ext =".lua", gitdir=gitdirgen, texdir=texdirtex, gitpref = "luaotfload-", script="mkglyphlist" },
+ { name = "status" ,kind = kind_generated, ext =".lua", gitdir=gitdirgen, texdir=texdirtex, gitpref = "luaotfload-", script="mkstatus",mkstatus="ignore" },
+
+
+
+-- scripts
+ { name = "mkimport" ,kind = kind_script, gitdir = gitdirscr, gitpref = "", ext=""},
+ { name = "mkglyphlist" ,kind = kind_script, gitdir = gitdirscr, gitpref = "", ext=""},
+ { name = "mkcharacters" ,kind = kind_script, gitdir = gitdirscr, gitpref = "", ext=""},
+ { name = "mkstatus" ,kind = kind_script, gitdir = gitdirscr, gitpref = "", ext=""},
+ { name = "mktests" ,kind = kind_script, gitdir = gitdirscr, gitpref = "", ext=""},
+
+-- documentation (source dirs need perhaps coding ...) but don't overdo for now
+
+ { name = "latex" , kind= kind_docu, ext = ".tex", gitpref = "luaotfload-", gitdir = gitdirdoc, texdir= texdirdoc, typeset = true },
+ { name = "main" , kind= kind_docu, ext = ".tex", gitpref = "luaotfload-", gitdir = gitdirdoc, texdir= texdirdoc, typeset = false },
+ { name = "conf" , kind= kind_docu, ext = ".tex", gitpref = "luaotfload-", gitdir = gitdirdoc, texdir= texdirdoc, typeset = true , generated = true},
+ { name = "tool" , kind= kind_docu, ext = ".tex", gitpref = "luaotfload-", gitdir = gitdirdoc, texdir= texdirdoc, typeset = true , generated = true},
+ { name = "filegraph" , kind= kind_docu, ext = ".tex", gitpref ="", gitdir = gitdirdoc, texdir= texdirdoc, typeset = true , generated = true},
+ { name = "conf" , kind= kind_docu, ext = ".rst", gitpref = "luaotfload.", gitdir = gitdirdoc, texdir= texdirdoc },
+ { name = "conf" , kind= kind_docu, ext = ".5" , gitpref = "luaotfload.", gitdir = gitdirdoc, texdir= texdirman},
+ { name = "tool" , kind= kind_docu, ext = ".rst", gitpref = "luaotfload-", gitdir = gitdirdoc, texdir= texdirdoc},
+ { name = "tool" , kind= kind_docu, ext = ".1" , gitpref = "luaotfload-", gitdir = gitdirdoc, texdir= texdirman },
+ { name = "README" , kind= kind_docu, texname = "README", gitpref="", ext = ".md" , gitdir = gitdirdoc, texdir= texdirdoc},
+ { name = "COPYING" , kind= kind_docu, ext = "" , gitpref="", gitdir = gitdirmain, texdir= texdirdoc},
+ { name = "NEWS" , kind= kind_docu, ext = "" , gitpref="", gitdir = gitdirmain , texdir= texdirdoc},
+ { name = "README" , kind= kind_docu, gitpref="", ext = ".md" , gitdir = gitdirmain}, -- github readme
+
+}
+
+
+
+-- functions
+-- list of kind:
+--local kind_essential = 0
+--local kind_merged = 1
+--local kind_tex = 2
+--local kind_ignored = 3
+--local kind_lualibs = 4
+--local kind_library = 5
+--local kind_core = 6
+--local kind_generated = 7
+--local kind_script = 8
+--local kind_docu = 9
+
+
+-- some selections
+-- due to the history and setup of the other files, there are not always simple "kind" selections.
+-- ctx base files are splitted in two sets:
+-- 1. font & node
+function luaotfload.filelist.selectctxfontentries ( filetable )
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.ctxtype == "ctxbase" and v.kind==1 then
+ table.insert(result,v)
+ end
+ end
+ return result
+end
+
+-- 2. lualibs libraries
+function luaotfload.filelist.selectctxlibsentries ( filetable )
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.ctxtype == "ctxbase" and v.kind==4 then
+ table.insert(result,v)
+ end
+ end
+ return result
+end
+
+-- ctx generic files
+-- 1. ignored files are not in the list ...
+function luaotfload.filelist.selectctxgeneusedentries ( filetable )
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.ctxtype == "ctxgene" and v.kind==1 then
+ table.insert(result,v)
+ end
+ end
+ return result
+end
+
+-- 2. ignored files are in the list
+function luaotfload.filelist.selectctxgeneentries ( filetable )
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.ctxtype == "ctxgene" and (v.kind==1 or v.kind== 3) then
+ table.insert(result,v)
+ end
+ end
+ return result
+end
+
+-- luaotfload-files (lol) are splitted in essential (0), core (6), lib (5) and gene (7) and scr (scripts):
+-- luaoftload libraries
+
+function luaotfload.filelist.selectlolessentries (filetable)
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.kind == 0 then
+ table.insert (result,v)
+ end
+ end
+ return result
+end
+
+
+function luaotfload.filelist.selectlollibentries (filetable)
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.kind == 5 then
+ table.insert (result,v)
+ end
+ end
+ return result
+end
+
+-- luaoftload core
+
+function luaotfload.filelist.selectlolcoreentries (filetable)
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.kind == 6 then
+ table.insert (result,v)
+ end
+ end
+ return result
+end
+
+-- core and lib lua-files
+
+function luaotfload.filelist.selectlolsrcluaentries (filetable)
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if (v.kind == 5 or v.kind==6) and v.ext==".lua" then
+ table.insert (result,v)
+ end
+ end
+ return result
+end
+
+
+
+-- luaoftload generated
+
+function luaotfload.filelist.selectlolgeneentries (filetable)
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.kind == 7 then
+ table.insert (result,v)
+ end
+ end
+ return result
+end
+
+
+
+-- scripts
+function luaotfload.filelist.selectlolscrentries ( filetable )
+ local result = {}
+ for i,v in ipairs (filetable) do
+ if v.kind==8 then
+ table.insert(result,v)
+ end
+ end
+ return result
+end
+
+
+
+
+
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload-glyphlist.lua b/macros/luatex/generic/luaotfload/luaotfload-glyphlist.lua
new file mode 100644
index 0000000000..43c927b3d3
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-glyphlist.lua
@@ -0,0 +1,4313 @@
+local ProvidesLuaModule = {
+ name = "luaotfload-glyphlist",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / autogenerated glyphlist",
+ copyright = "derived from https://raw.githubusercontent.com/adobe-type-tools/agl-aglfn/master/glyphlist.txt",
+ original = "Adobe Glyph List, version 2.0, September 20, 2002",
+ dataonly = true
+}
+
+if context then
+ logs.report("fatal error","this module is not for context")
+ os.exit(-1)
+end
+
+--[[doc--
+Everything below has been autogenerated. Run mkglyphlist to rebuild
+luaotfload-glyphlist.lua.
+--doc]]--
+
+return {
+ ["A"]=65,
+ ["AE"]=198,
+ ["AEacute"]=508,
+ ["AEmacron"]=482,
+ ["AEsmall"]=63462,
+ ["Aacute"]=193,
+ ["Aacutesmall"]=63457,
+ ["Abreve"]=258,
+ ["Abreveacute"]=7854,
+ ["Abrevecyrillic"]=1232,
+ ["Abrevedotbelow"]=7862,
+ ["Abrevegrave"]=7856,
+ ["Abrevehookabove"]=7858,
+ ["Abrevetilde"]=7860,
+ ["Acaron"]=461,
+ ["Acircle"]=9398,
+ ["Acircumflex"]=194,
+ ["Acircumflexacute"]=7844,
+ ["Acircumflexdotbelow"]=7852,
+ ["Acircumflexgrave"]=7846,
+ ["Acircumflexhookabove"]=7848,
+ ["Acircumflexsmall"]=63458,
+ ["Acircumflextilde"]=7850,
+ ["Acute"]=63177,
+ ["Acutesmall"]=63412,
+ ["Acyrillic"]=1040,
+ ["Adblgrave"]=512,
+ ["Adieresis"]=196,
+ ["Adieresiscyrillic"]=1234,
+ ["Adieresismacron"]=478,
+ ["Adieresissmall"]=63460,
+ ["Adotbelow"]=7840,
+ ["Adotmacron"]=480,
+ ["Agrave"]=192,
+ ["Agravesmall"]=63456,
+ ["Ahookabove"]=7842,
+ ["Aiecyrillic"]=1236,
+ ["Ainvertedbreve"]=514,
+ ["Alpha"]=913,
+ ["Alphatonos"]=902,
+ ["Amacron"]=256,
+ ["Amonospace"]=65313,
+ ["Aogonek"]=260,
+ ["Aring"]=197,
+ ["Aringacute"]=506,
+ ["Aringbelow"]=7680,
+ ["Aringsmall"]=63461,
+ ["Asmall"]=63329,
+ ["Atilde"]=195,
+ ["Atildesmall"]=63459,
+ ["Aybarmenian"]=1329,
+ ["B"]=66,
+ ["Bcircle"]=9399,
+ ["Bdotaccent"]=7682,
+ ["Bdotbelow"]=7684,
+ ["Becyrillic"]=1041,
+ ["Benarmenian"]=1330,
+ ["Beta"]=914,
+ ["Bhook"]=385,
+ ["Blinebelow"]=7686,
+ ["Bmonospace"]=65314,
+ ["Brevesmall"]=63220,
+ ["Bsmall"]=63330,
+ ["Btopbar"]=386,
+ ["C"]=67,
+ ["Caarmenian"]=1342,
+ ["Cacute"]=262,
+ ["Caron"]=63178,
+ ["Caronsmall"]=63221,
+ ["Ccaron"]=268,
+ ["Ccedilla"]=199,
+ ["Ccedillaacute"]=7688,
+ ["Ccedillasmall"]=63463,
+ ["Ccircle"]=9400,
+ ["Ccircumflex"]=264,
+ ["Cdot"]=266,
+ ["Cdotaccent"]=266,
+ ["Cedillasmall"]=63416,
+ ["Chaarmenian"]=1353,
+ ["Cheabkhasiancyrillic"]=1212,
+ ["Checyrillic"]=1063,
+ ["Chedescenderabkhasiancyrillic"]=1214,
+ ["Chedescendercyrillic"]=1206,
+ ["Chedieresiscyrillic"]=1268,
+ ["Cheharmenian"]=1347,
+ ["Chekhakassiancyrillic"]=1227,
+ ["Cheverticalstrokecyrillic"]=1208,
+ ["Chi"]=935,
+ ["Chook"]=391,
+ ["Circumflexsmall"]=63222,
+ ["Cmonospace"]=65315,
+ ["Coarmenian"]=1361,
+ ["Csmall"]=63331,
+ ["D"]=68,
+ ["DZ"]=497,
+ ["DZcaron"]=452,
+ ["Daarmenian"]=1332,
+ ["Dafrican"]=393,
+ ["Dcaron"]=270,
+ ["Dcedilla"]=7696,
+ ["Dcircle"]=9401,
+ ["Dcircumflexbelow"]=7698,
+ ["Dcroat"]=272,
+ ["Ddotaccent"]=7690,
+ ["Ddotbelow"]=7692,
+ ["Decyrillic"]=1044,
+ ["Deicoptic"]=1006,
+ ["Delta"]=8710,
+ ["Deltagreek"]=916,
+ ["Dhook"]=394,
+ ["Dieresis"]=63179,
+ ["DieresisAcute"]=63180,
+ ["DieresisGrave"]=63181,
+ ["Dieresissmall"]=63400,
+ ["Digammagreek"]=988,
+ ["Djecyrillic"]=1026,
+ ["Dlinebelow"]=7694,
+ ["Dmonospace"]=65316,
+ ["Dotaccentsmall"]=63223,
+ ["Dslash"]=272,
+ ["Dsmall"]=63332,
+ ["Dtopbar"]=395,
+ ["Dz"]=498,
+ ["Dzcaron"]=453,
+ ["Dzeabkhasiancyrillic"]=1248,
+ ["Dzecyrillic"]=1029,
+ ["Dzhecyrillic"]=1039,
+ ["E"]=69,
+ ["Eacute"]=201,
+ ["Eacutesmall"]=63465,
+ ["Ebreve"]=276,
+ ["Ecaron"]=282,
+ ["Ecedillabreve"]=7708,
+ ["Echarmenian"]=1333,
+ ["Ecircle"]=9402,
+ ["Ecircumflex"]=202,
+ ["Ecircumflexacute"]=7870,
+ ["Ecircumflexbelow"]=7704,
+ ["Ecircumflexdotbelow"]=7878,
+ ["Ecircumflexgrave"]=7872,
+ ["Ecircumflexhookabove"]=7874,
+ ["Ecircumflexsmall"]=63466,
+ ["Ecircumflextilde"]=7876,
+ ["Ecyrillic"]=1028,
+ ["Edblgrave"]=516,
+ ["Edieresis"]=203,
+ ["Edieresissmall"]=63467,
+ ["Edot"]=278,
+ ["Edotaccent"]=278,
+ ["Edotbelow"]=7864,
+ ["Efcyrillic"]=1060,
+ ["Egrave"]=200,
+ ["Egravesmall"]=63464,
+ ["Eharmenian"]=1335,
+ ["Ehookabove"]=7866,
+ ["Eightroman"]=8551,
+ ["Einvertedbreve"]=518,
+ ["Eiotifiedcyrillic"]=1124,
+ ["Elcyrillic"]=1051,
+ ["Elevenroman"]=8554,
+ ["Emacron"]=274,
+ ["Emacronacute"]=7702,
+ ["Emacrongrave"]=7700,
+ ["Emcyrillic"]=1052,
+ ["Emonospace"]=65317,
+ ["Encyrillic"]=1053,
+ ["Endescendercyrillic"]=1186,
+ ["Eng"]=330,
+ ["Enghecyrillic"]=1188,
+ ["Enhookcyrillic"]=1223,
+ ["Eogonek"]=280,
+ ["Eopen"]=400,
+ ["Epsilon"]=917,
+ ["Epsilontonos"]=904,
+ ["Ercyrillic"]=1056,
+ ["Ereversed"]=398,
+ ["Ereversedcyrillic"]=1069,
+ ["Escyrillic"]=1057,
+ ["Esdescendercyrillic"]=1194,
+ ["Esh"]=425,
+ ["Esmall"]=63333,
+ ["Eta"]=919,
+ ["Etarmenian"]=1336,
+ ["Etatonos"]=905,
+ ["Eth"]=208,
+ ["Ethsmall"]=63472,
+ ["Etilde"]=7868,
+ ["Etildebelow"]=7706,
+ ["Euro"]=8364,
+ ["Ezh"]=439,
+ ["Ezhcaron"]=494,
+ ["Ezhreversed"]=440,
+ ["F"]=70,
+ ["Fcircle"]=9403,
+ ["Fdotaccent"]=7710,
+ ["Feharmenian"]=1366,
+ ["Feicoptic"]=996,
+ ["Fhook"]=401,
+ ["Fitacyrillic"]=1138,
+ ["Fiveroman"]=8548,
+ ["Fmonospace"]=65318,
+ ["Fourroman"]=8547,
+ ["Fsmall"]=63334,
+ ["G"]=71,
+ ["GBsquare"]=13191,
+ ["Gacute"]=500,
+ ["Gamma"]=915,
+ ["Gammaafrican"]=404,
+ ["Gangiacoptic"]=1002,
+ ["Gbreve"]=286,
+ ["Gcaron"]=486,
+ ["Gcedilla"]=290,
+ ["Gcircle"]=9404,
+ ["Gcircumflex"]=284,
+ ["Gcommaaccent"]=290,
+ ["Gdot"]=288,
+ ["Gdotaccent"]=288,
+ ["Gecyrillic"]=1043,
+ ["Ghadarmenian"]=1346,
+ ["Ghemiddlehookcyrillic"]=1172,
+ ["Ghestrokecyrillic"]=1170,
+ ["Gheupturncyrillic"]=1168,
+ ["Ghook"]=403,
+ ["Gimarmenian"]=1331,
+ ["Gjecyrillic"]=1027,
+ ["Gmacron"]=7712,
+ ["Gmonospace"]=65319,
+ ["Grave"]=63182,
+ ["Gravesmall"]=63328,
+ ["Gsmall"]=63335,
+ ["Gsmallhook"]=667,
+ ["Gstroke"]=484,
+ ["H"]=72,
+ ["H18533"]=9679,
+ ["H18543"]=9642,
+ ["H18551"]=9643,
+ ["H22073"]=9633,
+ ["HPsquare"]=13259,
+ ["Haabkhasiancyrillic"]=1192,
+ ["Hadescendercyrillic"]=1202,
+ ["Hardsigncyrillic"]=1066,
+ ["Hbar"]=294,
+ ["Hbrevebelow"]=7722,
+ ["Hcedilla"]=7720,
+ ["Hcircle"]=9405,
+ ["Hcircumflex"]=292,
+ ["Hdieresis"]=7718,
+ ["Hdotaccent"]=7714,
+ ["Hdotbelow"]=7716,
+ ["Hmonospace"]=65320,
+ ["Hoarmenian"]=1344,
+ ["Horicoptic"]=1000,
+ ["Hsmall"]=63336,
+ ["Hungarumlaut"]=63183,
+ ["Hungarumlautsmall"]=63224,
+ ["Hzsquare"]=13200,
+ ["I"]=73,
+ ["IAcyrillic"]=1071,
+ ["IJ"]=306,
+ ["IUcyrillic"]=1070,
+ ["Iacute"]=205,
+ ["Iacutesmall"]=63469,
+ ["Ibreve"]=300,
+ ["Icaron"]=463,
+ ["Icircle"]=9406,
+ ["Icircumflex"]=206,
+ ["Icircumflexsmall"]=63470,
+ ["Icyrillic"]=1030,
+ ["Idblgrave"]=520,
+ ["Idieresis"]=207,
+ ["Idieresisacute"]=7726,
+ ["Idieresiscyrillic"]=1252,
+ ["Idieresissmall"]=63471,
+ ["Idot"]=304,
+ ["Idotaccent"]=304,
+ ["Idotbelow"]=7882,
+ ["Iebrevecyrillic"]=1238,
+ ["Iecyrillic"]=1045,
+ ["Ifraktur"]=8465,
+ ["Igrave"]=204,
+ ["Igravesmall"]=63468,
+ ["Ihookabove"]=7880,
+ ["Iicyrillic"]=1048,
+ ["Iinvertedbreve"]=522,
+ ["Iishortcyrillic"]=1049,
+ ["Imacron"]=298,
+ ["Imacroncyrillic"]=1250,
+ ["Imonospace"]=65321,
+ ["Iniarmenian"]=1339,
+ ["Iocyrillic"]=1025,
+ ["Iogonek"]=302,
+ ["Iota"]=921,
+ ["Iotaafrican"]=406,
+ ["Iotadieresis"]=938,
+ ["Iotatonos"]=906,
+ ["Ismall"]=63337,
+ ["Istroke"]=407,
+ ["Itilde"]=296,
+ ["Itildebelow"]=7724,
+ ["Izhitsacyrillic"]=1140,
+ ["Izhitsadblgravecyrillic"]=1142,
+ ["J"]=74,
+ ["Jaarmenian"]=1345,
+ ["Jcircle"]=9407,
+ ["Jcircumflex"]=308,
+ ["Jecyrillic"]=1032,
+ ["Jheharmenian"]=1355,
+ ["Jmonospace"]=65322,
+ ["Jsmall"]=63338,
+ ["K"]=75,
+ ["KBsquare"]=13189,
+ ["KKsquare"]=13261,
+ ["Kabashkircyrillic"]=1184,
+ ["Kacute"]=7728,
+ ["Kacyrillic"]=1050,
+ ["Kadescendercyrillic"]=1178,
+ ["Kahookcyrillic"]=1219,
+ ["Kappa"]=922,
+ ["Kastrokecyrillic"]=1182,
+ ["Kaverticalstrokecyrillic"]=1180,
+ ["Kcaron"]=488,
+ ["Kcedilla"]=310,
+ ["Kcircle"]=9408,
+ ["Kcommaaccent"]=310,
+ ["Kdotbelow"]=7730,
+ ["Keharmenian"]=1364,
+ ["Kenarmenian"]=1343,
+ ["Khacyrillic"]=1061,
+ ["Kheicoptic"]=998,
+ ["Khook"]=408,
+ ["Kjecyrillic"]=1036,
+ ["Klinebelow"]=7732,
+ ["Kmonospace"]=65323,
+ ["Koppacyrillic"]=1152,
+ ["Koppagreek"]=990,
+ ["Ksicyrillic"]=1134,
+ ["Ksmall"]=63339,
+ ["L"]=76,
+ ["LJ"]=455,
+ ["LL"]=63167,
+ ["Lacute"]=313,
+ ["Lambda"]=923,
+ ["Lcaron"]=317,
+ ["Lcedilla"]=315,
+ ["Lcircle"]=9409,
+ ["Lcircumflexbelow"]=7740,
+ ["Lcommaaccent"]=315,
+ ["Ldot"]=319,
+ ["Ldotaccent"]=319,
+ ["Ldotbelow"]=7734,
+ ["Ldotbelowmacron"]=7736,
+ ["Liwnarmenian"]=1340,
+ ["Lj"]=456,
+ ["Ljecyrillic"]=1033,
+ ["Llinebelow"]=7738,
+ ["Lmonospace"]=65324,
+ ["Lslash"]=321,
+ ["Lslashsmall"]=63225,
+ ["Lsmall"]=63340,
+ ["M"]=77,
+ ["MBsquare"]=13190,
+ ["Macron"]=63184,
+ ["Macronsmall"]=63407,
+ ["Macute"]=7742,
+ ["Mcircle"]=9410,
+ ["Mdotaccent"]=7744,
+ ["Mdotbelow"]=7746,
+ ["Menarmenian"]=1348,
+ ["Mmonospace"]=65325,
+ ["Msmall"]=63341,
+ ["Mturned"]=412,
+ ["Mu"]=924,
+ ["N"]=78,
+ ["NJ"]=458,
+ ["Nacute"]=323,
+ ["Ncaron"]=327,
+ ["Ncedilla"]=325,
+ ["Ncircle"]=9411,
+ ["Ncircumflexbelow"]=7754,
+ ["Ncommaaccent"]=325,
+ ["Ndotaccent"]=7748,
+ ["Ndotbelow"]=7750,
+ ["Nhookleft"]=413,
+ ["Nineroman"]=8552,
+ ["Nj"]=459,
+ ["Njecyrillic"]=1034,
+ ["Nlinebelow"]=7752,
+ ["Nmonospace"]=65326,
+ ["Nowarmenian"]=1350,
+ ["Nsmall"]=63342,
+ ["Ntilde"]=209,
+ ["Ntildesmall"]=63473,
+ ["Nu"]=925,
+ ["O"]=79,
+ ["OE"]=338,
+ ["OEsmall"]=63226,
+ ["Oacute"]=211,
+ ["Oacutesmall"]=63475,
+ ["Obarredcyrillic"]=1256,
+ ["Obarreddieresiscyrillic"]=1258,
+ ["Obreve"]=334,
+ ["Ocaron"]=465,
+ ["Ocenteredtilde"]=415,
+ ["Ocircle"]=9412,
+ ["Ocircumflex"]=212,
+ ["Ocircumflexacute"]=7888,
+ ["Ocircumflexdotbelow"]=7896,
+ ["Ocircumflexgrave"]=7890,
+ ["Ocircumflexhookabove"]=7892,
+ ["Ocircumflexsmall"]=63476,
+ ["Ocircumflextilde"]=7894,
+ ["Ocyrillic"]=1054,
+ ["Odblacute"]=336,
+ ["Odblgrave"]=524,
+ ["Odieresis"]=214,
+ ["Odieresiscyrillic"]=1254,
+ ["Odieresissmall"]=63478,
+ ["Odotbelow"]=7884,
+ ["Ogoneksmall"]=63227,
+ ["Ograve"]=210,
+ ["Ogravesmall"]=63474,
+ ["Oharmenian"]=1365,
+ ["Ohm"]=8486,
+ ["Ohookabove"]=7886,
+ ["Ohorn"]=416,
+ ["Ohornacute"]=7898,
+ ["Ohorndotbelow"]=7906,
+ ["Ohorngrave"]=7900,
+ ["Ohornhookabove"]=7902,
+ ["Ohorntilde"]=7904,
+ ["Ohungarumlaut"]=336,
+ ["Oi"]=418,
+ ["Oinvertedbreve"]=526,
+ ["Omacron"]=332,
+ ["Omacronacute"]=7762,
+ ["Omacrongrave"]=7760,
+ ["Omega"]=8486,
+ ["Omegacyrillic"]=1120,
+ ["Omegagreek"]=937,
+ ["Omegaroundcyrillic"]=1146,
+ ["Omegatitlocyrillic"]=1148,
+ ["Omegatonos"]=911,
+ ["Omicron"]=927,
+ ["Omicrontonos"]=908,
+ ["Omonospace"]=65327,
+ ["Oneroman"]=8544,
+ ["Oogonek"]=490,
+ ["Oogonekmacron"]=492,
+ ["Oopen"]=390,
+ ["Oslash"]=216,
+ ["Oslashacute"]=510,
+ ["Oslashsmall"]=63480,
+ ["Osmall"]=63343,
+ ["Ostrokeacute"]=510,
+ ["Otcyrillic"]=1150,
+ ["Otilde"]=213,
+ ["Otildeacute"]=7756,
+ ["Otildedieresis"]=7758,
+ ["Otildesmall"]=63477,
+ ["P"]=80,
+ ["Pacute"]=7764,
+ ["Pcircle"]=9413,
+ ["Pdotaccent"]=7766,
+ ["Pecyrillic"]=1055,
+ ["Peharmenian"]=1354,
+ ["Pemiddlehookcyrillic"]=1190,
+ ["Phi"]=934,
+ ["Phook"]=420,
+ ["Pi"]=928,
+ ["Piwrarmenian"]=1363,
+ ["Pmonospace"]=65328,
+ ["Psi"]=936,
+ ["Psicyrillic"]=1136,
+ ["Psmall"]=63344,
+ ["Q"]=81,
+ ["Qcircle"]=9414,
+ ["Qmonospace"]=65329,
+ ["Qsmall"]=63345,
+ ["R"]=82,
+ ["Raarmenian"]=1356,
+ ["Racute"]=340,
+ ["Rcaron"]=344,
+ ["Rcedilla"]=342,
+ ["Rcircle"]=9415,
+ ["Rcommaaccent"]=342,
+ ["Rdblgrave"]=528,
+ ["Rdotaccent"]=7768,
+ ["Rdotbelow"]=7770,
+ ["Rdotbelowmacron"]=7772,
+ ["Reharmenian"]=1360,
+ ["Rfraktur"]=8476,
+ ["Rho"]=929,
+ ["Ringsmall"]=63228,
+ ["Rinvertedbreve"]=530,
+ ["Rlinebelow"]=7774,
+ ["Rmonospace"]=65330,
+ ["Rsmall"]=63346,
+ ["Rsmallinverted"]=641,
+ ["Rsmallinvertedsuperior"]=694,
+ ["S"]=83,
+ ["SF010000"]=9484,
+ ["SF020000"]=9492,
+ ["SF030000"]=9488,
+ ["SF040000"]=9496,
+ ["SF050000"]=9532,
+ ["SF060000"]=9516,
+ ["SF070000"]=9524,
+ ["SF080000"]=9500,
+ ["SF090000"]=9508,
+ ["SF10000"]=9484,
+ ["SF100000"]=9472,
+ ["SF110000"]=9474,
+ ["SF190000"]=9569,
+ ["SF20000"]=9492,
+ ["SF200000"]=9570,
+ ["SF210000"]=9558,
+ ["SF220000"]=9557,
+ ["SF230000"]=9571,
+ ["SF240000"]=9553,
+ ["SF250000"]=9559,
+ ["SF260000"]=9565,
+ ["SF270000"]=9564,
+ ["SF280000"]=9563,
+ ["SF30000"]=9488,
+ ["SF360000"]=9566,
+ ["SF370000"]=9567,
+ ["SF380000"]=9562,
+ ["SF390000"]=9556,
+ ["SF40000"]=9496,
+ ["SF400000"]=9577,
+ ["SF410000"]=9574,
+ ["SF420000"]=9568,
+ ["SF430000"]=9552,
+ ["SF440000"]=9580,
+ ["SF450000"]=9575,
+ ["SF460000"]=9576,
+ ["SF470000"]=9572,
+ ["SF480000"]=9573,
+ ["SF490000"]=9561,
+ ["SF50000"]=9532,
+ ["SF500000"]=9560,
+ ["SF510000"]=9554,
+ ["SF520000"]=9555,
+ ["SF530000"]=9579,
+ ["SF540000"]=9578,
+ ["SF60000"]=9516,
+ ["SF70000"]=9524,
+ ["SF80000"]=9500,
+ ["SF90000"]=9508,
+ ["Sacute"]=346,
+ ["Sacutedotaccent"]=7780,
+ ["Sampigreek"]=992,
+ ["Scaron"]=352,
+ ["Scarondotaccent"]=7782,
+ ["Scaronsmall"]=63229,
+ ["Scedilla"]=350,
+ ["Schwa"]=399,
+ ["Schwacyrillic"]=1240,
+ ["Schwadieresiscyrillic"]=1242,
+ ["Scircle"]=9416,
+ ["Scircumflex"]=348,
+ ["Scommaaccent"]=536,
+ ["Sdotaccent"]=7776,
+ ["Sdotbelow"]=7778,
+ ["Sdotbelowdotaccent"]=7784,
+ ["Seharmenian"]=1357,
+ ["Sevenroman"]=8550,
+ ["Shaarmenian"]=1351,
+ ["Shacyrillic"]=1064,
+ ["Shchacyrillic"]=1065,
+ ["Sheicoptic"]=994,
+ ["Shhacyrillic"]=1210,
+ ["Shimacoptic"]=1004,
+ ["Sigma"]=931,
+ ["Sixroman"]=8549,
+ ["Smonospace"]=65331,
+ ["Softsigncyrillic"]=1068,
+ ["Ssmall"]=63347,
+ ["Stigmagreek"]=986,
+ ["T"]=84,
+ ["Tau"]=932,
+ ["Tbar"]=358,
+ ["Tcaron"]=356,
+ ["Tcedilla"]=354,
+ ["Tcircle"]=9417,
+ ["Tcircumflexbelow"]=7792,
+ ["Tcommaaccent"]=354,
+ ["Tdotaccent"]=7786,
+ ["Tdotbelow"]=7788,
+ ["Tecyrillic"]=1058,
+ ["Tedescendercyrillic"]=1196,
+ ["Tenroman"]=8553,
+ ["Tetsecyrillic"]=1204,
+ ["Theta"]=920,
+ ["Thook"]=428,
+ ["Thorn"]=222,
+ ["Thornsmall"]=63486,
+ ["Threeroman"]=8546,
+ ["Tildesmall"]=63230,
+ ["Tiwnarmenian"]=1359,
+ ["Tlinebelow"]=7790,
+ ["Tmonospace"]=65332,
+ ["Toarmenian"]=1337,
+ ["Tonefive"]=444,
+ ["Tonesix"]=388,
+ ["Tonetwo"]=423,
+ ["Tretroflexhook"]=430,
+ ["Tsecyrillic"]=1062,
+ ["Tshecyrillic"]=1035,
+ ["Tsmall"]=63348,
+ ["Twelveroman"]=8555,
+ ["Tworoman"]=8545,
+ ["U"]=85,
+ ["Uacute"]=218,
+ ["Uacutesmall"]=63482,
+ ["Ubreve"]=364,
+ ["Ucaron"]=467,
+ ["Ucircle"]=9418,
+ ["Ucircumflex"]=219,
+ ["Ucircumflexbelow"]=7798,
+ ["Ucircumflexsmall"]=63483,
+ ["Ucyrillic"]=1059,
+ ["Udblacute"]=368,
+ ["Udblgrave"]=532,
+ ["Udieresis"]=220,
+ ["Udieresisacute"]=471,
+ ["Udieresisbelow"]=7794,
+ ["Udieresiscaron"]=473,
+ ["Udieresiscyrillic"]=1264,
+ ["Udieresisgrave"]=475,
+ ["Udieresismacron"]=469,
+ ["Udieresissmall"]=63484,
+ ["Udotbelow"]=7908,
+ ["Ugrave"]=217,
+ ["Ugravesmall"]=63481,
+ ["Uhookabove"]=7910,
+ ["Uhorn"]=431,
+ ["Uhornacute"]=7912,
+ ["Uhorndotbelow"]=7920,
+ ["Uhorngrave"]=7914,
+ ["Uhornhookabove"]=7916,
+ ["Uhorntilde"]=7918,
+ ["Uhungarumlaut"]=368,
+ ["Uhungarumlautcyrillic"]=1266,
+ ["Uinvertedbreve"]=534,
+ ["Ukcyrillic"]=1144,
+ ["Umacron"]=362,
+ ["Umacroncyrillic"]=1262,
+ ["Umacrondieresis"]=7802,
+ ["Umonospace"]=65333,
+ ["Uogonek"]=370,
+ ["Upsilon"]=933,
+ ["Upsilon1"]=978,
+ ["Upsilonacutehooksymbolgreek"]=979,
+ ["Upsilonafrican"]=433,
+ ["Upsilondieresis"]=939,
+ ["Upsilondieresishooksymbolgreek"]=980,
+ ["Upsilonhooksymbol"]=978,
+ ["Upsilontonos"]=910,
+ ["Uring"]=366,
+ ["Ushortcyrillic"]=1038,
+ ["Usmall"]=63349,
+ ["Ustraightcyrillic"]=1198,
+ ["Ustraightstrokecyrillic"]=1200,
+ ["Utilde"]=360,
+ ["Utildeacute"]=7800,
+ ["Utildebelow"]=7796,
+ ["V"]=86,
+ ["Vcircle"]=9419,
+ ["Vdotbelow"]=7806,
+ ["Vecyrillic"]=1042,
+ ["Vewarmenian"]=1358,
+ ["Vhook"]=434,
+ ["Vmonospace"]=65334,
+ ["Voarmenian"]=1352,
+ ["Vsmall"]=63350,
+ ["Vtilde"]=7804,
+ ["W"]=87,
+ ["Wacute"]=7810,
+ ["Wcircle"]=9420,
+ ["Wcircumflex"]=372,
+ ["Wdieresis"]=7812,
+ ["Wdotaccent"]=7814,
+ ["Wdotbelow"]=7816,
+ ["Wgrave"]=7808,
+ ["Wmonospace"]=65335,
+ ["Wsmall"]=63351,
+ ["X"]=88,
+ ["Xcircle"]=9421,
+ ["Xdieresis"]=7820,
+ ["Xdotaccent"]=7818,
+ ["Xeharmenian"]=1341,
+ ["Xi"]=926,
+ ["Xmonospace"]=65336,
+ ["Xsmall"]=63352,
+ ["Y"]=89,
+ ["Yacute"]=221,
+ ["Yacutesmall"]=63485,
+ ["Yatcyrillic"]=1122,
+ ["Ycircle"]=9422,
+ ["Ycircumflex"]=374,
+ ["Ydieresis"]=376,
+ ["Ydieresissmall"]=63487,
+ ["Ydotaccent"]=7822,
+ ["Ydotbelow"]=7924,
+ ["Yericyrillic"]=1067,
+ ["Yerudieresiscyrillic"]=1272,
+ ["Ygrave"]=7922,
+ ["Yhook"]=435,
+ ["Yhookabove"]=7926,
+ ["Yiarmenian"]=1349,
+ ["Yicyrillic"]=1031,
+ ["Yiwnarmenian"]=1362,
+ ["Ymonospace"]=65337,
+ ["Ysmall"]=63353,
+ ["Ytilde"]=7928,
+ ["Yusbigcyrillic"]=1130,
+ ["Yusbigiotifiedcyrillic"]=1132,
+ ["Yuslittlecyrillic"]=1126,
+ ["Yuslittleiotifiedcyrillic"]=1128,
+ ["Z"]=90,
+ ["Zaarmenian"]=1334,
+ ["Zacute"]=377,
+ ["Zcaron"]=381,
+ ["Zcaronsmall"]=63231,
+ ["Zcircle"]=9423,
+ ["Zcircumflex"]=7824,
+ ["Zdot"]=379,
+ ["Zdotaccent"]=379,
+ ["Zdotbelow"]=7826,
+ ["Zecyrillic"]=1047,
+ ["Zedescendercyrillic"]=1176,
+ ["Zedieresiscyrillic"]=1246,
+ ["Zeta"]=918,
+ ["Zhearmenian"]=1338,
+ ["Zhebrevecyrillic"]=1217,
+ ["Zhecyrillic"]=1046,
+ ["Zhedescendercyrillic"]=1174,
+ ["Zhedieresiscyrillic"]=1244,
+ ["Zlinebelow"]=7828,
+ ["Zmonospace"]=65338,
+ ["Zsmall"]=63354,
+ ["Zstroke"]=437,
+ ["a"]=97,
+ ["aabengali"]=2438,
+ ["aacute"]=225,
+ ["aadeva"]=2310,
+ ["aagujarati"]=2694,
+ ["aagurmukhi"]=2566,
+ ["aamatragurmukhi"]=2622,
+ ["aarusquare"]=13059,
+ ["aavowelsignbengali"]=2494,
+ ["aavowelsigndeva"]=2366,
+ ["aavowelsigngujarati"]=2750,
+ ["abbreviationmarkarmenian"]=1375,
+ ["abbreviationsigndeva"]=2416,
+ ["abengali"]=2437,
+ ["abopomofo"]=12570,
+ ["abreve"]=259,
+ ["abreveacute"]=7855,
+ ["abrevecyrillic"]=1233,
+ ["abrevedotbelow"]=7863,
+ ["abrevegrave"]=7857,
+ ["abrevehookabove"]=7859,
+ ["abrevetilde"]=7861,
+ ["acaron"]=462,
+ ["acircle"]=9424,
+ ["acircumflex"]=226,
+ ["acircumflexacute"]=7845,
+ ["acircumflexdotbelow"]=7853,
+ ["acircumflexgrave"]=7847,
+ ["acircumflexhookabove"]=7849,
+ ["acircumflextilde"]=7851,
+ ["acute"]=180,
+ ["acutebelowcmb"]=791,
+ ["acutecmb"]=769,
+ ["acutecomb"]=769,
+ ["acutedeva"]=2388,
+ ["acutelowmod"]=719,
+ ["acutetonecmb"]=833,
+ ["acyrillic"]=1072,
+ ["adblgrave"]=513,
+ ["addakgurmukhi"]=2673,
+ ["adeva"]=2309,
+ ["adieresis"]=228,
+ ["adieresiscyrillic"]=1235,
+ ["adieresismacron"]=479,
+ ["adotbelow"]=7841,
+ ["adotmacron"]=481,
+ ["ae"]=230,
+ ["aeacute"]=509,
+ ["aekorean"]=12624,
+ ["aemacron"]=483,
+ ["afii00208"]=8213,
+ ["afii08941"]=8356,
+ ["afii10017"]=1040,
+ ["afii10018"]=1041,
+ ["afii10019"]=1042,
+ ["afii10020"]=1043,
+ ["afii10021"]=1044,
+ ["afii10022"]=1045,
+ ["afii10023"]=1025,
+ ["afii10024"]=1046,
+ ["afii10025"]=1047,
+ ["afii10026"]=1048,
+ ["afii10027"]=1049,
+ ["afii10028"]=1050,
+ ["afii10029"]=1051,
+ ["afii10030"]=1052,
+ ["afii10031"]=1053,
+ ["afii10032"]=1054,
+ ["afii10033"]=1055,
+ ["afii10034"]=1056,
+ ["afii10035"]=1057,
+ ["afii10036"]=1058,
+ ["afii10037"]=1059,
+ ["afii10038"]=1060,
+ ["afii10039"]=1061,
+ ["afii10040"]=1062,
+ ["afii10041"]=1063,
+ ["afii10042"]=1064,
+ ["afii10043"]=1065,
+ ["afii10044"]=1066,
+ ["afii10045"]=1067,
+ ["afii10046"]=1068,
+ ["afii10047"]=1069,
+ ["afii10048"]=1070,
+ ["afii10049"]=1071,
+ ["afii10050"]=1168,
+ ["afii10051"]=1026,
+ ["afii10052"]=1027,
+ ["afii10053"]=1028,
+ ["afii10054"]=1029,
+ ["afii10055"]=1030,
+ ["afii10056"]=1031,
+ ["afii10057"]=1032,
+ ["afii10058"]=1033,
+ ["afii10059"]=1034,
+ ["afii10060"]=1035,
+ ["afii10061"]=1036,
+ ["afii10062"]=1038,
+ ["afii10063"]=63172,
+ ["afii10064"]=63173,
+ ["afii10065"]=1072,
+ ["afii10066"]=1073,
+ ["afii10067"]=1074,
+ ["afii10068"]=1075,
+ ["afii10069"]=1076,
+ ["afii10070"]=1077,
+ ["afii10071"]=1105,
+ ["afii10072"]=1078,
+ ["afii10073"]=1079,
+ ["afii10074"]=1080,
+ ["afii10075"]=1081,
+ ["afii10076"]=1082,
+ ["afii10077"]=1083,
+ ["afii10078"]=1084,
+ ["afii10079"]=1085,
+ ["afii10080"]=1086,
+ ["afii10081"]=1087,
+ ["afii10082"]=1088,
+ ["afii10083"]=1089,
+ ["afii10084"]=1090,
+ ["afii10085"]=1091,
+ ["afii10086"]=1092,
+ ["afii10087"]=1093,
+ ["afii10088"]=1094,
+ ["afii10089"]=1095,
+ ["afii10090"]=1096,
+ ["afii10091"]=1097,
+ ["afii10092"]=1098,
+ ["afii10093"]=1099,
+ ["afii10094"]=1100,
+ ["afii10095"]=1101,
+ ["afii10096"]=1102,
+ ["afii10097"]=1103,
+ ["afii10098"]=1169,
+ ["afii10099"]=1106,
+ ["afii10100"]=1107,
+ ["afii10101"]=1108,
+ ["afii10102"]=1109,
+ ["afii10103"]=1110,
+ ["afii10104"]=1111,
+ ["afii10105"]=1112,
+ ["afii10106"]=1113,
+ ["afii10107"]=1114,
+ ["afii10108"]=1115,
+ ["afii10109"]=1116,
+ ["afii10110"]=1118,
+ ["afii10145"]=1039,
+ ["afii10146"]=1122,
+ ["afii10147"]=1138,
+ ["afii10148"]=1140,
+ ["afii10192"]=63174,
+ ["afii10193"]=1119,
+ ["afii10194"]=1123,
+ ["afii10195"]=1139,
+ ["afii10196"]=1141,
+ ["afii10831"]=63175,
+ ["afii10832"]=63176,
+ ["afii10846"]=1241,
+ ["afii208"]=8213,
+ ["afii299"]=8206,
+ ["afii300"]=8207,
+ ["afii301"]=8205,
+ ["afii57381"]=1642,
+ ["afii57388"]=1548,
+ ["afii57392"]=1632,
+ ["afii57393"]=1633,
+ ["afii57394"]=1634,
+ ["afii57395"]=1635,
+ ["afii57396"]=1636,
+ ["afii57397"]=1637,
+ ["afii57398"]=1638,
+ ["afii57399"]=1639,
+ ["afii57400"]=1640,
+ ["afii57401"]=1641,
+ ["afii57403"]=1563,
+ ["afii57407"]=1567,
+ ["afii57409"]=1569,
+ ["afii57410"]=1570,
+ ["afii57411"]=1571,
+ ["afii57412"]=1572,
+ ["afii57413"]=1573,
+ ["afii57414"]=1574,
+ ["afii57415"]=1575,
+ ["afii57416"]=1576,
+ ["afii57417"]=1577,
+ ["afii57418"]=1578,
+ ["afii57419"]=1579,
+ ["afii57420"]=1580,
+ ["afii57421"]=1581,
+ ["afii57422"]=1582,
+ ["afii57423"]=1583,
+ ["afii57424"]=1584,
+ ["afii57425"]=1585,
+ ["afii57426"]=1586,
+ ["afii57427"]=1587,
+ ["afii57428"]=1588,
+ ["afii57429"]=1589,
+ ["afii57430"]=1590,
+ ["afii57431"]=1591,
+ ["afii57432"]=1592,
+ ["afii57433"]=1593,
+ ["afii57434"]=1594,
+ ["afii57440"]=1600,
+ ["afii57441"]=1601,
+ ["afii57442"]=1602,
+ ["afii57443"]=1603,
+ ["afii57444"]=1604,
+ ["afii57445"]=1605,
+ ["afii57446"]=1606,
+ ["afii57448"]=1608,
+ ["afii57449"]=1609,
+ ["afii57450"]=1610,
+ ["afii57451"]=1611,
+ ["afii57452"]=1612,
+ ["afii57453"]=1613,
+ ["afii57454"]=1614,
+ ["afii57455"]=1615,
+ ["afii57456"]=1616,
+ ["afii57457"]=1617,
+ ["afii57458"]=1618,
+ ["afii57470"]=1607,
+ ["afii57505"]=1700,
+ ["afii57506"]=1662,
+ ["afii57507"]=1670,
+ ["afii57508"]=1688,
+ ["afii57509"]=1711,
+ ["afii57511"]=1657,
+ ["afii57512"]=1672,
+ ["afii57513"]=1681,
+ ["afii57514"]=1722,
+ ["afii57519"]=1746,
+ ["afii57534"]=1749,
+ ["afii57636"]=8362,
+ ["afii57645"]=1470,
+ ["afii57658"]=1475,
+ ["afii57664"]=1488,
+ ["afii57665"]=1489,
+ ["afii57666"]=1490,
+ ["afii57667"]=1491,
+ ["afii57668"]=1492,
+ ["afii57669"]=1493,
+ ["afii57670"]=1494,
+ ["afii57671"]=1495,
+ ["afii57672"]=1496,
+ ["afii57673"]=1497,
+ ["afii57674"]=1498,
+ ["afii57675"]=1499,
+ ["afii57676"]=1500,
+ ["afii57677"]=1501,
+ ["afii57678"]=1502,
+ ["afii57679"]=1503,
+ ["afii57680"]=1504,
+ ["afii57681"]=1505,
+ ["afii57682"]=1506,
+ ["afii57683"]=1507,
+ ["afii57684"]=1508,
+ ["afii57685"]=1509,
+ ["afii57686"]=1510,
+ ["afii57687"]=1511,
+ ["afii57688"]=1512,
+ ["afii57689"]=1513,
+ ["afii57690"]=1514,
+ ["afii57694"]=64298,
+ ["afii57695"]=64299,
+ ["afii57700"]=64331,
+ ["afii57705"]=64287,
+ ["afii57716"]=1520,
+ ["afii57717"]=1521,
+ ["afii57718"]=1522,
+ ["afii57723"]=64309,
+ ["afii57793"]=1460,
+ ["afii57794"]=1461,
+ ["afii57795"]=1462,
+ ["afii57796"]=1467,
+ ["afii57797"]=1464,
+ ["afii57798"]=1463,
+ ["afii57799"]=1456,
+ ["afii57800"]=1458,
+ ["afii57801"]=1457,
+ ["afii57802"]=1459,
+ ["afii57803"]=1474,
+ ["afii57804"]=1473,
+ ["afii57806"]=1465,
+ ["afii57807"]=1468,
+ ["afii57839"]=1469,
+ ["afii57841"]=1471,
+ ["afii57842"]=1472,
+ ["afii57929"]=700,
+ ["afii61248"]=8453,
+ ["afii61289"]=8467,
+ ["afii61352"]=8470,
+ ["afii61573"]=8236,
+ ["afii61574"]=8237,
+ ["afii61575"]=8238,
+ ["afii61664"]=8204,
+ ["afii63167"]=1645,
+ ["afii64937"]=701,
+ ["agrave"]=224,
+ ["agujarati"]=2693,
+ ["agurmukhi"]=2565,
+ ["ahiragana"]=12354,
+ ["ahookabove"]=7843,
+ ["aibengali"]=2448,
+ ["aibopomofo"]=12574,
+ ["aideva"]=2320,
+ ["aiecyrillic"]=1237,
+ ["aigujarati"]=2704,
+ ["aigurmukhi"]=2576,
+ ["aimatragurmukhi"]=2632,
+ ["ainarabic"]=1593,
+ ["ainfinalarabic"]=65226,
+ ["aininitialarabic"]=65227,
+ ["ainmedialarabic"]=65228,
+ ["ainvertedbreve"]=515,
+ ["aivowelsignbengali"]=2504,
+ ["aivowelsigndeva"]=2376,
+ ["aivowelsigngujarati"]=2760,
+ ["akatakana"]=12450,
+ ["akatakanahalfwidth"]=65393,
+ ["akorean"]=12623,
+ ["alef"]=1488,
+ ["alefarabic"]=1575,
+ ["alefdageshhebrew"]=64304,
+ ["aleffinalarabic"]=65166,
+ ["alefhamzaabovearabic"]=1571,
+ ["alefhamzaabovefinalarabic"]=65156,
+ ["alefhamzabelowarabic"]=1573,
+ ["alefhamzabelowfinalarabic"]=65160,
+ ["alefhebrew"]=1488,
+ ["aleflamedhebrew"]=64335,
+ ["alefmaddaabovearabic"]=1570,
+ ["alefmaddaabovefinalarabic"]=65154,
+ ["alefmaksuraarabic"]=1609,
+ ["alefmaksurafinalarabic"]=65264,
+ ["alefmaksurainitialarabic"]=65267,
+ ["alefmaksuramedialarabic"]=65268,
+ ["alefpatahhebrew"]=64302,
+ ["alefqamatshebrew"]=64303,
+ ["aleph"]=8501,
+ ["allequal"]=8780,
+ ["alpha"]=945,
+ ["alphatonos"]=940,
+ ["amacron"]=257,
+ ["amonospace"]=65345,
+ ["ampersand"]=38,
+ ["ampersandmonospace"]=65286,
+ ["ampersandsmall"]=63270,
+ ["amsquare"]=13250,
+ ["anbopomofo"]=12578,
+ ["angbopomofo"]=12580,
+ ["angkhankhuthai"]=3674,
+ ["angle"]=8736,
+ ["anglebracketleft"]=12296,
+ ["anglebracketleftvertical"]=65087,
+ ["anglebracketright"]=12297,
+ ["anglebracketrightvertical"]=65088,
+ ["angleleft"]=9001,
+ ["angleright"]=9002,
+ ["angstrom"]=8491,
+ ["anoteleia"]=903,
+ ["anudattadeva"]=2386,
+ ["anusvarabengali"]=2434,
+ ["anusvaradeva"]=2306,
+ ["anusvaragujarati"]=2690,
+ ["aogonek"]=261,
+ ["apaatosquare"]=13056,
+ ["aparen"]=9372,
+ ["apostrophearmenian"]=1370,
+ ["apostrophemod"]=700,
+ ["apple"]=63743,
+ ["approaches"]=8784,
+ ["approxequal"]=8776,
+ ["approxequalorimage"]=8786,
+ ["approximatelyequal"]=8773,
+ ["araeaekorean"]=12686,
+ ["araeakorean"]=12685,
+ ["arc"]=8978,
+ ["arighthalfring"]=7834,
+ ["aring"]=229,
+ ["aringacute"]=507,
+ ["aringbelow"]=7681,
+ ["arrowboth"]=8596,
+ ["arrowdashdown"]=8675,
+ ["arrowdashleft"]=8672,
+ ["arrowdashright"]=8674,
+ ["arrowdashup"]=8673,
+ ["arrowdblboth"]=8660,
+ ["arrowdbldown"]=8659,
+ ["arrowdblleft"]=8656,
+ ["arrowdblright"]=8658,
+ ["arrowdblup"]=8657,
+ ["arrowdown"]=8595,
+ ["arrowdownleft"]=8601,
+ ["arrowdownright"]=8600,
+ ["arrowdownwhite"]=8681,
+ ["arrowheaddownmod"]=709,
+ ["arrowheadleftmod"]=706,
+ ["arrowheadrightmod"]=707,
+ ["arrowheadupmod"]=708,
+ ["arrowhorizex"]=63719,
+ ["arrowleft"]=8592,
+ ["arrowleftdbl"]=8656,
+ ["arrowleftdblstroke"]=8653,
+ ["arrowleftoverright"]=8646,
+ ["arrowleftwhite"]=8678,
+ ["arrowright"]=8594,
+ ["arrowrightdblstroke"]=8655,
+ ["arrowrightheavy"]=10142,
+ ["arrowrightoverleft"]=8644,
+ ["arrowrightwhite"]=8680,
+ ["arrowtableft"]=8676,
+ ["arrowtabright"]=8677,
+ ["arrowup"]=8593,
+ ["arrowupdn"]=8597,
+ ["arrowupdnbse"]=8616,
+ ["arrowupdownbase"]=8616,
+ ["arrowupleft"]=8598,
+ ["arrowupleftofdown"]=8645,
+ ["arrowupright"]=8599,
+ ["arrowupwhite"]=8679,
+ ["arrowvertex"]=63718,
+ ["asciicircum"]=94,
+ ["asciicircummonospace"]=65342,
+ ["asciitilde"]=126,
+ ["asciitildemonospace"]=65374,
+ ["ascript"]=593,
+ ["ascriptturned"]=594,
+ ["asmallhiragana"]=12353,
+ ["asmallkatakana"]=12449,
+ ["asmallkatakanahalfwidth"]=65383,
+ ["asterisk"]=42,
+ ["asteriskaltonearabic"]=1645,
+ ["asteriskarabic"]=1645,
+ ["asteriskmath"]=8727,
+ ["asteriskmonospace"]=65290,
+ ["asterisksmall"]=65121,
+ ["asterism"]=8258,
+ ["asuperior"]=63209,
+ ["asymptoticallyequal"]=8771,
+ ["at"]=64,
+ ["atilde"]=227,
+ ["atmonospace"]=65312,
+ ["atsmall"]=65131,
+ ["aturned"]=592,
+ ["aubengali"]=2452,
+ ["aubopomofo"]=12576,
+ ["audeva"]=2324,
+ ["augujarati"]=2708,
+ ["augurmukhi"]=2580,
+ ["aulengthmarkbengali"]=2519,
+ ["aumatragurmukhi"]=2636,
+ ["auvowelsignbengali"]=2508,
+ ["auvowelsigndeva"]=2380,
+ ["auvowelsigngujarati"]=2764,
+ ["avagrahadeva"]=2365,
+ ["aybarmenian"]=1377,
+ ["ayin"]=1506,
+ ["ayinaltonehebrew"]=64288,
+ ["ayinhebrew"]=1506,
+ ["b"]=98,
+ ["babengali"]=2476,
+ ["backslash"]=92,
+ ["backslashmonospace"]=65340,
+ ["badeva"]=2348,
+ ["bagujarati"]=2732,
+ ["bagurmukhi"]=2604,
+ ["bahiragana"]=12400,
+ ["bahtthai"]=3647,
+ ["bakatakana"]=12496,
+ ["bar"]=124,
+ ["barmonospace"]=65372,
+ ["bbopomofo"]=12549,
+ ["bcircle"]=9425,
+ ["bdotaccent"]=7683,
+ ["bdotbelow"]=7685,
+ ["beamedsixteenthnotes"]=9836,
+ ["because"]=8757,
+ ["becyrillic"]=1073,
+ ["beharabic"]=1576,
+ ["behfinalarabic"]=65168,
+ ["behinitialarabic"]=65169,
+ ["behiragana"]=12409,
+ ["behmedialarabic"]=65170,
+ ["behmeeminitialarabic"]=64671,
+ ["behmeemisolatedarabic"]=64520,
+ ["behnoonfinalarabic"]=64621,
+ ["bekatakana"]=12505,
+ ["benarmenian"]=1378,
+ ["bet"]=1489,
+ ["beta"]=946,
+ ["betasymbolgreek"]=976,
+ ["betdagesh"]=64305,
+ ["betdageshhebrew"]=64305,
+ ["bethebrew"]=1489,
+ ["betrafehebrew"]=64332,
+ ["bhabengali"]=2477,
+ ["bhadeva"]=2349,
+ ["bhagujarati"]=2733,
+ ["bhagurmukhi"]=2605,
+ ["bhook"]=595,
+ ["bihiragana"]=12403,
+ ["bikatakana"]=12499,
+ ["bilabialclick"]=664,
+ ["bindigurmukhi"]=2562,
+ ["birusquare"]=13105,
+ ["blackcircle"]=9679,
+ ["blackdiamond"]=9670,
+ ["blackdownpointingtriangle"]=9660,
+ ["blackleftpointingpointer"]=9668,
+ ["blackleftpointingtriangle"]=9664,
+ ["blacklenticularbracketleft"]=12304,
+ ["blacklenticularbracketleftvertical"]=65083,
+ ["blacklenticularbracketright"]=12305,
+ ["blacklenticularbracketrightvertical"]=65084,
+ ["blacklowerlefttriangle"]=9699,
+ ["blacklowerrighttriangle"]=9698,
+ ["blackrectangle"]=9644,
+ ["blackrightpointingpointer"]=9658,
+ ["blackrightpointingtriangle"]=9654,
+ ["blacksmallsquare"]=9642,
+ ["blacksmilingface"]=9787,
+ ["blacksquare"]=9632,
+ ["blackstar"]=9733,
+ ["blackupperlefttriangle"]=9700,
+ ["blackupperrighttriangle"]=9701,
+ ["blackuppointingsmalltriangle"]=9652,
+ ["blackuppointingtriangle"]=9650,
+ ["blank"]=9251,
+ ["blinebelow"]=7687,
+ ["block"]=9608,
+ ["bmonospace"]=65346,
+ ["bobaimaithai"]=3610,
+ ["bohiragana"]=12412,
+ ["bokatakana"]=12508,
+ ["bparen"]=9373,
+ ["bqsquare"]=13251,
+ ["braceex"]=63732,
+ ["braceleft"]=123,
+ ["braceleftbt"]=63731,
+ ["braceleftmid"]=63730,
+ ["braceleftmonospace"]=65371,
+ ["braceleftsmall"]=65115,
+ ["bracelefttp"]=63729,
+ ["braceleftvertical"]=65079,
+ ["braceright"]=125,
+ ["bracerightbt"]=63742,
+ ["bracerightmid"]=63741,
+ ["bracerightmonospace"]=65373,
+ ["bracerightsmall"]=65116,
+ ["bracerighttp"]=63740,
+ ["bracerightvertical"]=65080,
+ ["bracketleft"]=91,
+ ["bracketleftbt"]=63728,
+ ["bracketleftex"]=63727,
+ ["bracketleftmonospace"]=65339,
+ ["bracketlefttp"]=63726,
+ ["bracketright"]=93,
+ ["bracketrightbt"]=63739,
+ ["bracketrightex"]=63738,
+ ["bracketrightmonospace"]=65341,
+ ["bracketrighttp"]=63737,
+ ["breve"]=728,
+ ["brevebelowcmb"]=814,
+ ["brevecmb"]=774,
+ ["breveinvertedbelowcmb"]=815,
+ ["breveinvertedcmb"]=785,
+ ["breveinverteddoublecmb"]=865,
+ ["bridgebelowcmb"]=810,
+ ["bridgeinvertedbelowcmb"]=826,
+ ["brokenbar"]=166,
+ ["bstroke"]=384,
+ ["bsuperior"]=63210,
+ ["btopbar"]=387,
+ ["buhiragana"]=12406,
+ ["bukatakana"]=12502,
+ ["bullet"]=8226,
+ ["bulletinverse"]=9688,
+ ["bulletoperator"]=8729,
+ ["bullseye"]=9678,
+ ["c"]=99,
+ ["caarmenian"]=1390,
+ ["cabengali"]=2458,
+ ["cacute"]=263,
+ ["cadeva"]=2330,
+ ["cagujarati"]=2714,
+ ["cagurmukhi"]=2586,
+ ["calsquare"]=13192,
+ ["candrabindubengali"]=2433,
+ ["candrabinducmb"]=784,
+ ["candrabindudeva"]=2305,
+ ["candrabindugujarati"]=2689,
+ ["capslock"]=8682,
+ ["careof"]=8453,
+ ["caron"]=711,
+ ["caronbelowcmb"]=812,
+ ["caroncmb"]=780,
+ ["carriagereturn"]=8629,
+ ["cbopomofo"]=12568,
+ ["ccaron"]=269,
+ ["ccedilla"]=231,
+ ["ccedillaacute"]=7689,
+ ["ccircle"]=9426,
+ ["ccircumflex"]=265,
+ ["ccurl"]=597,
+ ["cdot"]=267,
+ ["cdotaccent"]=267,
+ ["cdsquare"]=13253,
+ ["cedilla"]=184,
+ ["cedillacmb"]=807,
+ ["cent"]=162,
+ ["centigrade"]=8451,
+ ["centinferior"]=63199,
+ ["centmonospace"]=65504,
+ ["centoldstyle"]=63394,
+ ["centsuperior"]=63200,
+ ["chaarmenian"]=1401,
+ ["chabengali"]=2459,
+ ["chadeva"]=2331,
+ ["chagujarati"]=2715,
+ ["chagurmukhi"]=2587,
+ ["chbopomofo"]=12564,
+ ["cheabkhasiancyrillic"]=1213,
+ ["checkmark"]=10003,
+ ["checyrillic"]=1095,
+ ["chedescenderabkhasiancyrillic"]=1215,
+ ["chedescendercyrillic"]=1207,
+ ["chedieresiscyrillic"]=1269,
+ ["cheharmenian"]=1395,
+ ["chekhakassiancyrillic"]=1228,
+ ["cheverticalstrokecyrillic"]=1209,
+ ["chi"]=967,
+ ["chieuchacirclekorean"]=12919,
+ ["chieuchaparenkorean"]=12823,
+ ["chieuchcirclekorean"]=12905,
+ ["chieuchkorean"]=12618,
+ ["chieuchparenkorean"]=12809,
+ ["chochangthai"]=3594,
+ ["chochanthai"]=3592,
+ ["chochingthai"]=3593,
+ ["chochoethai"]=3596,
+ ["chook"]=392,
+ ["cieucacirclekorean"]=12918,
+ ["cieucaparenkorean"]=12822,
+ ["cieuccirclekorean"]=12904,
+ ["cieuckorean"]=12616,
+ ["cieucparenkorean"]=12808,
+ ["cieucuparenkorean"]=12828,
+ ["circle"]=9675,
+ ["circlemultiply"]=8855,
+ ["circleot"]=8857,
+ ["circleplus"]=8853,
+ ["circlepostalmark"]=12342,
+ ["circlewithlefthalfblack"]=9680,
+ ["circlewithrighthalfblack"]=9681,
+ ["circumflex"]=710,
+ ["circumflexbelowcmb"]=813,
+ ["circumflexcmb"]=770,
+ ["clear"]=8999,
+ ["clickalveolar"]=450,
+ ["clickdental"]=448,
+ ["clicklateral"]=449,
+ ["clickretroflex"]=451,
+ ["club"]=9827,
+ ["clubsuitblack"]=9827,
+ ["clubsuitwhite"]=9831,
+ ["cmcubedsquare"]=13220,
+ ["cmonospace"]=65347,
+ ["cmsquaredsquare"]=13216,
+ ["coarmenian"]=1409,
+ ["colon"]=58,
+ ["colonmonetary"]=8353,
+ ["colonmonospace"]=65306,
+ ["colonsign"]=8353,
+ ["colonsmall"]=65109,
+ ["colontriangularhalfmod"]=721,
+ ["colontriangularmod"]=720,
+ ["comma"]=44,
+ ["commaabovecmb"]=787,
+ ["commaaboverightcmb"]=789,
+ ["commaaccent"]=63171,
+ ["commaarabic"]=1548,
+ ["commaarmenian"]=1373,
+ ["commainferior"]=63201,
+ ["commamonospace"]=65292,
+ ["commareversedabovecmb"]=788,
+ ["commareversedmod"]=701,
+ ["commasmall"]=65104,
+ ["commasuperior"]=63202,
+ ["commaturnedabovecmb"]=786,
+ ["commaturnedmod"]=699,
+ ["compass"]=9788,
+ ["congruent"]=8773,
+ ["contourintegral"]=8750,
+ ["control"]=8963,
+ ["controlACK"]=6,
+ ["controlBEL"]=7,
+ ["controlBS"]=8,
+ ["controlCAN"]=24,
+ ["controlCR"]=13,
+ ["controlDC1"]=17,
+ ["controlDC2"]=18,
+ ["controlDC3"]=19,
+ ["controlDC4"]=20,
+ ["controlDEL"]=127,
+ ["controlDLE"]=16,
+ ["controlEM"]=25,
+ ["controlENQ"]=5,
+ ["controlEOT"]=4,
+ ["controlESC"]=27,
+ ["controlETB"]=23,
+ ["controlETX"]=3,
+ ["controlFF"]=12,
+ ["controlFS"]=28,
+ ["controlGS"]=29,
+ ["controlHT"]=9,
+ ["controlLF"]=10,
+ ["controlNAK"]=21,
+ ["controlRS"]=30,
+ ["controlSI"]=15,
+ ["controlSO"]=14,
+ ["controlSOT"]=2,
+ ["controlSTX"]=1,
+ ["controlSUB"]=26,
+ ["controlSYN"]=22,
+ ["controlUS"]=31,
+ ["controlVT"]=11,
+ ["copyright"]=169,
+ ["copyrightsans"]=63721,
+ ["copyrightserif"]=63193,
+ ["cornerbracketleft"]=12300,
+ ["cornerbracketlefthalfwidth"]=65378,
+ ["cornerbracketleftvertical"]=65089,
+ ["cornerbracketright"]=12301,
+ ["cornerbracketrighthalfwidth"]=65379,
+ ["cornerbracketrightvertical"]=65090,
+ ["corporationsquare"]=13183,
+ ["cosquare"]=13255,
+ ["coverkgsquare"]=13254,
+ ["cparen"]=9374,
+ ["cruzeiro"]=8354,
+ ["cstretched"]=663,
+ ["curlyand"]=8911,
+ ["curlyor"]=8910,
+ ["currency"]=164,
+ ["cyrBreve"]=63185,
+ ["cyrFlex"]=63186,
+ ["cyrbreve"]=63188,
+ ["cyrflex"]=63189,
+ ["d"]=100,
+ ["daarmenian"]=1380,
+ ["dabengali"]=2470,
+ ["dadarabic"]=1590,
+ ["dadeva"]=2342,
+ ["dadfinalarabic"]=65214,
+ ["dadinitialarabic"]=65215,
+ ["dadmedialarabic"]=65216,
+ ["dagesh"]=1468,
+ ["dageshhebrew"]=1468,
+ ["dagger"]=8224,
+ ["daggerdbl"]=8225,
+ ["dagujarati"]=2726,
+ ["dagurmukhi"]=2598,
+ ["dahiragana"]=12384,
+ ["dakatakana"]=12480,
+ ["dalarabic"]=1583,
+ ["dalet"]=1491,
+ ["daletdagesh"]=64307,
+ ["daletdageshhebrew"]=64307,
+ ["dalethatafpatah"]=1491,
+ ["dalethatafpatahhebrew"]=1491,
+ ["dalethatafsegol"]=1491,
+ ["dalethatafsegolhebrew"]=1491,
+ ["dalethebrew"]=1491,
+ ["dalethiriq"]=1491,
+ ["dalethiriqhebrew"]=1491,
+ ["daletholam"]=1491,
+ ["daletholamhebrew"]=1491,
+ ["daletpatah"]=1491,
+ ["daletpatahhebrew"]=1491,
+ ["daletqamats"]=1491,
+ ["daletqamatshebrew"]=1491,
+ ["daletqubuts"]=1491,
+ ["daletqubutshebrew"]=1491,
+ ["daletsegol"]=1491,
+ ["daletsegolhebrew"]=1491,
+ ["daletsheva"]=1491,
+ ["daletshevahebrew"]=1491,
+ ["dalettsere"]=1491,
+ ["dalettserehebrew"]=1491,
+ ["dalfinalarabic"]=65194,
+ ["dammaarabic"]=1615,
+ ["dammalowarabic"]=1615,
+ ["dammatanaltonearabic"]=1612,
+ ["dammatanarabic"]=1612,
+ ["danda"]=2404,
+ ["dargahebrew"]=1447,
+ ["dargalefthebrew"]=1447,
+ ["dasiapneumatacyrilliccmb"]=1157,
+ ["dblGrave"]=63187,
+ ["dblanglebracketleft"]=12298,
+ ["dblanglebracketleftvertical"]=65085,
+ ["dblanglebracketright"]=12299,
+ ["dblanglebracketrightvertical"]=65086,
+ ["dblarchinvertedbelowcmb"]=811,
+ ["dblarrowleft"]=8660,
+ ["dblarrowright"]=8658,
+ ["dbldanda"]=2405,
+ ["dblgrave"]=63190,
+ ["dblgravecmb"]=783,
+ ["dblintegral"]=8748,
+ ["dbllowline"]=8215,
+ ["dbllowlinecmb"]=819,
+ ["dbloverlinecmb"]=831,
+ ["dblprimemod"]=698,
+ ["dblverticalbar"]=8214,
+ ["dblverticallineabovecmb"]=782,
+ ["dbopomofo"]=12553,
+ ["dbsquare"]=13256,
+ ["dcaron"]=271,
+ ["dcedilla"]=7697,
+ ["dcircle"]=9427,
+ ["dcircumflexbelow"]=7699,
+ ["dcroat"]=273,
+ ["ddabengali"]=2465,
+ ["ddadeva"]=2337,
+ ["ddagujarati"]=2721,
+ ["ddagurmukhi"]=2593,
+ ["ddalarabic"]=1672,
+ ["ddalfinalarabic"]=64393,
+ ["dddhadeva"]=2396,
+ ["ddhabengali"]=2466,
+ ["ddhadeva"]=2338,
+ ["ddhagujarati"]=2722,
+ ["ddhagurmukhi"]=2594,
+ ["ddotaccent"]=7691,
+ ["ddotbelow"]=7693,
+ ["decimalseparatorarabic"]=1643,
+ ["decimalseparatorpersian"]=1643,
+ ["decyrillic"]=1076,
+ ["degree"]=176,
+ ["dehihebrew"]=1453,
+ ["dehiragana"]=12391,
+ ["deicoptic"]=1007,
+ ["dekatakana"]=12487,
+ ["deleteleft"]=9003,
+ ["deleteright"]=8998,
+ ["delta"]=948,
+ ["deltaturned"]=397,
+ ["denominatorminusonenumeratorbengali"]=2552,
+ ["dezh"]=676,
+ ["dhabengali"]=2471,
+ ["dhadeva"]=2343,
+ ["dhagujarati"]=2727,
+ ["dhagurmukhi"]=2599,
+ ["dhook"]=599,
+ ["dialytikatonos"]=901,
+ ["dialytikatonoscmb"]=836,
+ ["diamond"]=9830,
+ ["diamondsuitwhite"]=9826,
+ ["dieresis"]=168,
+ ["dieresisacute"]=63191,
+ ["dieresisbelowcmb"]=804,
+ ["dieresiscmb"]=776,
+ ["dieresisgrave"]=63192,
+ ["dieresistonos"]=901,
+ ["dihiragana"]=12386,
+ ["dikatakana"]=12482,
+ ["dittomark"]=12291,
+ ["divide"]=247,
+ ["divides"]=8739,
+ ["divisionslash"]=8725,
+ ["djecyrillic"]=1106,
+ ["dkshade"]=9619,
+ ["dlinebelow"]=7695,
+ ["dlsquare"]=13207,
+ ["dmacron"]=273,
+ ["dmonospace"]=65348,
+ ["dnblock"]=9604,
+ ["dochadathai"]=3598,
+ ["dodekthai"]=3604,
+ ["dohiragana"]=12393,
+ ["dokatakana"]=12489,
+ ["dollar"]=36,
+ ["dollarinferior"]=63203,
+ ["dollarmonospace"]=65284,
+ ["dollaroldstyle"]=63268,
+ ["dollarsmall"]=65129,
+ ["dollarsuperior"]=63204,
+ ["dong"]=8363,
+ ["dorusquare"]=13094,
+ ["dotaccent"]=729,
+ ["dotaccentcmb"]=775,
+ ["dotbelowcmb"]=803,
+ ["dotbelowcomb"]=803,
+ ["dotkatakana"]=12539,
+ ["dotlessi"]=305,
+ ["dotlessj"]=63166,
+ ["dotlessjstrokehook"]=644,
+ ["dotmath"]=8901,
+ ["dottedcircle"]=9676,
+ ["doubleyodpatah"]=64287,
+ ["doubleyodpatahhebrew"]=64287,
+ ["downtackbelowcmb"]=798,
+ ["downtackmod"]=725,
+ ["dparen"]=9375,
+ ["dsuperior"]=63211,
+ ["dtail"]=598,
+ ["dtopbar"]=396,
+ ["duhiragana"]=12389,
+ ["dukatakana"]=12485,
+ ["dz"]=499,
+ ["dzaltone"]=675,
+ ["dzcaron"]=454,
+ ["dzcurl"]=677,
+ ["dzeabkhasiancyrillic"]=1249,
+ ["dzecyrillic"]=1109,
+ ["dzhecyrillic"]=1119,
+ ["e"]=101,
+ ["eacute"]=233,
+ ["earth"]=9793,
+ ["ebengali"]=2447,
+ ["ebopomofo"]=12572,
+ ["ebreve"]=277,
+ ["ecandradeva"]=2317,
+ ["ecandragujarati"]=2701,
+ ["ecandravowelsigndeva"]=2373,
+ ["ecandravowelsigngujarati"]=2757,
+ ["ecaron"]=283,
+ ["ecedillabreve"]=7709,
+ ["echarmenian"]=1381,
+ ["echyiwnarmenian"]=1415,
+ ["ecircle"]=9428,
+ ["ecircumflex"]=234,
+ ["ecircumflexacute"]=7871,
+ ["ecircumflexbelow"]=7705,
+ ["ecircumflexdotbelow"]=7879,
+ ["ecircumflexgrave"]=7873,
+ ["ecircumflexhookabove"]=7875,
+ ["ecircumflextilde"]=7877,
+ ["ecyrillic"]=1108,
+ ["edblgrave"]=517,
+ ["edeva"]=2319,
+ ["edieresis"]=235,
+ ["edot"]=279,
+ ["edotaccent"]=279,
+ ["edotbelow"]=7865,
+ ["eegurmukhi"]=2575,
+ ["eematragurmukhi"]=2631,
+ ["efcyrillic"]=1092,
+ ["egrave"]=232,
+ ["egujarati"]=2703,
+ ["eharmenian"]=1383,
+ ["ehbopomofo"]=12573,
+ ["ehiragana"]=12360,
+ ["ehookabove"]=7867,
+ ["eibopomofo"]=12575,
+ ["eight"]=56,
+ ["eightarabic"]=1640,
+ ["eightbengali"]=2542,
+ ["eightcircle"]=9319,
+ ["eightcircleinversesansserif"]=10129,
+ ["eightdeva"]=2414,
+ ["eighteencircle"]=9329,
+ ["eighteenparen"]=9349,
+ ["eighteenperiod"]=9369,
+ ["eightgujarati"]=2798,
+ ["eightgurmukhi"]=2670,
+ ["eighthackarabic"]=1640,
+ ["eighthangzhou"]=12328,
+ ["eighthnotebeamed"]=9835,
+ ["eightideographicparen"]=12839,
+ ["eightinferior"]=8328,
+ ["eightmonospace"]=65304,
+ ["eightoldstyle"]=63288,
+ ["eightparen"]=9339,
+ ["eightperiod"]=9359,
+ ["eightpersian"]=1784,
+ ["eightroman"]=8567,
+ ["eightsuperior"]=8312,
+ ["eightthai"]=3672,
+ ["einvertedbreve"]=519,
+ ["eiotifiedcyrillic"]=1125,
+ ["ekatakana"]=12456,
+ ["ekatakanahalfwidth"]=65396,
+ ["ekonkargurmukhi"]=2676,
+ ["ekorean"]=12628,
+ ["elcyrillic"]=1083,
+ ["element"]=8712,
+ ["elevencircle"]=9322,
+ ["elevenparen"]=9342,
+ ["elevenperiod"]=9362,
+ ["elevenroman"]=8570,
+ ["ellipsis"]=8230,
+ ["ellipsisvertical"]=8942,
+ ["emacron"]=275,
+ ["emacronacute"]=7703,
+ ["emacrongrave"]=7701,
+ ["emcyrillic"]=1084,
+ ["emdash"]=8212,
+ ["emdashvertical"]=65073,
+ ["emonospace"]=65349,
+ ["emphasismarkarmenian"]=1371,
+ ["emptyset"]=8709,
+ ["enbopomofo"]=12579,
+ ["encyrillic"]=1085,
+ ["endash"]=8211,
+ ["endashvertical"]=65074,
+ ["endescendercyrillic"]=1187,
+ ["eng"]=331,
+ ["engbopomofo"]=12581,
+ ["enghecyrillic"]=1189,
+ ["enhookcyrillic"]=1224,
+ ["enspace"]=8194,
+ ["eogonek"]=281,
+ ["eokorean"]=12627,
+ ["eopen"]=603,
+ ["eopenclosed"]=666,
+ ["eopenreversed"]=604,
+ ["eopenreversedclosed"]=606,
+ ["eopenreversedhook"]=605,
+ ["eparen"]=9376,
+ ["epsilon"]=949,
+ ["epsilontonos"]=941,
+ ["equal"]=61,
+ ["equalmonospace"]=65309,
+ ["equalsmall"]=65126,
+ ["equalsuperior"]=8316,
+ ["equivalence"]=8801,
+ ["erbopomofo"]=12582,
+ ["ercyrillic"]=1088,
+ ["ereversed"]=600,
+ ["ereversedcyrillic"]=1101,
+ ["escyrillic"]=1089,
+ ["esdescendercyrillic"]=1195,
+ ["esh"]=643,
+ ["eshcurl"]=646,
+ ["eshortdeva"]=2318,
+ ["eshortvowelsigndeva"]=2374,
+ ["eshreversedloop"]=426,
+ ["eshsquatreversed"]=645,
+ ["esmallhiragana"]=12359,
+ ["esmallkatakana"]=12455,
+ ["esmallkatakanahalfwidth"]=65386,
+ ["estimated"]=8494,
+ ["esuperior"]=63212,
+ ["eta"]=951,
+ ["etarmenian"]=1384,
+ ["etatonos"]=942,
+ ["eth"]=240,
+ ["etilde"]=7869,
+ ["etildebelow"]=7707,
+ ["etnahtafoukhhebrew"]=1425,
+ ["etnahtafoukhlefthebrew"]=1425,
+ ["etnahtahebrew"]=1425,
+ ["etnahtalefthebrew"]=1425,
+ ["eturned"]=477,
+ ["eukorean"]=12641,
+ ["euro"]=8364,
+ ["evowelsignbengali"]=2503,
+ ["evowelsigndeva"]=2375,
+ ["evowelsigngujarati"]=2759,
+ ["exclam"]=33,
+ ["exclamarmenian"]=1372,
+ ["exclamdbl"]=8252,
+ ["exclamdown"]=161,
+ ["exclamdownsmall"]=63393,
+ ["exclammonospace"]=65281,
+ ["exclamsmall"]=63265,
+ ["existential"]=8707,
+ ["ezh"]=658,
+ ["ezhcaron"]=495,
+ ["ezhcurl"]=659,
+ ["ezhreversed"]=441,
+ ["ezhtail"]=442,
+ ["f"]=102,
+ ["fadeva"]=2398,
+ ["fagurmukhi"]=2654,
+ ["fahrenheit"]=8457,
+ ["fathaarabic"]=1614,
+ ["fathalowarabic"]=1614,
+ ["fathatanarabic"]=1611,
+ ["fbopomofo"]=12552,
+ ["fcircle"]=9429,
+ ["fdotaccent"]=7711,
+ ["feharabic"]=1601,
+ ["feharmenian"]=1414,
+ ["fehfinalarabic"]=65234,
+ ["fehinitialarabic"]=65235,
+ ["fehmedialarabic"]=65236,
+ ["feicoptic"]=997,
+ ["female"]=9792,
+ ["ff"]=64256,
+ ["ffi"]=64259,
+ ["ffl"]=64260,
+ ["fi"]=64257,
+ ["fifteencircle"]=9326,
+ ["fifteenparen"]=9346,
+ ["fifteenperiod"]=9366,
+ ["figuredash"]=8210,
+ ["filledbox"]=9632,
+ ["filledrect"]=9644,
+ ["finalkaf"]=1498,
+ ["finalkafdagesh"]=64314,
+ ["finalkafdageshhebrew"]=64314,
+ ["finalkafhebrew"]=1498,
+ ["finalkafqamats"]=1498,
+ ["finalkafqamatshebrew"]=1498,
+ ["finalkafsheva"]=1498,
+ ["finalkafshevahebrew"]=1498,
+ ["finalmem"]=1501,
+ ["finalmemhebrew"]=1501,
+ ["finalnun"]=1503,
+ ["finalnunhebrew"]=1503,
+ ["finalpe"]=1507,
+ ["finalpehebrew"]=1507,
+ ["finaltsadi"]=1509,
+ ["finaltsadihebrew"]=1509,
+ ["firsttonechinese"]=713,
+ ["fisheye"]=9673,
+ ["fitacyrillic"]=1139,
+ ["five"]=53,
+ ["fivearabic"]=1637,
+ ["fivebengali"]=2539,
+ ["fivecircle"]=9316,
+ ["fivecircleinversesansserif"]=10126,
+ ["fivedeva"]=2411,
+ ["fiveeighths"]=8541,
+ ["fivegujarati"]=2795,
+ ["fivegurmukhi"]=2667,
+ ["fivehackarabic"]=1637,
+ ["fivehangzhou"]=12325,
+ ["fiveideographicparen"]=12836,
+ ["fiveinferior"]=8325,
+ ["fivemonospace"]=65301,
+ ["fiveoldstyle"]=63285,
+ ["fiveparen"]=9336,
+ ["fiveperiod"]=9356,
+ ["fivepersian"]=1781,
+ ["fiveroman"]=8564,
+ ["fivesuperior"]=8309,
+ ["fivethai"]=3669,
+ ["fl"]=64258,
+ ["florin"]=402,
+ ["fmonospace"]=65350,
+ ["fmsquare"]=13209,
+ ["fofanthai"]=3615,
+ ["fofathai"]=3613,
+ ["fongmanthai"]=3663,
+ ["forall"]=8704,
+ ["four"]=52,
+ ["fourarabic"]=1636,
+ ["fourbengali"]=2538,
+ ["fourcircle"]=9315,
+ ["fourcircleinversesansserif"]=10125,
+ ["fourdeva"]=2410,
+ ["fourgujarati"]=2794,
+ ["fourgurmukhi"]=2666,
+ ["fourhackarabic"]=1636,
+ ["fourhangzhou"]=12324,
+ ["fourideographicparen"]=12835,
+ ["fourinferior"]=8324,
+ ["fourmonospace"]=65300,
+ ["fournumeratorbengali"]=2551,
+ ["fouroldstyle"]=63284,
+ ["fourparen"]=9335,
+ ["fourperiod"]=9355,
+ ["fourpersian"]=1780,
+ ["fourroman"]=8563,
+ ["foursuperior"]=8308,
+ ["fourteencircle"]=9325,
+ ["fourteenparen"]=9345,
+ ["fourteenperiod"]=9365,
+ ["fourthai"]=3668,
+ ["fourthtonechinese"]=715,
+ ["fparen"]=9377,
+ ["fraction"]=8260,
+ ["franc"]=8355,
+ ["g"]=103,
+ ["gabengali"]=2455,
+ ["gacute"]=501,
+ ["gadeva"]=2327,
+ ["gafarabic"]=1711,
+ ["gaffinalarabic"]=64403,
+ ["gafinitialarabic"]=64404,
+ ["gafmedialarabic"]=64405,
+ ["gagujarati"]=2711,
+ ["gagurmukhi"]=2583,
+ ["gahiragana"]=12364,
+ ["gakatakana"]=12460,
+ ["gamma"]=947,
+ ["gammalatinsmall"]=611,
+ ["gammasuperior"]=736,
+ ["gangiacoptic"]=1003,
+ ["gbopomofo"]=12557,
+ ["gbreve"]=287,
+ ["gcaron"]=487,
+ ["gcedilla"]=291,
+ ["gcircle"]=9430,
+ ["gcircumflex"]=285,
+ ["gcommaaccent"]=291,
+ ["gdot"]=289,
+ ["gdotaccent"]=289,
+ ["gecyrillic"]=1075,
+ ["gehiragana"]=12370,
+ ["gekatakana"]=12466,
+ ["geometricallyequal"]=8785,
+ ["gereshaccenthebrew"]=1436,
+ ["gereshhebrew"]=1523,
+ ["gereshmuqdamhebrew"]=1437,
+ ["germandbls"]=223,
+ ["gershayimaccenthebrew"]=1438,
+ ["gershayimhebrew"]=1524,
+ ["getamark"]=12307,
+ ["ghabengali"]=2456,
+ ["ghadarmenian"]=1394,
+ ["ghadeva"]=2328,
+ ["ghagujarati"]=2712,
+ ["ghagurmukhi"]=2584,
+ ["ghainarabic"]=1594,
+ ["ghainfinalarabic"]=65230,
+ ["ghaininitialarabic"]=65231,
+ ["ghainmedialarabic"]=65232,
+ ["ghemiddlehookcyrillic"]=1173,
+ ["ghestrokecyrillic"]=1171,
+ ["gheupturncyrillic"]=1169,
+ ["ghhadeva"]=2394,
+ ["ghhagurmukhi"]=2650,
+ ["ghook"]=608,
+ ["ghzsquare"]=13203,
+ ["gihiragana"]=12366,
+ ["gikatakana"]=12462,
+ ["gimarmenian"]=1379,
+ ["gimel"]=1490,
+ ["gimeldagesh"]=64306,
+ ["gimeldageshhebrew"]=64306,
+ ["gimelhebrew"]=1490,
+ ["gjecyrillic"]=1107,
+ ["glottalinvertedstroke"]=446,
+ ["glottalstop"]=660,
+ ["glottalstopinverted"]=662,
+ ["glottalstopmod"]=704,
+ ["glottalstopreversed"]=661,
+ ["glottalstopreversedmod"]=705,
+ ["glottalstopreversedsuperior"]=740,
+ ["glottalstopstroke"]=673,
+ ["glottalstopstrokereversed"]=674,
+ ["gmacron"]=7713,
+ ["gmonospace"]=65351,
+ ["gohiragana"]=12372,
+ ["gokatakana"]=12468,
+ ["gparen"]=9378,
+ ["gpasquare"]=13228,
+ ["gradient"]=8711,
+ ["grave"]=96,
+ ["gravebelowcmb"]=790,
+ ["gravecmb"]=768,
+ ["gravecomb"]=768,
+ ["gravedeva"]=2387,
+ ["gravelowmod"]=718,
+ ["gravemonospace"]=65344,
+ ["gravetonecmb"]=832,
+ ["greater"]=62,
+ ["greaterequal"]=8805,
+ ["greaterequalorless"]=8923,
+ ["greatermonospace"]=65310,
+ ["greaterorequivalent"]=8819,
+ ["greaterorless"]=8823,
+ ["greateroverequal"]=8807,
+ ["greatersmall"]=65125,
+ ["gscript"]=609,
+ ["gstroke"]=485,
+ ["guhiragana"]=12368,
+ ["guillemotleft"]=171,
+ ["guillemotright"]=187,
+ ["guilsinglleft"]=8249,
+ ["guilsinglright"]=8250,
+ ["gukatakana"]=12464,
+ ["guramusquare"]=13080,
+ ["gysquare"]=13257,
+ ["h"]=104,
+ ["haabkhasiancyrillic"]=1193,
+ ["haaltonearabic"]=1729,
+ ["habengali"]=2489,
+ ["hadescendercyrillic"]=1203,
+ ["hadeva"]=2361,
+ ["hagujarati"]=2745,
+ ["hagurmukhi"]=2617,
+ ["haharabic"]=1581,
+ ["hahfinalarabic"]=65186,
+ ["hahinitialarabic"]=65187,
+ ["hahiragana"]=12399,
+ ["hahmedialarabic"]=65188,
+ ["haitusquare"]=13098,
+ ["hakatakana"]=12495,
+ ["hakatakanahalfwidth"]=65418,
+ ["halantgurmukhi"]=2637,
+ ["hamzaarabic"]=1569,
+ ["hamzadammaarabic"]=1569,
+ ["hamzadammatanarabic"]=1569,
+ ["hamzafathaarabic"]=1569,
+ ["hamzafathatanarabic"]=1569,
+ ["hamzalowarabic"]=1569,
+ ["hamzalowkasraarabic"]=1569,
+ ["hamzalowkasratanarabic"]=1569,
+ ["hamzasukunarabic"]=1569,
+ ["hangulfiller"]=12644,
+ ["hardsigncyrillic"]=1098,
+ ["harpoonleftbarbup"]=8636,
+ ["harpoonrightbarbup"]=8640,
+ ["hasquare"]=13258,
+ ["hatafpatah"]=1458,
+ ["hatafpatah16"]=1458,
+ ["hatafpatah23"]=1458,
+ ["hatafpatah2f"]=1458,
+ ["hatafpatahhebrew"]=1458,
+ ["hatafpatahnarrowhebrew"]=1458,
+ ["hatafpatahquarterhebrew"]=1458,
+ ["hatafpatahwidehebrew"]=1458,
+ ["hatafqamats"]=1459,
+ ["hatafqamats1b"]=1459,
+ ["hatafqamats28"]=1459,
+ ["hatafqamats34"]=1459,
+ ["hatafqamatshebrew"]=1459,
+ ["hatafqamatsnarrowhebrew"]=1459,
+ ["hatafqamatsquarterhebrew"]=1459,
+ ["hatafqamatswidehebrew"]=1459,
+ ["hatafsegol"]=1457,
+ ["hatafsegol17"]=1457,
+ ["hatafsegol24"]=1457,
+ ["hatafsegol30"]=1457,
+ ["hatafsegolhebrew"]=1457,
+ ["hatafsegolnarrowhebrew"]=1457,
+ ["hatafsegolquarterhebrew"]=1457,
+ ["hatafsegolwidehebrew"]=1457,
+ ["hbar"]=295,
+ ["hbopomofo"]=12559,
+ ["hbrevebelow"]=7723,
+ ["hcedilla"]=7721,
+ ["hcircle"]=9431,
+ ["hcircumflex"]=293,
+ ["hdieresis"]=7719,
+ ["hdotaccent"]=7715,
+ ["hdotbelow"]=7717,
+ ["he"]=1492,
+ ["heart"]=9829,
+ ["heartsuitblack"]=9829,
+ ["heartsuitwhite"]=9825,
+ ["hedagesh"]=64308,
+ ["hedageshhebrew"]=64308,
+ ["hehaltonearabic"]=1729,
+ ["heharabic"]=1607,
+ ["hehebrew"]=1492,
+ ["hehfinalaltonearabic"]=64423,
+ ["hehfinalalttwoarabic"]=65258,
+ ["hehfinalarabic"]=65258,
+ ["hehhamzaabovefinalarabic"]=64421,
+ ["hehhamzaaboveisolatedarabic"]=64420,
+ ["hehinitialaltonearabic"]=64424,
+ ["hehinitialarabic"]=65259,
+ ["hehiragana"]=12408,
+ ["hehmedialaltonearabic"]=64425,
+ ["hehmedialarabic"]=65260,
+ ["heiseierasquare"]=13179,
+ ["hekatakana"]=12504,
+ ["hekatakanahalfwidth"]=65421,
+ ["hekutaarusquare"]=13110,
+ ["henghook"]=615,
+ ["herutusquare"]=13113,
+ ["het"]=1495,
+ ["hethebrew"]=1495,
+ ["hhook"]=614,
+ ["hhooksuperior"]=689,
+ ["hieuhacirclekorean"]=12923,
+ ["hieuhaparenkorean"]=12827,
+ ["hieuhcirclekorean"]=12909,
+ ["hieuhkorean"]=12622,
+ ["hieuhparenkorean"]=12813,
+ ["hihiragana"]=12402,
+ ["hikatakana"]=12498,
+ ["hikatakanahalfwidth"]=65419,
+ ["hiriq"]=1460,
+ ["hiriq14"]=1460,
+ ["hiriq21"]=1460,
+ ["hiriq2d"]=1460,
+ ["hiriqhebrew"]=1460,
+ ["hiriqnarrowhebrew"]=1460,
+ ["hiriqquarterhebrew"]=1460,
+ ["hiriqwidehebrew"]=1460,
+ ["hlinebelow"]=7830,
+ ["hmonospace"]=65352,
+ ["hoarmenian"]=1392,
+ ["hohipthai"]=3627,
+ ["hohiragana"]=12411,
+ ["hokatakana"]=12507,
+ ["hokatakanahalfwidth"]=65422,
+ ["holam"]=1465,
+ ["holam19"]=1465,
+ ["holam26"]=1465,
+ ["holam32"]=1465,
+ ["holamhebrew"]=1465,
+ ["holamnarrowhebrew"]=1465,
+ ["holamquarterhebrew"]=1465,
+ ["holamwidehebrew"]=1465,
+ ["honokhukthai"]=3630,
+ ["hookabovecomb"]=777,
+ ["hookcmb"]=777,
+ ["hookpalatalizedbelowcmb"]=801,
+ ["hookretroflexbelowcmb"]=802,
+ ["hoonsquare"]=13122,
+ ["horicoptic"]=1001,
+ ["horizontalbar"]=8213,
+ ["horncmb"]=795,
+ ["hotsprings"]=9832,
+ ["house"]=8962,
+ ["hparen"]=9379,
+ ["hsuperior"]=688,
+ ["hturned"]=613,
+ ["huhiragana"]=12405,
+ ["huiitosquare"]=13107,
+ ["hukatakana"]=12501,
+ ["hukatakanahalfwidth"]=65420,
+ ["hungarumlaut"]=733,
+ ["hungarumlautcmb"]=779,
+ ["hv"]=405,
+ ["hyphen"]=45,
+ ["hypheninferior"]=63205,
+ ["hyphenmonospace"]=65293,
+ ["hyphensmall"]=65123,
+ ["hyphensuperior"]=63206,
+ ["hyphentwo"]=8208,
+ ["i"]=105,
+ ["iacute"]=237,
+ ["iacyrillic"]=1103,
+ ["ibengali"]=2439,
+ ["ibopomofo"]=12583,
+ ["ibreve"]=301,
+ ["icaron"]=464,
+ ["icircle"]=9432,
+ ["icircumflex"]=238,
+ ["icyrillic"]=1110,
+ ["idblgrave"]=521,
+ ["ideographearthcircle"]=12943,
+ ["ideographfirecircle"]=12939,
+ ["ideographicallianceparen"]=12863,
+ ["ideographiccallparen"]=12858,
+ ["ideographiccentrecircle"]=12965,
+ ["ideographicclose"]=12294,
+ ["ideographiccomma"]=12289,
+ ["ideographiccommaleft"]=65380,
+ ["ideographiccongratulationparen"]=12855,
+ ["ideographiccorrectcircle"]=12963,
+ ["ideographicearthparen"]=12847,
+ ["ideographicenterpriseparen"]=12861,
+ ["ideographicexcellentcircle"]=12957,
+ ["ideographicfestivalparen"]=12864,
+ ["ideographicfinancialcircle"]=12950,
+ ["ideographicfinancialparen"]=12854,
+ ["ideographicfireparen"]=12843,
+ ["ideographichaveparen"]=12850,
+ ["ideographichighcircle"]=12964,
+ ["ideographiciterationmark"]=12293,
+ ["ideographiclaborcircle"]=12952,
+ ["ideographiclaborparen"]=12856,
+ ["ideographicleftcircle"]=12967,
+ ["ideographiclowcircle"]=12966,
+ ["ideographicmedicinecircle"]=12969,
+ ["ideographicmetalparen"]=12846,
+ ["ideographicmoonparen"]=12842,
+ ["ideographicnameparen"]=12852,
+ ["ideographicperiod"]=12290,
+ ["ideographicprintcircle"]=12958,
+ ["ideographicreachparen"]=12867,
+ ["ideographicrepresentparen"]=12857,
+ ["ideographicresourceparen"]=12862,
+ ["ideographicrightcircle"]=12968,
+ ["ideographicsecretcircle"]=12953,
+ ["ideographicselfparen"]=12866,
+ ["ideographicsocietyparen"]=12851,
+ ["ideographicspace"]=12288,
+ ["ideographicspecialparen"]=12853,
+ ["ideographicstockparen"]=12849,
+ ["ideographicstudyparen"]=12859,
+ ["ideographicsunparen"]=12848,
+ ["ideographicsuperviseparen"]=12860,
+ ["ideographicwaterparen"]=12844,
+ ["ideographicwoodparen"]=12845,
+ ["ideographiczero"]=12295,
+ ["ideographmetalcircle"]=12942,
+ ["ideographmooncircle"]=12938,
+ ["ideographnamecircle"]=12948,
+ ["ideographsuncircle"]=12944,
+ ["ideographwatercircle"]=12940,
+ ["ideographwoodcircle"]=12941,
+ ["ideva"]=2311,
+ ["idieresis"]=239,
+ ["idieresisacute"]=7727,
+ ["idieresiscyrillic"]=1253,
+ ["idotbelow"]=7883,
+ ["iebrevecyrillic"]=1239,
+ ["iecyrillic"]=1077,
+ ["ieungacirclekorean"]=12917,
+ ["ieungaparenkorean"]=12821,
+ ["ieungcirclekorean"]=12903,
+ ["ieungkorean"]=12615,
+ ["ieungparenkorean"]=12807,
+ ["igrave"]=236,
+ ["igujarati"]=2695,
+ ["igurmukhi"]=2567,
+ ["ihiragana"]=12356,
+ ["ihookabove"]=7881,
+ ["iibengali"]=2440,
+ ["iicyrillic"]=1080,
+ ["iideva"]=2312,
+ ["iigujarati"]=2696,
+ ["iigurmukhi"]=2568,
+ ["iimatragurmukhi"]=2624,
+ ["iinvertedbreve"]=523,
+ ["iishortcyrillic"]=1081,
+ ["iivowelsignbengali"]=2496,
+ ["iivowelsigndeva"]=2368,
+ ["iivowelsigngujarati"]=2752,
+ ["ij"]=307,
+ ["ikatakana"]=12452,
+ ["ikatakanahalfwidth"]=65394,
+ ["ikorean"]=12643,
+ ["ilde"]=732,
+ ["iluyhebrew"]=1452,
+ ["imacron"]=299,
+ ["imacroncyrillic"]=1251,
+ ["imageorapproximatelyequal"]=8787,
+ ["imatragurmukhi"]=2623,
+ ["imonospace"]=65353,
+ ["increment"]=8710,
+ ["infinity"]=8734,
+ ["iniarmenian"]=1387,
+ ["integral"]=8747,
+ ["integralbottom"]=8993,
+ ["integralbt"]=8993,
+ ["integralex"]=63733,
+ ["integraltop"]=8992,
+ ["integraltp"]=8992,
+ ["intersection"]=8745,
+ ["intisquare"]=13061,
+ ["invbullet"]=9688,
+ ["invcircle"]=9689,
+ ["invsmileface"]=9787,
+ ["iocyrillic"]=1105,
+ ["iogonek"]=303,
+ ["iota"]=953,
+ ["iotadieresis"]=970,
+ ["iotadieresistonos"]=912,
+ ["iotalatin"]=617,
+ ["iotatonos"]=943,
+ ["iparen"]=9380,
+ ["irigurmukhi"]=2674,
+ ["ismallhiragana"]=12355,
+ ["ismallkatakana"]=12451,
+ ["ismallkatakanahalfwidth"]=65384,
+ ["issharbengali"]=2554,
+ ["istroke"]=616,
+ ["isuperior"]=63213,
+ ["iterationhiragana"]=12445,
+ ["iterationkatakana"]=12541,
+ ["itilde"]=297,
+ ["itildebelow"]=7725,
+ ["iubopomofo"]=12585,
+ ["iucyrillic"]=1102,
+ ["ivowelsignbengali"]=2495,
+ ["ivowelsigndeva"]=2367,
+ ["ivowelsigngujarati"]=2751,
+ ["izhitsacyrillic"]=1141,
+ ["izhitsadblgravecyrillic"]=1143,
+ ["j"]=106,
+ ["jaarmenian"]=1393,
+ ["jabengali"]=2460,
+ ["jadeva"]=2332,
+ ["jagujarati"]=2716,
+ ["jagurmukhi"]=2588,
+ ["jbopomofo"]=12560,
+ ["jcaron"]=496,
+ ["jcircle"]=9433,
+ ["jcircumflex"]=309,
+ ["jcrossedtail"]=669,
+ ["jdotlessstroke"]=607,
+ ["jecyrillic"]=1112,
+ ["jeemarabic"]=1580,
+ ["jeemfinalarabic"]=65182,
+ ["jeeminitialarabic"]=65183,
+ ["jeemmedialarabic"]=65184,
+ ["jeharabic"]=1688,
+ ["jehfinalarabic"]=64395,
+ ["jhabengali"]=2461,
+ ["jhadeva"]=2333,
+ ["jhagujarati"]=2717,
+ ["jhagurmukhi"]=2589,
+ ["jheharmenian"]=1403,
+ ["jis"]=12292,
+ ["jmonospace"]=65354,
+ ["jparen"]=9381,
+ ["jsuperior"]=690,
+ ["k"]=107,
+ ["kabashkircyrillic"]=1185,
+ ["kabengali"]=2453,
+ ["kacute"]=7729,
+ ["kacyrillic"]=1082,
+ ["kadescendercyrillic"]=1179,
+ ["kadeva"]=2325,
+ ["kaf"]=1499,
+ ["kafarabic"]=1603,
+ ["kafdagesh"]=64315,
+ ["kafdageshhebrew"]=64315,
+ ["kaffinalarabic"]=65242,
+ ["kafhebrew"]=1499,
+ ["kafinitialarabic"]=65243,
+ ["kafmedialarabic"]=65244,
+ ["kafrafehebrew"]=64333,
+ ["kagujarati"]=2709,
+ ["kagurmukhi"]=2581,
+ ["kahiragana"]=12363,
+ ["kahookcyrillic"]=1220,
+ ["kakatakana"]=12459,
+ ["kakatakanahalfwidth"]=65398,
+ ["kappa"]=954,
+ ["kappasymbolgreek"]=1008,
+ ["kapyeounmieumkorean"]=12657,
+ ["kapyeounphieuphkorean"]=12676,
+ ["kapyeounpieupkorean"]=12664,
+ ["kapyeounssangpieupkorean"]=12665,
+ ["karoriisquare"]=13069,
+ ["kashidaautoarabic"]=1600,
+ ["kashidaautonosidebearingarabic"]=1600,
+ ["kasmallkatakana"]=12533,
+ ["kasquare"]=13188,
+ ["kasraarabic"]=1616,
+ ["kasratanarabic"]=1613,
+ ["kastrokecyrillic"]=1183,
+ ["katahiraprolongmarkhalfwidth"]=65392,
+ ["kaverticalstrokecyrillic"]=1181,
+ ["kbopomofo"]=12558,
+ ["kcalsquare"]=13193,
+ ["kcaron"]=489,
+ ["kcedilla"]=311,
+ ["kcircle"]=9434,
+ ["kcommaaccent"]=311,
+ ["kdotbelow"]=7731,
+ ["keharmenian"]=1412,
+ ["kehiragana"]=12369,
+ ["kekatakana"]=12465,
+ ["kekatakanahalfwidth"]=65401,
+ ["kenarmenian"]=1391,
+ ["kesmallkatakana"]=12534,
+ ["kgreenlandic"]=312,
+ ["khabengali"]=2454,
+ ["khacyrillic"]=1093,
+ ["khadeva"]=2326,
+ ["khagujarati"]=2710,
+ ["khagurmukhi"]=2582,
+ ["khaharabic"]=1582,
+ ["khahfinalarabic"]=65190,
+ ["khahinitialarabic"]=65191,
+ ["khahmedialarabic"]=65192,
+ ["kheicoptic"]=999,
+ ["khhadeva"]=2393,
+ ["khhagurmukhi"]=2649,
+ ["khieukhacirclekorean"]=12920,
+ ["khieukhaparenkorean"]=12824,
+ ["khieukhcirclekorean"]=12906,
+ ["khieukhkorean"]=12619,
+ ["khieukhparenkorean"]=12810,
+ ["khokhaithai"]=3586,
+ ["khokhonthai"]=3589,
+ ["khokhuatthai"]=3587,
+ ["khokhwaithai"]=3588,
+ ["khomutthai"]=3675,
+ ["khook"]=409,
+ ["khorakhangthai"]=3590,
+ ["khzsquare"]=13201,
+ ["kihiragana"]=12365,
+ ["kikatakana"]=12461,
+ ["kikatakanahalfwidth"]=65399,
+ ["kiroguramusquare"]=13077,
+ ["kiromeetorusquare"]=13078,
+ ["kirosquare"]=13076,
+ ["kiyeokacirclekorean"]=12910,
+ ["kiyeokaparenkorean"]=12814,
+ ["kiyeokcirclekorean"]=12896,
+ ["kiyeokkorean"]=12593,
+ ["kiyeokparenkorean"]=12800,
+ ["kiyeoksioskorean"]=12595,
+ ["kjecyrillic"]=1116,
+ ["klinebelow"]=7733,
+ ["klsquare"]=13208,
+ ["kmcubedsquare"]=13222,
+ ["kmonospace"]=65355,
+ ["kmsquaredsquare"]=13218,
+ ["kohiragana"]=12371,
+ ["kohmsquare"]=13248,
+ ["kokaithai"]=3585,
+ ["kokatakana"]=12467,
+ ["kokatakanahalfwidth"]=65402,
+ ["kooposquare"]=13086,
+ ["koppacyrillic"]=1153,
+ ["koreanstandardsymbol"]=12927,
+ ["koroniscmb"]=835,
+ ["kparen"]=9382,
+ ["kpasquare"]=13226,
+ ["ksicyrillic"]=1135,
+ ["ktsquare"]=13263,
+ ["kturned"]=670,
+ ["kuhiragana"]=12367,
+ ["kukatakana"]=12463,
+ ["kukatakanahalfwidth"]=65400,
+ ["kvsquare"]=13240,
+ ["kwsquare"]=13246,
+ ["l"]=108,
+ ["labengali"]=2482,
+ ["lacute"]=314,
+ ["ladeva"]=2354,
+ ["lagujarati"]=2738,
+ ["lagurmukhi"]=2610,
+ ["lakkhangyaothai"]=3653,
+ ["lamaleffinalarabic"]=65276,
+ ["lamalefhamzaabovefinalarabic"]=65272,
+ ["lamalefhamzaaboveisolatedarabic"]=65271,
+ ["lamalefhamzabelowfinalarabic"]=65274,
+ ["lamalefhamzabelowisolatedarabic"]=65273,
+ ["lamalefisolatedarabic"]=65275,
+ ["lamalefmaddaabovefinalarabic"]=65270,
+ ["lamalefmaddaaboveisolatedarabic"]=65269,
+ ["lamarabic"]=1604,
+ ["lambda"]=955,
+ ["lambdastroke"]=411,
+ ["lamed"]=1500,
+ ["lameddagesh"]=64316,
+ ["lameddageshhebrew"]=64316,
+ ["lamedhebrew"]=1500,
+ ["lamedholam"]=1500,
+ ["lamedholamdagesh"]=1500,
+ ["lamedholamdageshhebrew"]=1500,
+ ["lamedholamhebrew"]=1500,
+ ["lamfinalarabic"]=65246,
+ ["lamhahinitialarabic"]=64714,
+ ["laminitialarabic"]=65247,
+ ["lamjeeminitialarabic"]=64713,
+ ["lamkhahinitialarabic"]=64715,
+ ["lamlamhehisolatedarabic"]=65010,
+ ["lammedialarabic"]=65248,
+ ["lammeemhahinitialarabic"]=64904,
+ ["lammeeminitialarabic"]=64716,
+ ["lammeemjeeminitialarabic"]=65247,
+ ["lammeemkhahinitialarabic"]=65247,
+ ["largecircle"]=9711,
+ ["lbar"]=410,
+ ["lbelt"]=620,
+ ["lbopomofo"]=12556,
+ ["lcaron"]=318,
+ ["lcedilla"]=316,
+ ["lcircle"]=9435,
+ ["lcircumflexbelow"]=7741,
+ ["lcommaaccent"]=316,
+ ["ldot"]=320,
+ ["ldotaccent"]=320,
+ ["ldotbelow"]=7735,
+ ["ldotbelowmacron"]=7737,
+ ["leftangleabovecmb"]=794,
+ ["lefttackbelowcmb"]=792,
+ ["less"]=60,
+ ["lessequal"]=8804,
+ ["lessequalorgreater"]=8922,
+ ["lessmonospace"]=65308,
+ ["lessorequivalent"]=8818,
+ ["lessorgreater"]=8822,
+ ["lessoverequal"]=8806,
+ ["lesssmall"]=65124,
+ ["lezh"]=622,
+ ["lfblock"]=9612,
+ ["lhookretroflex"]=621,
+ ["lira"]=8356,
+ ["liwnarmenian"]=1388,
+ ["lj"]=457,
+ ["ljecyrillic"]=1113,
+ ["ll"]=63168,
+ ["lladeva"]=2355,
+ ["llagujarati"]=2739,
+ ["llinebelow"]=7739,
+ ["llladeva"]=2356,
+ ["llvocalicbengali"]=2529,
+ ["llvocalicdeva"]=2401,
+ ["llvocalicvowelsignbengali"]=2531,
+ ["llvocalicvowelsigndeva"]=2403,
+ ["lmiddletilde"]=619,
+ ["lmonospace"]=65356,
+ ["lmsquare"]=13264,
+ ["lochulathai"]=3628,
+ ["logicaland"]=8743,
+ ["logicalnot"]=172,
+ ["logicalnotreversed"]=8976,
+ ["logicalor"]=8744,
+ ["lolingthai"]=3621,
+ ["longs"]=383,
+ ["lowlinecenterline"]=65102,
+ ["lowlinecmb"]=818,
+ ["lowlinedashed"]=65101,
+ ["lozenge"]=9674,
+ ["lparen"]=9383,
+ ["lslash"]=322,
+ ["lsquare"]=8467,
+ ["lsuperior"]=63214,
+ ["ltshade"]=9617,
+ ["luthai"]=3622,
+ ["lvocalicbengali"]=2444,
+ ["lvocalicdeva"]=2316,
+ ["lvocalicvowelsignbengali"]=2530,
+ ["lvocalicvowelsigndeva"]=2402,
+ ["lxsquare"]=13267,
+ ["m"]=109,
+ ["mabengali"]=2478,
+ ["macron"]=175,
+ ["macronbelowcmb"]=817,
+ ["macroncmb"]=772,
+ ["macronlowmod"]=717,
+ ["macronmonospace"]=65507,
+ ["macute"]=7743,
+ ["madeva"]=2350,
+ ["magujarati"]=2734,
+ ["magurmukhi"]=2606,
+ ["mahapakhhebrew"]=1444,
+ ["mahapakhlefthebrew"]=1444,
+ ["mahiragana"]=12414,
+ ["maichattawalowleftthai"]=63637,
+ ["maichattawalowrightthai"]=63636,
+ ["maichattawathai"]=3659,
+ ["maichattawaupperleftthai"]=63635,
+ ["maieklowleftthai"]=63628,
+ ["maieklowrightthai"]=63627,
+ ["maiekthai"]=3656,
+ ["maiekupperleftthai"]=63626,
+ ["maihanakatleftthai"]=63620,
+ ["maihanakatthai"]=3633,
+ ["maitaikhuleftthai"]=63625,
+ ["maitaikhuthai"]=3655,
+ ["maitholowleftthai"]=63631,
+ ["maitholowrightthai"]=63630,
+ ["maithothai"]=3657,
+ ["maithoupperleftthai"]=63629,
+ ["maitrilowleftthai"]=63634,
+ ["maitrilowrightthai"]=63633,
+ ["maitrithai"]=3658,
+ ["maitriupperleftthai"]=63632,
+ ["maiyamokthai"]=3654,
+ ["makatakana"]=12510,
+ ["makatakanahalfwidth"]=65423,
+ ["male"]=9794,
+ ["mansyonsquare"]=13127,
+ ["maqafhebrew"]=1470,
+ ["mars"]=9794,
+ ["masoracirclehebrew"]=1455,
+ ["masquare"]=13187,
+ ["mbopomofo"]=12551,
+ ["mbsquare"]=13268,
+ ["mcircle"]=9436,
+ ["mcubedsquare"]=13221,
+ ["mdotaccent"]=7745,
+ ["mdotbelow"]=7747,
+ ["meemarabic"]=1605,
+ ["meemfinalarabic"]=65250,
+ ["meeminitialarabic"]=65251,
+ ["meemmedialarabic"]=65252,
+ ["meemmeeminitialarabic"]=64721,
+ ["meemmeemisolatedarabic"]=64584,
+ ["meetorusquare"]=13133,
+ ["mehiragana"]=12417,
+ ["meizierasquare"]=13182,
+ ["mekatakana"]=12513,
+ ["mekatakanahalfwidth"]=65426,
+ ["mem"]=1502,
+ ["memdagesh"]=64318,
+ ["memdageshhebrew"]=64318,
+ ["memhebrew"]=1502,
+ ["menarmenian"]=1396,
+ ["merkhahebrew"]=1445,
+ ["merkhakefulahebrew"]=1446,
+ ["merkhakefulalefthebrew"]=1446,
+ ["merkhalefthebrew"]=1445,
+ ["mhook"]=625,
+ ["mhzsquare"]=13202,
+ ["middledotkatakanahalfwidth"]=65381,
+ ["middot"]=183,
+ ["mieumacirclekorean"]=12914,
+ ["mieumaparenkorean"]=12818,
+ ["mieumcirclekorean"]=12900,
+ ["mieumkorean"]=12609,
+ ["mieumpansioskorean"]=12656,
+ ["mieumparenkorean"]=12804,
+ ["mieumpieupkorean"]=12654,
+ ["mieumsioskorean"]=12655,
+ ["mihiragana"]=12415,
+ ["mikatakana"]=12511,
+ ["mikatakanahalfwidth"]=65424,
+ ["minus"]=8722,
+ ["minusbelowcmb"]=800,
+ ["minuscircle"]=8854,
+ ["minusmod"]=727,
+ ["minusplus"]=8723,
+ ["minute"]=8242,
+ ["miribaarusquare"]=13130,
+ ["mirisquare"]=13129,
+ ["mlonglegturned"]=624,
+ ["mlsquare"]=13206,
+ ["mmcubedsquare"]=13219,
+ ["mmonospace"]=65357,
+ ["mmsquaredsquare"]=13215,
+ ["mohiragana"]=12418,
+ ["mohmsquare"]=13249,
+ ["mokatakana"]=12514,
+ ["mokatakanahalfwidth"]=65427,
+ ["molsquare"]=13270,
+ ["momathai"]=3617,
+ ["moverssquare"]=13223,
+ ["moverssquaredsquare"]=13224,
+ ["mparen"]=9384,
+ ["mpasquare"]=13227,
+ ["mssquare"]=13235,
+ ["msuperior"]=63215,
+ ["mturned"]=623,
+ ["mu"]=181,
+ ["mu1"]=181,
+ ["muasquare"]=13186,
+ ["muchgreater"]=8811,
+ ["muchless"]=8810,
+ ["mufsquare"]=13196,
+ ["mugreek"]=956,
+ ["mugsquare"]=13197,
+ ["muhiragana"]=12416,
+ ["mukatakana"]=12512,
+ ["mukatakanahalfwidth"]=65425,
+ ["mulsquare"]=13205,
+ ["multiply"]=215,
+ ["mumsquare"]=13211,
+ ["munahhebrew"]=1443,
+ ["munahlefthebrew"]=1443,
+ ["musicalnote"]=9834,
+ ["musicalnotedbl"]=9835,
+ ["musicflatsign"]=9837,
+ ["musicsharpsign"]=9839,
+ ["mussquare"]=13234,
+ ["muvsquare"]=13238,
+ ["muwsquare"]=13244,
+ ["mvmegasquare"]=13241,
+ ["mvsquare"]=13239,
+ ["mwmegasquare"]=13247,
+ ["mwsquare"]=13245,
+ ["n"]=110,
+ ["nabengali"]=2472,
+ ["nabla"]=8711,
+ ["nacute"]=324,
+ ["nadeva"]=2344,
+ ["nagujarati"]=2728,
+ ["nagurmukhi"]=2600,
+ ["nahiragana"]=12394,
+ ["nakatakana"]=12490,
+ ["nakatakanahalfwidth"]=65413,
+ ["napostrophe"]=329,
+ ["nasquare"]=13185,
+ ["nbopomofo"]=12555,
+ ["nbspace"]=160,
+ ["ncaron"]=328,
+ ["ncedilla"]=326,
+ ["ncircle"]=9437,
+ ["ncircumflexbelow"]=7755,
+ ["ncommaaccent"]=326,
+ ["ndotaccent"]=7749,
+ ["ndotbelow"]=7751,
+ ["nehiragana"]=12397,
+ ["nekatakana"]=12493,
+ ["nekatakanahalfwidth"]=65416,
+ ["newsheqelsign"]=8362,
+ ["nfsquare"]=13195,
+ ["ngabengali"]=2457,
+ ["ngadeva"]=2329,
+ ["ngagujarati"]=2713,
+ ["ngagurmukhi"]=2585,
+ ["ngonguthai"]=3591,
+ ["nhiragana"]=12435,
+ ["nhookleft"]=626,
+ ["nhookretroflex"]=627,
+ ["nieunacirclekorean"]=12911,
+ ["nieunaparenkorean"]=12815,
+ ["nieuncieuckorean"]=12597,
+ ["nieuncirclekorean"]=12897,
+ ["nieunhieuhkorean"]=12598,
+ ["nieunkorean"]=12596,
+ ["nieunpansioskorean"]=12648,
+ ["nieunparenkorean"]=12801,
+ ["nieunsioskorean"]=12647,
+ ["nieuntikeutkorean"]=12646,
+ ["nihiragana"]=12395,
+ ["nikatakana"]=12491,
+ ["nikatakanahalfwidth"]=65414,
+ ["nikhahitleftthai"]=63641,
+ ["nikhahitthai"]=3661,
+ ["nine"]=57,
+ ["ninearabic"]=1641,
+ ["ninebengali"]=2543,
+ ["ninecircle"]=9320,
+ ["ninecircleinversesansserif"]=10130,
+ ["ninedeva"]=2415,
+ ["ninegujarati"]=2799,
+ ["ninegurmukhi"]=2671,
+ ["ninehackarabic"]=1641,
+ ["ninehangzhou"]=12329,
+ ["nineideographicparen"]=12840,
+ ["nineinferior"]=8329,
+ ["ninemonospace"]=65305,
+ ["nineoldstyle"]=63289,
+ ["nineparen"]=9340,
+ ["nineperiod"]=9360,
+ ["ninepersian"]=1785,
+ ["nineroman"]=8568,
+ ["ninesuperior"]=8313,
+ ["nineteencircle"]=9330,
+ ["nineteenparen"]=9350,
+ ["nineteenperiod"]=9370,
+ ["ninethai"]=3673,
+ ["nj"]=460,
+ ["njecyrillic"]=1114,
+ ["nkatakana"]=12531,
+ ["nkatakanahalfwidth"]=65437,
+ ["nlegrightlong"]=414,
+ ["nlinebelow"]=7753,
+ ["nmonospace"]=65358,
+ ["nmsquare"]=13210,
+ ["nnabengali"]=2467,
+ ["nnadeva"]=2339,
+ ["nnagujarati"]=2723,
+ ["nnagurmukhi"]=2595,
+ ["nnnadeva"]=2345,
+ ["nohiragana"]=12398,
+ ["nokatakana"]=12494,
+ ["nokatakanahalfwidth"]=65417,
+ ["nonbreakingspace"]=160,
+ ["nonenthai"]=3603,
+ ["nonuthai"]=3609,
+ ["noonarabic"]=1606,
+ ["noonfinalarabic"]=65254,
+ ["noonghunnaarabic"]=1722,
+ ["noonghunnafinalarabic"]=64415,
+ ["noonhehinitialarabic"]=65255,
+ ["nooninitialarabic"]=65255,
+ ["noonjeeminitialarabic"]=64722,
+ ["noonjeemisolatedarabic"]=64587,
+ ["noonmedialarabic"]=65256,
+ ["noonmeeminitialarabic"]=64725,
+ ["noonmeemisolatedarabic"]=64590,
+ ["noonnoonfinalarabic"]=64653,
+ ["notcontains"]=8716,
+ ["notelement"]=8713,
+ ["notelementof"]=8713,
+ ["notequal"]=8800,
+ ["notgreater"]=8815,
+ ["notgreaternorequal"]=8817,
+ ["notgreaternorless"]=8825,
+ ["notidentical"]=8802,
+ ["notless"]=8814,
+ ["notlessnorequal"]=8816,
+ ["notparallel"]=8742,
+ ["notprecedes"]=8832,
+ ["notsubset"]=8836,
+ ["notsucceeds"]=8833,
+ ["notsuperset"]=8837,
+ ["nowarmenian"]=1398,
+ ["nparen"]=9385,
+ ["nssquare"]=13233,
+ ["nsuperior"]=8319,
+ ["ntilde"]=241,
+ ["nu"]=957,
+ ["nuhiragana"]=12396,
+ ["nukatakana"]=12492,
+ ["nukatakanahalfwidth"]=65415,
+ ["nuktabengali"]=2492,
+ ["nuktadeva"]=2364,
+ ["nuktagujarati"]=2748,
+ ["nuktagurmukhi"]=2620,
+ ["numbersign"]=35,
+ ["numbersignmonospace"]=65283,
+ ["numbersignsmall"]=65119,
+ ["numeralsigngreek"]=884,
+ ["numeralsignlowergreek"]=885,
+ ["numero"]=8470,
+ ["nun"]=1504,
+ ["nundagesh"]=64320,
+ ["nundageshhebrew"]=64320,
+ ["nunhebrew"]=1504,
+ ["nvsquare"]=13237,
+ ["nwsquare"]=13243,
+ ["nyabengali"]=2462,
+ ["nyadeva"]=2334,
+ ["nyagujarati"]=2718,
+ ["nyagurmukhi"]=2590,
+ ["o"]=111,
+ ["oacute"]=243,
+ ["oangthai"]=3629,
+ ["obarred"]=629,
+ ["obarredcyrillic"]=1257,
+ ["obarreddieresiscyrillic"]=1259,
+ ["obengali"]=2451,
+ ["obopomofo"]=12571,
+ ["obreve"]=335,
+ ["ocandradeva"]=2321,
+ ["ocandragujarati"]=2705,
+ ["ocandravowelsigndeva"]=2377,
+ ["ocandravowelsigngujarati"]=2761,
+ ["ocaron"]=466,
+ ["ocircle"]=9438,
+ ["ocircumflex"]=244,
+ ["ocircumflexacute"]=7889,
+ ["ocircumflexdotbelow"]=7897,
+ ["ocircumflexgrave"]=7891,
+ ["ocircumflexhookabove"]=7893,
+ ["ocircumflextilde"]=7895,
+ ["ocyrillic"]=1086,
+ ["odblacute"]=337,
+ ["odblgrave"]=525,
+ ["odeva"]=2323,
+ ["odieresis"]=246,
+ ["odieresiscyrillic"]=1255,
+ ["odotbelow"]=7885,
+ ["oe"]=339,
+ ["oekorean"]=12634,
+ ["ogonek"]=731,
+ ["ogonekcmb"]=808,
+ ["ograve"]=242,
+ ["ogujarati"]=2707,
+ ["oharmenian"]=1413,
+ ["ohiragana"]=12362,
+ ["ohookabove"]=7887,
+ ["ohorn"]=417,
+ ["ohornacute"]=7899,
+ ["ohorndotbelow"]=7907,
+ ["ohorngrave"]=7901,
+ ["ohornhookabove"]=7903,
+ ["ohorntilde"]=7905,
+ ["ohungarumlaut"]=337,
+ ["oi"]=419,
+ ["oinvertedbreve"]=527,
+ ["okatakana"]=12458,
+ ["okatakanahalfwidth"]=65397,
+ ["okorean"]=12631,
+ ["olehebrew"]=1451,
+ ["omacron"]=333,
+ ["omacronacute"]=7763,
+ ["omacrongrave"]=7761,
+ ["omdeva"]=2384,
+ ["omega"]=969,
+ ["omega1"]=982,
+ ["omegacyrillic"]=1121,
+ ["omegalatinclosed"]=631,
+ ["omegaroundcyrillic"]=1147,
+ ["omegatitlocyrillic"]=1149,
+ ["omegatonos"]=974,
+ ["omgujarati"]=2768,
+ ["omicron"]=959,
+ ["omicrontonos"]=972,
+ ["omonospace"]=65359,
+ ["one"]=49,
+ ["onearabic"]=1633,
+ ["onebengali"]=2535,
+ ["onecircle"]=9312,
+ ["onecircleinversesansserif"]=10122,
+ ["onedeva"]=2407,
+ ["onedotenleader"]=8228,
+ ["oneeighth"]=8539,
+ ["onefitted"]=63196,
+ ["onegujarati"]=2791,
+ ["onegurmukhi"]=2663,
+ ["onehackarabic"]=1633,
+ ["onehalf"]=189,
+ ["onehangzhou"]=12321,
+ ["oneideographicparen"]=12832,
+ ["oneinferior"]=8321,
+ ["onemonospace"]=65297,
+ ["onenumeratorbengali"]=2548,
+ ["oneoldstyle"]=63281,
+ ["oneparen"]=9332,
+ ["oneperiod"]=9352,
+ ["onepersian"]=1777,
+ ["onequarter"]=188,
+ ["oneroman"]=8560,
+ ["onesuperior"]=185,
+ ["onethai"]=3665,
+ ["onethird"]=8531,
+ ["oogonek"]=491,
+ ["oogonekmacron"]=493,
+ ["oogurmukhi"]=2579,
+ ["oomatragurmukhi"]=2635,
+ ["oopen"]=596,
+ ["oparen"]=9386,
+ ["openbullet"]=9702,
+ ["option"]=8997,
+ ["ordfeminine"]=170,
+ ["ordmasculine"]=186,
+ ["orthogonal"]=8735,
+ ["oshortdeva"]=2322,
+ ["oshortvowelsigndeva"]=2378,
+ ["oslash"]=248,
+ ["oslashacute"]=511,
+ ["osmallhiragana"]=12361,
+ ["osmallkatakana"]=12457,
+ ["osmallkatakanahalfwidth"]=65387,
+ ["ostrokeacute"]=511,
+ ["osuperior"]=63216,
+ ["otcyrillic"]=1151,
+ ["otilde"]=245,
+ ["otildeacute"]=7757,
+ ["otildedieresis"]=7759,
+ ["oubopomofo"]=12577,
+ ["overline"]=8254,
+ ["overlinecenterline"]=65098,
+ ["overlinecmb"]=773,
+ ["overlinedashed"]=65097,
+ ["overlinedblwavy"]=65100,
+ ["overlinewavy"]=65099,
+ ["overscore"]=175,
+ ["ovowelsignbengali"]=2507,
+ ["ovowelsigndeva"]=2379,
+ ["ovowelsigngujarati"]=2763,
+ ["p"]=112,
+ ["paampssquare"]=13184,
+ ["paasentosquare"]=13099,
+ ["pabengali"]=2474,
+ ["pacute"]=7765,
+ ["padeva"]=2346,
+ ["pagedown"]=8671,
+ ["pageup"]=8670,
+ ["pagujarati"]=2730,
+ ["pagurmukhi"]=2602,
+ ["pahiragana"]=12401,
+ ["paiyannoithai"]=3631,
+ ["pakatakana"]=12497,
+ ["palatalizationcyrilliccmb"]=1156,
+ ["palochkacyrillic"]=1216,
+ ["pansioskorean"]=12671,
+ ["paragraph"]=182,
+ ["parallel"]=8741,
+ ["parenleft"]=40,
+ ["parenleftaltonearabic"]=64830,
+ ["parenleftbt"]=63725,
+ ["parenleftex"]=63724,
+ ["parenleftinferior"]=8333,
+ ["parenleftmonospace"]=65288,
+ ["parenleftsmall"]=65113,
+ ["parenleftsuperior"]=8317,
+ ["parenlefttp"]=63723,
+ ["parenleftvertical"]=65077,
+ ["parenright"]=41,
+ ["parenrightaltonearabic"]=64831,
+ ["parenrightbt"]=63736,
+ ["parenrightex"]=63735,
+ ["parenrightinferior"]=8334,
+ ["parenrightmonospace"]=65289,
+ ["parenrightsmall"]=65114,
+ ["parenrightsuperior"]=8318,
+ ["parenrighttp"]=63734,
+ ["parenrightvertical"]=65078,
+ ["partialdiff"]=8706,
+ ["paseqhebrew"]=1472,
+ ["pashtahebrew"]=1433,
+ ["pasquare"]=13225,
+ ["patah"]=1463,
+ ["patah11"]=1463,
+ ["patah1d"]=1463,
+ ["patah2a"]=1463,
+ ["patahhebrew"]=1463,
+ ["patahnarrowhebrew"]=1463,
+ ["patahquarterhebrew"]=1463,
+ ["patahwidehebrew"]=1463,
+ ["pazerhebrew"]=1441,
+ ["pbopomofo"]=12550,
+ ["pcircle"]=9439,
+ ["pdotaccent"]=7767,
+ ["pe"]=1508,
+ ["pecyrillic"]=1087,
+ ["pedagesh"]=64324,
+ ["pedageshhebrew"]=64324,
+ ["peezisquare"]=13115,
+ ["pefinaldageshhebrew"]=64323,
+ ["peharabic"]=1662,
+ ["peharmenian"]=1402,
+ ["pehebrew"]=1508,
+ ["pehfinalarabic"]=64343,
+ ["pehinitialarabic"]=64344,
+ ["pehiragana"]=12410,
+ ["pehmedialarabic"]=64345,
+ ["pekatakana"]=12506,
+ ["pemiddlehookcyrillic"]=1191,
+ ["perafehebrew"]=64334,
+ ["percent"]=37,
+ ["percentarabic"]=1642,
+ ["percentmonospace"]=65285,
+ ["percentsmall"]=65130,
+ ["period"]=46,
+ ["periodarmenian"]=1417,
+ ["periodcentered"]=183,
+ ["periodhalfwidth"]=65377,
+ ["periodinferior"]=63207,
+ ["periodmonospace"]=65294,
+ ["periodsmall"]=65106,
+ ["periodsuperior"]=63208,
+ ["perispomenigreekcmb"]=834,
+ ["perpendicular"]=8869,
+ ["perthousand"]=8240,
+ ["peseta"]=8359,
+ ["pfsquare"]=13194,
+ ["phabengali"]=2475,
+ ["phadeva"]=2347,
+ ["phagujarati"]=2731,
+ ["phagurmukhi"]=2603,
+ ["phi"]=966,
+ ["phi1"]=981,
+ ["phieuphacirclekorean"]=12922,
+ ["phieuphaparenkorean"]=12826,
+ ["phieuphcirclekorean"]=12908,
+ ["phieuphkorean"]=12621,
+ ["phieuphparenkorean"]=12812,
+ ["philatin"]=632,
+ ["phinthuthai"]=3642,
+ ["phisymbolgreek"]=981,
+ ["phook"]=421,
+ ["phophanthai"]=3614,
+ ["phophungthai"]=3612,
+ ["phosamphaothai"]=3616,
+ ["pi"]=960,
+ ["pieupacirclekorean"]=12915,
+ ["pieupaparenkorean"]=12819,
+ ["pieupcieuckorean"]=12662,
+ ["pieupcirclekorean"]=12901,
+ ["pieupkiyeokkorean"]=12658,
+ ["pieupkorean"]=12610,
+ ["pieupparenkorean"]=12805,
+ ["pieupsioskiyeokkorean"]=12660,
+ ["pieupsioskorean"]=12612,
+ ["pieupsiostikeutkorean"]=12661,
+ ["pieupthieuthkorean"]=12663,
+ ["pieuptikeutkorean"]=12659,
+ ["pihiragana"]=12404,
+ ["pikatakana"]=12500,
+ ["pisymbolgreek"]=982,
+ ["piwrarmenian"]=1411,
+ ["plus"]=43,
+ ["plusbelowcmb"]=799,
+ ["pluscircle"]=8853,
+ ["plusminus"]=177,
+ ["plusmod"]=726,
+ ["plusmonospace"]=65291,
+ ["plussmall"]=65122,
+ ["plussuperior"]=8314,
+ ["pmonospace"]=65360,
+ ["pmsquare"]=13272,
+ ["pohiragana"]=12413,
+ ["pointingindexdownwhite"]=9759,
+ ["pointingindexleftwhite"]=9756,
+ ["pointingindexrightwhite"]=9758,
+ ["pointingindexupwhite"]=9757,
+ ["pokatakana"]=12509,
+ ["poplathai"]=3611,
+ ["postalmark"]=12306,
+ ["postalmarkface"]=12320,
+ ["pparen"]=9387,
+ ["precedes"]=8826,
+ ["prescription"]=8478,
+ ["primemod"]=697,
+ ["primereversed"]=8245,
+ ["product"]=8719,
+ ["projective"]=8965,
+ ["prolongedkana"]=12540,
+ ["propellor"]=8984,
+ ["propersubset"]=8834,
+ ["propersuperset"]=8835,
+ ["proportion"]=8759,
+ ["proportional"]=8733,
+ ["psi"]=968,
+ ["psicyrillic"]=1137,
+ ["psilipneumatacyrilliccmb"]=1158,
+ ["pssquare"]=13232,
+ ["puhiragana"]=12407,
+ ["pukatakana"]=12503,
+ ["pvsquare"]=13236,
+ ["pwsquare"]=13242,
+ ["q"]=113,
+ ["qadeva"]=2392,
+ ["qadmahebrew"]=1448,
+ ["qafarabic"]=1602,
+ ["qaffinalarabic"]=65238,
+ ["qafinitialarabic"]=65239,
+ ["qafmedialarabic"]=65240,
+ ["qamats"]=1464,
+ ["qamats10"]=1464,
+ ["qamats1a"]=1464,
+ ["qamats1c"]=1464,
+ ["qamats27"]=1464,
+ ["qamats29"]=1464,
+ ["qamats33"]=1464,
+ ["qamatsde"]=1464,
+ ["qamatshebrew"]=1464,
+ ["qamatsnarrowhebrew"]=1464,
+ ["qamatsqatanhebrew"]=1464,
+ ["qamatsqatannarrowhebrew"]=1464,
+ ["qamatsqatanquarterhebrew"]=1464,
+ ["qamatsqatanwidehebrew"]=1464,
+ ["qamatsquarterhebrew"]=1464,
+ ["qamatswidehebrew"]=1464,
+ ["qarneyparahebrew"]=1439,
+ ["qbopomofo"]=12561,
+ ["qcircle"]=9440,
+ ["qhook"]=672,
+ ["qmonospace"]=65361,
+ ["qof"]=1511,
+ ["qofdagesh"]=64327,
+ ["qofdageshhebrew"]=64327,
+ ["qofhatafpatah"]=1511,
+ ["qofhatafpatahhebrew"]=1511,
+ ["qofhatafsegol"]=1511,
+ ["qofhatafsegolhebrew"]=1511,
+ ["qofhebrew"]=1511,
+ ["qofhiriq"]=1511,
+ ["qofhiriqhebrew"]=1511,
+ ["qofholam"]=1511,
+ ["qofholamhebrew"]=1511,
+ ["qofpatah"]=1511,
+ ["qofpatahhebrew"]=1511,
+ ["qofqamats"]=1511,
+ ["qofqamatshebrew"]=1511,
+ ["qofqubuts"]=1511,
+ ["qofqubutshebrew"]=1511,
+ ["qofsegol"]=1511,
+ ["qofsegolhebrew"]=1511,
+ ["qofsheva"]=1511,
+ ["qofshevahebrew"]=1511,
+ ["qoftsere"]=1511,
+ ["qoftserehebrew"]=1511,
+ ["qparen"]=9388,
+ ["quarternote"]=9833,
+ ["qubuts"]=1467,
+ ["qubuts18"]=1467,
+ ["qubuts25"]=1467,
+ ["qubuts31"]=1467,
+ ["qubutshebrew"]=1467,
+ ["qubutsnarrowhebrew"]=1467,
+ ["qubutsquarterhebrew"]=1467,
+ ["qubutswidehebrew"]=1467,
+ ["question"]=63,
+ ["questionarabic"]=1567,
+ ["questionarmenian"]=1374,
+ ["questiondown"]=191,
+ ["questiondownsmall"]=63423,
+ ["questiongreek"]=894,
+ ["questionmonospace"]=65311,
+ ["questionsmall"]=63295,
+ ["quotedbl"]=34,
+ ["quotedblbase"]=8222,
+ ["quotedblleft"]=8220,
+ ["quotedblmonospace"]=65282,
+ ["quotedblprime"]=12318,
+ ["quotedblprimereversed"]=12317,
+ ["quotedblright"]=8221,
+ ["quoteleft"]=8216,
+ ["quoteleftreversed"]=8219,
+ ["quotereversed"]=8219,
+ ["quoteright"]=8217,
+ ["quoterightn"]=329,
+ ["quotesinglbase"]=8218,
+ ["quotesingle"]=39,
+ ["quotesinglemonospace"]=65287,
+ ["r"]=114,
+ ["raarmenian"]=1404,
+ ["rabengali"]=2480,
+ ["racute"]=341,
+ ["radeva"]=2352,
+ ["radical"]=8730,
+ ["radicalex"]=63717,
+ ["radoverssquare"]=13230,
+ ["radoverssquaredsquare"]=13231,
+ ["radsquare"]=13229,
+ ["rafe"]=1471,
+ ["rafehebrew"]=1471,
+ ["ragujarati"]=2736,
+ ["ragurmukhi"]=2608,
+ ["rahiragana"]=12425,
+ ["rakatakana"]=12521,
+ ["rakatakanahalfwidth"]=65431,
+ ["ralowerdiagonalbengali"]=2545,
+ ["ramiddlediagonalbengali"]=2544,
+ ["ramshorn"]=612,
+ ["ratio"]=8758,
+ ["rbopomofo"]=12566,
+ ["rcaron"]=345,
+ ["rcedilla"]=343,
+ ["rcircle"]=9441,
+ ["rcommaaccent"]=343,
+ ["rdblgrave"]=529,
+ ["rdotaccent"]=7769,
+ ["rdotbelow"]=7771,
+ ["rdotbelowmacron"]=7773,
+ ["referencemark"]=8251,
+ ["reflexsubset"]=8838,
+ ["reflexsuperset"]=8839,
+ ["registered"]=174,
+ ["registersans"]=63720,
+ ["registerserif"]=63194,
+ ["reharabic"]=1585,
+ ["reharmenian"]=1408,
+ ["rehfinalarabic"]=65198,
+ ["rehiragana"]=12428,
+ ["rehyehaleflamarabic"]=1585,
+ ["rekatakana"]=12524,
+ ["rekatakanahalfwidth"]=65434,
+ ["resh"]=1512,
+ ["reshdageshhebrew"]=64328,
+ ["reshhatafpatah"]=1512,
+ ["reshhatafpatahhebrew"]=1512,
+ ["reshhatafsegol"]=1512,
+ ["reshhatafsegolhebrew"]=1512,
+ ["reshhebrew"]=1512,
+ ["reshhiriq"]=1512,
+ ["reshhiriqhebrew"]=1512,
+ ["reshholam"]=1512,
+ ["reshholamhebrew"]=1512,
+ ["reshpatah"]=1512,
+ ["reshpatahhebrew"]=1512,
+ ["reshqamats"]=1512,
+ ["reshqamatshebrew"]=1512,
+ ["reshqubuts"]=1512,
+ ["reshqubutshebrew"]=1512,
+ ["reshsegol"]=1512,
+ ["reshsegolhebrew"]=1512,
+ ["reshsheva"]=1512,
+ ["reshshevahebrew"]=1512,
+ ["reshtsere"]=1512,
+ ["reshtserehebrew"]=1512,
+ ["reversedtilde"]=8765,
+ ["reviahebrew"]=1431,
+ ["reviamugrashhebrew"]=1431,
+ ["revlogicalnot"]=8976,
+ ["rfishhook"]=638,
+ ["rfishhookreversed"]=639,
+ ["rhabengali"]=2525,
+ ["rhadeva"]=2397,
+ ["rho"]=961,
+ ["rhook"]=637,
+ ["rhookturned"]=635,
+ ["rhookturnedsuperior"]=693,
+ ["rhosymbolgreek"]=1009,
+ ["rhotichookmod"]=734,
+ ["rieulacirclekorean"]=12913,
+ ["rieulaparenkorean"]=12817,
+ ["rieulcirclekorean"]=12899,
+ ["rieulhieuhkorean"]=12608,
+ ["rieulkiyeokkorean"]=12602,
+ ["rieulkiyeoksioskorean"]=12649,
+ ["rieulkorean"]=12601,
+ ["rieulmieumkorean"]=12603,
+ ["rieulpansioskorean"]=12652,
+ ["rieulparenkorean"]=12803,
+ ["rieulphieuphkorean"]=12607,
+ ["rieulpieupkorean"]=12604,
+ ["rieulpieupsioskorean"]=12651,
+ ["rieulsioskorean"]=12605,
+ ["rieulthieuthkorean"]=12606,
+ ["rieultikeutkorean"]=12650,
+ ["rieulyeorinhieuhkorean"]=12653,
+ ["rightangle"]=8735,
+ ["righttackbelowcmb"]=793,
+ ["righttriangle"]=8895,
+ ["rihiragana"]=12426,
+ ["rikatakana"]=12522,
+ ["rikatakanahalfwidth"]=65432,
+ ["ring"]=730,
+ ["ringbelowcmb"]=805,
+ ["ringcmb"]=778,
+ ["ringhalfleft"]=703,
+ ["ringhalfleftarmenian"]=1369,
+ ["ringhalfleftbelowcmb"]=796,
+ ["ringhalfleftcentered"]=723,
+ ["ringhalfright"]=702,
+ ["ringhalfrightbelowcmb"]=825,
+ ["ringhalfrightcentered"]=722,
+ ["rinvertedbreve"]=531,
+ ["rittorusquare"]=13137,
+ ["rlinebelow"]=7775,
+ ["rlongleg"]=636,
+ ["rlonglegturned"]=634,
+ ["rmonospace"]=65362,
+ ["rohiragana"]=12429,
+ ["rokatakana"]=12525,
+ ["rokatakanahalfwidth"]=65435,
+ ["roruathai"]=3619,
+ ["rparen"]=9389,
+ ["rrabengali"]=2524,
+ ["rradeva"]=2353,
+ ["rragurmukhi"]=2652,
+ ["rreharabic"]=1681,
+ ["rrehfinalarabic"]=64397,
+ ["rrvocalicbengali"]=2528,
+ ["rrvocalicdeva"]=2400,
+ ["rrvocalicgujarati"]=2784,
+ ["rrvocalicvowelsignbengali"]=2500,
+ ["rrvocalicvowelsigndeva"]=2372,
+ ["rrvocalicvowelsigngujarati"]=2756,
+ ["rsuperior"]=63217,
+ ["rtblock"]=9616,
+ ["rturned"]=633,
+ ["rturnedsuperior"]=692,
+ ["ruhiragana"]=12427,
+ ["rukatakana"]=12523,
+ ["rukatakanahalfwidth"]=65433,
+ ["rupeemarkbengali"]=2546,
+ ["rupeesignbengali"]=2547,
+ ["rupiah"]=63197,
+ ["ruthai"]=3620,
+ ["rvocalicbengali"]=2443,
+ ["rvocalicdeva"]=2315,
+ ["rvocalicgujarati"]=2699,
+ ["rvocalicvowelsignbengali"]=2499,
+ ["rvocalicvowelsigndeva"]=2371,
+ ["rvocalicvowelsigngujarati"]=2755,
+ ["s"]=115,
+ ["sabengali"]=2488,
+ ["sacute"]=347,
+ ["sacutedotaccent"]=7781,
+ ["sadarabic"]=1589,
+ ["sadeva"]=2360,
+ ["sadfinalarabic"]=65210,
+ ["sadinitialarabic"]=65211,
+ ["sadmedialarabic"]=65212,
+ ["sagujarati"]=2744,
+ ["sagurmukhi"]=2616,
+ ["sahiragana"]=12373,
+ ["sakatakana"]=12469,
+ ["sakatakanahalfwidth"]=65403,
+ ["sallallahoualayhewasallamarabic"]=65018,
+ ["samekh"]=1505,
+ ["samekhdagesh"]=64321,
+ ["samekhdageshhebrew"]=64321,
+ ["samekhhebrew"]=1505,
+ ["saraaathai"]=3634,
+ ["saraaethai"]=3649,
+ ["saraaimaimalaithai"]=3652,
+ ["saraaimaimuanthai"]=3651,
+ ["saraamthai"]=3635,
+ ["saraathai"]=3632,
+ ["saraethai"]=3648,
+ ["saraiileftthai"]=63622,
+ ["saraiithai"]=3637,
+ ["saraileftthai"]=63621,
+ ["saraithai"]=3636,
+ ["saraothai"]=3650,
+ ["saraueeleftthai"]=63624,
+ ["saraueethai"]=3639,
+ ["saraueleftthai"]=63623,
+ ["sarauethai"]=3638,
+ ["sarauthai"]=3640,
+ ["sarauuthai"]=3641,
+ ["sbopomofo"]=12569,
+ ["scaron"]=353,
+ ["scarondotaccent"]=7783,
+ ["scedilla"]=351,
+ ["schwa"]=601,
+ ["schwacyrillic"]=1241,
+ ["schwadieresiscyrillic"]=1243,
+ ["schwahook"]=602,
+ ["scircle"]=9442,
+ ["scircumflex"]=349,
+ ["scommaaccent"]=537,
+ ["sdotaccent"]=7777,
+ ["sdotbelow"]=7779,
+ ["sdotbelowdotaccent"]=7785,
+ ["seagullbelowcmb"]=828,
+ ["second"]=8243,
+ ["secondtonechinese"]=714,
+ ["section"]=167,
+ ["seenarabic"]=1587,
+ ["seenfinalarabic"]=65202,
+ ["seeninitialarabic"]=65203,
+ ["seenmedialarabic"]=65204,
+ ["segol"]=1462,
+ ["segol13"]=1462,
+ ["segol1f"]=1462,
+ ["segol2c"]=1462,
+ ["segolhebrew"]=1462,
+ ["segolnarrowhebrew"]=1462,
+ ["segolquarterhebrew"]=1462,
+ ["segoltahebrew"]=1426,
+ ["segolwidehebrew"]=1462,
+ ["seharmenian"]=1405,
+ ["sehiragana"]=12379,
+ ["sekatakana"]=12475,
+ ["sekatakanahalfwidth"]=65406,
+ ["semicolon"]=59,
+ ["semicolonarabic"]=1563,
+ ["semicolonmonospace"]=65307,
+ ["semicolonsmall"]=65108,
+ ["semivoicedmarkkana"]=12444,
+ ["semivoicedmarkkanahalfwidth"]=65439,
+ ["sentisquare"]=13090,
+ ["sentosquare"]=13091,
+ ["seven"]=55,
+ ["sevenarabic"]=1639,
+ ["sevenbengali"]=2541,
+ ["sevencircle"]=9318,
+ ["sevencircleinversesansserif"]=10128,
+ ["sevendeva"]=2413,
+ ["seveneighths"]=8542,
+ ["sevengujarati"]=2797,
+ ["sevengurmukhi"]=2669,
+ ["sevenhackarabic"]=1639,
+ ["sevenhangzhou"]=12327,
+ ["sevenideographicparen"]=12838,
+ ["seveninferior"]=8327,
+ ["sevenmonospace"]=65303,
+ ["sevenoldstyle"]=63287,
+ ["sevenparen"]=9338,
+ ["sevenperiod"]=9358,
+ ["sevenpersian"]=1783,
+ ["sevenroman"]=8566,
+ ["sevensuperior"]=8311,
+ ["seventeencircle"]=9328,
+ ["seventeenparen"]=9348,
+ ["seventeenperiod"]=9368,
+ ["seventhai"]=3671,
+ ["sfthyphen"]=173,
+ ["shaarmenian"]=1399,
+ ["shabengali"]=2486,
+ ["shacyrillic"]=1096,
+ ["shaddaarabic"]=1617,
+ ["shaddadammaarabic"]=64609,
+ ["shaddadammatanarabic"]=64606,
+ ["shaddafathaarabic"]=64608,
+ ["shaddafathatanarabic"]=1617,
+ ["shaddakasraarabic"]=64610,
+ ["shaddakasratanarabic"]=64607,
+ ["shade"]=9618,
+ ["shadedark"]=9619,
+ ["shadelight"]=9617,
+ ["shademedium"]=9618,
+ ["shadeva"]=2358,
+ ["shagujarati"]=2742,
+ ["shagurmukhi"]=2614,
+ ["shalshelethebrew"]=1427,
+ ["shbopomofo"]=12565,
+ ["shchacyrillic"]=1097,
+ ["sheenarabic"]=1588,
+ ["sheenfinalarabic"]=65206,
+ ["sheeninitialarabic"]=65207,
+ ["sheenmedialarabic"]=65208,
+ ["sheicoptic"]=995,
+ ["sheqel"]=8362,
+ ["sheqelhebrew"]=8362,
+ ["sheva"]=1456,
+ ["sheva115"]=1456,
+ ["sheva15"]=1456,
+ ["sheva22"]=1456,
+ ["sheva2e"]=1456,
+ ["shevahebrew"]=1456,
+ ["shevanarrowhebrew"]=1456,
+ ["shevaquarterhebrew"]=1456,
+ ["shevawidehebrew"]=1456,
+ ["shhacyrillic"]=1211,
+ ["shimacoptic"]=1005,
+ ["shin"]=1513,
+ ["shindagesh"]=64329,
+ ["shindageshhebrew"]=64329,
+ ["shindageshshindot"]=64300,
+ ["shindageshshindothebrew"]=64300,
+ ["shindageshsindot"]=64301,
+ ["shindageshsindothebrew"]=64301,
+ ["shindothebrew"]=1473,
+ ["shinhebrew"]=1513,
+ ["shinshindot"]=64298,
+ ["shinshindothebrew"]=64298,
+ ["shinsindot"]=64299,
+ ["shinsindothebrew"]=64299,
+ ["shook"]=642,
+ ["sigma"]=963,
+ ["sigma1"]=962,
+ ["sigmafinal"]=962,
+ ["sigmalunatesymbolgreek"]=1010,
+ ["sihiragana"]=12375,
+ ["sikatakana"]=12471,
+ ["sikatakanahalfwidth"]=65404,
+ ["siluqhebrew"]=1469,
+ ["siluqlefthebrew"]=1469,
+ ["similar"]=8764,
+ ["sindothebrew"]=1474,
+ ["siosacirclekorean"]=12916,
+ ["siosaparenkorean"]=12820,
+ ["sioscieuckorean"]=12670,
+ ["sioscirclekorean"]=12902,
+ ["sioskiyeokkorean"]=12666,
+ ["sioskorean"]=12613,
+ ["siosnieunkorean"]=12667,
+ ["siosparenkorean"]=12806,
+ ["siospieupkorean"]=12669,
+ ["siostikeutkorean"]=12668,
+ ["six"]=54,
+ ["sixarabic"]=1638,
+ ["sixbengali"]=2540,
+ ["sixcircle"]=9317,
+ ["sixcircleinversesansserif"]=10127,
+ ["sixdeva"]=2412,
+ ["sixgujarati"]=2796,
+ ["sixgurmukhi"]=2668,
+ ["sixhackarabic"]=1638,
+ ["sixhangzhou"]=12326,
+ ["sixideographicparen"]=12837,
+ ["sixinferior"]=8326,
+ ["sixmonospace"]=65302,
+ ["sixoldstyle"]=63286,
+ ["sixparen"]=9337,
+ ["sixperiod"]=9357,
+ ["sixpersian"]=1782,
+ ["sixroman"]=8565,
+ ["sixsuperior"]=8310,
+ ["sixteencircle"]=9327,
+ ["sixteencurrencydenominatorbengali"]=2553,
+ ["sixteenparen"]=9347,
+ ["sixteenperiod"]=9367,
+ ["sixthai"]=3670,
+ ["slash"]=47,
+ ["slashmonospace"]=65295,
+ ["slong"]=383,
+ ["slongdotaccent"]=7835,
+ ["smileface"]=9786,
+ ["smonospace"]=65363,
+ ["sofpasuqhebrew"]=1475,
+ ["softhyphen"]=173,
+ ["softsigncyrillic"]=1100,
+ ["sohiragana"]=12381,
+ ["sokatakana"]=12477,
+ ["sokatakanahalfwidth"]=65407,
+ ["soliduslongoverlaycmb"]=824,
+ ["solidusshortoverlaycmb"]=823,
+ ["sorusithai"]=3625,
+ ["sosalathai"]=3624,
+ ["sosothai"]=3595,
+ ["sosuathai"]=3626,
+ ["space"]=32,
+ ["spacehackarabic"]=32,
+ ["spade"]=9824,
+ ["spadesuitblack"]=9824,
+ ["spadesuitwhite"]=9828,
+ ["sparen"]=9390,
+ ["squarebelowcmb"]=827,
+ ["squarecc"]=13252,
+ ["squarecm"]=13213,
+ ["squarediagonalcrosshatchfill"]=9641,
+ ["squarehorizontalfill"]=9636,
+ ["squarekg"]=13199,
+ ["squarekm"]=13214,
+ ["squarekmcapital"]=13262,
+ ["squareln"]=13265,
+ ["squarelog"]=13266,
+ ["squaremg"]=13198,
+ ["squaremil"]=13269,
+ ["squaremm"]=13212,
+ ["squaremsquared"]=13217,
+ ["squareorthogonalcrosshatchfill"]=9638,
+ ["squareupperlefttolowerrightfill"]=9639,
+ ["squareupperrighttolowerleftfill"]=9640,
+ ["squareverticalfill"]=9637,
+ ["squarewhitewithsmallblack"]=9635,
+ ["srsquare"]=13275,
+ ["ssabengali"]=2487,
+ ["ssadeva"]=2359,
+ ["ssagujarati"]=2743,
+ ["ssangcieuckorean"]=12617,
+ ["ssanghieuhkorean"]=12677,
+ ["ssangieungkorean"]=12672,
+ ["ssangkiyeokkorean"]=12594,
+ ["ssangnieunkorean"]=12645,
+ ["ssangpieupkorean"]=12611,
+ ["ssangsioskorean"]=12614,
+ ["ssangtikeutkorean"]=12600,
+ ["ssuperior"]=63218,
+ ["sterling"]=163,
+ ["sterlingmonospace"]=65505,
+ ["strokelongoverlaycmb"]=822,
+ ["strokeshortoverlaycmb"]=821,
+ ["subset"]=8834,
+ ["subsetnotequal"]=8842,
+ ["subsetorequal"]=8838,
+ ["succeeds"]=8827,
+ ["suchthat"]=8715,
+ ["suhiragana"]=12377,
+ ["sukatakana"]=12473,
+ ["sukatakanahalfwidth"]=65405,
+ ["sukunarabic"]=1618,
+ ["summation"]=8721,
+ ["sun"]=9788,
+ ["superset"]=8835,
+ ["supersetnotequal"]=8843,
+ ["supersetorequal"]=8839,
+ ["svsquare"]=13276,
+ ["syouwaerasquare"]=13180,
+ ["t"]=116,
+ ["tabengali"]=2468,
+ ["tackdown"]=8868,
+ ["tackleft"]=8867,
+ ["tadeva"]=2340,
+ ["tagujarati"]=2724,
+ ["tagurmukhi"]=2596,
+ ["taharabic"]=1591,
+ ["tahfinalarabic"]=65218,
+ ["tahinitialarabic"]=65219,
+ ["tahiragana"]=12383,
+ ["tahmedialarabic"]=65220,
+ ["taisyouerasquare"]=13181,
+ ["takatakana"]=12479,
+ ["takatakanahalfwidth"]=65408,
+ ["tatweelarabic"]=1600,
+ ["tau"]=964,
+ ["tav"]=1514,
+ ["tavdages"]=64330,
+ ["tavdagesh"]=64330,
+ ["tavdageshhebrew"]=64330,
+ ["tavhebrew"]=1514,
+ ["tbar"]=359,
+ ["tbopomofo"]=12554,
+ ["tcaron"]=357,
+ ["tccurl"]=680,
+ ["tcedilla"]=355,
+ ["tcheharabic"]=1670,
+ ["tchehfinalarabic"]=64379,
+ ["tchehinitialarabic"]=64380,
+ ["tchehmedialarabic"]=64381,
+ ["tchehmeeminitialarabic"]=64380,
+ ["tcircle"]=9443,
+ ["tcircumflexbelow"]=7793,
+ ["tcommaaccent"]=355,
+ ["tdieresis"]=7831,
+ ["tdotaccent"]=7787,
+ ["tdotbelow"]=7789,
+ ["tecyrillic"]=1090,
+ ["tedescendercyrillic"]=1197,
+ ["teharabic"]=1578,
+ ["tehfinalarabic"]=65174,
+ ["tehhahinitialarabic"]=64674,
+ ["tehhahisolatedarabic"]=64524,
+ ["tehinitialarabic"]=65175,
+ ["tehiragana"]=12390,
+ ["tehjeeminitialarabic"]=64673,
+ ["tehjeemisolatedarabic"]=64523,
+ ["tehmarbutaarabic"]=1577,
+ ["tehmarbutafinalarabic"]=65172,
+ ["tehmedialarabic"]=65176,
+ ["tehmeeminitialarabic"]=64676,
+ ["tehmeemisolatedarabic"]=64526,
+ ["tehnoonfinalarabic"]=64627,
+ ["tekatakana"]=12486,
+ ["tekatakanahalfwidth"]=65411,
+ ["telephone"]=8481,
+ ["telephoneblack"]=9742,
+ ["telishagedolahebrew"]=1440,
+ ["telishaqetanahebrew"]=1449,
+ ["tencircle"]=9321,
+ ["tenideographicparen"]=12841,
+ ["tenparen"]=9341,
+ ["tenperiod"]=9361,
+ ["tenroman"]=8569,
+ ["tesh"]=679,
+ ["tet"]=1496,
+ ["tetdagesh"]=64312,
+ ["tetdageshhebrew"]=64312,
+ ["tethebrew"]=1496,
+ ["tetsecyrillic"]=1205,
+ ["tevirhebrew"]=1435,
+ ["tevirlefthebrew"]=1435,
+ ["thabengali"]=2469,
+ ["thadeva"]=2341,
+ ["thagujarati"]=2725,
+ ["thagurmukhi"]=2597,
+ ["thalarabic"]=1584,
+ ["thalfinalarabic"]=65196,
+ ["thanthakhatlowleftthai"]=63640,
+ ["thanthakhatlowrightthai"]=63639,
+ ["thanthakhatthai"]=3660,
+ ["thanthakhatupperleftthai"]=63638,
+ ["theharabic"]=1579,
+ ["thehfinalarabic"]=65178,
+ ["thehinitialarabic"]=65179,
+ ["thehmedialarabic"]=65180,
+ ["thereexists"]=8707,
+ ["therefore"]=8756,
+ ["theta"]=952,
+ ["theta1"]=977,
+ ["thetasymbolgreek"]=977,
+ ["thieuthacirclekorean"]=12921,
+ ["thieuthaparenkorean"]=12825,
+ ["thieuthcirclekorean"]=12907,
+ ["thieuthkorean"]=12620,
+ ["thieuthparenkorean"]=12811,
+ ["thirteencircle"]=9324,
+ ["thirteenparen"]=9344,
+ ["thirteenperiod"]=9364,
+ ["thonangmonthothai"]=3601,
+ ["thook"]=429,
+ ["thophuthaothai"]=3602,
+ ["thorn"]=254,
+ ["thothahanthai"]=3607,
+ ["thothanthai"]=3600,
+ ["thothongthai"]=3608,
+ ["thothungthai"]=3606,
+ ["thousandcyrillic"]=1154,
+ ["thousandsseparatorarabic"]=1644,
+ ["thousandsseparatorpersian"]=1644,
+ ["three"]=51,
+ ["threearabic"]=1635,
+ ["threebengali"]=2537,
+ ["threecircle"]=9314,
+ ["threecircleinversesansserif"]=10124,
+ ["threedeva"]=2409,
+ ["threeeighths"]=8540,
+ ["threegujarati"]=2793,
+ ["threegurmukhi"]=2665,
+ ["threehackarabic"]=1635,
+ ["threehangzhou"]=12323,
+ ["threeideographicparen"]=12834,
+ ["threeinferior"]=8323,
+ ["threemonospace"]=65299,
+ ["threenumeratorbengali"]=2550,
+ ["threeoldstyle"]=63283,
+ ["threeparen"]=9334,
+ ["threeperiod"]=9354,
+ ["threepersian"]=1779,
+ ["threequarters"]=190,
+ ["threequartersemdash"]=63198,
+ ["threeroman"]=8562,
+ ["threesuperior"]=179,
+ ["threethai"]=3667,
+ ["thzsquare"]=13204,
+ ["tihiragana"]=12385,
+ ["tikatakana"]=12481,
+ ["tikatakanahalfwidth"]=65409,
+ ["tikeutacirclekorean"]=12912,
+ ["tikeutaparenkorean"]=12816,
+ ["tikeutcirclekorean"]=12898,
+ ["tikeutkorean"]=12599,
+ ["tikeutparenkorean"]=12802,
+ ["tilde"]=732,
+ ["tildebelowcmb"]=816,
+ ["tildecmb"]=771,
+ ["tildecomb"]=771,
+ ["tildedoublecmb"]=864,
+ ["tildeoperator"]=8764,
+ ["tildeoverlaycmb"]=820,
+ ["tildeverticalcmb"]=830,
+ ["timescircle"]=8855,
+ ["tipehahebrew"]=1430,
+ ["tipehalefthebrew"]=1430,
+ ["tippigurmukhi"]=2672,
+ ["titlocyrilliccmb"]=1155,
+ ["tiwnarmenian"]=1407,
+ ["tlinebelow"]=7791,
+ ["tmonospace"]=65364,
+ ["toarmenian"]=1385,
+ ["tohiragana"]=12392,
+ ["tokatakana"]=12488,
+ ["tokatakanahalfwidth"]=65412,
+ ["tonebarextrahighmod"]=741,
+ ["tonebarextralowmod"]=745,
+ ["tonebarhighmod"]=742,
+ ["tonebarlowmod"]=744,
+ ["tonebarmidmod"]=743,
+ ["tonefive"]=445,
+ ["tonesix"]=389,
+ ["tonetwo"]=424,
+ ["tonos"]=900,
+ ["tonsquare"]=13095,
+ ["topatakthai"]=3599,
+ ["tortoiseshellbracketleft"]=12308,
+ ["tortoiseshellbracketleftsmall"]=65117,
+ ["tortoiseshellbracketleftvertical"]=65081,
+ ["tortoiseshellbracketright"]=12309,
+ ["tortoiseshellbracketrightsmall"]=65118,
+ ["tortoiseshellbracketrightvertical"]=65082,
+ ["totaothai"]=3605,
+ ["tpalatalhook"]=427,
+ ["tparen"]=9391,
+ ["trademark"]=8482,
+ ["trademarksans"]=63722,
+ ["trademarkserif"]=63195,
+ ["tretroflexhook"]=648,
+ ["triagdn"]=9660,
+ ["triaglf"]=9668,
+ ["triagrt"]=9658,
+ ["triagup"]=9650,
+ ["ts"]=678,
+ ["tsadi"]=1510,
+ ["tsadidagesh"]=64326,
+ ["tsadidageshhebrew"]=64326,
+ ["tsadihebrew"]=1510,
+ ["tsecyrillic"]=1094,
+ ["tsere"]=1461,
+ ["tsere12"]=1461,
+ ["tsere1e"]=1461,
+ ["tsere2b"]=1461,
+ ["tserehebrew"]=1461,
+ ["tserenarrowhebrew"]=1461,
+ ["tserequarterhebrew"]=1461,
+ ["tserewidehebrew"]=1461,
+ ["tshecyrillic"]=1115,
+ ["tsuperior"]=63219,
+ ["ttabengali"]=2463,
+ ["ttadeva"]=2335,
+ ["ttagujarati"]=2719,
+ ["ttagurmukhi"]=2591,
+ ["tteharabic"]=1657,
+ ["ttehfinalarabic"]=64359,
+ ["ttehinitialarabic"]=64360,
+ ["ttehmedialarabic"]=64361,
+ ["tthabengali"]=2464,
+ ["tthadeva"]=2336,
+ ["tthagujarati"]=2720,
+ ["tthagurmukhi"]=2592,
+ ["tturned"]=647,
+ ["tuhiragana"]=12388,
+ ["tukatakana"]=12484,
+ ["tukatakanahalfwidth"]=65410,
+ ["tusmallhiragana"]=12387,
+ ["tusmallkatakana"]=12483,
+ ["tusmallkatakanahalfwidth"]=65391,
+ ["twelvecircle"]=9323,
+ ["twelveparen"]=9343,
+ ["twelveperiod"]=9363,
+ ["twelveroman"]=8571,
+ ["twentycircle"]=9331,
+ ["twentyhangzhou"]=21316,
+ ["twentyparen"]=9351,
+ ["twentyperiod"]=9371,
+ ["two"]=50,
+ ["twoarabic"]=1634,
+ ["twobengali"]=2536,
+ ["twocircle"]=9313,
+ ["twocircleinversesansserif"]=10123,
+ ["twodeva"]=2408,
+ ["twodotenleader"]=8229,
+ ["twodotleader"]=8229,
+ ["twodotleadervertical"]=65072,
+ ["twogujarati"]=2792,
+ ["twogurmukhi"]=2664,
+ ["twohackarabic"]=1634,
+ ["twohangzhou"]=12322,
+ ["twoideographicparen"]=12833,
+ ["twoinferior"]=8322,
+ ["twomonospace"]=65298,
+ ["twonumeratorbengali"]=2549,
+ ["twooldstyle"]=63282,
+ ["twoparen"]=9333,
+ ["twoperiod"]=9353,
+ ["twopersian"]=1778,
+ ["tworoman"]=8561,
+ ["twostroke"]=443,
+ ["twosuperior"]=178,
+ ["twothai"]=3666,
+ ["twothirds"]=8532,
+ ["u"]=117,
+ ["uacute"]=250,
+ ["ubar"]=649,
+ ["ubengali"]=2441,
+ ["ubopomofo"]=12584,
+ ["ubreve"]=365,
+ ["ucaron"]=468,
+ ["ucircle"]=9444,
+ ["ucircumflex"]=251,
+ ["ucircumflexbelow"]=7799,
+ ["ucyrillic"]=1091,
+ ["udattadeva"]=2385,
+ ["udblacute"]=369,
+ ["udblgrave"]=533,
+ ["udeva"]=2313,
+ ["udieresis"]=252,
+ ["udieresisacute"]=472,
+ ["udieresisbelow"]=7795,
+ ["udieresiscaron"]=474,
+ ["udieresiscyrillic"]=1265,
+ ["udieresisgrave"]=476,
+ ["udieresismacron"]=470,
+ ["udotbelow"]=7909,
+ ["ugrave"]=249,
+ ["ugujarati"]=2697,
+ ["ugurmukhi"]=2569,
+ ["uhiragana"]=12358,
+ ["uhookabove"]=7911,
+ ["uhorn"]=432,
+ ["uhornacute"]=7913,
+ ["uhorndotbelow"]=7921,
+ ["uhorngrave"]=7915,
+ ["uhornhookabove"]=7917,
+ ["uhorntilde"]=7919,
+ ["uhungarumlaut"]=369,
+ ["uhungarumlautcyrillic"]=1267,
+ ["uinvertedbreve"]=535,
+ ["ukatakana"]=12454,
+ ["ukatakanahalfwidth"]=65395,
+ ["ukcyrillic"]=1145,
+ ["ukorean"]=12636,
+ ["umacron"]=363,
+ ["umacroncyrillic"]=1263,
+ ["umacrondieresis"]=7803,
+ ["umatragurmukhi"]=2625,
+ ["umonospace"]=65365,
+ ["underscore"]=95,
+ ["underscoredbl"]=8215,
+ ["underscoremonospace"]=65343,
+ ["underscorevertical"]=65075,
+ ["underscorewavy"]=65103,
+ ["union"]=8746,
+ ["universal"]=8704,
+ ["uogonek"]=371,
+ ["uparen"]=9392,
+ ["upblock"]=9600,
+ ["upperdothebrew"]=1476,
+ ["upsilon"]=965,
+ ["upsilondieresis"]=971,
+ ["upsilondieresistonos"]=944,
+ ["upsilonlatin"]=650,
+ ["upsilontonos"]=973,
+ ["uptackbelowcmb"]=797,
+ ["uptackmod"]=724,
+ ["uragurmukhi"]=2675,
+ ["uring"]=367,
+ ["ushortcyrillic"]=1118,
+ ["usmallhiragana"]=12357,
+ ["usmallkatakana"]=12453,
+ ["usmallkatakanahalfwidth"]=65385,
+ ["ustraightcyrillic"]=1199,
+ ["ustraightstrokecyrillic"]=1201,
+ ["utilde"]=361,
+ ["utildeacute"]=7801,
+ ["utildebelow"]=7797,
+ ["uubengali"]=2442,
+ ["uudeva"]=2314,
+ ["uugujarati"]=2698,
+ ["uugurmukhi"]=2570,
+ ["uumatragurmukhi"]=2626,
+ ["uuvowelsignbengali"]=2498,
+ ["uuvowelsigndeva"]=2370,
+ ["uuvowelsigngujarati"]=2754,
+ ["uvowelsignbengali"]=2497,
+ ["uvowelsigndeva"]=2369,
+ ["uvowelsigngujarati"]=2753,
+ ["v"]=118,
+ ["vadeva"]=2357,
+ ["vagujarati"]=2741,
+ ["vagurmukhi"]=2613,
+ ["vakatakana"]=12535,
+ ["vav"]=1493,
+ ["vavdagesh"]=64309,
+ ["vavdagesh65"]=64309,
+ ["vavdageshhebrew"]=64309,
+ ["vavhebrew"]=1493,
+ ["vavholam"]=64331,
+ ["vavholamhebrew"]=64331,
+ ["vavvavhebrew"]=1520,
+ ["vavyodhebrew"]=1521,
+ ["vcircle"]=9445,
+ ["vdotbelow"]=7807,
+ ["vecyrillic"]=1074,
+ ["veharabic"]=1700,
+ ["vehfinalarabic"]=64363,
+ ["vehinitialarabic"]=64364,
+ ["vehmedialarabic"]=64365,
+ ["vekatakana"]=12537,
+ ["venus"]=9792,
+ ["verticalbar"]=124,
+ ["verticallineabovecmb"]=781,
+ ["verticallinebelowcmb"]=809,
+ ["verticallinelowmod"]=716,
+ ["verticallinemod"]=712,
+ ["vewarmenian"]=1406,
+ ["vhook"]=651,
+ ["vikatakana"]=12536,
+ ["viramabengali"]=2509,
+ ["viramadeva"]=2381,
+ ["viramagujarati"]=2765,
+ ["visargabengali"]=2435,
+ ["visargadeva"]=2307,
+ ["visargagujarati"]=2691,
+ ["vmonospace"]=65366,
+ ["voarmenian"]=1400,
+ ["voicediterationhiragana"]=12446,
+ ["voicediterationkatakana"]=12542,
+ ["voicedmarkkana"]=12443,
+ ["voicedmarkkanahalfwidth"]=65438,
+ ["vokatakana"]=12538,
+ ["vparen"]=9393,
+ ["vtilde"]=7805,
+ ["vturned"]=652,
+ ["vuhiragana"]=12436,
+ ["vukatakana"]=12532,
+ ["w"]=119,
+ ["wacute"]=7811,
+ ["waekorean"]=12633,
+ ["wahiragana"]=12431,
+ ["wakatakana"]=12527,
+ ["wakatakanahalfwidth"]=65436,
+ ["wakorean"]=12632,
+ ["wasmallhiragana"]=12430,
+ ["wasmallkatakana"]=12526,
+ ["wattosquare"]=13143,
+ ["wavedash"]=12316,
+ ["wavyunderscorevertical"]=65076,
+ ["wawarabic"]=1608,
+ ["wawfinalarabic"]=65262,
+ ["wawhamzaabovearabic"]=1572,
+ ["wawhamzaabovefinalarabic"]=65158,
+ ["wbsquare"]=13277,
+ ["wcircle"]=9446,
+ ["wcircumflex"]=373,
+ ["wdieresis"]=7813,
+ ["wdotaccent"]=7815,
+ ["wdotbelow"]=7817,
+ ["wehiragana"]=12433,
+ ["weierstrass"]=8472,
+ ["wekatakana"]=12529,
+ ["wekorean"]=12638,
+ ["weokorean"]=12637,
+ ["wgrave"]=7809,
+ ["whitebullet"]=9702,
+ ["whitecircle"]=9675,
+ ["whitecircleinverse"]=9689,
+ ["whitecornerbracketleft"]=12302,
+ ["whitecornerbracketleftvertical"]=65091,
+ ["whitecornerbracketright"]=12303,
+ ["whitecornerbracketrightvertical"]=65092,
+ ["whitediamond"]=9671,
+ ["whitediamondcontainingblacksmalldiamond"]=9672,
+ ["whitedownpointingsmalltriangle"]=9663,
+ ["whitedownpointingtriangle"]=9661,
+ ["whiteleftpointingsmalltriangle"]=9667,
+ ["whiteleftpointingtriangle"]=9665,
+ ["whitelenticularbracketleft"]=12310,
+ ["whitelenticularbracketright"]=12311,
+ ["whiterightpointingsmalltriangle"]=9657,
+ ["whiterightpointingtriangle"]=9655,
+ ["whitesmallsquare"]=9643,
+ ["whitesmilingface"]=9786,
+ ["whitesquare"]=9633,
+ ["whitestar"]=9734,
+ ["whitetelephone"]=9743,
+ ["whitetortoiseshellbracketleft"]=12312,
+ ["whitetortoiseshellbracketright"]=12313,
+ ["whiteuppointingsmalltriangle"]=9653,
+ ["whiteuppointingtriangle"]=9651,
+ ["wihiragana"]=12432,
+ ["wikatakana"]=12528,
+ ["wikorean"]=12639,
+ ["wmonospace"]=65367,
+ ["wohiragana"]=12434,
+ ["wokatakana"]=12530,
+ ["wokatakanahalfwidth"]=65382,
+ ["won"]=8361,
+ ["wonmonospace"]=65510,
+ ["wowaenthai"]=3623,
+ ["wparen"]=9394,
+ ["wring"]=7832,
+ ["wsuperior"]=695,
+ ["wturned"]=653,
+ ["wynn"]=447,
+ ["x"]=120,
+ ["xabovecmb"]=829,
+ ["xbopomofo"]=12562,
+ ["xcircle"]=9447,
+ ["xdieresis"]=7821,
+ ["xdotaccent"]=7819,
+ ["xeharmenian"]=1389,
+ ["xi"]=958,
+ ["xmonospace"]=65368,
+ ["xparen"]=9395,
+ ["xsuperior"]=739,
+ ["y"]=121,
+ ["yaadosquare"]=13134,
+ ["yabengali"]=2479,
+ ["yacute"]=253,
+ ["yadeva"]=2351,
+ ["yaekorean"]=12626,
+ ["yagujarati"]=2735,
+ ["yagurmukhi"]=2607,
+ ["yahiragana"]=12420,
+ ["yakatakana"]=12516,
+ ["yakatakanahalfwidth"]=65428,
+ ["yakorean"]=12625,
+ ["yamakkanthai"]=3662,
+ ["yasmallhiragana"]=12419,
+ ["yasmallkatakana"]=12515,
+ ["yasmallkatakanahalfwidth"]=65388,
+ ["yatcyrillic"]=1123,
+ ["ycircle"]=9448,
+ ["ycircumflex"]=375,
+ ["ydieresis"]=255,
+ ["ydotaccent"]=7823,
+ ["ydotbelow"]=7925,
+ ["yeharabic"]=1610,
+ ["yehbarreearabic"]=1746,
+ ["yehbarreefinalarabic"]=64431,
+ ["yehfinalarabic"]=65266,
+ ["yehhamzaabovearabic"]=1574,
+ ["yehhamzaabovefinalarabic"]=65162,
+ ["yehhamzaaboveinitialarabic"]=65163,
+ ["yehhamzaabovemedialarabic"]=65164,
+ ["yehinitialarabic"]=65267,
+ ["yehmedialarabic"]=65268,
+ ["yehmeeminitialarabic"]=64733,
+ ["yehmeemisolatedarabic"]=64600,
+ ["yehnoonfinalarabic"]=64660,
+ ["yehthreedotsbelowarabic"]=1745,
+ ["yekorean"]=12630,
+ ["yen"]=165,
+ ["yenmonospace"]=65509,
+ ["yeokorean"]=12629,
+ ["yeorinhieuhkorean"]=12678,
+ ["yerahbenyomohebrew"]=1450,
+ ["yerahbenyomolefthebrew"]=1450,
+ ["yericyrillic"]=1099,
+ ["yerudieresiscyrillic"]=1273,
+ ["yesieungkorean"]=12673,
+ ["yesieungpansioskorean"]=12675,
+ ["yesieungsioskorean"]=12674,
+ ["yetivhebrew"]=1434,
+ ["ygrave"]=7923,
+ ["yhook"]=436,
+ ["yhookabove"]=7927,
+ ["yiarmenian"]=1397,
+ ["yicyrillic"]=1111,
+ ["yikorean"]=12642,
+ ["yinyang"]=9775,
+ ["yiwnarmenian"]=1410,
+ ["ymonospace"]=65369,
+ ["yod"]=1497,
+ ["yoddagesh"]=64313,
+ ["yoddageshhebrew"]=64313,
+ ["yodhebrew"]=1497,
+ ["yodyodhebrew"]=1522,
+ ["yodyodpatahhebrew"]=64287,
+ ["yohiragana"]=12424,
+ ["yoikorean"]=12681,
+ ["yokatakana"]=12520,
+ ["yokatakanahalfwidth"]=65430,
+ ["yokorean"]=12635,
+ ["yosmallhiragana"]=12423,
+ ["yosmallkatakana"]=12519,
+ ["yosmallkatakanahalfwidth"]=65390,
+ ["yotgreek"]=1011,
+ ["yoyaekorean"]=12680,
+ ["yoyakorean"]=12679,
+ ["yoyakthai"]=3618,
+ ["yoyingthai"]=3597,
+ ["yparen"]=9396,
+ ["ypogegrammeni"]=890,
+ ["ypogegrammenigreekcmb"]=837,
+ ["yr"]=422,
+ ["yring"]=7833,
+ ["ysuperior"]=696,
+ ["ytilde"]=7929,
+ ["yturned"]=654,
+ ["yuhiragana"]=12422,
+ ["yuikorean"]=12684,
+ ["yukatakana"]=12518,
+ ["yukatakanahalfwidth"]=65429,
+ ["yukorean"]=12640,
+ ["yusbigcyrillic"]=1131,
+ ["yusbigiotifiedcyrillic"]=1133,
+ ["yuslittlecyrillic"]=1127,
+ ["yuslittleiotifiedcyrillic"]=1129,
+ ["yusmallhiragana"]=12421,
+ ["yusmallkatakana"]=12517,
+ ["yusmallkatakanahalfwidth"]=65389,
+ ["yuyekorean"]=12683,
+ ["yuyeokorean"]=12682,
+ ["yyabengali"]=2527,
+ ["yyadeva"]=2399,
+ ["z"]=122,
+ ["zaarmenian"]=1382,
+ ["zacute"]=378,
+ ["zadeva"]=2395,
+ ["zagurmukhi"]=2651,
+ ["zaharabic"]=1592,
+ ["zahfinalarabic"]=65222,
+ ["zahinitialarabic"]=65223,
+ ["zahiragana"]=12374,
+ ["zahmedialarabic"]=65224,
+ ["zainarabic"]=1586,
+ ["zainfinalarabic"]=65200,
+ ["zakatakana"]=12470,
+ ["zaqefgadolhebrew"]=1429,
+ ["zaqefqatanhebrew"]=1428,
+ ["zarqahebrew"]=1432,
+ ["zayin"]=1494,
+ ["zayindagesh"]=64310,
+ ["zayindageshhebrew"]=64310,
+ ["zayinhebrew"]=1494,
+ ["zbopomofo"]=12567,
+ ["zcaron"]=382,
+ ["zcircle"]=9449,
+ ["zcircumflex"]=7825,
+ ["zcurl"]=657,
+ ["zdot"]=380,
+ ["zdotaccent"]=380,
+ ["zdotbelow"]=7827,
+ ["zecyrillic"]=1079,
+ ["zedescendercyrillic"]=1177,
+ ["zedieresiscyrillic"]=1247,
+ ["zehiragana"]=12380,
+ ["zekatakana"]=12476,
+ ["zero"]=48,
+ ["zeroarabic"]=1632,
+ ["zerobengali"]=2534,
+ ["zerodeva"]=2406,
+ ["zerogujarati"]=2790,
+ ["zerogurmukhi"]=2662,
+ ["zerohackarabic"]=1632,
+ ["zeroinferior"]=8320,
+ ["zeromonospace"]=65296,
+ ["zerooldstyle"]=63280,
+ ["zeropersian"]=1776,
+ ["zerosuperior"]=8304,
+ ["zerothai"]=3664,
+ ["zerowidthjoiner"]=65279,
+ ["zerowidthnonjoiner"]=8204,
+ ["zerowidthspace"]=8203,
+ ["zeta"]=950,
+ ["zhbopomofo"]=12563,
+ ["zhearmenian"]=1386,
+ ["zhebrevecyrillic"]=1218,
+ ["zhecyrillic"]=1078,
+ ["zhedescendercyrillic"]=1175,
+ ["zhedieresiscyrillic"]=1245,
+ ["zihiragana"]=12376,
+ ["zikatakana"]=12472,
+ ["zinorhebrew"]=1454,
+ ["zlinebelow"]=7829,
+ ["zmonospace"]=65370,
+ ["zohiragana"]=12382,
+ ["zokatakana"]=12478,
+ ["zparen"]=9397,
+ ["zretroflexhook"]=656,
+ ["zstroke"]=438,
+ ["zuhiragana"]=12378,
+ ["zukatakana"]=12474,
+}
diff --git a/macros/luatex/generic/luaotfload/luaotfload-init.lua b/macros/luatex/generic/luaotfload/luaotfload-init.lua
new file mode 100644
index 0000000000..9c932892f4
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-init.lua
@@ -0,0 +1,781 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-init.lua
+-- DESCRIPTION: part of luaotfload / font loader initialization
+-- REQUIREMENTS: luatex v.0.80 or later; packages lualibs
+-- AUTHOR: Philipp Gesang (Phg), <phg@phi-gamma.net>, Marcel Krüger
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-init",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / initialization",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+-----------------------------------------------------------------------
+
+
+local setmetatable = setmetatable
+local kpsefind_file = kpse.find_file
+local lfsisdir = lfs.isdir
+
+--[[doc--
+
+ Initialization phases:
+
+ - Load Lualibs from package
+ - Set up the logger routines
+ - Load Fontloader
+ - as package specified in configuration
+ - from Context install
+ - (optional: from raw unpackaged files distributed with
+ Luaotfload)
+
+ The initialization of the Lualibs may be made configurable in the
+ future as well allowing to load both the files and the merged package
+ depending on a configuration setting. However, this would require
+ separating out the configuration parser into a self-contained
+ package, which might be problematic due to its current dependency on
+ the Lualibs itself.
+
+--doc]]--
+
+local log --- filled in after loading the log module
+local logreport --- filled in after loading the log module
+
+--[[doc--
+
+ \subsection{Preparing the Font Loader}
+ We treat the fontloader as a semi-black box so behavior is
+ consistent between formats.
+ We load the fontloader code directly in the same fashion as the
+ Plain format \identifier{luatex-fonts} that is part of Context.
+ How this is executed depends on the presence on the
+ \emphasis{merged font loader code}.
+ In \identifier{luaotfload} this is contained in the file
+ \fileent{luaotfload-merged.lua}.
+ If this file cannot be found, the original libraries from \CONTEXT
+ of which the merged code was composed are loaded instead.
+ Since these files are not shipped with Luaotfload, an installation
+ of Context is required.
+ (Since we pull the fontloader directly from the Context minimals,
+ the necessary Context version is likely to be more recent than that
+ of other TeX distributions like Texlive.)
+ The imported font loader will call \luafunction{callback.register}
+ once while reading \fileent{font-def.lua}.
+ This is unavoidable unless we modify the imported files, but
+ harmless if we make it call a dummy instead.
+ However, this problem might vanish if we decide to do the merging
+ ourselves, like the \identifier{lualibs} package does.
+ With this step we would obtain the freedom to load our own
+ overrides in the process right where they are needed, at the cost
+ of losing encapsulation.
+ The decision on how to progress is currently on indefinite hold.
+
+--doc]]--
+
+local init_early = function ()
+
+ local store = { }
+ config = config or { } --- global
+ config.luaotfload = config.luaotfload or { }
+ config.lualibs = config.lualibs or { }
+ config.lualibs.verbose = false
+ config.lualibs.prefer_merged = true
+ config.lualibs.load_extended = true
+ fonts = fonts or { }
+
+ require "lualibs"
+
+ if not lualibs then error "this module requires Luaotfload" end
+ if not luaotfload then error "this module requires Luaotfload" end
+
+ --[[doc--
+
+ The logger needs to be in place prior to loading the fontloader due
+ to order of initialization being crucial for the logger functions
+ that are swapped.
+
+ --doc]]--
+
+ luaotfload.loaders.luaotfload "log"
+ log = luaotfload.log
+ logreport = log.report
+ log.set_loglevel (default_log_level)
+
+ logreport ("log", 4, "init", "Concealing callback.register().")
+ store.trapped_register = callback.register
+
+ callback.register = function (id)
+ logreport ("log", 4, "init",
+ "Dummy callback.register() invoked on %s.",
+ id)
+ end
+
+ --[[doc--
+
+ By default, the fontloader requires a number of \emphasis{private
+ attributes} for internal use.
+ These must be kept consistent with the attribute handling methods
+ as provided by \identifier{luatexbase}.
+ Our strategy is to override the function that allocates new
+ attributes before we initialize the font loader, making it a
+ wrapper around \luafunction{luatexbase.new_attribute}.\footnote{%
+ Many thanks, again, to Hans Hagen for making this part
+ configurable!
+ }
+ The attribute identifiers are prefixed “\fileent{luaotfload@}” to
+ avoid name clashes.
+
+ --doc]]--
+
+ local new_attribute = luatexbase.new_attribute
+ local the_attributes = luatexbase.attributes
+
+ attributes = attributes or { } --- this writes a global, sorry
+
+ attributes.private = function (name)
+ local attr = "luaotfload@" .. name --- used to be: “otfl@”
+ local number = the_attributes[attr]
+ if not number then number = new_attribute(attr) end
+ return number
+ end
+
+ luaotfload.loaders.fontloader "basics-gen"
+
+ return store
+end --- [init_early]
+
+--[[doc--
+
+ These next lines replicate the behavior of
+ \fileent{luatex-fonts.lua}.
+
+--doc]]--
+
+local push_namespaces = function ()
+ logreport ("log", 4, "init", "push namespace for font loader")
+ local normalglobal = { }
+ for k, v in next, _G do
+ normalglobal[k] = v
+ end
+ return normalglobal
+end
+
+local pop_namespaces = function (normalglobal,
+ isolate,
+ context_environment)
+ if normalglobal then
+ local _G = _G
+ local mode = "non-destructive"
+ if isolate then mode = "destructive" end
+ logreport ("log", 4, "init", "pop namespace from font loader -- " .. mode)
+ for k, v in next, _G do
+ if not normalglobal[k] then
+ context_environment[k] = v
+ if isolate then
+ _G[k] = nil
+ end
+ end
+ end
+ for k, v in next, normalglobal do
+ _G[k] = v
+ end
+ -- just to be sure:
+ setmetatable(context_environment, _G)
+ else
+ logreport ("both", 0, "init",
+ "irrecoverable error during pop_namespace: no globals to restore")
+ os.exit ()
+ end
+end
+
+--- below paths are relative to the texmf-context
+local ltx = "tex/generic/context/luatex"
+local ctx = { "tex/context/base/mkiv", "tex/context/base" }
+
+local context_modules = {
+
+ --- Since 2.6 those are directly provided by the Lualibs package.
+ { false, "l-lua" },
+ { false, "l-lpeg" },
+ { false, "l-function" },
+ { false, "l-string" },
+ { false, "l-table" },
+ { false, "l-io" },
+ { false, "l-file" },
+ { false, "l-boolean" },
+ { false, "l-math" },
+ { false, "l-unicode" }, -- NEW UF 19.09.2018
+ { false, "util-str" },
+ { false, "util-fil" },
+
+ --- These constitute the fontloader proper.
+ { ltx, "luatex-basics-gen" },
+ { ctx, "data-con" },
+ { ltx, "luatex-basics-nod" },
+ { ltx, "luatex-basics-chr" }, -- NEW UF 14.12.2018
+ { ctx, "font-ini" },
+ { ltx, "luatex-fonts-mis" }, -- NEW UF 19.09.2018
+ { ctx, "font-con" },
+ { ltx, "luatex-fonts-enc" },
+ { ctx, "font-cid" },
+ { ctx, "font-map" },
+-- { ltx, "luatex-fonts-syn" }, -- ignore??
+ { ctx, "font-vfc" }, -- NEW UF 19.09.2018
+ { ctx, "font-oti" },
+ { ctx, "font-otr" },
+ { ctx, "font-ott" },
+ { ctx, "font-cff" },
+ { ctx, "font-ttf" },
+ { ctx, "font-dsp" },
+ { ctx, "font-oup" },
+ { ctx, "font-otl" },
+ { ctx, "font-oto" },
+ { ctx, "font-otj" },
+ { ctx, "font-ota" },
+ { ctx, "font-ots" },
+ { ctx, "font-osd" },
+ { ctx, "font-ocl" },
+ { ctx, "font-otc" },
+ { ctx, "font-onr" },
+ { ctx, "font-one" },
+ { ctx, "font-afk" },
+ { ctx, "luatex-fonts-tfm" },
+ { ctx, "font-lua" },
+ { ctx, "font-def" },
+ { ltx, "luatex-fonts-def" },
+ { ltx, "luatex-fonts-ext" },
+ { ctx, "font-imp-tex" },
+ { ctx, "font-imp-ligatures"},
+ { ctx, "font-imp-italics" },
+ { ctx, "font-imp-effects" },
+ { ltx, "luatex-fonts-lig" },
+ { ltx, "luatex-fonts-gbn" },
+
+
+} --[[context_modules]]
+
+local load_context_modules = function (pth)
+
+ local load_module = luaotfload.loaders.context
+ local ignore_module = luaotfload.loaders.ignore
+
+ logreport ("both", 2, "init",
+ "Loading fontloader components from context.")
+ local n = #context_modules
+ for i = 1, n do
+ local sub, spec = unpack (context_modules [i])
+ if sub == false then
+ ignore_module (spec)
+ else
+ local tsub = type (sub)
+ if not pth then
+ load_module (spec)
+ elseif tsub == "string" then
+ load_module (spec, file.join (pth, sub))
+ elseif tsub == "table" then
+ local pfx
+ local nsub = #sub
+ for j = 1, nsub do
+ local full = file.join (pth, sub [j])
+ if lfsisdir (full) then --- pick the first real one
+ pfx = full
+ break
+ end
+ end
+ if pfx then
+ load_module (spec, pfx)
+ else
+ logreport ("both", 0, "init",
+ "None of the %d search paths for module %q exist; \z
+ falling back to default path.",
+ nsub, tostring (spec))
+ load_module (spec) --- maybe we’ll get by after all?
+ end
+ else
+ logreport ("both", 0, "init",
+ "Internal error, please report. \z
+ This is not your fault.")
+ os.exit (-1)
+ end
+ end
+ end
+
+end
+
+local init_adapt = function ()
+
+ local context_environment = { }
+ local our_environment = push_namespaces ()
+
+ --[[doc--
+
+ The font loader requires that the attribute with index zero be
+ zero. We happily oblige.
+ (Cf. \fileent{luatex-fonts-nod.lua}.)
+
+ --doc]]--
+
+ tex.attribute[0] = 0
+
+ return our_environment, context_environment
+
+end --- [init_adapt]
+
+--[[doc--
+
+ In Context, characters.data is where the data from char-def.lua
+ resides. The file is huge (>4.4 MB as of 2016) and only a stripped
+ down version is part of the isolated font loader. Nevertheless, we
+ include an excerpt generated by the mkcharacters script that contains
+ a subset of the fields of each character defined and some extra
+ metadata.
+
+ Currently, these are (compare the mkcharacters script!)
+
+ · "direction"
+ · "mirror"
+ · "category"
+ · "textclass"
+
+ The directional information is required for packages like Simurgh [0]
+ to work correctly. In an early stage [1] it was necessary to load
+ further files from Context directly, including the full blown version
+ of char-def. Since we have no use for most of the so imported
+ functionality, the required parts have been isolated and are now
+ instated along with luaotfload-characters.lua. We can extend the set
+ of imported features easily should it not be enough.
+
+ [0] https://github.com/persian-tex/simurgh
+ [1] http://tex.stackexchange.com/a/132301/14066
+
+--doc]]--
+
+--[[--14.12.2018disable characters
+--characters = characters or { } --- should be created in basics-gen
+--characters.data = nil
+--local chardef = "luaotfload-characters"
+--
+--do
+-- local setmetatableindex = function (t, f)
+-- local mt = getmetatable (t)
+-- if mt then
+-- mt.__index = f
+-- else
+-- setmetatable (t, { __index = f })
+-- end
+-- end
+--
+-- --- there are some special tables for each field that provide access
+-- --- to fields of the character table by means of a metatable
+--
+-- local mkcharspecial = function (characters, tablename, field)
+--
+-- local chardata = characters.data
+--
+-- if chardata then
+-- local newspecial = { }
+-- characters [tablename] = newspecial --> e.g. “characters.data.mirrors”
+--
+-- local idx = function (t, char)
+-- local c = chardata [char]
+-- if c then
+-- local m = c [field] --> e.g. “mirror”
+-- if m then
+-- t [char] = m
+-- return m
+-- end
+-- end
+-- newspecial [char] = false
+-- return char
+-- end
+--
+-- setmetatableindex (newspecial, idx)
+-- end
+--
+-- end
+--
+-- local mkcategories = function (characters) -- different from the others
+--
+-- local chardata = characters.data
+-- local categories = characters.categories or { }
+-- characters.categories = categories
+--
+-- setmetatable (categories, { __index = function (t, char)
+-- if char then
+-- local c = chardata [char]
+-- c = c.category or char
+-- t [char] = c
+-- return c
+-- end
+-- end})
+--
+-- end
+--
+-- local load_failed = false
+-- local chardata --> characters.data; loaded on demand
+--
+-- local load_chardef = function ()
+--
+-- logreport ("both", 1, "aux", "Loading character metadata from %s.", chardef)
+-- chardata = dofile (kpse.find_file (chardef, "lua"))
+--
+-- if chardata == nil then
+-- logreport ("both", 0, "aux",
+-- "Could not load %s; continuing with empty character table.",
+-- chardef)
+-- chardata = { }
+-- load_failed = true
+-- end
+--
+-- characters = { } --- nuke metatable
+-- characters.data = chardata
+-- characters.classifiers = chardata.classifiers
+-- chardata.classifiers = nil
+--
+-- --- institute some of the functionality from char-ini.lua
+--
+-- mkcharspecial (characters, "mirrors", "mirror")
+-- mkcharspecial (characters, "directions", "direction")
+-- mkcharspecial (characters, "textclasses", "textclass")
+-- mkcategories (characters)
+--
+-- end
+--
+-- local charindex = function (t, k)
+-- if chardata == nil and load_failed ~= true then
+-- load_chardef ()
+-- end
+--
+-- return rawget (characters, k)
+-- end
+--
+-- setmetatableindex (characters, charindex)
+--
+--end
+--]] --14.12.2018disable characters
+
+local init_main = function ()
+
+ local load_fontloader_module = luaotfload.loaders.fontloader
+ local ignore_module = luaotfload.loaders.ignore
+
+ --[[doc--
+
+ Now that things are sorted out we can finally load the
+ fontloader.
+
+ --doc]]--
+
+ local fontloader = config.luaotfload and config.luaotfload.run.fontloader
+ or "reference"
+ fontloader = tostring (fontloader)
+
+ if fontloader == "reference" then
+ logreport ("log", 0, "init", "Using reference fontloader.")
+ load_fontloader_module (luaotfload.fontloader_package)
+
+ elseif fontloader == "default" then
+ --- Same as above but loader name not correctly replaced by the file name
+ --- of our fontloader package. Perhaps something’s wrong with the status
+ --- file which contains the datestamped filename? In any case, it can’t
+ --- hurt reporting it as a bug.
+ logreport ("both", 0, "init", "Fontloader substitution failed, got “default”.")
+ logreport ("log", 4, "init", "Falling back to reference fontloader.")
+ load_fontloader_module (luaotfload.fontloader_package)
+
+ elseif fontloader == "unpackaged" then
+ logreport ("log", 0, "init",
+ "Loading fontloader components individually.")
+ --- The loading sequence is known to change, so this might have to be
+ --- updated with future updates. Do not modify it though unless there is
+ --- a change to the upstream package!
+
+ --- Since 2.6 those are directly provided by the Lualibs package.
+ ignore_module "l-lua"
+ ignore_module "l-lpeg"
+ ignore_module "l-function"
+ ignore_module "l-string"
+ ignore_module "l-table"
+ ignore_module "l-io"
+ ignore_module "l-file"
+ ignore_module "l-boolean"
+ ignore_module "l-math"
+ ignore_module "util-str"
+ ignore_module "util-fil"
+ ignore_module "luatex-basics-gen"
+
+ load_fontloader_module "data-con"
+ load_fontloader_module "basics-nod"
+ load_fontloader_module "basics-chr"
+ load_fontloader_module "font-ini"
+ load_fontloader_module "fonts-mis"
+ load_fontloader_module "font-con"
+ load_fontloader_module "fonts-enc"
+ load_fontloader_module "font-cid"
+ load_fontloader_module "font-map"
+-- load_fontloader_module "fonts-syn" -- ignore?
+ load_fontloader_module "font-vfc"
+ load_fontloader_module "font-otr"
+ load_fontloader_module "font-oti"
+ load_fontloader_module "font-ott"
+ load_fontloader_module "font-cff"
+ load_fontloader_module "font-ttf"
+ load_fontloader_module "font-dsp"
+ load_fontloader_module "font-oup"
+ load_fontloader_module "font-otl"
+ load_fontloader_module "font-oto"
+ load_fontloader_module "font-otj"
+ load_fontloader_module "font-ota"
+ load_fontloader_module "font-ots"
+ load_fontloader_module "font-osd"
+ load_fontloader_module "font-ocl"
+ load_fontloader_module "font-otc"
+ load_fontloader_module "font-onr"
+ load_fontloader_module "font-one"
+ load_fontloader_module "font-afk"
+ load_fontloader_module "fonts-tfm"
+ load_fontloader_module "font-lua"
+ load_fontloader_module "font-def"
+ load_fontloader_module "fonts-def"
+ load_fontloader_module "fonts-ext"
+ load_fontloader_module "font-imp-tex"
+ load_fontloader_module "font-imp-ligatures"
+ load_fontloader_module "font-imp-italics"
+ load_fontloader_module "font-imp-effects"
+ load_fontloader_module "fonts-lig"
+ load_fontloader_module "fonts-gbn"
+
+ elseif fontloader == "context" then
+ logreport ("log", 0, "init",
+ "Loading Context modules in lookup path.")
+ load_context_modules ()
+
+ elseif lfsisdir (fontloader) then
+ logreport ("log", 0, "init",
+ "Loading Context files under prefix “%s”.",
+ fontloader)
+ load_context_modules (fontloader)
+
+ elseif lfs.isfile (fontloader) then
+ logreport ("log", 0, "init",
+ "Loading fontloader from absolute path “%s”.",
+ fontloader)
+ local _void = require (fontloader)
+
+ elseif kpsefind_file (fontloader) then
+ local path = kpsefind_file (fontloader)
+ logreport ("log", 0, "init",
+ "Loading fontloader “%s” from kpse-resolved path “%s”.",
+ fontloader, path)
+ local _void = require (path)
+
+ elseif kpsefind_file (("fontloader-%s.lua"):format(fontloader)) then
+ logreport ("log", 0, "init",
+ "Using predefined fontloader “%s”.",
+ fontloader)
+ load_fontloader_module (fontloader)
+
+ else
+ logreport ("both", 0, "init",
+ "No match for requested fontloader “%s”.",
+ fontloader)
+ fontloader = luaotfload.fontloader_package
+ logreport ("both", 0, "init",
+ "Defaulting to predefined fontloader “%s”.",
+ fontloader)
+ load_fontloader_module (fontloader)
+ end
+
+ ---load_fontloader_module "font-odv.lua" --- <= Devanagari support from Context
+
+ logreport ("log", 0, "init",
+ "Context OpenType loader version “%s”",
+ fonts.handlers.otf.version)
+end --- [init_main]
+
+local init_cleanup = function (store)
+ --- reinstate all the stuff we had to move out of the way to
+ --- accomodate the loader
+
+ --[[doc--
+
+ Here we adjust the globals created during font loader
+ initialization. If the second argument to
+ \luafunction{pop_namespaces()} is \verb|true| this will restore the
+ state of \luafunction{_G}, eliminating every global generated since
+ the last call to \luafunction{push_namespaces()}. At the moment we
+ see no reason to do this, and since the font loader is considered
+ an essential part of \identifier{luatex} as well as a very well
+ organized piece of code, we happily concede it the right to add to
+ \luafunction{_G} if needed.
+
+ --doc]]--
+
+ pop_namespaces (store.our_environment,
+ false,
+ store.context_environment)
+
+ --[[doc--
+
+ \subsection{Callbacks}
+ After the fontloader is ready we can restore the callback trap
+ from \identifier{luatexbase}.
+
+ --doc]]--
+
+ logreport ("log", 4, "init",
+ "Restoring original callback.register().")
+ callback.register = store.trapped_register
+end --- [init_cleanup]
+
+local init_post_install_callbacks = function ()
+ --[[doc--
+
+ we do our own callback handling with the means provided by
+ luatexbase.
+ note: \luafunction{pre_linebreak_filter} and
+ \luafunction{hpack_filter} are coupled in \context in the
+ concept of \emphasis{node processor}.
+
+ --doc]]--
+
+ -- MK Pass current text direction to simple_font_handler
+ local handler = nodes.simple_font_handler
+ local callback = function(head, groupcode, _, _, direction)
+ return handler(head, groupcode, nil, nil, direction or tex.get'textdir')
+ end
+ luatexbase.add_to_callback("pre_linebreak_filter",
+ callback,
+ "luaotfload.node_processor",
+ 1)
+ luatexbase.add_to_callback("hpack_filter",
+ callback,
+ "luaotfload.node_processor",
+ 1)
+ -- /MK
+end
+
+local init_post_load_agl = function ()
+
+ --[[doc--
+
+ Adobe Glyph List.
+ -----------------------------------------------------------------
+
+ Context provides a somewhat different font-age.lua from an
+ unclear origin. Unfortunately, the file name it reads from is
+ hard-coded in font-enc.lua, so we have to replace the entire
+ table.
+
+ This shouldn’t cause any complications. Due to its implementation
+ the glyph list will be loaded upon loading a OTF or TTF for the
+ first time during a TeX run. (If one sticks to TFM/OFM then it is
+ never read at all.) For this reason we can install a metatable
+ that looks up the file of our choosing and only falls back to the
+ Context one in case it cannot be found.
+
+ --doc]]--
+
+ local encodings = fonts.encodings
+
+ if not encodings then
+ --- Might happen during refactoring; we continue graciously but in
+ --- a somewhat defect state.
+ logreport ("log", 0, "init",
+ "preconditions unmet, skipping the Adobe Glyph List; "
+ .. "this is a Luaotfload bug.")
+ return
+ end
+
+ if next (fonts.encodings.agl) then
+ --- unnecessary because the file shouldn’t be loaded at this time
+ --- but we’re just making sure
+ fonts.encodings.agl = nil
+ collectgarbage"collect"
+ end
+
+ local agl_init = { } --- start out empty, fill on demand
+ encodings.agl = agl_init --- ugh, replaced again later
+
+ setmetatable (agl_init, { __index = function (t, k)
+
+ if k ~= "unicodes" then
+ return nil
+ end
+
+ local glyphlist = kpsefind_file "luaotfload-glyphlist.lua"
+ if glyphlist then
+ logreport ("log", 1, "init", "loading the Adobe glyph list")
+ else
+ glyphlist = kpsefind_file "font-age.lua"
+ logreport ("both", 0, "init",
+ "loading the extended glyph list from ConTeXt")
+ end
+
+ if not glyphlist then
+ logreport ("both", 4, "init",
+ "Adobe glyph list not found, please check your installation.")
+ return nil
+ end
+ logreport ("both", 4, "init",
+ "found Adobe glyph list file at ``%s``, using that.",
+ glyphlist)
+
+ local unicodes = dofile(glyphlist)
+ encodings.agl = { unicodes = unicodes }
+ return unicodes
+ end })
+
+end
+
+--- (unit -> unit) list
+local init_post_actions = {
+ init_post_install_callbacks,
+ init_post_load_agl,
+}
+
+--- unit -> size_t
+local init_post = function ()
+ --- hook for actions that need to take place after the fontloader is
+ --- installed
+
+ local n = #init_post_actions
+ for i = 1, n do
+ local action = init_post_actions[i]
+ local taction = type (action)
+ if not action or taction ~= "function" then
+ logreport ("both", 1, "init",
+ "post hook WARNING: action %d not a function but %s/%s; ignoring.",
+ i, action, taction)
+ else
+ --- call closure
+ action ()
+ end
+ end
+
+ return n
+end --- [init_post]
+
+return {
+ early = init_early,
+ main = function (store)
+ local starttime = os.gettimeofday ()
+ store.our_environment, store.context_environment = init_adapt ()
+ init_main ()
+ init_cleanup (store)
+ logreport ("both", 1, "init",
+ "fontloader loaded in %0.3f seconds",
+ os.gettimeofday() - starttime)
+ local n = init_post ()
+ logreport ("both", 5, "init", "post hook terminated, %d actions performed", n)
+ return true
+ end
+}
+
+-- vim:tw=79:sw=2:ts=2:expandtab
diff --git a/macros/luatex/generic/luaotfload/luaotfload-latex.pdf b/macros/luatex/generic/luaotfload/luaotfload-latex.pdf
new file mode 100644
index 0000000000..43bfb25a2b
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-latex.pdf
Binary files differ
diff --git a/macros/luatex/generic/luaotfload/luaotfload-latex.tex b/macros/luatex/generic/luaotfload/luaotfload-latex.tex
new file mode 100644
index 0000000000..8a68efd035
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-latex.tex
@@ -0,0 +1,530 @@
+% !Mode:: "TeX:EN:UTF-8:Main"
+\suppresslongerror1%% sigh ...
+%% Copyright (C) 2009-2018
+%%
+%% by Elie Roux <elie.roux@telecom-bretagne.eu>
+%% and Khaled Hosny <khaledhosny@eglug.org>
+%% and Philipp Gesang <phg@phi-gamma.net>
+%%
+%% This file is part of Luaotfload.
+%%
+%% Home: https://github.com/lualatex/luaotfload
+%% Support: <lualatex-dev@tug.org>.
+%%
+%% Luaotfload is under the GPL v2.0 (exactly) license.
+%%
+%% ----------------------------------------------------------------------------
+%%
+%% Luaotfload is free software; you can redistribute it and/or
+%% modify it under the terms of the GNU General Public License
+%% as published by the Free Software Foundation; version 2
+%% of the License.
+%%
+%% Luaotfload is distributed in the hope that it will be useful,
+%% but WITHOUT ANY WARRANTY; without even the implied warranty of
+%% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+%% GNU General Public License for more details.
+%%
+%% You should have received a copy of the GNU General Public License
+%% along with Luaotfload; if not, see <http://www.gnu.org/licenses/>.
+%%
+%% ----------------------------------------------------------------------------
+%%
+
+\documentclass{ltxdoc}
+
+\makeatletter
+
+\usepackage {metalogo,multicol,fancyvrb,xspace}
+\usepackage [x11names] {xcolor}
+
+\def \primarycolor {DodgerBlue4} %%-> rgb 16 78 139 | #104e8b
+\def \secondarycolor {Goldenrod4} %%-> rgb 139 105 200 | #8b6914
+
+\usepackage[
+ bookmarks=true,
+ colorlinks=true,
+ linkcolor=\primarycolor,
+ urlcolor=\secondarycolor,
+ citecolor=\primarycolor,
+ unicode,
+ pdftitle={The Luaotfload package},
+ pdfsubject={OpenType layout system for Plain TeX and LaTeX},
+ pdfauthor={Elie Roux \& Khaled Hosny \& Philipp Gesang \& Ulrike Fischer},
+ pdfkeywords={luatex, lualatex, unicode, opentype}
+]{hyperref}
+
+\usepackage {fontspec}
+\usepackage {unicode-math}
+
+\setmainfont[
+% Numbers = OldStyle, %% buggy with font cache
+ Ligatures = TeX,
+ BoldFont = {Linux Libertine O Bold},
+ ItalicFont = {Linux Libertine O Italic},
+ SlantedFont = {Linux Libertine O Italic},
+]{Linux Libertine O}
+\setmonofont[Ligatures=TeX,Scale=MatchLowercase]{InconsolataN-Regular.otf}
+%setsansfont[Ligatures=TeX]{Linux Biolinum O}
+\setsansfont[Ligatures=TeX,Scale=MatchLowercase]{IwonaMedium-Regular.otf}
+%setmathfont{XITS Math}
+
+\usepackage{hologo}
+
+\newcommand\TEX {\TeX\xspace}
+\newcommand\LUA {Lua\xspace}
+\newcommand\PDFTEX {pdf\TeX\xspace}
+\newcommand\LUATEX {Lua\TeX\xspace}
+\newcommand\XETEX {\XeTeX\xspace}
+\newcommand\LATEX {\LaTeX\xspace}
+\newcommand\LUALATEX {Lua\LaTeX\xspace}
+\newcommand\CONTEXT {Con\TeX t\xspace}
+\newcommand\OpenType {\identifier{Open\kern-.25ex Type}\xspace}
+
+%% \groupedcommand, with some omissions taken from syst-aux.mkiv
+\let \handlegroupnormalbefore \relax
+\let \handlegroupnormalafter \relax
+
+\protected \def \handlegroupnormal #1#2{%
+ \bgroup % 1
+ \def \handlegroupbefore {#1}%
+ \def \handlegroupafter {#2}%
+ \afterassignment \handlegroupnormalbefore
+ \let \next =
+}
+
+\def \handlegroupnormalbefore {%
+ \bgroup % 2
+ \handlegroupbefore
+ \bgroup % 3
+ \aftergroup \handlegroupnormalafter%
+}
+
+\def \handlegroupnormalafter {%
+ \handlegroupafter
+ \egroup % 3
+ \egroup % 2
+}
+
+\let \groupedcommand \handlegroupnormal %% only the two arg version
+
+\def \definehighlight [#1][#2]{%
+ \ifcsname #1\endcsname\else
+ \expandafter\def\csname #1\endcsname{%
+ \leavevmode
+ \groupedcommand {#2}\empty%
+ }
+ \fi%
+}
+
+%% old, simplistic definition: obsolete now that we have
+%% \groupedcommand
+%\def\definehighlight[#1][#2]%
+ %{\ifcsname #1\endcsname\else
+ %\expandafter\def\csname #1\endcsname%
+ %{\bgroup#2\csname #1_indeed\endcsname}
+ %\expandafter\def\csname #1_indeed\endcsname##1%
+ %{##1\egroup}%
+ %\fi}
+
+\def\restoreunderscore{\catcode`\_=12\relax}
+
+\definehighlight [fileent][\ttfamily\restoreunderscore] %% files, dirs
+\definehighlight [texmacro][\sffamily\itshape\textbackslash] %% cs
+\definehighlight [luaident][\sffamily\itshape\restoreunderscore] %% lua identifiers
+\definehighlight [identifier][\sffamily] %% names
+\definehighlight [abbrev][\rmfamily\scshape] %% acronyms
+\definehighlight [emphasis][\rmfamily\slshape] %% level 1 emph
+
+\definehighlight [Largefont][\Large] %% font size
+\definehighlight [smallcaps][\sc] %% font feature
+\definehighlight [nonproportional][\tt] %% font switch
+
+\newcommand*\email[1]{\href{mailto:#1}{#1}}
+
+\renewcommand\partname{Part}%% gets rid of the stupid “file” heading
+
+\usepackage{syntax}%% bnf for font request syntax
+
+\usepackage{titlesec}
+
+\def\movecountertomargin#1{\llap{\rmfamily\upshape#1\hskip2em}}
+\def\zeropoint{0pt}
+\titleformat \part
+ {\normalsize\rmfamily\bfseries}
+ {\movecountertomargin\thepart} \zeropoint {}
+\titleformat \section
+ {\normalsize\rmfamily\scshape}
+ {\movecountertomargin\thesection} \zeropoint {}
+\titleformat \subsection
+ {\small\rmfamily\itshape}
+ {\movecountertomargin\thesubsection} \zeropoint {}
+\titleformat \subsubsection
+ {\normalsize\rmfamily\upshape}
+ {\movecountertomargin\thesubsubsection} \zeropoint {}
+
+\usepackage{tocloft}
+\renewcommand \cftpartfont {\rmfamily\upshape}
+\renewcommand \cftsecfont {\rmfamily\upshape}
+\renewcommand \cftsubsecfont {\rmfamily\upshape}
+\setlength \cftbeforepartskip {1ex}
+\setlength \cftbeforesecskip {1ex}
+
+\VerbatimFootnotes
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% structurals
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\def \definestructural #1{%
+ \expandafter \let \csname end#1\endcsname \relax
+
+ \expandafter \def \csname begin#1\endcsname {%
+ \@ifnextchar[{\csname begin#1indeed\endcsname}
+ {\csname begin#1indeed\endcsname[]}%
+ }
+
+ \expandafter \def \csname begin#1indeed\endcsname [##1]##2{%
+ \edef \first {##1}%
+ \ifx \first \empty
+ \csname #1\endcsname [##2]{##2}%
+ \else
+ \csname #1\endcsname [\first]{##2}%
+ \fi
+ }
+}
+
+\definestructural {section}
+\definestructural {subsection}
+\definestructural {subsubsection}
+
+\def \fakesection #1{\section*{#1}}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% inline verbatim
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+%% Context offers both \type{…} and \type<<…>>, but not an unbalanced
+%% one that we could map directly onto Latex’s \verb|…|.
+\usepackage{pdfpages}
+\usepackage {listings}
+\usepackage {luatexbase}
+\lstset {
+ basicstyle=\ttfamily,
+}
+
+%\let \inlinecode \lstinline
+\protected \def \inlinecode {\lstinline}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% codelistings; this sucks hard since we lack access to buffers
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\newcount \othercatcode \othercatcode 12
+\newcount \activecatcode \othercatcode 13
+
+\newcatcodetable \vrbcatcodes
+\setcatcodetable \vrbcatcodes {%
+ \catcodetable \CatcodeTableIniTeX
+ \catcode 9 \othercatcode %% \tabasciicode
+ \catcode 13 \othercatcode %% \endoflineasciicode
+ \catcode 12 \othercatcode %% \formfeedasciicode
+ \catcode 26 \othercatcode %% \endoffileasciicode
+ \catcode 32 \othercatcode %% \spaceasciicode
+}
+
+\directlua {
+ document = document or { }
+ document.vrbcatcodesidx = tonumber (\the \vrbcatcodes)
+}
+
+\newcatcodetable \literalcatcodes
+\setcatcodetable \literalcatcodes {%
+ \catcodetable \CatcodeTableString
+ \catcode 32 \activecatcode %% \spaceasciicode
+}
+
+\def \listingsurroundskip {\vskip \baselineskip}
+
+\def \beginlisting {%
+ \noindent
+ \begingroup
+ \catcodetable \vrbcatcodes
+ \beginlistingindeed%
+}
+
+\directlua {
+ local texsprint = tex.sprint
+ local stringis_empty = string.is_empty
+ local stringsub = string.sub
+ local stringgsub = string.gsub
+ %local backslash = unicode.utf8.char (0x200c)
+ local backslash = unicode.utf8.char (0x5c)
+ local escaped = [[\string\string\string\]]
+ document.printlines = function (buffer)
+ local lines = string.explode (buffer, "\noexpand\n")
+ print ""
+ for i, line in next, lines do
+ local line = stringgsub (line, backslash, escaped)
+ if stringis_empty (line) then
+ print (i, "listing: <empty line />")
+ texsprint [[\string\listingpar]]
+ else
+ local line = [[\string\beginlistingline]]
+ .. line
+ .. [[\string\endlistingline]]
+ .. [[\string\listingpar]]
+ print (i, "listing: «" .. line .. "»")
+ texsprint (document.vrbcatcodesidx, line)
+ end
+ end
+ end
+}
+
+\def \listingpar {\endgraf}
+
+\let \endlistingline \relax
+\let \endlisting \relax
+
+\protected \def \beginlistingline{%
+ \leavevmode
+ \begingroup
+ \beginlistinglineindeed%
+}
+
+\def \beginlistinglineindeed #1\endlistingline{%
+ \endgroup
+ \hbox{%
+ \addfontfeature {RawFeature=-tlig;-liga}%% So one can’t just turn them all off at once using the ``Ligatures`` key?
+ \obeyspaces
+ #1}%
+}
+
+\def \beginlistingindeed#1\endlisting{%
+ \endgroup
+ \begingroup
+ \endgraf
+ \listingsurroundskip
+ \ttfamily
+ \small
+ \parindent = 0em
+ \leftskip = 2em
+ \hangindent = 2em
+ \directlua{document.printlines ([==[\detokenize {#1}]==])}%
+ \listingsurroundskip
+ \endgroup
+}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% enumerations and lists
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\def \definelist [#1]#2{% name, itemcode
+ \expandafter \def \csname begin#1\endcsname {%
+ \begin {itemize}
+ \let \normalitem = \item
+ \def \altitem ####1{%
+ \def \first {####1}%
+ #2
+ }
+ \let \beginnormalitem \item
+ \let \endnormalitem \relax
+ \let \beginaltitem \altitem
+ \let \endaltitem \relax
+ }
+
+ \expandafter \def \csname end#1\endcsname {%
+ \end {itemize}
+ }
+}
+
+\definelist [descriptions]{\normalitem {\textbf \first}\hfill\break}
+\definelist [definitions]{\normalitem {\fileent {\first}}}
+\definelist [filelist]{\normalitem {\fileent {\first}}\space--\hskip 1em}
+\definelist [functionlist]{\normalitem {\luaident {\first}}\hfill\break}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% columns
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\def \begindoublecolumns {\begin {multicols} {2}}
+\def \enddoublecolumns {\end {multicols}}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% alignment
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\def \begincentered {\begin {center}}
+\def \endcentered {\end {center}}
+
+\def \beginnarrower {\begin {quote}}
+\def \endnarrower {\end {quote}}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% special elements
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\let \beginfrontmatter \relax
+\let \endfrontmatter \relax
+
+\def \beginabstractcontent {\begin {abstract}}
+\def \endabstractcontent {\end {abstract}}
+
+\let \setdocumenttitle \title
+\let \setdocumentdate \date
+\let \setdocumentauthor \author
+\let \typesetdocumenttitle \maketitle
+
+\AtBeginDocument {%% seriously?
+ \let \typesetcontent \tableofcontents%
+}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% floats
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+%% syntax definition
+\def \beginsyntaxfloat #1#2{%% #1:label #2:caption
+ \begin {figure} [b]
+ \edef \syntaxlabel {#1}%
+ \def \syntaxcaption {#2}%
+ \setlength\grammarparsep{0pt plus 2pt minus 2pt}%
+ \setlength\grammarindent{5cm}%
+ \begingroup
+ \small
+ \begin {grammar}
+}
+
+\def \endsyntaxfloat {%
+ \end {grammar}
+ \endgroup
+ \caption \syntaxcaption
+ \label \syntaxlabel
+ \end {figure}
+}
+
+%% figures, e.g. the file graph
+\def \figurefloat #1#2#3{%% #1:label #2:caption #3:file
+ \begin {figure} [b]
+ \caption {#2}%
+ \includegraphics[width=\textwidth]{#3}%
+ \label {#1}
+ \end {figure}
+}
+
+%% tables
+\def \tablefloat #1#2{%% #1:label #2:caption
+ \begin {table} [t]
+ \hrule
+ \caption {#2}%
+ \label {#1}
+ \hrule
+ \end {table}
+}
+
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% hyperlinks
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\protected \def \hyperlink{%
+ \@ifnextchar[{\hyperlinkindeed}%
+ {\hyperlinkindeed[]}%
+}
+
+\def \hyperlinkindeed [#1]#2{%
+ \def \first {#1}%
+ \ifx \first \empty
+ \url {#2}%
+ \else
+ \href {#2}{#1}%
+ \fi%
+}
+
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% tables
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% Our tables aren’t anything special so we stick with “tabular” on the
+%% Latex end.
+%%
+%% This is going to be largely incompatible with Context since format
+%% specifications work quite differently (even between different
+%% Context table variants).
+
+\def \begintabulate [#1]#2\endtabulate{%
+ \begingroup
+ \let \beginrow = \relax %% -> \NC in Context
+ \let \newcell = & %% -> \NC
+ \let \endrow = \cr %% -> \NC \NR
+ \begin {tabular}{#1}%
+ #2
+ \end {tabular}
+ \endgroup
+}
+
+\let \endtabulate \relax
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% escaped characters
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\let \charpercent \textpercent
+\let \charbackslash \textbackslash
+\let \chartilde \textasciitilde
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% main
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\makeatother
+
+\newif \ifcontextmkiv \contextmkivfalse
+
+\usepackage{luacode}
+
+% a few lua functions to grab the file lists.
+\begin{luacode}
+require("luaotfload-filelist.lua")
+
+function printctxlibslist ()
+ t= luaotfload.filelist.selectctxlibsentries (luaotfload.filelist.data)
+ for i,v in ipairs (t) do
+ tex.sprint("\\beginaltitem {"..v.name.. v.ext.."}\\endaltitem")
+ end
+end
+
+function printctxallgenericlist ()
+ t= luaotfload.filelist.selectctxgeneentries (luaotfload.filelist.data)
+ for i,v in ipairs (t) do
+ tex.sprint("\\beginaltitem {"..v.ctxpref..v.name..v.ext.."}\\endaltitem")
+ end
+end
+
+function printctxfontlist ()
+ t= luaotfload.filelist.selectctxfontentries (luaotfload.filelist.data)
+ for i,v in ipairs (t) do
+ tex.sprint("\\beginaltitem {"..v.name..v.ext.."}\\endaltitem")
+ end
+end
+\end{luacode}
+
+
+\begin {document}
+ \input {luaotfload-main.tex}
+\clearpage
+\includepdf[fitpaper,pagecommand={\label{file-graph}}]{filegraph}
+\clearpage
+
+\includepdf[pages=1,pagecommand={\phantomsection\addcontentsline{toc}{section}{Appendix: Manual of luaotfload.conf}{\thepage}{}}]{luaotfload-conf.pdf}
+\includepdf[pages=2-]{luaotfload-conf.pdf}
+
+\clearpage
+
+\includepdf[pages=1,pagecommand={\phantomsection\addcontentsline{toc}{section}{Appendix: Manual of luaotfload-tool}{\thepage}{}
+}]{luaotfload-tool.pdf}
+\includepdf[pages=2-]{luaotfload-tool.pdf}
+
+\end {document}
+
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload-letterspace.lua b/macros/luatex/generic/luaotfload/luaotfload-letterspace.lua
new file mode 100644
index 0000000000..1acf67df8b
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-letterspace.lua
@@ -0,0 +1,578 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-letterspace.lua
+-- DESCRIPTION: part of luaotfload / letterspacing
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-letterspace",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / color",
+ license = "GPL v2.0",
+ copyright = "PRAGMA ADE / ConTeXt Development Team",
+ author = "Hans Hagen, PRAGMA-ADE, Hasselt NL; adapted by Philipp Gesang, Ulrike Fischer, Marcel Krüger"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+--- This code diverged quite a bit from its origin in Context. Please
+--- do *not* report bugs on the Context list.
+
+local logreport = luaotfload.log.report
+
+local getmetatable = getmetatable
+local setmetatable = setmetatable
+local tonumber = tonumber
+local unpack = table.unpack
+
+local next = next
+local node, fonts = node, fonts
+
+local nodedirect = node.direct
+
+local getfield = nodedirect.getfield
+local setfield = nodedirect.setfield
+
+local getfont = nodedirect.getfont
+local getid = nodedirect.getid
+
+local getnext = nodedirect.getnext
+local setnext = nodedirect.setnext
+
+local getprev = nodedirect.getprev
+local setprev = nodedirect.setprev
+
+local getboth = nodedirect.getboth
+
+local setlink = nodedirect.setlink
+
+local getdisc = nodedirect.getdisc
+local setdisc = nodedirect.setdisc
+
+local getsubtype = nodedirect.getsubtype
+local setsubtype = nodedirect.setsubtype
+
+local getchar = nodedirect.getchar
+local setchar = nodedirect.setchar
+
+local getkern = nodedirect.getkern
+local setkern = nodedirect.setkern
+
+local getglue = nodedirect.getglue
+local setglue = nodedirect.setglue
+
+local find_node_tail = nodedirect.tail
+local todirect = nodedirect.todirect
+local tonode = nodedirect.tonode
+
+local insert_node_before = nodedirect.insert_before
+local free_node = nodedirect.free
+local copy_node = nodedirect.copy
+local new_node = nodedirect.new
+
+local glyph_code = node.id"glyph"
+local kern_code = node.id"kern"
+local disc_code = node.id"disc"
+local glue_code = node.id"glue"
+local whatsit_code = node.id"whatsit"
+
+local fonthashes = fonts.hashes
+local identifiers = fonthashes.identifiers
+local chardata = fonthashes.characters
+local otffeatures = fonts.constructors.newfeatures "otf"
+
+local function getprevreal(n)
+ repeat
+ n = getprev(n)
+ until not n or getid(n) ~= whatsit_code
+ return n
+end
+local function getnextreal(n)
+ repeat
+ n = getnext(n)
+ until not n or getid(n) ~= whatsit_code
+ return n
+end
+
+--[[doc--
+
+ Since the letterspacing method was derived initially from Context’s
+ typo-krn.lua we keep the sub-namespace “letterspace” inside the
+ “luaotfload” table.
+
+--doc]]--
+
+luaotfload.letterspace = luaotfload.letterspace or { }
+local letterspace = luaotfload.letterspace
+
+local lectured = false
+letterspace.keepligature = true
+letterspace.keeptogether = false
+letterspace.keepwordspacing = false
+
+---=================================================================---
+--- preliminary definitions
+---=================================================================---
+-- We set up a layer emulating some Context internals that are needed
+-- for the letterspacing callback.
+-----------------------------------------------------------------------
+--- node-ini
+-----------------------------------------------------------------------
+
+local kerning_code = 0
+local userkern_code = 1
+local userskip_code = 0
+local spaceskip_code = 13
+local xspaceskip_code = 14
+
+if not chardata then
+ chardata = { }
+ table.setmetatableindex(chardata, function(t, k)
+ if k == true then
+ return chardata[currentfont()]
+ else
+ local tfmdata = font.getfont(k) or font.fonts[k]
+ if tfmdata then
+ local characters = tfmdata.characters
+ t[k] = characters
+ return characters
+ end
+ end
+ end)
+ fonthashes.characters = chardata
+end
+
+---=================================================================---
+--- character kerning functionality
+---=================================================================---
+
+-- UF changed 2017-07-14
+local kern_injector = function (fillup, kern)
+ if fillup then
+ local g = new_node(glue_code)
+ setglue(g, 0, kern, 0, 1, 0)
+ return g
+ end
+ local g = new_node(kern_code)
+ setkern(g,kern)
+ return g
+end
+-- /UF
+
+local kernable_skip = function (n)
+ local st = getsubtype (n)
+ return st == userskip_code
+ or st == spaceskip_code
+ or st == xspaceskip_code
+end
+
+--[[doc--
+
+ Caveat lector.
+ This is an adaptation of the Context character kerning mechanism
+ that emulates XeTeX-style fontwise letterspacing. Note that in its
+ present state it is far inferior to the original, which is
+ attribute-based and ignores font-boundaries. Nevertheless, due to
+ popular demand the following callback has been added.
+
+--doc]]--
+
+local kernamounts = table.setmetatableindex(function (t, f) --- fontid -> {kern, fill}
+ local tfmdata = font.getfont(f) or font.fonts[f]
+ if tfmdata then
+ local fontproperties = tfmdata.properties
+ local fontparameters = tfmdata.parameters
+ if fontproperties and fontparameters then
+ local r
+ if fontproperties.kerncharacters == "max" then
+ r = {fontparameters.quad/4, true}
+ elseif fontproperties.kerncharacters then
+ r = {fontproperties.kerncharacters * fontparameters.quad, false}
+ else
+ r = {}
+ end
+ t[f] = r
+ return r
+ end
+ end
+ return {}
+end)
+
+local kerncharacters
+kerncharacters = function (head)
+ local start = head
+ local lastfont = nil
+ local keeptogether = letterspace.keeptogether --- function
+ local keepligature = letterspace.keepligature
+-- if not lectured and keepligature ~= true then
+-- logreport ("both", 0, "letterspace",
+-- "Breaking ligatures through letterspacing is deprecated and "
+-- .. "will be removed soon. Please disable unwanted ligatures through "
+-- .. "font features instead and reset luaotfload.letterspace.keepligature "
+-- .. "to true to maintain compatibility with future versions of luaotfload.")
+-- lectured = true
+-- end
+ if type(keepligature) ~= "function" then
+ local savedligature = keepligature
+ keepligature = function() return savedligature end
+ end
+ local keepwordspacing = letterspace.keepwordspacing
+ if type(keepwordspacing) ~= "function" then
+ local savedwordspacing = keepwordspacing
+ keepwordspacing = function() return savedwordspacing end
+ end
+
+ local kernamounts = kernamounts
+ local firstkern = true
+
+ while start do
+ local id = getid(start)
+ if id == glyph_code then
+ --- 1) look up kern factor (slow, but cached rudimentarily)
+ local fontid = getfont(start)
+ local krn, fillup = unpack(kernamounts[fontid])
+ if not krn or krn == 0 then
+ firstkern = true
+ goto nextnode
+ elseif firstkern then
+ firstkern = false
+ if (id ~= disc_code) and (not getfield(start, "components")) then
+ --- not a ligature, skip node
+ goto nextnode
+ end
+ end
+
+ lastfont = fontid
+
+ --- 2) resolve ligatures
+ local c = getfield(start, "components")
+
+ if c then
+ if keepligature(start) then
+ -- keep 'm
+ c = nil
+ else
+ while c do
+ local s = start
+ local p, n = getboth (s)
+ if p then
+ setlink (p, c)
+ else
+ head = c
+ end
+ if n then
+ local tail = find_node_tail(c)
+ setlink (tail, n)
+ end
+ start = c
+ setfield(s, "components", nil)
+ free_node(s) --> double free with multipart components
+ c = getfield (start, "components")
+ end
+ end
+ end -- kern ligature
+
+ --- 3) apply the extra kerning
+ local prev = getprevreal(start)
+ if prev then
+ local pid = getid(prev)
+
+ if not pid then
+ -- nothing
+
+ elseif pid == glue_code and kernable_skip(prev)
+ and not keepwordspacing(prev, lastfont) then
+ local wd, stretch, shrink = getglue(prev)
+ if wd > 0 then
+ local newwd = wd + krn
+ local stretched = (stretch * newwd) / wd
+ local shrunk = (shrink * newwd) / wd
+ if fillup then
+ setglue(prev, newwd, 2 * stretched, 2 * shrunk, 1, 0)
+ else
+ setglue(prev, newwd, stretched, shrunk, 0, 0)
+ end
+ end
+
+ elseif pid == kern_code then
+ local prev_subtype = getsubtype(prev)
+ if prev_subtype == kerning_code --- context does this by means of an
+ or prev_subtype == userkern_code --- attribute; we may need a test
+ then
+
+ local pprev = getprevreal(prev)
+ local pprev_id = getid(pprev)
+
+ if keeptogether
+ and pprev_id == glyph_code
+ and keeptogether(pprev, start)
+ then
+ -- keep
+ else
+ setsubtype (prev, userkern_code)
+ local prev_kern = getkern(prev)
+ prev_kern = prev_kern + krn
+ setkern (prev, prev_kern)
+ end
+ end
+
+ elseif pid == glyph_code then
+ if getfont(prev) == lastfont then
+ local prevchar = getchar(prev)
+ local lastchar = getchar(start)
+ if keeptogether and keeptogether(prev, start) then
+ -- keep 'm
+ elseif identifiers[lastfont] then
+ local lastfontchars = chardata[lastfont]
+ if lastfontchars then
+ local prevchardata = lastfontchars[prevchar]
+ if not prevchardata then
+ --- font doesn’t contain the glyph
+ else
+ local kern = 0
+ local kerns = prevchardata.kerns
+ if kerns then kern = kerns[lastchar] or kern end
+ krn = kern + krn -- here
+ insert_node_before(head,start,kern_injector(fillup,krn))
+ end
+ end
+ end
+ else
+ insert_node_before(head,start,kern_injector(fillup,krn))
+ end
+
+ elseif pid == disc_code then
+ local disc = prev -- disc
+ local pre, post, replace = getdisc (disc)
+ local prv = getprevreal(disc)
+ local nxt = getnextreal(disc)
+
+ if pre and prv then -- must pair with start.prev
+ -- this one happens in most cases
+ local before = copy_node(prv)
+ setprev(pre, before)
+ setnext(before, pre)
+ setprev(before, nil)
+ pre = kerncharacters (before)
+ pre = getnext(pre)
+ setprev(pre, nil)
+ setfield(disc, "pre", pre)
+ free_node(before)
+ end
+
+ if post and nxt then -- must pair with start
+ local after = copy_node(nxt)
+ local tail = find_node_tail(post)
+ setnext(tail, after)
+ setprev(after, tail)
+ post = kerncharacters (post)
+ setnext(getprev(after), nil)
+ setfield(disc, "post", post)
+ free_node(after)
+ end
+
+ if replace and prv and nxt then -- must pair with start and start.prev
+ local before = copy_node(prv)
+ local after = copy_node(nxt)
+ local tail = find_node_tail(replace)
+ setprev(replace, before)
+ setnext(before, replace)
+ setprev(before, nil)
+ setnext(tail, after)
+ setprev(after, tail)
+ setnext(after, nil)
+ replace = kerncharacters (before)
+ replace = getnext(replace)
+ setprev(replace, nil)
+ setnext(getprev(after), nil)
+ setfield(disc, "replace", replace)
+ free_node(after)
+ free_node(before)
+
+ elseif identifiers[lastfont] then
+ if prv
+ and getid(prv) == glyph_code
+ and getfont(prv) == lastfont
+ then
+ local kern = 0
+ local prevchar = getchar(prv)
+ local lastchar = getchar(start)
+ local lastfontchars = chardata[lastfont]
+ if lastfontchars then
+ local prevchardata = lastfontchars[prevchar]
+ if not prevchardata then
+ --- font doesn’t contain the glyph
+ else
+ local kerns = prevchardata.kerns
+ if kerns then kern = kerns[lastchar] or kern end
+ end
+ end
+ krn = kern + krn -- here
+ end
+ setfield(disc, "replace", kern_injector(false, krn))
+ end --[[if replace and prv and nxt]]
+ end --[[if not pid]]
+ end --[[if prev]]
+ end --[[if id == glyph_code]]
+
+ ::nextnode::
+ if start then
+ start = getnext(start)
+ end
+ end
+ return head
+end
+
+---=================================================================---
+--- integration
+---=================================================================---
+
+--- · callback: kerncharacters
+--- · enabler: enablefontkerning
+
+--- callback wrappers
+
+--- (node_t -> node_t) -> string -> string list -> bool
+local registered_as = { } --- procname -> callbacks
+local add_processor = function (processor, name, ...)
+ local callbacks = { ... }
+ for i=1, #callbacks do
+ luatexbase.add_to_callback(callbacks[i], processor, name)
+ end
+ registered_as[name] = callbacks --- for removal
+ return true
+end
+
+--- string -> bool
+local remove_processor = function (name)
+ local callbacks = registered_as[name]
+ if callbacks then
+ for i=1, #callbacks do
+ luatexbase.remove_from_callback(callbacks[i], name)
+ end
+ return true
+ end
+ return false --> unregistered
+end
+
+--- When font kerning is requested, usually by defining a font with the
+--- ``letterspace`` parameter, we inject a wrapper for the
+--- ``kerncharacters()`` node processor in the relevant callbacks. This
+--- wrapper initially converts the received head node into its “direct”
+--- counterpart. Likewise, the callback result is converted back to an
+--- ordinary node prior to returning. Internally, ``kerncharacters()``
+--- performs all node operations on direct nodes.
+
+--- unit -> bool
+local enablefontkerning = function ( )
+
+ local handler = function (hd)
+ local direct_hd = todirect (hd)
+ logreport ("term", 5, "letterspace",
+ "kerncharacters() invoked with node.direct interface \z
+ (``%s`` -> ``%s``)", tostring (hd), tostring (direct_hd))
+ local direct_hd = kerncharacters (direct_hd)
+ if not direct_hd then --- bad
+ logreport ("both", 0, "letterspace",
+ "kerncharacters() failed to return a valid new head")
+ end
+ return tonode (direct_hd)
+ end
+
+ return add_processor( handler
+ , "luaotfload.letterspace"
+ , "pre_linebreak_filter"
+ , "hpack_filter")
+end
+
+--[[doc--
+
+ Fontwise kerning is enabled via the “kernfactor” option at font
+ definition time. Unlike the Context implementation which relies on
+ Luatex attributes, it uses a font property for passing along the
+ letterspacing factor of a node.
+
+ The callback is activated the first time a letterspaced font is
+ requested and stays active until the end of the run. Since the font
+ is a property of individual glyphs, every glyph in the entire
+ document must be checked for the kern property. This is quite
+ inefficient compared to Context’s attribute based approach, but Xetex
+ compatibility reduces our options significantly.
+
+--doc]]--
+
+
+local fontkerning_enabled = false --- callback state
+
+--- fontobj -> float -> unit
+local initializefontkerning = function (tfmdata, factor)
+ if factor ~= "max" then
+ factor = tonumber (factor) or 0
+ end
+ if factor == "max" or factor ~= 0 then
+ local fontproperties = tfmdata.properties
+ if fontproperties then
+ --- hopefully this field stays unused otherwise
+ fontproperties.kerncharacters = factor
+ end
+ if not fontkerning_enabled then
+ fontkerning_enabled = enablefontkerning ()
+ end
+ end
+end
+
+--- like the font colorization, fontwise kerning is hooked into the
+--- feature mechanism
+
+otffeatures.register {
+ name = "kernfactor",
+ description = "kernfactor",
+ initializers = {
+ base = initializefontkerning,
+ node = initializefontkerning,
+ }
+}
+
+--[[doc--
+
+ The “letterspace” feature is essentially identical with the above
+ “kernfactor” method, but scales the factor to percentages to match
+ Xetex’s behavior. (See the Xetex reference, page 5, section 1.2.2.)
+
+ Since Xetex doesn’t appear to have a (documented) “max” keyword, we
+ assume all input values are numeric.
+
+--doc]]--
+
+local initializecompatfontkerning = function (tfmdata, percentage)
+ local factor = tonumber (percentage)
+ if not factor then
+ logreport ("both", 0, "letterspace",
+ "Invalid argument to letterspace: %s (type %q), " ..
+ "was expecting percentage as Lua number instead.",
+ percentage, type (percentage))
+ return
+ end
+ return initializefontkerning (tfmdata, factor * 0.01)
+end
+
+otffeatures.register {
+ name = "letterspace",
+ description = "letterspace",
+ initializers = {
+ base = initializecompatfontkerning,
+ node = initializecompatfontkerning,
+ }
+}
+
+--[[example--
+
+See https://bitbucket.org/phg/lua-la-tex-tests/src/tip/pln-letterspace-8-compare.tex
+for an example.
+
+--example]]--
+
+--- vim:sw=2:ts=2:expandtab:tw=71
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload-loaders.lua b/macros/luatex/generic/luaotfload/luaotfload-loaders.lua
new file mode 100644
index 0000000000..39ffd243f7
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-loaders.lua
@@ -0,0 +1,240 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-loaders.lua
+-- DESCRIPTION: Luaotfload callback handling
+-- REQUIREMENTS: luatex v.0.80 or later; package lualibs
+-- AUTHOR: Philipp Gesang <phg@phi-gamma.net>
+-- AUTHOR: Hans Hagen, Khaled Hosny, Elie Roux, David Carlisle
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-loaders",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / callback handling",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+-----------------------------------------------------------------------
+
+
+
+if not lualibs then error "this module requires Luaotfload" end
+if not luaotfload then error "this module requires Luaotfload" end
+
+local logreport = luaotfload.log and luaotfload.log.report or print
+
+local lua_reader = function (specification)
+ local fullname = specification.filename or ""
+ if fullname == "" then
+ local forced = specification.forced or ""
+ if forced ~= "" then
+ fullname = specification.name .. "." .. forced
+ else
+ fullname = specification.name
+ end
+ end
+ local fullname = resolvers.findfile (fullname) or ""
+ if fullname ~= "" then
+ local loader = loadfile (fullname)
+ loader = loader and loader ()
+ return loader and loader (specification)
+ end
+end
+
+local eval_reader = function (specification)
+ local eval = specification.eval
+ if not eval or type (eval) ~= "function" then return nil end
+ logreport ("both", 0, "loaders",
+ "eval: found tfmdata for “%s”, injecting.",
+ specification.name)
+ return eval ()
+end
+
+local unsupported_reader = function (format)
+ return function (specification)
+ logreport ("both", 4, "loaders",
+ "font format “%s” unsupported; cannot load %s.",
+ format, tostring (specification.name))
+ end
+end
+
+local type1_reader = fonts.readers.afm
+local tfm_reader = fonts.readers.tfm
+
+local install_formats = function ()
+ local fonts = fonts
+ if not fonts then return false end
+
+ local readers = fonts.readers
+ local sequence = readers.sequence
+ local seqset = table.tohash (sequence)
+ local formats = fonts.formats
+ if not readers or not formats then return false end
+
+ local aux = function (which, reader)
+ if not which or type (which) ~= "string"
+ or not reader or type (reader) ~= "function" then
+ logreport ("both", 2, "loaders", "Error installing reader for “%s”.", which)
+ return false
+ end
+ formats [which] = "type1"
+ readers [which] = reader
+ if not seqset [which] then
+ logreport ("both", 3, "loaders",
+ "Extending reader sequence for “%s”.", which)
+ sequence [#sequence + 1] = which
+ seqset [which] = true
+ end
+ return true
+ end
+
+ return aux ("evl", eval_reader)
+ and aux ("lua", lua_reader)
+ and aux ("pfa", unsupported_reader "pfa")
+ and aux ("afm", type1_reader)
+ and aux ("pfb", type1_reader)
+ and aux ("tfm", tfm_reader)
+ and aux ("ofm", tfm_reader)
+ and aux ("dfont", unsupported_reader "dfont")
+end
+
+local not_found_msg = function (specification, size, id)
+ logreport ("both", 0, "loaders", "")
+ logreport ("both", 0, "loaders",
+ "--------------------------------------------------------")
+ logreport ("both", 0, "loaders", "")
+ logreport ("both", 0, "loaders", "Font definition failed for:")
+ logreport ("both", 0, "loaders", "")
+ logreport ("both", 0, "loaders", " > id : %d", id)
+ logreport ("both", 0, "loaders", " > specification : %q", specification)
+ if size > 0 then
+ logreport ("both", 0, "loaders", " > size : %.2f pt", size / 2^16)
+ end
+ logreport ("both", 0, "loaders", "")
+ logreport ("both", 0, "loaders",
+ "--------------------------------------------------------")
+end
+--[[doc--
+
+ \subsection{\CONTEXT override}
+ \label{define-font}
+ We provide a simplified version of the original font definition
+ callback.
+
+--doc]]--
+
+
+local definers --- (string, spec -> size -> id -> tmfdata) hash_t
+do
+ local read = fonts.definers.read
+
+ local patch = function (specification, size, id)
+ local fontdata = read (specification, size, id)
+----if not fontdata then not_found_msg (specification, size, id) end
+ if type (fontdata) == "table" and fontdata.encodingbytes == 2 then
+ --- We need to test for `encodingbytes` to avoid passing
+ --- tfm fonts to `patch_font`. These fonts are fragile
+ --- because they use traditional TeX font handling.
+ luatexbase.call_callback ("luaotfload.patch_font", fontdata, specification, id)
+ else
+ luatexbase.call_callback ("luaotfload.patch_font_unsafe", fontdata, specification, id)
+ end
+ return fontdata
+ end
+
+ local mk_info = function (name)
+ local definer = name == "patch" and patch or read
+ return function (specification, size, id)
+ logreport ("both", 0, "loaders", "defining font no. %d", id)
+ logreport ("both", 0, "loaders", " > active font definer: %q", name)
+ logreport ("both", 0, "loaders", " > spec %q", specification)
+ logreport ("both", 0, "loaders", " > at size %.2f pt", size / 2^16)
+ local result = definer (specification, size, id)
+ if not result then return not_found_msg (specification, size, id) end
+ if type (result) == "number" then
+ logreport ("both", 0, "loaders", " > font definition yielded id %d", result)
+ return result
+ end
+ logreport ("both", 0, "loaders", " > font definition successful")
+ logreport ("both", 0, "loaders", " > name %q", result.name or "<nil>")
+ logreport ("both", 0, "loaders", " > fontname %q", result.fontname or "<nil>")
+ logreport ("both", 0, "loaders", " > fullname %q", result.fullname or "<nil>")
+ logreport ("both", 0, "loaders", " > type %s", result.type or "<nil>")
+ local spec = result.specification
+ if spec then
+ logreport ("both", 0, "loaders", " > file %q", spec.filename or "<nil>")
+ logreport ("both", 0, "loaders", " > subfont %s", spec.sub or "<nil>")
+ end
+ return result
+ end
+ end
+
+ definers = {
+ patch = patch,
+ generic = read,
+ info_patch = mk_info "patch",
+ info_generic = mk_info "generic",
+ }
+end
+
+--[[doc--
+
+ We create callbacks for patching fonts on the fly, to be used by
+ other packages. In addition to the regular \identifier{patch_font}
+ callback there is an unsafe variant \identifier{patch_font_unsafe}
+ that will be invoked even if the target font lacks certain essential
+ tfmdata tables.
+
+ The callbacks initially contain the empty function that we are going
+ to override below.
+
+--doc]]--
+
+local purge_define_font = function ()
+ local cdesc = luatexbase.callback_descriptions "define_font"
+ --- define_font is an “exclusive” callback, meaning that there can
+ --- only ever be one entry. Everything beyond that would indicate
+ --- that something is broken.
+ local _, d = next (cdesc)
+ if d then
+ local i, d2 = next (cdesc, 1)
+ if d2 then --> issue warning
+ logreport ("both", 0, "loaders",
+ "Callback table for define_font contains multiple entries: \z
+ { [%d] = “%s” } -- seems fishy.", i, d2)
+ end
+ logreport ("log", 0, "loaders",
+ "Entry ``%s`` present in define_font callback; overriding.", d)
+ luatexbase.remove_from_callback ("define_font", d)
+ end
+end
+
+local install_callbacks = function ()
+ local create_callback = luatexbase.create_callback
+ local dummy_function = function () end
+ create_callback ("luaotfload.patch_font", "simple", dummy_function)
+ create_callback ("luaotfload.patch_font_unsafe", "simple", dummy_function)
+ purge_define_font ()
+ local definer = config.luaotfload.run.definer
+ luatexbase.add_to_callback ("define_font",
+ definers[definer or "patch"],
+ "luaotfload.define_font",
+ 1)
+ return true
+end
+
+return function ()
+ if not install_formats () then
+ logreport ("log", 0, "loaders", "Error initializing OFM/PF{A,B} loaders.")
+ return false
+ end
+ if not install_callbacks () then
+ logreport ("log", 0, "loaders", "Error installing font loader callbacks.")
+ return false
+ end
+ return true
+end
+-- vim:tw=79:sw=2:ts=2:expandtab
diff --git a/macros/luatex/generic/luaotfload/luaotfload-log.lua b/macros/luatex/generic/luaotfload/luaotfload-log.lua
new file mode 100644
index 0000000000..17938ffd3d
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-log.lua
@@ -0,0 +1,394 @@
+-------------------------------------------------------------------------------
+-- FILE: luaotfload-log.lua
+-- DESCRIPTION: part of luaotfload / logging
+-------------------------------------------------------------------------------
+
+
+local ProvidesLuaModule = {
+ name = "luaotfload-log",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / logging",
+ license = "GPL v2.0",
+ author = "Khaled Hosny, Elie Roux, Philipp Gesang",
+ copyright = "Luaotfload Development Team",
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+--[[doc--
+The logging system is slow in general, as we always have the function
+call overhead even if we aren’t going to output anything. On the other
+hand, the more efficient approach followed by Context isn’t an option
+because we lack a user interface to toggle per-subsystem tracing.
+--doc]]--
+
+local module_name = "luaotfload" --- prefix for messages
+local debug = debug
+
+luaotfload = luaotfload or { }
+luaotfload.log = luaotfload.log or { }
+local log = luaotfload.log
+
+local ioopen = io.open
+local iowrite = io.write
+local lfsisdir = lfs.isdir
+local lfsisfile = lfs.isfile
+local osdate = os.date
+local ostime = os.time
+local osuuid = os.uuid
+local select = select
+local stringformat = string.format
+local stringsub = string.sub
+local tableconcat = table.concat
+local texiowrite_nl = texio.write_nl
+local texiowrite = texio.write
+local type = type
+
+local dummyfunction = function () end
+
+local texjob = false
+if tex and (tex.jobname or tex.formatname) then
+ --- TeX
+ texjob = true
+end
+
+local loglevel = 0 --- default
+local logout = "log"
+
+--- int -> bool
+local set_loglevel = function (n)
+ if type(n) == "number" then
+ loglevel = n
+ end
+ return true
+end
+log.set_loglevel = set_loglevel
+
+--- unit -> int
+local get_loglevel = function ( )
+ return loglevel
+end
+log.get_loglevel = get_loglevel
+
+local writeln --- pointer to terminal/log writer
+local statusln --- terminal writer that reuses the current line
+local first_status = true --- indicate the begin of a status region
+
+local log_msg = [[
+logging output redirected to %s
+to monitor the progress run "tail -f %s" in another terminal
+]]
+
+local tmppath = os.getenv "TMPDIR" or "/tmp"
+
+local choose_logfile = function ( )
+ if lfsisdir (tmppath) then
+ local fname
+ repeat --- ensure that file of that name doesn’t exist
+ fname = tmppath .. "/luaotfload-log-" .. osuuid()
+ until not lfsisfile (fname)
+ iowrite (stringformat (log_msg, fname, fname))
+ return ioopen (fname, "w")
+ end
+ --- missing /tmp
+ return false
+end
+
+local set_logout = function (s, finalizers)
+ if s == "stdout" then
+ logout = "redirect"
+ elseif s == "file" then --- inject custom logger
+ logout = "redirect"
+ local chan = choose_logfile ()
+ chan:write (stringformat ("logging initiated at %s",
+ osdate ("%Y-%m-%d %H:%M:%S", --- i. e. osdate "%F %T"
+ ostime ())))
+ local writefile = function (...)
+ if select ("#", ...) == 2 then
+ chan:write (select (2, ...))
+ else
+ chan:write (select (1, ...))
+ end
+ end
+ local writefile_nl= function (...)
+ chan:write "\n"
+ if select ("#", ...) == 2 then
+ chan:write (select (2, ...))
+ else
+ chan:write (select (1, ...))
+ end
+ end
+
+ local writeln_orig = writeln
+
+ texiowrite = writefile
+ texiowrite_nl = writefile_nl
+ writeln = writefile_nl
+ statusln = dummyfunction
+
+ finalizers[#finalizers+1] = function ()
+ chan:write (stringformat ("\nlogging finished at %s\n",
+ osdate ("%Y-%m-%d %H:%M:%S", --- i. e. osdate "%F %T"
+ ostime ())))
+ chan:close ()
+ texiowrite = texio.write
+ texiowrite_nl = texio.write_nl
+ writeln = writeln_orig
+ end
+ --else --- remains “log”
+ end
+ return finalizers
+end
+
+log.set_logout = set_logout
+
+local format_error_handler
+if debug then
+ local debugtraceback = debug.traceback
+ format_error_handler = function (err)
+ print ""
+ print (stringformat ("luaotfload error: %q", err))
+ print (stringformat ("Lua interpreter %s", debugtraceback ()))
+ print ""
+ end
+else
+ format_error_handler = function (err)
+ print ""
+ print (stringformat ("luaotfload error: %q", err))
+ print "Lua debug module not available; please enable for a backtrace"
+ print ""
+ end
+end
+
+local basic_logger = function (category, fmt, ...)
+ local res = { module_name, "|", category or "UNKNOWN", ":" }
+ if fmt then
+ local ok, val = xpcall (stringformat, format_error_handler, fmt, ...)
+ if ok then
+ res [#res + 1] = val
+ else
+ res [#res + 1] = stringformat ("ERROR: %q", val)
+ end
+ end
+ texiowrite_nl (logout, tableconcat(res, " "))
+end
+
+--- with faux db update with maximum verbosity:
+---
+--- --------- --------
+--- buffering time (s)
+--- --------- --------
+--- full 4.12
+--- line 4.20
+--- none 4.39
+--- --------- --------
+---
+
+io.stdout:setvbuf "no"
+io.stderr:setvbuf "no"
+
+local kill_line = "\r\x1b[K"
+
+if texjob == true then
+ --- We imitate the texio.* functions so the output is consistent.
+ writeln = function (str)
+ iowrite "\n"
+ iowrite(str)
+ end
+ statusln = function (str)
+ if first_status == false then
+ iowrite (kill_line)
+ else
+ iowrite "\n"
+ end
+ iowrite (str)
+ end
+else
+ writeln = function (str)
+ iowrite(str)
+ iowrite "\n"
+ end
+ statusln = function (str)
+ if first_status == false then
+ iowrite (kill_line)
+ end
+ iowrite (str)
+ end
+end
+
+stdout = function (writer, category, ...)
+ local res = { module_name, "|", category, ":" }
+ local nargs = select("#", ...)
+ if nargs == 0 then
+ --writeln tableconcat(res, " ")
+ --return
+ elseif nargs == 1 then
+ res[#res+1] = select(1, ...) -- around 30% faster than unpack()
+ else
+ res[#res+1] = stringformat(...)
+ end
+ writer (tableconcat(res, " "))
+end
+
+--- at default (zero), we aim to be quiet
+local level_ids = { common = 1, loading = 2, search = 3 }
+
+--[[doc--
+
+ The report() logger is used more or less all over luaotfload.
+ Its requirements are twofold:
+
+ 1) Provide two logging channels, the terminal and the log file;
+ 2) Allow for control over verbosity levels.
+
+ The first part is addressed by specifying the log *mode* as the
+ first argument that can be either “log”, meaning the log file, or
+ “both”: log file and stdout. Anything else is taken as referring to
+ stdout only.
+
+ Verbosity levels, though not as fine-grained as e.g. Context’s
+ system of tracers, allow keeping the logging spam caused by
+ different subsystems manageable. By default, luaotfload will not
+ emit anything if things are running smoothly on level zero. Only
+ warning messages are relayed, while the other messages are skipped
+ over. (This is a little sub-optimal performance-wise since the
+ function calls to the logger are executed regardless.) The log
+ level during a Luatex run can be adjusted by setting the “loglevel”
+ field in config.luaotfload, or by calling log.set_loglevel() as
+ defined above.
+
+--doc]]--
+
+local report = function (mode, lvl, ...)
+ if type(lvl) == "string" then
+ lvl = level_ids[lvl]
+ end
+ if not lvl then lvl = 0 end
+
+ if loglevel >= lvl then
+ if mode == "log" then
+ basic_logger (...)
+ elseif mode == "both" and logout ~= "redirect" then
+ basic_logger (...)
+ stdout (writeln, ...)
+ else
+ stdout (writeln, ...)
+ end
+ end
+end
+
+log.report = report
+
+--[[doc--
+
+ status_logger -- Overwrites the most recently printed line of the
+ terminal. Its purpose is to provide feedback without spamming
+ stdout with irrelevant messages, i.e. when building the database.
+
+ Status logging must be initialized by calling status_start() and
+ properly reset via status_stop().
+
+ The arguments low and high indicate the loglevel threshold at which
+ linewise and full logging is triggered, respectively. E.g.
+
+ names_status (1, 4, "term", "Hello, world!")
+
+ will print nothing if the loglevel is less than one, reuse the
+ current line if the loglevel ranges from one to three inclusively,
+ and output the message on a separate line otherwise.
+
+--doc]]--
+
+local status_logger = function (mode, ...)
+ if mode == "log" then
+ basic_logger (...)
+ else
+ if mode == "both" and logout ~= "redirect" then
+ basic_logger (...)
+ stdout (statusln, ...)
+ else
+ stdout (statusln, ...)
+ end
+ first_status = false
+ end
+end
+
+--[[doc--
+
+ status_start -- Initialize status logging. This installs the status
+ logger if the loglevel is in the specified range, and the normal
+ logger otherwise. It also resets the first line state which
+ causing the next line printed using the status logger to not kill
+ the current line.
+
+--doc]]--
+
+local status_writer
+local status_low = 99
+local status_high = 99
+
+local status_start = function (low, high)
+ first_status = true
+ status_low = low
+ status_high = high
+
+ if os.type == "windows" --- Assume broken terminal.
+ or os.getenv "TERM" == "dumb"
+ then
+ status_writer = function (mode, ...)
+ report (mode, high, ...)
+ end
+ return
+ end
+
+ if low <= loglevel and loglevel < high then
+ status_writer = status_logger
+ else
+ status_writer = function (mode, ...)
+ report (mode, high, ...)
+ end
+ end
+end
+
+--[[doc--
+
+ status_stop -- Finalize a status region by outputting a newline and
+ printing a message.
+
+--doc]]--
+
+local status_stop = function (...)
+ if first_status == false then
+ status_writer(...)
+ if texjob == false then
+ writeln ""
+ end
+ end
+end
+
+log.names_status = function (...) status_writer (...) end
+log.names_status_start = status_start
+log.names_status_stop = status_stop
+
+--[[doc--
+
+ The fontloader comes with the Context logging mechanisms
+ inaccessible. Instead, it provides dumb fallbacks based
+ on the functions in texio.write*() that can be overridden
+ by providing a function texio.reporter().
+
+ The fontloader output can be quite verbose, so we disable
+ it entirely by default.
+
+--doc]]--
+
+local texioreporter = function (message)
+ report ("log", 2, message)
+end
+
+texio.reporter = texioreporter
+--- vim:shiftwidth=4:expandtab:ft=lua
diff --git a/macros/luatex/generic/luaotfload/luaotfload-main.lua b/macros/luatex/generic/luaotfload/luaotfload-main.lua
new file mode 100644
index 0000000000..6c4b920181
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-main.lua
@@ -0,0 +1,313 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-main.lua
+-- DESCRIPTION: OpenType layout system / luaotfload entry point
+-- REQUIREMENTS: luatex v.0.95.0 or later; package lualibs
+-- AUTHOR: Élie Roux, Khaled Hosny, Philipp Gesang, Ulrike Fischer, Marcel Krüger
+-----------------------------------------------------------------------
+
+local authors = "\z
+ Hans Hagen,\z
+ Khaled Hosny,\z
+ Elie Roux,\z
+ Will Robertson,\z
+ Philipp Gesang,\z
+ Dohyun Kim,\z
+ Reuben Thomas,\z
+ David Carlisle,\
+ Ulrike Fischer,\z
+ Marcel Krüger\z
+"
+-- version number is used below!
+local ProvidesLuaModule = {
+ name = "luaotfload-main",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload entry point",
+ author = authors,
+ copyright = authors,
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+local osgettimeofday = os.gettimeofday
+config = config or { }
+luaotfload = luaotfload or { }
+local luaotfload = luaotfload
+luaotfload.log = luaotfload.log or { }
+luaotfload.version = ProvidesLuaModule.version
+luaotfload.loaders = { }
+luaotfload.min_luatex_version = { 0, 95, 0 }
+luaotfload.fontloader_package = "reference" --- default: from current Context
+
+if not tex or not tex.luatexversion then
+ error "this program must be run in TeX mode" --- or call tex.initialize() =)
+else
+ --- version check
+ local major = tex.luatexversion / 100
+ local minor = tex.luatexversion % 100
+ local revision = tex.luatexrevision --[[ : string ]]
+ local revno = tonumber (revision)
+ local minimum = luaotfload.min_luatex_version
+ local actual = { major, minor, revno or 0 }
+ if actual [1] < minimum [1]
+ or actual == minimum and actual [2] < minimum [2]
+ or actual == minimum and actual [2] == minimum [2] and actual [3] < minimum [3]
+ then
+ texio.write_nl ("term and log",
+ string.format ("\tFATAL ERROR\n\z
+ \tLuaotfload requires a Luatex version >= %d.%d.%d.\n\z
+ \tPlease update your TeX distribution!\n\n",
+ (unpack or table.unpack) (minimum)))
+ error "version check failed"
+ end
+end
+
+if status.safer_option ~= 0 then
+ texio.write_nl("term and log","luaotfload can't run with option --safer. Aborting")
+ error("safer_option used")
+end
+
+
+
+
+--[[doc--
+
+ This file initializes the system and loads the font loader. To
+ minimize potential conflicts between other packages and the code
+ imported from \CONTEXT, several precautions are in order. Some of
+ the functionality that the font loader expects to be present, like
+ raw access to callbacks, are assumed to have been disabled by
+ \identifier{luatexbase} when this file is processed. In some cases
+ it is possible to trick it by putting dummies into place and
+ restoring the behavior from \identifier{luatexbase} after
+ initilization. Other cases such as attribute allocation require
+ that we hook the functionality from \identifier{luatexbase} into
+ locations where they normally wouldn’t be.
+
+ Anyways we can import the code base without modifications, which is
+ due mostly to the extra effort by Hans Hagen to make \LUATEX-Fonts
+ self-contained and encapsulate it, and especially due to his
+ willingness to incorporate our suggestions.
+
+--doc]]--
+
+local luatexbase = luatexbase
+local require = require
+local type = type
+
+
+--[[doc--
+
+ \subsection{Module loading}
+ We load the files imported from \CONTEXT with function derived this way. It
+ automatically prepends a prefix to its argument, so we can refer to the
+ files with their actual \CONTEXT name.
+
+--doc]]--
+
+local make_loader_name = function (prefix, name)
+ local msg = luaotfload.log and luaotfload.log.report
+ or function (stream, lvl, cat, ...)
+ if lvl > 1 then --[[not pressing]] return end
+ texio.write_nl ("log",
+ string.format ("luaotfload | %s : ",
+ tostring (cat)))
+ texio.write (string.format (...))
+ end
+ if not name then
+ msg ("both", 0, "load",
+ "Fatal error: make_loader_name (“%s”, “%s”).",
+ tostring (prefix), tostring (name))
+ return "dummy-name"
+ end
+ name = tostring (name)
+ if prefix == false then
+ msg ("log", 9, "load",
+ "No prefix requested, passing module name “%s” unmodified.",
+ name)
+ return tostring (name) .. ".lua"
+ end
+ prefix = tostring (prefix)
+ msg ("log", 9, "load",
+ "Composing module name from constituents %s, %s.",
+ prefix, name)
+ return prefix .. "-" .. name .. ".lua"
+end
+
+local timing_info = {
+ t_load = { },
+ t_init = { },
+}
+
+local make_loader = function (prefix)
+ return function (name)
+ local t_0 = osgettimeofday ()
+ local modname = make_loader_name (prefix, name)
+ --- We don’t want the stack info from inside, so just pcall().
+ local ok, data = pcall (require, modname)
+ local t_end = osgettimeofday ()
+ timing_info.t_load [name] = t_end - t_0
+ if not ok then
+ io.write "\n"
+ local msg = luaotfload.log and luaotfload.log.report or print
+ msg ("both", 0, "load", "FATAL ERROR")
+ msg ("both", 0, "load", " × Failed to load module %q.",
+ tostring (modname))
+ local lines = string.split (data, "\n\t")
+ if not lines then
+ msg ("both", 0, "load", " × Error message: %q", data)
+ else
+ msg ("both", 0, "load", " × Error message:")
+ for i = 1, #lines do
+ msg ("both", 0, "load", " × %q.", lines [i])
+ end
+ end
+ io.write "\n\n"
+ local debug = debug
+ if debug then
+ io.write (debug.traceback())
+ io.write "\n\n"
+ end
+ os.exit(-1)
+ end
+ return data
+ end
+end
+
+--[[doc--
+ Certain files are kept around that aren’t loaded because they are part of
+ the imported fontloader. In order to keep the initialization structure
+ intact we also provide a no-op version of the module loader that can be
+ called in the expected places.
+--doc]]--
+
+local dummy_loader = function (name)
+ luaotfload.log.report ("log", 3, "load",
+ "Skipping module “%s” on purpose.",
+ name)
+end
+
+local context_loader = function (name, path)
+ luaotfload.log.report ("log", 3, "load",
+ "Loading module “%s” from Context.",
+ name)
+ local t_0 = osgettimeofday ()
+ local modname = make_loader_name (false, name)
+ local modpath = modname
+ if path then
+ if lfs.isdir (path) then
+ luaotfload.log.report ("log", 3, "load",
+ "Prepending path “%s”.",
+ path)
+ modpath = file.join (path, modname)
+ else
+ luaotfload.log.report ("both", 0, "load",
+ "Non-existant path “%s” specified, ignoring.",
+ path)
+ end
+ end
+ local ret = require (modpath)
+ local t_end = osgettimeofday ()
+ timing_info.t_load [name] = t_end - t_0
+
+ if ret ~= true then
+ --- require () returns “true” upon success unless the loaded file
+ --- yields a non-zero exit code. This isn’t per se indicating that
+ --- something isn’t right, but against HH’s coding practices. We’ll
+ --- silently ignore this ever happening on lower log levels.
+ luaotfload.log.report ("log", 4, "load",
+ "Module “%s” returned “%s”.", ret)
+ end
+ return ret
+end
+
+local install_loaders = function ()
+ local loaders = { }
+ local loadmodule = make_loader "luaotfload"
+ loaders.luaotfload = loadmodule
+ loaders.fontloader = make_loader "fontloader"
+ loaders.context = context_loader
+ loaders.ignore = dummy_loader
+----loaders.plaintex = make_loader "luatex" --=> for Luatex-Plain
+
+ loaders.initialize = function (name)
+ local tmp = loadmodule (name)
+ local logreport = luaotfload.log.report
+ local init = type(tmp) == "table" and tmp.init or tmp
+ if init and type (init) == "function" then
+ local t_0 = osgettimeofday ()
+ if not init () then
+ logreport ("log", 0, "load",
+ "Failed to load module “%s”.", name)
+ return
+ end
+ local t_end = osgettimeofday ()
+ local d_t = t_end - t_0
+ logreport ("log", 4, "load",
+ "Module “%s” loaded in %d ms.",
+ name, d_t)
+ timing_info.t_init [name] = d_t
+ end
+ end
+
+ return loaders
+end
+
+local luaotfload_initialized = false --- prevent multiple invocations
+
+luaotfload.main = function ()
+
+ if luaotfload_initialized then
+ logreport ("log", 0, "load",
+ "Luaotfload initialization requested but is already \z
+ loaded, ignoring.")
+ return
+ end
+ luaotfload_initialized = true
+
+ luaotfload.loaders = install_loaders ()
+ local loaders = luaotfload.loaders
+ local loadmodule = loaders.luaotfload
+ local initialize = loaders.initialize
+
+ local starttime = osgettimeofday ()
+ local init = loadmodule "init" --- fontloader initialization
+ local store = init.early () --- injects the log module too
+ local logreport = luaotfload.log.report
+
+ initialize "parsers" --- fonts.conf and syntax
+ initialize "configuration" --- configuration options
+
+ if not init.main (store) then
+ logreport ("log", 0, "load", "Main fontloader initialization failed.")
+ end
+
+ initialize "loaders" --- Font loading; callbacks
+ initialize "database" --- Font management.
+ initialize "colors" --- Per-font colors.
+
+ local init_resolvers = loadmodule "resolvers" --- Font lookup
+ init_resolvers ()
+
+ if not config.actions.reconfigure () then
+ logreport ("log", 0, "load", "Post-configuration hooks failed.")
+ end
+
+ initialize "features" --- font request and feature handling
+ loadmodule "letterspace" --- extra character kerning
+ loadmodule "embolden" --- fake bold
+ loadmodule "notdef" --- missing glyph handling
+ initialize "auxiliary" --- additional high-level functionality
+
+ luaotfload.aux.start_rewrite_fontname () --- to be migrated to fontspec
+
+ logreport ("both", 0, "main",
+ "initialization completed in %0.3f seconds\n",
+ osgettimeofday() - starttime)
+----inspect (timing_info)
+end
+
+-- vim:tw=79:sw=4:ts=4:et
diff --git a/macros/luatex/generic/luaotfload/luaotfload-main.tex b/macros/luatex/generic/luaotfload/luaotfload-main.tex
new file mode 100644
index 0000000000..424b4e0fa8
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-main.tex
@@ -0,0 +1,2035 @@
+%% Copyright (C) 2009-2018
+%%
+%% by Elie Roux <elie.roux@telecom-bretagne.eu>
+%% and Khaled Hosny <khaledhosny@eglug.org>
+%% and Philipp Gesang <phg@phi-gamma.net>
+%%
+%% This file is part of Luaotfload.
+%%
+%% Home: https://github.com/lualatex/luaotfload
+%% Support: <lualatex-dev@tug.org>.
+%%
+%% Luaotfload is under the GPL v2.0 (exactly) license.
+%%
+%% ----------------------------------------------------------------------------
+%%
+%% Luaotfload is free software; you can redistribute it and/or
+%% modify it under the terms of the GNU General Public License
+%% as published by the Free Software Foundation; version 2
+%% of the License.
+%%
+%% Luaotfload is distributed in the hope that it will be useful,
+%% but WITHOUT ANY WARRANTY; without even the implied warranty of
+%% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+%% GNU General Public License for more details.
+%%
+%% You should have received a copy of the GNU General Public License
+%% along with Luaotfload; if not, see <http://www.gnu.org/licenses/>.
+%%
+%% ----------------------------------------------------------------------------
+%%
+
+\beginfrontmatter
+
+ \setdocumenttitle {The \identifier{luaotfload} package}
+ \setdocumentdate {2019-08-11 v2.991}
+ \setdocumentauthor {Elie Roux · Khaled Hosny · Philipp Gesang · Ulrike Fischer\\
+ Home: \hyperlink {https://github.com/lualatex/luaotfload}\\
+ New Home: \hyperlink {https://github.com/u-fischer/luaotfload}\\
+ Support: \email {lualatex-dev@tug.org}}
+
+ \typesetdocumenttitle
+
+ \beginabstractcontent
+ This package is an adaptation of the \CONTEXT font loading system.
+ It allows for loading \OpenType fonts with an extended syntax and adds
+ support for a variety of font features.
+
+ After discussion of the font loading API, this manual gives an
+ overview of the core components of \identifier{Luaotfload}: The
+ packaged font loader code, the names database, configuration, and
+ helper functions on the \LUA\ end.
+ \endabstractcontent
+
+\endfrontmatter
+
+\pdfbookmark[1]{\contentsname}{table}
+\typesetcontent
+\beginsection {New in version 2.99 (by Ulrike Fischer)}
+\begin{itemize}
+\item Code cleanup.
+\item The fontloader has been synched with the context files from 2019-08-11.
+\end{itemize}
+\endsection
+\beginsection {New in version 2.98 (by Ulrike Fischer)}
+\begin{itemize}
+\item The\marginpar{\mbox{}\hfill \textbf{breaking change!}} handling of missing chars has been changed. In This version a missing char will insert the \inlinecode{/.notdef} char of the fonts (this is sometimes a space, sometimes a rectangle with a cross) and no longer simply ignore the glyph. This behaviour can be reverted by using \inlinecode{notdef=false} as font feature.
+\item The font feature \inlinecode{embolden} can now be used to fake a bold font.
+\item The fontloader has been synched with the context files from 2019-07-04.
+\end{itemize}
+\endsection
+\beginsection {New in version 2.97 (by Ulrike Fischer)}
+\begin{itemize}
+\item the new generic fontloader improves the handling of large fonts (but some fonts still need a 64bit luatex version to create the font files).
+\item A number of small bug (also in luaotfload-tool) have been corrected, see the NEWS file for details.
+
+\end{itemize}
+\endsection
+
+\beginsection {New in version 2.96 (by Ulrike Fischer)}
+\begin{itemize}
+\item In\marginpar{\mbox{}\hfill \textbf{Incompatible change!}}
+version 2.95 letterspacing was broken due to a change in the fontloader (issue 38). This has been repaired. At the same time a number of oddities and bugs in the letterspacing has been corrected. This can change existing documents. See page~\pageref{p:letterspace} for more information.
+
+\item A problem with the detection of bold fonts has been corrected (issue 41, pull request 42).
+
+\end{itemize}
+\endsection
+
+
+
+\beginsection {New in version 2.95 (by Ulrike Fischer)}
+\begin{itemize}
+\item
+This version imports from context the generic fontloader in the version of 2019-01-28. Contrary to the last announcement, it still works with luatex 1.07. So updates will continue.
+
+\item The handling of the lucida-fonts had been improved (issue 33).
+
+\item tex-files are no longer misused as font fallbacks (issue 35).
+
+\item The resolver code has be refactorated (pull request 36).
+
+\end{itemize}
+\endsection
+\beginsection {New in version 2.94 (by Ulrike Fischer)}
+\begin{itemize}
+\item
+This version imports from context the generic fontloader in the version of 2018-12-19. It is the last version that works with luatex 1.07 and texlive 2018. As context has moved to luatex 1.09 newer versions of the fontloader needs now this luatex version too. This means that until the texlive 2018 freeze there will be probably no update of luaotfload.
+
+\item This version changes the handling of the \inlinecode{mode} key. It no longer accepts only the values \inlinecode{base} and \inlinecode{node}, but can be used to load a font with an alternative font loader/renderer.
+
+
+\end{itemize}
+\endsection
+
+\beginsection {New in version 2.93 (by Ulrike Fischer)}
+Mainly internal clean up of the version info to allow automatic versioning.
+\endsection
+
+\beginsection {New in version 2.92 (by Ulrike Fischer)}
+
+\begin{itemize}
+
+ \item Better devanagari support (issue \#9).
+ \item \identifier{Luaotfload} doesn't work when luatex is used with the option \inlinecode{--safer}. So it now aborts cleanly when the option is detected -- but you still can get errors from fontspec later! (issue \#12).
+ \item The syntax \inlinecode{file:} for legacy font works again (issue \#11).
+ \item The fontloader has been synched with the newest context version from october, 18.
+\end{itemize}
+\endsection
+\beginsection {New in version 2.91 (by Ulrike Fischer)}
+
+This version mostly correct two bugs found in the previous fontloader: Glyphvariants weren't copied and pasted correctly. Glyphs encoded in the PUA couldn't be accessed anymore.
+
+\endsection
+
+
+\beginsection {New in version 2.9 (by Ulrike Fischer)}
+
+On the one side there is not very much new in this version: The native components of \identifier{Luaotfload} are nearly unchanged. A few bugs have been corrected, the various files lists which loads the components of the font loader have been cleaned up.
+
+On the other side there is a lot new:
+
+\begindescriptions
+
+ \beginaltitem {Fontloader} The fontloader files imported from \CONTEXT\ have been updated to the current version.
+ This was necessary to make \identifier{Luaotfload} compatible with the coming \LUATEX 1.08/1.09. Compared to the previous version from february 2017 quite a number of things have changed. Most importantly the handling of arabic fonts has greatly improved. But this also means that changes in the output are possible.
+ \endaltitem
+
+ \beginaltitem {Lualibs} The update of the fontloader files also required an update of the \identifier{Lualibs} package. This \identifier{Luaotfload} version needs version 2.6 of \identifier{Lualibs}.
+ \endaltitem
+
+ \beginaltitem {Maintenance} As the current maintainer wasn't available and it was urgent to get a \identifier{Luaotfload} compatible with \LUATEX 1.08/1.09 maintenance has been transfered to Ulrike Fischer and Marcel Krüger. The package is currently maintained and developed at \hyperlink{https://github.com/u-fischer/luaotfload}. Issues should be reported there.
+ \endaltitem
+
+ \beginaltitem {Documentation}
+ The core of documentation is nearly unchanged. I added this introduction. I recreated with the help of @marmot the graphic on \pageref{file-graph}. I updated the file lists. I imported as appendix pdf versions of the two man files which are part of the \identifier{Luaotfload} documentation.
+ \endaltitem
+
+\enddescriptions
+
+\endsection
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Introduction}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+Font management and installation has always been painful with \TEX. A
+lot of files are needed for one font (\abbrev{tfm}, \abbrev{pfb},
+\abbrev{map}, \abbrev{fd}, \abbrev{vf}), and due to the 8-Bit encoding
+each font is limited to 256 characters.
+
+But the font world has evolved since the original \TEX, and new
+typographic systems have appeared, most notably the so called
+\emphasis{smart font} technologies like \OpenType fonts (\abbrev{otf}).
+
+These fonts can contain many more characters than \TEX fonts, as well
+as additional functionality like ligatures, old-style numbers, small
+capitals, etc., and support more complex writing systems like Arabic
+and Indic\footnote{%
+ Unfortunately, \identifier{luaotfload} doesn‘t support many Indic
+ scripts right now.
+ Assistance in implementing the prerequisites is greatly
+ appreciated.
+}
+scripts.
+
+\OpenType fonts are widely deployed and available for all modern
+operating systems.
+
+As of 2013 they have become the de facto standard for advanced text
+layout.
+
+However, until recently the only way to use them directly in the \TEX
+world was with the \XETEX engine.
+
+Unlike \XETEX, \LUATEX has no built-in support for \OpenType or
+technologies other than the original \TEX fonts.
+
+Instead, it provides hooks for executing \LUA code during the \TEX run
+that allow implementing extensions for loading fonts and manipulating
+how input text is processed without modifying the underlying engine.
+
+This is where \identifier{luaotfload} comes into play:
+Based on code from \CONTEXT, it extends \LUATEX with functionality necessary
+for handling \OpenType fonts.
+
+Additionally, it provides means for accessing fonts known to the operating
+system conveniently by indexing the metadata.
+
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Thanks}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\identifier{Luaotfload} is part of \LUALATEX, the community-driven
+project to provide a foundation for using the \LATEX format with the
+full capabilites of the \LUATEX engine.
+%
+As such, the distinction between end users, contributors, and project
+maintainers is intentionally kept less strict, lest we unduly
+personalize the common effort.
+
+Nevertheless, the current maintainers would like to express their
+gratitude to Khaled Hosny, Akira Kakuto, Hironori Kitagawa and Dohyun
+Kim.
+%
+Their contributions -- be it patches, advice, or systematic
+testing -- made the switch from version 1.x to 2.2 possible.
+%
+Also, Hans Hagen, the author of the font loader, made porting the
+code to \LATEX a breeze due to the extra effort he invested into
+isolating it from the rest of \CONTEXT, not to mention his assistance
+in the task and willingness to respond to our suggestions.
+
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Loading Fonts}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\identifier{luaotfload} supports an extended font request syntax:
+
+\beginnarrower
+ \nonproportional{\string\font\string\foo\space= \string{}%
+ \meta{prefix}\nonproportional{:}%
+ \meta{font name}\nonproportional{:}%
+ \meta{font features}\nonproportional{\string}}%
+ \meta{\TEX font features}
+\endnarrower
+
+\noindent
+The curly brackets are optional and escape the spaces in the enclosed
+font name.
+%
+Alternatively, double quotes serve the same purpose.
+%
+A selection of individual parts of the syntax are discussed below;
+for a more formal description see figure \ref{font-syntax}.
+
+\beginsyntaxfloat
+ {font-syntax}
+ {Font request syntax.
+ Braces or double quotes around the
+ \emphasis{specification} rule will
+ preserve whitespace in file names.
+ In addition to the font style modifiers
+ (\emphasis{slash-notation}) given above, there
+ are others that are recognized but will be silently
+ ignored: \nonproportional{aat},
+ \nonproportional{icu}, and
+ \nonproportional{gr}.
+ The special terminals are:
+ \smallcaps {feature\textunderscore id} for a valid font
+ feature name and
+ \smallcaps {feature\textunderscore value} for the corresponding
+ value.
+ \smallcaps {tfmname} is the name of a \abbrev{tfm} file.
+ \smallcaps {digit} again refers to bytes 48--57, and
+ \smallcaps {all\textunderscore characters} to all byte values.
+ \smallcaps {csname} and \smallcaps {dimension} are the \TEX concepts.}
+%
+ <definition> ::= `\\font', {\sc csname}, `=', <font request>, [ <size> ] ;
+
+ <size> ::= `at', {\sc dimension} ;
+
+ <font request> ::= `"', <unquoted font request> `"'
+ \alt `{', <unquoted font request> `}'
+ \alt <unquoted font request> ;
+
+ <unquoted font request> ::= <specification>, [`:', <feature list> ]
+ \alt <path lookup>, [ [`:'], <feature list> ] ;
+
+ <specification> ::= <prefixed spec>, [ <subfont no> ], \{ <modifier> \}
+ \alt <anon lookup>, \{ <modifier> \} ;
+
+ <prefixed spec> ::= `combo:', <combo list>
+ \alt `file:', <file lookup>
+ \alt `name:', <name lookup> ;
+
+ <combo list> ::= <combo def 1>, \{ `;', <combo def> \} ;
+
+ <combo def 1> ::= <combo id>, `->', <combo id> ;
+
+ <combo def> ::= <combo id>, `->', <combo id chars> ;
+
+ <combo id> ::= (`(', \{ {\sc digit} \}, `)' | \{ {\sc digit} \} ) ;
+
+ <combo id chars> ::= (`(', \{ {\sc digit} \}, `,', <combo chars>, `)'
+ \alt \{ {\sc digit} \} ) ;
+
+ <combo chars> ::= `fallback'
+ \alt \{ <combo range>, \{ `*', <combo range> \} \} ;
+
+ <combo range> ::= <combo num>, [ `-', <combo num> ] ;
+
+ <combo num> ::= `0x', \{ {\sc hexdigit} \}
+ \alt `U+', \{ {\sc digit} \}
+ \alt \{ {\sc digit} \} ;
+
+ <file lookup> ::= \{ <name character> \} ;
+
+ <name lookup> ::= \{ <name character> \} ;
+
+ <anon lookup> ::= {\sc tfmname} | <name lookup> ;
+
+ <path lookup> ::= `[', \{ <path content> \}, `]', [ <subfont no> ] ;
+
+ <path content> ::= <path balanced>
+ \alt `\\', {\sc all_characters}
+ \alt {\sc all_characters} - `]'
+
+ <path balanced> ::= `[', [ <path content> ], `]'
+
+ <modifier> ::= `/', (`I' | `B' | `BI' | `IB' | `S=', \{ {\sc digit} \} ) ;
+
+ <subfont no> ::= `(', \{ {\sc digit} \}, `)' ;
+
+ <feature list> ::= <feature expr>, \{ `;', <feature expr> \} ;
+
+ <feature expr> ::= {\sc feature_id}, `=', {\sc feature_value}
+ \alt <feature switch>, {\sc feature_id} ;
+
+ <feature switch> ::= `+' | `-' ;
+
+ <name character> ::= {\sc all_characters} - ( `(' | `/' | `:' ) ;
+\endsyntaxfloat
+
+%% Below guarded space gets borked in index; why‽
+\beginsubsection{Prefix -- the \texorpdfstring{\identifier{luaotfload}}{luaotfload}{ }Way}
+
+In \identifier{luaotfload}, the canonical syntax for font requests
+requires a \emphasis{prefix}:
+%
+\beginnarrower
+ \nonproportional{\string\font\string\fontname\space= }%
+ \meta{prefix}%
+ \nonproportional{:}%
+ \meta{fontname}%
+ \dots
+\endnarrower
+%
+where \meta{prefix} is either \inlinecode{file:} or \inlinecode {name:}.\footnote{%
+ \identifier{Luaotfload} also knows two further prefixes, \inlinecode {kpse:}
+ and \inlinecode {my:}.
+ %
+ A \inlinecode {kpse} lookup is restricted to files that can be found by
+ \identifier{kpathsea} and will not attempt to locate system fonts.
+ %
+ This behavior can be of value when an extra degree of encapsulation is
+ needed, for instance when supplying a customized tex distribution.
+
+ The \inlinecode {my} lookup takes this a step further: it lets you define
+ a custom resolver function and hook it into the \luaident{resolve_font}
+ callback.
+ %
+ This ensures full control over how a file is located.
+ %
+ For a working example see the
+ \hyperlink [test in the luaotfload
+ repo]{https://github.com/u-fischer/luaotfload/blob/master/testfiles/my-resolver.lvt}.
+}
+%
+It determines whether the font loader should interpret the request as
+a \emphasis{file name} or
+ \emphasis{font name}, respectively,
+which again influences how it will attempt to locate the font.
+%
+Examples for font names are
+ “Latin Modern Italic”,
+ “GFS Bodoni Rg”, and
+ “PT Serif Caption”
+-- they are the human readable identifiers
+usually listed in drop-down menus and the like.\footnote{%
+ Font names may appear like a great choice at first because they
+ offer seemingly more intuitive identifiers in comparison to arguably
+ cryptic file names:
+ %
+ “PT Sans Bold” is a lot more descriptive than \fileent{PTS75F.ttf}.
+ On the other hand, font names are quite arbitrary and there is no
+ universal method to determine their meaning.
+ %
+ While \identifier{luaotfload} provides fairly sophisticated heuristic
+ to figure out a matching font style, weight, and optical size, it
+ cannot be relied upon to work satisfactorily for all font files.
+ %
+ For an in-depth analysis of the situation and how broken font names
+ are, please refer to
+ \hyperlink [this post]{http://www.ntg.nl/pipermail/ntg-context/2013/073889.html}
+ by Hans Hagen, the author of the font loader.
+ %
+ If in doubt, use filenames.
+ %
+ \fileent{luaotfload-tool} can perform the matching for you with the
+ option \inlinecode {--find=<name>}, and you can use the file name it returns
+ in your font definition.
+}
+%
+In order for fonts installed both in system locations and in your
+\fileent{texmf} to be accessible by font name, \identifier{luaotfload} must
+first collect the metadata included in the files.
+%
+Please refer to section~\ref{sec:fontdb} below for instructions on how to
+create the database.
+
+File names are whatever your file system allows them to be, except
+that that they may not contain the characters
+ \inlinecode {(},
+ \inlinecode {:}, and
+ \inlinecode {/}.
+%
+As is obvious from the last exception, the \inlinecode {file:} lookup will
+not process paths to the font location -- only those
+files found when generating the database are addressable this way.
+%
+Continue below in the \XETEX section if you need to load your fonts
+by path.
+%
+The file names corresponding to the example font names above are
+ \fileent{lmroman12-italic.otf},
+ \fileent{GFSBodoni.otf}, and
+ \fileent{PTZ56F.ttf}.
+
+\endsubsection
+
+\beginsubsection {Bracketed Lookups}
+\label{sec:bracket}
+Bracketed lookups allow for arbitrary character content to be used in a
+definition.
+%
+A simple bracketed request looks follows the scheme
+
+\beginnarrower
+ \nonproportional{\string\font\string\fontname\space = [}%
+ \meta{/path/to/file}%
+ \nonproportional{]}
+\endnarrower
+
+\noindent
+Inside the square brackets, every character except for a closing bracket is
+permitted, allowing for arbitrary paths to a font file -- including Windows
+style paths with UNC or drive letter prepended -- to be specified.
+%
+The \identifier{Luaotfload} syntax differs from \XETEX in that the subfont
+selector goes \emphasis{after} the closing bracket:
+
+\beginnarrower
+ \nonproportional{\string\font\string\fontname\space = [}%
+ \meta{/path/to/file}%
+ \nonproportional{]}
+ \nonproportional{(}n\nonproportional{)}
+\endnarrower
+
+Naturally, path-less file names are equally valid and processed the
+same way as an ordinary \inlinecode {file:} lookup.
+
+\beginsubsection {Compatibility}
+
+In addition to the regular prefixed requests, \identifier{luaotfload}
+accepts loading fonts the \XETEX way.
+%
+There are again two modes: bracketed and unbracketed.
+For the bracketed variety, see above, \ref{sec:bracket}.
+
+Unbracketed (or, for lack of a better word: \emphasis{anonymous})
+font requests resemble the conventional \TEX syntax.
+
+\beginnarrower
+ \nonproportional{\string\font\string\fontname\space= }%
+ \meta{font name}
+ \dots
+\endnarrower
+\endsubsection
+
+However, they have a broader spectrum of possible interpretations:
+before anything else, \identifier{luaotfload} attempts to load a
+traditional \TEX Font Metric (\abbrev{tfm} or \abbrev{ofm}).
+%
+If this fails, it performs a \inlinecode {path:} lookup, which itself will
+fall back to a \inlinecode {file:} lookup.
+%
+Lastly, if none of the above succeeded, attempt to resolve the request as a
+\inlinecode {name:} lookup by searching the font index for \meta{font name}.
+%
+The behavior of this “anonymous” lookup is configurable, see the configuation
+manpage for details.
+
+Furthermore, \identifier{luaotfload} supports the slashed (shorthand)
+font style notation from \XETEX.
+
+\beginnarrower
+ \nonproportional{\string\font\string\fontname\space= }%
+ \meta{font name}%
+ \nonproportional{/}%
+ \meta{modifier}
+ \dots
+\endnarrower
+
+\noindent
+Currently, four style modifiers are supported:
+ \inlinecode {I} for italic shape,
+ \inlinecode {B} for bold weight,
+ \inlinecode {BI} or \inlinecode {IB} for the combination of both.
+%
+Other “slashed” modifiers are too specific to the \XETEX engine and
+have no meaning in \LUATEX.
+
+\endsubsection
+
+\beginsubsection{Examples}
+
+\beginsubsubsection{Loading by File Name}
+
+For example, conventional \TeX\ font can be loaded with a
+\inlinecode {file:} request like so:
+
+\beginlisting
+ \font \lmromanten = {file:ec-lmr10} at 10pt
+\endlisting
+
+The \OpenType version of Janusz Nowacki’s font \emphasis{Antykwa
+Półtawskiego}\footnote{%
+ \hyperlink {http://jmn.pl/antykwa-poltawskiego/}, also available in
+ in \TEX Live.
+}
+in its condensed variant can be loaded as follows:
+
+\beginlisting
+ \font \apcregular = file:antpoltltcond-regular.otf at 42pt
+\endlisting
+
+The next example shows how to load the \emphasis{Porson} font digitized by
+the Greek Font Society using \XETEX-style syntax and an absolute path from a
+non-standard directory:
+
+\beginlisting
+ \font \gfsporson = "[/tmp/GFSPorson.otf]" at 12pt
+\endlisting
+
+\identifier{TrueType} collection files (the extension is usually
+\inlinecode{.ttc}) contain more than a single font. In order to refer to these
+subfonts, the respective index may be added in parentheses after the file
+name.\footnote{%
+ Incidentally, this syntactical detail also prevents one from loading files
+ that end in balanced parentheses.
+}
+
+\beginlisting
+ \font \cambriamain = "file:cambria.ttc(0)" at 10pt
+ \font \cambriamath = "file:cambria.ttc(1)" at 10pt
+\endlisting
+
+and likewise, requesting subfont inside a TTC container by path:
+
+\beginlisting
+ \font \asanamain = "[/home/typesetter/.fonts/math/asana.ttc](0):mode=node;+tlig" at 10pt
+ \font \asanamath = "[/home/typesetter/.fonts/math/asana.ttc](1):mode=base" at 10pt
+\endlisting
+
+\endsubsubsection
+
+\beginsubsubsection{Loading by Font Name}
+
+The \inlinecode {name:} lookup does not depend on cryptic filenames:
+
+\beginlisting
+ \font \pagellaregular = {name:TeX Gyre Pagella} at 9pt
+\endlisting
+
+A bit more specific but essentially the same lookup would be:
+
+\beginlisting
+ \font \pagellaregular = {name:TeX Gyre Pagella Regular} at 9pt
+\endlisting
+
+\noindent
+Which fits nicely with the whole set:
+
+\beginlisting
+ \font\pagellaregular = {name:TeX Gyre Pagella Regular} at 9pt
+ \font\pagellaitalic = {name:TeX Gyre Pagella Italic} at 9pt
+ \font\pagellabold = {name:TeX Gyre Pagella Bold} at 9pt
+ \font\pagellabolditalic = {name:TeX Gyre Pagella Bolditalic} at 9pt
+
+ {\pagellaregular foo bar baz\endgraf}
+ {\pagellaitalic foo bar baz\endgraf}
+ {\pagellabold foo bar baz\endgraf}
+ {\pagellabolditalic foo bar baz\endgraf}
+
+ ...
+\endlisting
+
+\endsubsubsection
+
+\beginsubsubsection{Modifiers}
+
+If the entire \emphasis{Iwona} family\footnote{%
+ \hyperlink {http://jmn.pl/kurier-i-iwona/},
+ also in \TEX Live.
+}
+is installed in some location accessible by \identifier{luaotfload},
+the regular shape can be loaded as follows:
+
+\beginlisting
+ \font \iwona = Iwona at 20pt
+\endlisting
+
+\noindent
+To load the most common of the other styles, the slash notation can
+be employed as shorthand:
+
+\beginlisting
+ \font \iwonaitalic = Iwona/I at 20pt
+ \font \iwonabold = Iwona/B at 20pt
+ \font \iwonabolditalic = Iwona/BI at 20pt
+\endlisting
+
+\noindent
+which is equivalent to these full names:
+
+\beginlisting
+ \font \iwonaitalic = "Iwona Italic" at 20pt
+ \font \iwonabold = "Iwona Bold" at 20pt
+ \font \iwonabolditalic = "Iwona BoldItalic" at 20pt
+\endlisting
+
+\endsubsubsection
+\endsubsection
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Font features}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\emphasis{Font features} are the second to last component in the
+general scheme for font requests:
+
+\beginnarrower
+ \nonproportional{\string\font\string\foo\space= "}%
+ \meta{prefix}%
+ \nonproportional{:}%
+ \meta{font name}%
+ \nonproportional{:}%
+ \meta{font features}%
+ \meta{\TEX font features}%
+ \nonproportional{"}
+\endnarrower
+
+\noindent
+If style modifiers are present (\XETEX style), they must precede
+\meta{font features}.
+
+The element \meta{font features} is a semicolon-separated list of feature
+tags\footnote{%
+ Cf. \hyperlink {http://www.microsoft.com/typography/otspec/featurelist.htm}.
+}
+and font options.
+%
+Prepending a font feature with a \inlinecode{+} (plus sign) enables it,
+whereas a \inlinecode{-} (minus) disables it. For instance, the request
+
+\beginlisting
+ \font \test = LatinModernRoman:+clig;-kern
+\endlisting
+
+\noindent activates contextual ligatures (\inlinecode{clig}) and
+disables kerning (\inlinecode{kern}).
+%
+Alternatively the options \inlinecode{true} or \inlinecode{false} can
+be passed to the feature in a key/value expression.
+%
+The following request has the same meaning as the last one:
+
+\beginlisting
+ \font \test = LatinModernRoman:clig=true;kern=false
+\endlisting
+
+\noindent
+Furthermore, this second syntax is required should a font feature
+accept other options besides a true/false switch.
+%
+For example, \emphasis{stylistic alternates} (\inlinecode{salt}) are
+variants of given glyphs.
+%
+They can be selected either explicitly by supplying the variant
+index (starting from one), or randomly by setting the value to,
+obviously, \inlinecode{random}.
+
+%% TODO verify that this actually works with a font that supports
+%% the salt/random feature!\fi
+\beginlisting
+ \font \librmsaltfirst = LatinModernRoman:salt=1
+\endlisting
+
+\beginsubsection {Basic font features}\label{sec:mode}
+
+\begindescriptions
+
+ \beginaltitem {mode}
+ Until version 2.94
+ \identifier{luaotfload} had two \OpenType processing
+ \emphasis{modes}:
+ \identifier{base} and \identifier{node}.
+
+ \identifier{base} mode works by mapping \OpenType
+ features to traditional \TEX ligature and kerning mechanisms.
+ %
+ Supporting only non-contextual substitutions and kerning
+ pairs, it is the slightly faster, albeit somewhat limited, variant.
+ %
+ \identifier{node} mode works by processing \TeX’s internal
+ node list directly at the \LUA end and supports
+ a wider range of \OpenType features.
+ %
+ The downside is that the intricate operations required for
+ \identifier{node} mode may slow down typesetting especially
+ with complex fonts and it does not work in math mode.
+
+ By default \identifier{luaotfload} is in \identifier{node}
+ mode, and \identifier{base} mode has to be requested where needed,
+ e.~g. for math fonts.
+
+ Since version 2.94 it is possible to call other font renderers with the mode key. A simple example with a plain reader can be found at \hyperlink{https://github.com/u-fischer/luaotfload/pull/26\#issuecomment-437716326}.
+ A more useful example needs the new experimental harftex engine (windows binaries can be found at w32tex.org), and the harf renderer (\hyperlink{https://github.com/khaledhosny/harf}). With both it is possible to render a font using the harfbuzz library (used also by xetex).
+
+
+ \endaltitem
+
+ \beginaltitem {script} \label{script-tag}
+ An \OpenType script tag;\footnote{%
+ See \hyperlink {http://www.microsoft.com/typography/otspec/scripttags.htm}
+ for a list of valid values.
+ %
+ For scripts derived from the Latin alphabet the value
+ \inlinecode{latn} is good choice.
+ }
+ the default value is \inlinecode{dflt}.
+ %
+ Some fonts, including very popular ones by foundries like Adobe,
+ do not assign features to the \inlinecode{dflt} script, in
+ which case the script needs to be set explicitly.
+ \endaltitem
+
+ \beginaltitem {language}
+ An \OpenType language system identifier,\footnote{%
+ Cf. \hyperlink {http://www.microsoft.com/typography/otspec/languagetags.htm}.
+ }
+ defaulting to \inlinecode{dflt}.
+ \endaltitem
+
+ \beginaltitem {color}
+ A font color, defined as a triplet of two-digit hexadecimal
+ \abbrev{rgb} values, with an optional fourth value for
+ transparency
+ (where \inlinecode{00} is completely transparent and
+ \inlinecode{FF} is opaque).
+
+ For example, in order to set text in semitransparent red:
+
+ \beginlisting
+ \font \test = "Latin Modern Roman:color=FF0000BB"
+ \endlisting
+ \endaltitem
+
+
+ \beginaltitem {embolden}
+ A factor, defined as a decimal number.
+
+ For example
+
+ \beginlisting
+ \font\test = "Latin Modern Roman:mode=node;embolden=2;"
+ \endlisting
+
+ {\font\test= "Latin Modern Roman:mode=node;"\test Dies is not bold.
+ \font\test= "Latin Modern Roman:mode=node;embolden=2;" \test Dies is a faked bold font.}
+
+ \endaltitem
+
+ \beginaltitem {kernfactor \& letterspace}\label{p:letterspace}
+ Define a font with letterspacing (tracking) enabled.
+ %
+ In \identifier{luaotfload}, letterspacing is implemented by
+ inserting additional kerning between glyphs.
+
+ This approach is derived from and still quite similar to the
+ \emphasis{character kerning} (\texmacro{setcharacterkerning} /
+ \texmacro{definecharacterkerning} \& al.) functionality of
+ Context, see the file \fileent{typo-krn.lua} there.
+ %
+ The main difference is that \identifier{luaotfload} does not
+ use \LUATEX attributes to assign letterspacing to regions,
+ but defines virtual letterspaced versions of a font.
+
+ The option \identifier{kernfactor} accepts a numeric value that
+ determines the letterspacing factor to be applied to the font
+ size.
+ %
+ E.~g. a kern factor of $0.42$ applied to a $10$ pt font
+ results in $4.2$ pt of additional kerning applied to each
+ pair of glyphs.
+ %
+
+ Spaces\marginpar{\mbox{}\hfill NEW in v2.96!} between words are now stretched too. This is consistent with the \XETEX behaviour (and the amount of stretching should be similar). This
+ naturally changes the output of a document. In case you want the old behaviour back use
+ \beginlisting
+ \directlua{luaotfload.letterspace.keepwordspacing = true}
+ \endlisting
+
+ The difference between both options is obvious:
+
+ \begingroup
+ \fontspec{IwonaMedium-Regular.otf}[LetterSpace=60]
+ New: hello world
+
+ \directlua{luaotfload.letterspace.keepwordspacing = true}
+
+ Old: hello world
+
+ \directlua{luaotfload.letterspace.keepwordspacing = false}
+ \endgroup
+
+
+ Ligatures\marginpar{\mbox{}\hfill NEW in v2.96!} are no longer split into their component glyphs.
+ This change too make the \identifier{luaotfload} more compatible with \XETEX. It also makes it much easier to activate or deactivate ligature sets in letterspaced fonts.
+ If you want to split ligatures, you should deactivate as you would do it with a not-letterspaced font, e.g. with the fontspec \identifier{Ligatures} option, or the low-level \identifier{-liga} and similar.
+
+
+ {\font \test = "file:Iwona-Regular.otf:mode=base;+liga;+tlig;letterspace=12.5"
+ \test With standard ligatures: fi -- ff\par
+
+ \font \test = "file:Iwona-Regular.otf:mode=base;-liga;+tlig;letterspace=12.5"
+ \test Only with tlig: fi -- ff \par
+
+ \font \test = "file:Iwona-Regular.otf:mode=base;-liga;letterspace=12.5"
+ \test No ligatures: fi -- ff \par
+ }
+
+ For compatibility with \XETEX an alternative
+ \identifier{letterspace} option is supplied that interprets the
+ supplied value as a \emphasis{percentage} of the font size but
+ is otherwise identical to \identifier{kernfactor}.
+ %
+ Consequently, both definitions in below snippet yield the same
+ letterspacing width:
+
+ \beginlisting
+ \font \iwonakernedA = "file:Iwona-Regular.otf:kernfactor=0.125"
+ \font \iwonakernedB = "file:Iwona-Regular.otf:letterspace=12.5"
+ \endlisting
+
+ The \identifier{microtype} package uses a special implementation of letterspacing, and the commands \inlinecode{\lsstyle} and \inlinecode{\textls} are not affected by these changes.
+
+ Setting the ligatures with the font options is the recommended way, to activate or deactivate them. In case of special requirements
+ specific pairs of letters and ligatures may be exempt from
+ letterspacing by defining the \LUA functions
+ \luaident{keeptogether} and \luaident{keepligature},
+ respectively, inside the namespace \inlinecode {luaotfload.letterspace}.
+ %
+ Both functions are called whenever the letterspacing callback
+ encounters an appropriate node or set of nodes.
+ %
+ If they return a true-ish value, no extra kern is inserted at
+ the current position.
+ %
+ \luaident{keeptogether} receives a pair of consecutive
+ glyph nodes in order of their appearance in the node list.
+ %
+ \luaident{keepligature} receives a single node which can be
+ analyzed into components.
+ %
+ (For details refer to the \emphasis{glyph nodes} section in the
+ \LUATEX reference manual.)
+ %
+ The implementation of both functions is left entirely to the
+ user.
+ \endaltitem
+
+\iffalse
+ \startbuffer [printvectors]
+ \directlua{inspect(fonts.protrusions.setups.default)
+ inspect(fonts.expansions.setups.default)}
+ \stopbuffer
+\fi
+
+ \beginaltitem {protrusion \& expansion}
+ These keys control microtypographic features of the font,
+ namely \emphasis{character protrusion} and \emphasis{font
+ expansion}.
+ %
+ Their arguments are names of \LUA tables that contain
+ values for the respective features.\footnote{%
+ For examples of the table layout please refer to the
+ section of the file \fileent{luaotfload-fonts-ext.lua} where the
+ default values are defined.
+ %
+ Alternatively and with loss of information, you can dump
+ those tables into your terminal by issuing
+ \unless \iffalse
+ \beginlisting
+ \directlua{inspect(fonts.protrusions.setups.default)
+ inspect(fonts.expansions.setups.default)}
+ \endlisting
+ \else
+ \typebuffer [printvectors]
+ \fi
+ at some point after loading \fileent{luaotfload.sty}.
+ }
+ %
+ For both, only the set \identifier{default} is predefined.
+
+ For example, to define a font with the default
+ protrusion vector applied\footnote{%
+ You also need to set
+ \inlinecode {pdfprotrudechars=2} and
+ \inlinecode {pdfadjustspacing=2}
+ to activate protrusion and expansion, respectively.
+ See the
+ \hyperlink [\PDFTEX manual]{http://mirrors.ctan.org/systems/pdftex/manual/pdftex-a.pdf}%
+ for details.
+ }:
+
+ \beginlisting
+ \font \test = LatinModernRoman:protrusion=default
+ \endlisting
+ \endaltitem
+\enddescriptions
+
+\endsubsection
+
+\beginsubsection {Non-standard font features}
+\identifier{luaotfload} adds a number of features that are not defined
+in the original \OpenType specification, most of them
+aiming at emulating the behavior familiar from other \TEX engines.
+%
+Currently (2014) there are three of them:
+
+\begindescriptions
+
+ \beginaltitem {anum}
+ Substitutes the glyphs in the \abbrev{ascii} number range
+ with their counterparts from eastern Arabic or Persian,
+ depending on the value of \identifier{language}.
+ \endaltitem
+
+ \beginaltitem {tlig}
+ Applies legacy \TEX ligatures\footnote{%
+ These contain the feature set \inlinecode {trep} of earlier
+ versions of \identifier{luaotfload}.
+
+ Note to \XETEX users: this is the equivalent of the
+ assignment \inlinecode {mapping=text-tex} using \XETEX's input
+ remapping feature.
+ }:
+
+ \unless \iffalse
+ %% Using braced arg syntax with inline code appears to be
+ %% impossible within Latex tables -- just ignore the weird
+ %% exclamation points below.
+ \begintabulate [rlrl]
+ \beginrow `` \newcell {\inlinecode !``! } \newcell '' \newcell {\inlinecode !''!} \endrow
+ \beginrow ` \newcell {\inlinecode !`! } \newcell ' \newcell {\inlinecode !'! } \endrow
+ \beginrow " \newcell {\inlinecode !"! } \newcell -- \newcell {\inlinecode !--!} \endrow
+ \beginrow --- \newcell {\inlinecode !---!} \newcell !` \newcell {\inlinecode ?!`?} \endrow
+ \beginrow ?` \newcell {\inlinecode !?`! } \newcell \newcell \endrow
+ \endtabulate
+ \else
+ %% XXX find a way to wrap these in the tabulate environment
+ \startframed [frame=off,width=broad,align=middle]
+ \startframed [frame=off,width=\dimexpr(\textwidth/2)]
+ \startxtable [align=middle]
+ \startxrow \startxcell `` \stopxcell \startxcell \inlinecode {``} \stopxcell \startxcell '' \stopxcell \startxcell \inlinecode {''} \stopxcell \stopxrow
+ \startxrow \startxcell ` \stopxcell \startxcell \inlinecode {`} \stopxcell \startxcell ' \stopxcell \startxcell \inlinecode {'} \stopxcell \stopxrow
+ \startxrow \startxcell " \stopxcell \startxcell \inlinecode {"} \stopxcell \startxcell -- \stopxcell \startxcell \inlinecode {--} \stopxcell \stopxrow
+ \startxrow \startxcell --- \stopxcell \startxcell \inlinecode {---} \stopxcell \startxcell !` \stopxcell \startxcell \inlinecode {!`} \stopxcell \stopxrow
+ \startxrow \startxcell ?` \stopxcell \startxcell \inlinecode {?`} \stopxcell \startxcell \stopxcell \startxcell \stopxcell \stopxrow
+ \stopxtable
+ \stopframed
+ \stopframed
+ \fi
+ \endaltitem
+
+ \beginaltitem {itlc}
+ Computes italic correction values (active by default).
+ \endaltitem
+
+\enddescriptions
+
+\endsubsection
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Combining fonts}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+Version 2.7 and later support combining characters from multiple fonts into a
+single virtualized one. This requires that the affected fonts be loaded in
+advance as well as a special \emphasis{request syntax}. Furthermore, this
+allows to define \emphasis{fallback fonts} to supplement fonts that may lack
+certain required glyphs.
+
+Combinations are created by defining a font using the \luaident{combo:} prefix.
+
+\beginsubsection {Fallbacks}
+
+For example, the \identifier{Latin Modern} family of fonts does, as indicated
+in the name, not provide Cyrillic glyphs. If Latin script dominates in the copy
+with interspersed Cyrillic, a fallback can be created from a similiar looking
+font like \identifier{Computer Modern Unicode}, taking advantage of the fact
+that it too derives from Knuth’s original \identifier{Computer Modern} series:
+
+\beginlisting
+ \input luaotfload.sty
+ \font \lm = file:lmroman10-regular.otf:mode=base
+ \font \cmu = file:cmunrm.otf:mode=base
+ \font \lmu = "combo: 1->\fontid\lm; 2->\fontid\cmu,fallback"
+ \lmu Eh bien, mon prince. Gênes et Lueques ne sont plus que des
+ apanages, des поместья, de la famille Buonaparte.
+ \bye
+\endlisting
+
+As simple as this may look on the first glance, this approach is entirely
+inappropriate if more than a couple letters are required from a different font.
+Because the combination pulls nothing except the glyph data, all of the
+important other information that constitute a proper font -- kerning, styles,
+features, and suchlike -- will be missing.
+
+\endsubsection %% Fallbacks
+
+\beginsubsection {Combinations}
+
+Generalizing the idea of a \emphasis{fallback font}, it is also possible to
+pick definite sets of glyphs from multiple fonts. On a bad day, for instance,
+it may be the sanest choice to start out with \identifier{EB Garamond} italics,
+typeset all decimal digits in the bold italics of \identifier{GNU Freefont},
+and tone down the punctuation with extra thin glyphs from \identifier{Source
+Sans}:
+
+\beginlisting
+ \def \feats {-tlig;-liga;mode=base;-kern}
+ \def \fileone {EBGaramond12-Italic.otf}
+ \def \filetwo {FreeMonoBoldOblique.otf}
+ \def \filethree {SourceSansPro-ExtraLight.otf}
+
+ \input luaotfload.sty
+
+ \font \one = file:\fileone :\feats
+ \font \two = file:\filetwo :\feats
+ \font \three = file:\filethree:\feats
+
+ \font \onetwothree = "combo: 1 -> \fontid\one;
+ 2 -> \fontid\two, 0x30-0x39;
+ 3 -> \fontid\three, 0x21*0x3f; "
+
+ {\onetwothree \TeX—0123456789—?!}
+ \bye
+\endlisting
+
+\noindent Despite the atrocious result, the example demonstrates well the
+syntax that is used to specify ranges and fonts. Fonts are being referred to by
+their internal index which can be obtained by passing the font command into the
+\texmacro{fontid} macro, e. g. \inlinecode{\fontid\one}, after a font has been
+defined. The first component of the combination is the base font which will be
+extended by the others. It is specified by the index alone.
+
+All further fonts require either the literal \inlinecode{fallback} or a list of
+codepoint definitions to be appended after a comma. The elements of this list
+again denote either single codepoints like \inlinecode{0x21} (referring to the
+exclamation point character) or ranges of codepoints (\inlinecode{0x30-0x39}).
+Elements are separated by the \identifier{ASCII} asterisk character
+(\inlinecode{*}). The characters referenced in the list will be imported from
+the respective font, if available.
+
+\endsubsection %% Combinations
+
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Font names database}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\label{sec:fontdb}
+
+As mentioned above, \identifier{luaotfload} keeps track of which
+fonts are available to \LUATEX by means of a \emphasis{database}.
+%
+This allows referring to fonts not only by explicit filenames but
+also by the proper names contained in the metadata which is often
+more accessible to humans.\footnote{%
+ The tool \hyperlink[\fileent{otfinfo}]{http://www.lcdf.org/type/}
+ (comes with \TEX Live), when invoked on a font file with the
+ \inlinecode {-i} option, lists the variety of name fields defined for
+ it.
+}
+
+When \identifier{luaotfload} is asked to load a font by a font name,
+it will check if the database exists and load it, or else generate a
+fresh one.
+%
+Should it then fail to locate the font, an update to the database is
+performed in case the font has been added to the system only
+recently.
+%
+As soon as the database is updated, the resolver will try
+and look up the font again, all without user intervention.
+%
+The goal is for \identifier{luaotfload} to act in the background and
+behave as unobtrusively as possible, while providing a convenient
+interface to the fonts installed on the system.
+
+Generating the database for the first time may take a while since it
+inspects every font file on your computer.
+%
+This is particularly noticeable if it occurs during a typesetting run.
+In any case, subsequent updates to the database will be quite fast.
+
+\beginsubsection[luaotfload-tool]
+ {\fileent{luaotfload-tool}}
+
+It can still be desirable at times to do some of these steps
+manually, and without having to compile a document.
+%
+To this end, \identifier{luaotfload} comes with the utility
+\fileent{luaotfload-tool} that offers an interface to the database
+functionality.
+%
+Being a \LUA script, there are two ways to run it:
+either make it executable (\inlinecode {chmod +x} on unixoid systems) or
+pass it as an argument to \fileent{texlua}.\footnote{%
+ Tests by the maintainer show only marginal performance gain by
+ running with Luigi Scarso’s
+ \hyperlink [\identifier{Luajit\kern-.25ex\TEX}]{https://foundry.supelec.fr/projects/luajittex/},
+ which is probably due to the fact that most of the time is spent
+ on file system operations.
+
+ \emphasis{Note}:
+ On \abbrev{MS} \identifier{Windows} systems, the script can be run
+ either by calling the wrapper application
+ \fileent{luaotfload-tool.exe} or as
+ \inlinecode {texlua.exe luaotfload-tool.lua}.
+}
+%
+Invoked with the argument \inlinecode {--update} it will perform a database
+update, scanning for fonts not indexed.
+
+\beginlisting
+ luaotfload-tool --update
+\endlisting
+
+Adding the \inlinecode {--force} switch will initiate a complete
+rebuild of the database.
+
+\beginlisting
+ luaotfload-tool --update --force
+\endlisting
+
+\endsubsection
+
+\beginsubsection{Search Paths}
+
+\identifier{luaotfload} scans those directories where fonts are
+expected to be located on a given system.
+%
+On a Linux machine it follows the paths listed in the
+\identifier{Fontconfig} configuration files;
+consult \inlinecode {man 5 fonts.conf} for further information.
+%
+On \identifier{Windows} systems, the standard location is
+\inlinecode {Windows\\Fonts},
+%
+while \identifier{Mac OS~X} requires a multitude of paths to
+be examined.
+%
+The complete list is is given in table \ref{table-searchpaths}.
+Other paths can be specified by setting the environment variable
+\inlinecode {OSFONTDIR}.
+%
+If it is non-empty, then search will be extended to the included
+directories.
+
+\tablefloat {table-searchpaths}
+ {List of paths searched for each supported operating system.}
+ {%
+ \unless \iffalse
+ \begincentered
+ \begintabulate [lp{.5\textwidth}]
+ \beginrow
+ Windows \newcell \inlinecode !\% WINDIR\%\\ Fonts!
+ \endrow
+ \beginrow
+ Linux \newcell \fileent{/usr/local/etc/fonts/fonts.conf} and\hfill\break
+ \fileent{/etc/fonts/fonts.conf}
+ \endrow
+ \beginrow
+ Mac \newcell \fileent{\textasciitilde/Library/Fonts},\break
+ \fileent{/Library/Fonts},\break
+ \fileent{/System/Library/Fonts}, and\hfill\break
+ \fileent{/Network/Library/Fonts}
+ \endrow
+ \endtabulate
+ \endcentered
+ \else
+ \setuplocalinterlinespace [14pt]
+ \starttabulate [|l|p(.5\textwidth)|]
+ \NC Windows \NC \inlinecode {\% WINDIR\%\\ Fonts} \NC \NR
+ \NC Linux \NC \fileent{/usr/local/etc/fonts/fonts.conf} and\crlf
+ \fileent{/etc/fonts/fonts.conf} \NC \NR
+ \NC
+ Mac \NC \fileent{\textasciitilde/Library/Fonts},\crlf
+ \fileent{/Library/Fonts},\break
+ \fileent{/System/Library/Fonts}, and\crlf
+ \fileent{/Network/Library/Fonts} \NC \NR
+ \stoptabulate
+ \fi%
+ }
+
+\endsubsection
+
+\beginsubsection{Querying from Outside}
+
+\fileent{luaotfload-tool} also provides rudimentary means of
+accessing the information collected in the font database.
+%
+If the option \inlinecode {--find=}\emphasis{name} is given, the script will
+try and search the fonts indexed by \identifier{luaotfload} for a
+matching name.
+%
+For instance, the invocation
+
+\beginlisting
+ luaotfload-tool --find="Iwona Regular"
+\endlisting
+
+\noindent
+will verify if “Iwona Regular” is found in the database and can be
+readily requested in a document.
+
+If you are unsure about the actual font name, then add the
+\inlinecode {-F} (or \inlinecode {--fuzzy}) switch to the command line to enable
+approximate matching.
+%
+Suppose you cannot precisely remember if the variant of
+\identifier{Iwona} you are looking for was “Bright” or “Light”.
+The query
+
+\beginlisting
+ luaotfload-tool -F --find="Iwona Bright"
+\endlisting
+
+\noindent
+will tell you that indeed the latter name is correct.
+
+Basic information about fonts in the database can be displayed
+using the \inlinecode {-i} option (\inlinecode {--info}).
+%
+\beginlisting
+ luaotfload-tool -i --find="Iwona Light Italic"
+\endlisting
+%
+\noindent
+The meaning of the printed values is described in section 4.4 of the
+\LUATEX reference manual.\footnote{%
+ In \TEX Live: \fileent{texmf-dist/doc/luatex/base/luatexref-t.pdf}.
+}
+
+For a much more detailed report about a given font try the
+\inlinecode {-I} option instead (\inlinecode {--inspect}).
+\beginlisting
+ luaotfload-tool -I --find="Iwona Light Italic"
+\endlisting
+
+\inlinecode {luaotfload-tool --help} will list the available command line
+switches, including some not discussed in detail here.
+%
+For a full documentation of \identifier{luaotfload-tool} and its
+capabilities refer to the manpage
+(\inlinecode {man 1 luaotfload-tool}).\footnote{%
+ Or see \inlinecode {luaotfload-tool.rst} in the source directory.
+}
+
+\endsubsection
+
+\beginsubsection {Blacklisting Fonts}
+\label{font-blacklist}
+
+Some fonts are problematic in general, or just in \LUATEX.
+%
+If you find that compiling your document takes far too long or eats
+away all your system’s memory, you can track down the culprit by
+running \inlinecode {luaotfload-tool -v} to increase verbosity.
+%
+Take a note of the \emphasis{filename} of the font that database
+creation fails with and append it to the file
+\fileent{luaotfload-blacklist.cnf}.
+
+A blacklist file is a list of font filenames, one per line.
+Specifying the full path to where the file is located is optional, the
+plain filename should suffice.
+%
+File extensions (\fileent{.otf}, \fileent{.ttf}, etc.) may be omitted.
+%
+Anything after a percent (\inlinecode {\%}) character until the end of the line
+is ignored, so use this to add comments.
+%
+Place this file to some location where the \identifier{kpse}
+library can find it, e.~g.
+\fileent{texmf-local/tex/luatex/luaotfload} if you are running
+\identifier{\TEX Live},\footnote{%
+ You may have to run \inlinecode {mktexlsr} if you created a new file in
+ your \fileent{texmf} tree.
+}
+or just leave it in the working directory of your document.
+%
+\identifier{luaotfload} reads all files named
+\fileent{luaotfload-blacklist.cnf} it finds, so the fonts in
+\fileent{./luaotfload-blacklist.cnf} extend the global blacklist.
+
+Furthermore, a filename prepended with a dash character (\inlinecode{-}) is
+removed from the blacklist, causing it to be temporarily whitelisted
+without modifying the global file.
+%
+An example with explicit paths:
+
+\beginlisting
+% example otf-blacklist.cnf
+/Library/Fonts/GillSans.ttc % Luaotfload ignores this font.
+-/Library/Fonts/Optima.ttc % This one is usable again, even if
+ % blacklisted somewhere else.
+\endlisting
+
+\endsubsection
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {The Fontloader}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\beginsubsection {Overview}
+
+To a large extent, \identifier{luaotfload} relies on code originally
+written by Hans Hagen for the
+\hyperlink[\identifier{\CONTEXT}]{http://wiki.contextgarden.net}
+format.
+%
+It integrates the font loader, written entirely in \LUA, as distributed
+in the \identifier{\LUATEX-Fonts} package.
+%
+The original \LUA source files have been combined using the \CONTEXT
+packaging library into a single, self-contained blob. In
+this form the font loader depends only on the \identifier{lualibs}
+package and requires only minor adaptions to integrate into
+\identifier{luaotfload}.
+
+The guiding principle is to let \CONTEXT/\LUATEX-Fonts take care of the
+implementation, and update the imported code as frequently as
+necessary.
+%
+As maintainers, we aim at importing files from upstream essentially
+\emphasis{unmodified}, except for renaming them to prevent name
+clashes.
+%
+This job has been greatly alleviated since the advent of
+\LUATEX-Fonts, prior to which the individual dependencies had to be
+manually spotted and extracted from the \CONTEXT source code in a
+complicated and error-prone fashion.
+
+\endsubsection
+
+\beginsubsection {Contents and Dependencies}
+
+Below is a commented list of the files distributed with
+\identifier{luaotfload} in one way or the other.
+%
+See see the figure on page \pageref{file-graph} for a
+graphical representation of the dependencies.
+%
+\label{package}%
+Through the script \fileent{mkimport} a \CONTEXT library
+is invoked to create the \identifier{luaotfload} fontloader as a merged
+(amalgamated) source file.\footnote{%
+ In \CONTEXT, this facility can be accessed by means of a
+ \hyperlink[script]{https://bitbucket.org/phg/context-mirror/src/beta/scripts/context/lua/mtx-package.lua?at=beta}
+ which is integrated into \fileent{mtxrun} as a subcommand.
+ Run \inlinecode {mtxrun --script package --help} to display further
+ information.
+ For the actual merging code see the file
+ \fileent{util-mrg.lua} that is part of \CONTEXT.
+}
+%
+This file constitutes the “default fontloader” and is part of the
+\identifier{luaotfload} package as \fileent{fontloader-YY-MM-DD.lua},
+where the uppercase letters are placeholders for the build date.
+%
+A companion to it, \fileent{luatex-basics-gen.lua} (renamed to \fileent{fontloader-basics-gen.lua} in \identifier{luaotfload})
+must be loaded beforehand to set up parts of the environment required by the \CONTEXT
+libraries.
+%
+During a \TEX\ run, the fontloader initialization and injection happens
+in the module \fileent{luaotfload-init.lua}.
+%
+Additionally, the “reference fontloader” as imported from \LUATEX-Fonts
+is provided as the file \fileent{fontloader-reference.lua}.
+%
+This file is self-contained in that it packages all the auxiliary \LUA
+libraries too, as Luaotfload did up to the 2.5 series; since that job
+has been offloaded to the \identifier{Lualibs} package, loading this
+fontloader introduces a certain code duplication.
+
+A number of \emphasis{\LUA utility libraries} are not part of the
+\identifier{luaotfload} fontloader, contrary to its equivalent in
+\LUATEX-Fonts. These are already provided by the \identifier{lualibs}
+and have thus been omitted from the merge.\footnote{%
+ Faithful listeners will remember the pre-2.6 era when the fontloader
+ used to be integrated as-is which caused all kinds of code
+ duplication with the pervasive \identifier{lualibs} package.
+ This conceptual glitch has since been amended by tightening the
+ coupling with the excellent \CONTEXT\ toolchain.
+}
+
+\begindoublecolumns
+ \begindefinitions
+ \directlua{ printctxlibslist ()}
+ \enddefinitions
+\enddoublecolumns
+
+The reference fontloader is home to several \LUA files that can be
+grouped twofold as below:
+
+\begindefinitions
+ \beginnormalitem
+ The \emphasis{font loader} itself.
+ These files have been written for \LUATEX-Fonts and they are
+ distributed along with \identifier{luaotfload} so as to resemble
+ the state of the code when it was imported. Their purpose is either
+ to give a slightly aged version of a file if upstream considers
+ latest developments for not yet ready for use outside Context; or,
+ to install placeholders or minimalist versions of APIs relied upon
+ but usually provided by parts of Context not included in the
+ fontloader.
+ \begindoublecolumns
+ \begindefinitions
+ \directlua{printctxallgenericlist ()}
+ \enddefinitions
+ \enddoublecolumns
+ \endnormalitem
+
+ \beginnormalitem
+ Code related to \emphasis{font handling and node processing}, taken
+ directly from \CONTEXT.
+ \begindoublecolumns
+ \begindefinitions
+ \directlua{printctxfontlist ()}
+ \enddefinitions
+ \enddoublecolumns
+ \endnormalitem
+\enddefinitions
+
+As an alternative to the merged file, \identifier {Luaotfload} may load
+individual unpackaged \LUA libraries that come with the source, or even
+use the files from Context directly.
+%
+Thus if you prefer running bleeding edge code from the \CONTEXT beta,
+choose the \inlinecode {context} fontloader via the configuration file
+(see sections \ref{sec:conf} and \ref{sec:pkg} below).
+
+Also, the merged file at some point loads the Adobe Glyph List from a
+\LUA table that is contained in \fileent{luaotfload-glyphlist.lua},
+which is automatically generated by the script
+\fileent{mkglyphlist}.\footnote{%
+ See \fileent{luaotfload-font-enc.lua}.
+ The hard-coded file name is why we have to replace the procedure
+ that loads the file in \fileent{luaotfload-init.lua}.
+}
+%
+There is a make target \identifier{glyphs} that will create a fresh
+glyph list so we don’t need to import it from \CONTEXT any longer.
+
+In addition to these, \identifier{luaotfload} requires a number of
+files not contained in the merge. Some of these have no equivalent in
+\LUATEX-Fonts or \CONTEXT, some were taken unmodified from the latter.
+
+
+\beginfilelist
+ \beginaltitem {luaotfload-features.lua}
+ font feature handling; incorporates some of the code from
+ \fileent{font-otc} from \CONTEXT;
+ \endaltitem
+ \beginaltitem {luaotfload-configuration.lua}
+ handling of \fileent{luaotfload.conf(5)}.
+ \endaltitem
+ \beginaltitem {luaotfload-log.lua}
+ overrides the \CONTEXT logging functionality.
+ \endaltitem
+ \beginaltitem {luaotfload-loaders.lua}
+ registers readers in the fontloader for various kinds of
+ font formats
+ \endaltitem
+ \beginaltitem {luaotfload-parsers.lua}
+ various \abbrev{lpeg}-based parsers.
+ \endaltitem
+ \beginaltitem {luaotfload-database.lua}
+ font names database.
+ \endaltitem
+ \beginaltitem {luaotfload-resolvers.lua}
+ file name resolvers.
+ \endaltitem
+ \beginaltitem {luaotfload-colors.lua}
+ color handling.
+ \endaltitem
+ \beginaltitem {luaotfload-auxiliary.lua}
+ access to internal functionality for package authors (proposals
+ for additions welcome).
+ \endaltitem
+ \beginaltitem {luaotfload-letterspace.lua}
+ font-based letterspacing.
+ \endaltitem
+ \beginaltitem {luaotfload-filelist.lua}
+ data about the files in the package.
+ \endaltitem
+\endfilelist
+
+%\figurefloat
+% {file-graph}
+% {Schematic of the files in \identifier{Luaotfload}}
+% {filegraph.pdf}
+
+\endsubsection
+
+\beginsubsection {Packaging}
+
+\label{sec:pkg}%
+The fontloader code is integrated as an isolated component that can be
+switched out on demand.
+%
+To specify the fontloader you wish to use, the configuration file
+(described in section \ref{sec:conf}) provides the option
+\inlinecode{fontloader}.
+%
+Its value can be one of the identifiers \inlinecode{default} or
+\inlinecode{reference} (see above, section \ref{package}) or the name
+of a file somewhere in the search path of \LUATEX.
+%
+This will make \identifier {Luaotfload} locate the \CONTEXT source by
+means of \identifier{kpathsea} lookups and use those instead of the
+merged package.
+%
+The parameter may be extended with a path to the \CONTEXT
+\fileent{texmf}, separated with a colon:
+
+\beginlisting
+[run]
+ fontloader = context:~/context/tex/texmf-context
+\endlisting
+
+\noindent This setting allows accessing an installation -- e. g. the
+standalone distribution or a source repository -- outside the current
+\TEX distribution.
+
+Like the \identifier{Lualibs} package, the fontloader is deployed as a
+\emphasis{merged package} containing a series of \LUA files joined
+together in their expected order and stripped of non-significant parts.
+%
+The \fileent{mkimport} utility assists in pulling the files from a
+\CONTEXT tree and packaging them for use with \identifier{Luaotfload}.%
+%
+The state of the files currently in \identifier{Luaotfload}’s
+repository can be queried:
+\beginlisting
+./scripts/mkimport news
+\endlisting
+%
+The subcommand for importing takes the prefix of the desired \CONTEXT
+\identifier{texmf} as an optional argument:
+\beginlisting
+./scripts/mkimport import ~/context/tex/texmf-context
+\endlisting
+%
+Whereas the command for packaging requires a path to the
+\emphasis{package description file} and the output name to be passed.
+\beginlisting
+./scripts/mkimport package fontloader-custom.lua
+\endlisting
+
+From the toplevel makefile, the targets \inlinecode{import} and
+\inlinecode{package} provide easy access to the commands as invoked during
+the \identifier{Luaotfload} build process.\footnote{%
+ \emphasis{Hint for those interested in the packaging process}: issue
+ \inlinecode{make show} for a list of available build routines.
+}
+These will call \inlinecode{mkimport} script with the correct
+parameters to generate a datestamped package.
+%
+Whether files have been updated in the upstream distribution can be
+queried by \inlinecode{./scripts/mkimport news}.
+%
+This will compare the imported files with their counterparts in the
+\CONTEXT distribution and report changes.
+
+\endsubsection
+
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Configuration Files}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\beginnarrower
+ \emphasis{Caution}: For the authoritative documentation, consult the
+ manpage for \fileent{luaotfload.conf(5)}.
+\endnarrower
+
+\label{sec:conf}
+The runtime behavior of \identifier{Luaotfload} can be customized by
+means of a configuration file.
+% location
+At startup, it attempts to locate a file called \fileent
+{luaotfload.conf} or \fileent {luaotfloadrc} at a number of candidate
+locations:
+
+\begincentered
+ \begindefinitions
+ \beginnormalitem \fileent{./luaotfload.conf} \endnormalitem
+ \beginnormalitem \fileent{./luaotfloadrc} \endnormalitem
+ \beginnormalitem \fileent{\$XDG_CONFIG_HOME/luaotfload/luaotfload.conf} \endnormalitem
+ \beginnormalitem \fileent{\$XDG_CONFIG_HOME/luaotfload/luaotfload.rc} \endnormalitem
+ \beginnormalitem \fileent{~/.luaotfloadrc} \endnormalitem
+ \enddefinitions
+\endcentered
+
+\beginnarrower
+ \emphasis{Caution}: The configuration potentially modifies the final
+ document. A project-local file belongs under version control along
+ with the rest of the document. This is to ensure that everybody who
+ builds the project also receives the same customizations as the
+ author.
+\endnarrower
+
+% syntax
+The syntax is fairly close to the format used by
+\fileent{git-config(1)} which in turn was derived from the popular
+\identifier{.INI} format: Lines of key-value pairs are grouped under
+different configuration “sections”.\footnote{%
+ The configuration parser in \fileent {luoatfload-parsers.lua} might
+ be employed by other packages for similar purposes.
+}
+% example settings
+An example for customization via \fileent {luaotfload.conf} might look
+as below:
+
+\beginlisting
+; Example luaotfload.conf containing a rudimentary configuration
+[db]
+ update-live = false
+[run]
+ color-callback = pre_linebreak_filter
+ definer = info_patch
+ log-level = 5
+[default-features]
+ global = mode=base
+\endlisting
+
+This specifies that for the given project, \identifier{Luaotfload}
+shall not attempt to automatically scan for fonts if it can’t resolve a
+request. The font-based colorization will happen during \LUATEX’s
+pre-linebreak filter. The fontloader will output verbose information
+about the fonts at definition time along with globally increased
+verbosity. Lastly, the fontloader defaults to the less expensive
+\luaident{base} mode like it does in \CONTEXT.
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Auxiliary Functions}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+With release version 2.2, \identifier{Luaotfload} received
+additional functions for package authors to call from outside
+(see the file \fileent{luaotfload-auxiliary.lua} for details).
+%
+The purpose of this addition twofold.
+%
+Firstly, \identifier{luaotfload} failed to provide a stable interface
+to internals in the past which resulted in an unmanageable situation
+of different packages abusing the raw access to font objects by means
+of the \luaident{patch_font} callback.
+%
+When the structure of the font object changed due to an update, all
+of these imploded and several packages had to be fixed while
+simultaneously providing fallbacks for earlier versions.
+%
+Now the patching is done on the \identifier{luaotfload} side and can
+be adapted with future modifications to font objects without touching
+the packages that depend on it.
+%
+Second, some the capabilities of the font loader and the names
+database are not immediately relevant in \identifier{luaotfload}
+itself but might nevertheless be of great value to package authors or
+end users.
+
+Note that the current interface is not yet set in stone and the
+development team is open to suggestions for improvements or
+additions.
+
+\beginsubsection {Callback Functions}
+
+The \luaident{patch_font} callback is inserted in the wrapper
+\identifier{luaotfload} provides for the font definition callback.
+%
+At this place it allows manipulating the font object immediately after
+the font loader is done creating it.
+%
+For a short demonstration of its usefulness, here is a snippet that
+writes an entire font object to the file \fileent{fontdump.lua}:
+
+\beginlisting
+ \input luaotfload.sty
+ \directlua{
+ local dumpfile = "fontdump.lua"
+ local dump_font = function (tfmdata)
+ local data = table.serialize(tfmdata)
+ io.savedata(dumpfile, data)
+ end
+
+ luatexbase.add_to_callback(
+ "luaotfload.patch_font",
+ dump_font,
+ "my_private_callbacks.dump_font"
+ )
+ }
+ \font \dumpme = name:Iwona
+ \bye
+\endlisting
+
+\emphasis{Beware}: this creates a Lua file of around 150,000 lines of
+code, taking up 3~\abbrev{mb} of disk space.
+%
+By inspecting the output you can get a first impression of how a font
+is structured in \LUATEX’s memory, what elements it is composed of,
+and in what ways it can be rearranged.
+
+\beginsubsubsection {Compatibility with Earlier Versions}
+
+As has been touched on in the preface to this section, the structure
+of the object as returned by the fontloader underwent rather drastic
+changes during different stages of its development, and not all
+packages that made use of font patching have kept up with every one
+of it.
+%
+To ensure compatibility with these as well as older versions of
+some packages, \identifier{luaotfload} sets up copies of or references
+to data in the font table where it used to be located.
+%
+For instance, important parameters like the requested point size, the
+units factor, and the font name have again been made accessible from
+the toplevel of the table even though they were migrated to different
+subtables in the meantime.
+
+\endsubsubsection
+
+\beginsubsubsection{Patches}
+
+These are mostly concerned with establishing compatibility with \XETEX.
+
+\beginfunctionlist
+
+ \beginaltitem {set_sscale_dimens}
+ Calculate \texmacro{fontdimen}s 10 and 11 to emulate \XETEX.
+ \endaltitem
+
+ \beginaltitem {set_capheight}
+ Calculates \texmacro{fontdimen} 8 like \XETEX.
+ \endaltitem
+
+ \beginaltitem {patch_cambria_domh}
+ Correct some values of the font \emphasis{Cambria Math}.
+ \endaltitem
+
+\endfunctionlist
+
+\endsubsection
+
+\beginsubsection {Package Author’s Interface}
+
+As \LUATEX release 1.0 is nearing, the demand for a reliable interface
+for package authors increases.
+
+\endsubsubsection
+
+\beginsubsubsection{Font Properties}
+
+Below functions mostly concern querying the different components of a
+font like for instance the glyphs it contains, or what font features
+are defined for which scripts.
+
+\beginfunctionlist
+
+ \beginaltitem {aux.font_has_glyph (id : int, index : int)}
+ Predicate that returns true if the font \luaident{id}
+ has glyph \luaident{index}.
+ \endaltitem
+
+ \beginaltitem {aux.slot_of_name(name : string)}
+ Translates an Adobe Glyph name to the corresponding glyph
+ slot.
+ \endaltitem
+
+ \beginaltitem {aux.name_of_slot(slot : int)}
+ The inverse of \luaident{slot_of_name}; note that this
+ might be incomplete as multiple glyph names may map to the
+ same codepoint, only one of which is returned by
+ \luaident{name_of_slot}.
+ \endaltitem
+
+ \beginaltitem {aux.provides_script(id : int, script : string)}
+ Test if a font supports \luaident{script}.
+ \endaltitem
+
+ \beginaltitem {aux.provides_language(id : int, script : string, language : string)}
+ Test if a font defines \luaident{language} for a given
+ \luaident{script}.
+ \endaltitem
+
+ \beginaltitem {aux.provides_feature(id : int, script : string,
+ language : string, feature : string)}
+ Test if a font defines \luaident{feature} for
+ \luaident{language} for a given \luaident{script}.
+ \endaltitem
+
+ \beginaltitem {aux.get_math_dimension(id : int, dimension : string)}
+ Get the dimension \luaident{dimension} of font \luaident{id}.
+ \endaltitem
+
+ \beginaltitem {aux.sprint_math_dimension(id : int, dimension : string)}
+ Same as \luaident{get_math_dimension()}, but output the value
+ in scaled points at the \TEX end.
+ \endaltitem
+
+\endfunctionlist
+
+\endsubsubsection
+
+\beginsubsubsection{Database}
+
+%% not implemented, may come back later
+\beginfunctionlist
+% \beginaltitem {aux.scan_external_dir(dir : string)}
+% Include fonts in directory \luaident{dir} in font lookups without
+% adding them to the database.
+%
+ \beginaltitem {aux.read_font_index (void)}
+ Read the index file from the appropriate location (usually
+ the bytecode file \fileent{luaotfload-names.luc} somewhere
+ in the \fileent{texmf-var} tree) and return the result as a
+ table. The file is processed with each call so it is up to
+ the user to store the result for later access.
+ \endaltitem
+
+ \beginaltitem {aux.font_index (void)}
+ Return a reference of the font names table used internally
+ by \identifier{luaotfload}. The index will be read if it
+ has not been loaded up to this point. Also a font scan that
+ overwrites the current index file might be triggered. Since
+ the return value points to the actual index, any
+ modifications to the table might influence runtime behavior
+ of \identifier{luaotfload}.
+ \endaltitem
+
+\endfunctionlist
+
+\endsubsubsection
+
+\endsubsection
+\endsection
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\beginsection {Troubleshooting}
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\beginsubsection {Database Generation}
+
+If you encounter problems with some fonts, please first update to the
+latest version of this package before reporting a bug, as
+\identifier{luaotfload} is under active development and still a moving
+target.
+%
+The development takes place on \identifier{github} at
+\hyperlink {https://github.com/lualatex/luaotfload} where there is an issue
+tracker for submitting bug reports, feature requests and the likes.
+
+Bug reports are more likely to be addressed if they contain the output
+of
+
+\beginlisting
+ luaotfload-tool --diagnose=environment,files,permissions
+\endlisting
+
+\noindent Consult the man page for a description of these options.
+
+Errors during database generation can be traced by increasing the
+verbosity level and redirecting log output to \fileent{stdout}:
+
+\beginlisting
+ luaotfload-tool -fuvvv --log=stdout
+\endlisting
+
+\noindent or to a file in \fileent{/tmp}:
+
+\beginlisting
+ luaotfload-tool -fuvvv --log=file
+\endlisting
+
+\noindent In the latter case, invoke the \inlinecode {tail(1)} utility on the
+file for live monitoring of the progress.
+
+If database generation fails, the font last printed to the terminal or
+log file is likely to be the culprit.
+%
+Please specify it when reporting a bug, and blacklist it for the time
+being (see above, page \pageref{font-blacklist}).
+
+\endsubsection
+
+\beginsubsection {Font Features}
+
+A common problem is the lack of features for some
+\OpenType fonts even when specified.
+%
+This can be related to the fact that some fonts do not provide features
+for the \inlinecode {dflt} script (see above on page \pageref{script-tag}),
+which is the default one in this package.
+%
+If this happens, assigning a noth script when the font is defined should
+fix it.
+%
+For example with \inlinecode {latn}:
+
+\beginlisting
+ \font \test = file:MyFont.otf:script=latn;+liga;
+\endlisting
+
+You can get a list of features that a font defines for scripts and
+languages by querying it in \fileent{luaotfload-tool}:
+
+\beginlisting
+ luaotfload-tool --find="Iwona" --inspect
+\endlisting
+
+\endsubsection
+
+\beginsubsection {\LUATEX Programming}
+
+Another strategy that helps avoiding problems is to not access raw
+\LUATEX internals directly.
+%
+Some of them, even though they are dangerous to access, have not been
+overridden or disabled.
+%
+Thus, whenever possible prefer the functions in the \luaident{aux}
+namespace over direct manipulation of font objects. For example, raw
+access to the \luaident{font.fonts} table like:
+
+\beginlisting
+ local somefont = font.fonts[2]
+\endlisting
+
+\noindent can render already defined fonts unusable.
+%
+Instead, the function \luaident{font.getfont()} should be used
+because it has been replaced by a safe variant.
+
+However, \luaident{font.getfont()} only covers fonts handled by the
+font loader, e.~g. \identifier{OpenType} and \identifier{TrueType}
+fonts, but not \abbrev{tfm} or \abbrev{ofm}.
+%
+Should you absolutely require access to all fonts known to \LUATEX,
+including the virtual and autogenerated ones, then you need to query
+both \luaident{font.getfont()} and \luaident{font.fonts}.
+%
+In this case, best define you own accessor:
+
+\beginlisting
+ local unsafe_getfont = function (id)
+ local tfmdata = font.getfont (id)
+ if not tfmdata then
+ tfmdata = font.fonts[id]
+ end
+ return tfmdata
+ end
+
+ --- use like getfont()
+ local somefont = unsafe_getfont (2)
+\endlisting
+
+\endsubsection
+\endsection
+
+\beginsection {License}
+
+\identifier {luaotfload} is licensed under the terms of the
+\hyperlink [GNU General Public License version 2.0]%
+ {https://www.gnu.org/licenses/old-licenses/gpl-2.0.html}.
+Following the underlying fontloader code \identifier {luaotfload}
+recognizes only that exact version as its license.
+The „any later version” clause of the original license text as
+copyrighted by the \hyperlink [Free Software Foundation]{http://www.fsf.org/}
+\emphasis {does not apply} to either \identifier {luaotfload} or the
+code imported from \CONTEXT.
+
+The complete text of the license is given as a separate file \fileent
+{COPYING} in the toplevel directory of the
+\hyperlink [\fileent {Luaotfload} Git repository]{https://github.com/lualatex/luaotfload/blob/master/COPYING}.\\
+Distributions probably package it as \fileent
+{doc/luatex/luaotfload/COPYING} in the relevant \fileent {texmf} tree.
+
+\endsection
+
+\endinput
+
+% vim:ft=tex:tw=79:et:sw=2
diff --git a/macros/luatex/generic/luaotfload/luaotfload-notdef.lua b/macros/luatex/generic/luaotfload/luaotfload-notdef.lua
new file mode 100644
index 0000000000..196ea928bb
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-notdef.lua
@@ -0,0 +1,105 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-notdef.lua
+-- DESCRIPTION: part of luaotfload / notdef
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-notdef",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / color",
+ license = "GPL v2.0",
+ author = "Marcel Krüger"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+local nodenew = node.direct.new
+local getfont = font.getfont
+local setfont = node.direct.setfont
+local getwhd = node.direct.getwhd
+local insert_after = node.direct.insert_after
+local traverse_char = node.direct.traverse_char
+local protect_glyph = node.direct.protect_glyph
+local otffeatures = fonts.constructors.newfeatures "otf"
+
+local function setnotdef(tfmdata, factor)
+ local desc = tfmdata.shared.rawdata.descriptions
+ -- So we have to find the .notdef glyph. We only know that it has GID
+ -- 0, but we need it's Unicode mapping. Normally it isn't mapped in
+ -- the font, so we auto-assigned the first private slot:
+ local guess = desc[0xF0000]
+ if guess and guess.index == 0 then
+ tfmdata.notdefcode = 0xF0000
+ return
+ end
+ print')'
+ -- If this didn't happen, it might be mapped to one of the
+ -- replacement characters:
+ for code = 0xFFFC,0xFFFF do
+ guess = desc[code]
+ if guess and guess.index == 0 then
+ tfmdata.notdefcode = code
+ return
+ end
+ end
+ print')))'
+ -- Oh no, we couldn't find it. Maybe we can find it by name?
+ local code = tfmdata.resources.unicodes[".notdef"]
+ -- Better safe than sorry
+ guess = code and desc[code]
+ if guess and guess.index == 0 then
+ tfmdata.notdefcode = code
+ return
+ end
+ print'))))'
+ -- So the font didn't do the obvious things and then it lied to us.
+ -- At this point we should think about sending an automated complain
+ -- to the font author, but we probably can't trust the contact
+ -- information either.
+ -- We will fall back to brute force now:
+ for code, char in pairs(desc) do
+ if char.index == 0 then
+ tfmdata.notdefcode = code
+ return
+ end
+ end
+ -- If we ever reach this point, something odd happened. Either there
+ -- are no glyphs at all (then LuaTeX will complain anyway, so let's
+ -- ignore that case) or someone tried to use this with a legacy font.
+ -- In that case there most likely isn't a `.notdef` glyph anyway and
+ -- inserting glyph 0 would insert a random character, so `notdefcode`
+ -- better stays `nil`.
+end
+
+local glyph_id = node.id'glyph'
+local function donotdef(head, font, _, _, _)
+ local tfmdata = getfont(font)
+ local notdef, chars = tfmdata.unscaled.notdefcode, tfmdata.characters
+ if not notdef then return end
+ for cur, cid, fid in traverse_char(head) do if fid == font then
+ local w, h, d = getwhd(cur)
+ if w == 0 and h == 0 and d == 0 and not chars[cid] then
+ local notdefnode = nodenew(glyph_id, 256)
+ setfont(notdefnode, font, notdef)
+ insert_after(cur, cur, notdefnode)
+ protect_glyph(cur)
+ end
+ end end
+end
+
+otffeatures.register {
+ name = "notdef",
+ description = "Add notdef glyphs",
+ default = 1,
+ initializers = {
+ node = setnotdef,
+ },
+ processors = {
+ node = donotdef,
+ }
+}
+
+--- vim:sw=2:ts=2:expandtab:tw=71
diff --git a/macros/luatex/generic/luaotfload/luaotfload-parsers.lua b/macros/luatex/generic/luaotfload/luaotfload-parsers.lua
new file mode 100644
index 0000000000..5a7ccd576f
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-parsers.lua
@@ -0,0 +1,799 @@
+-------------------------------------------------------------------------------
+-- FILE: luaotfload-parsers.lua
+-- DESCRIPTION: various lpeg-based parsers used in Luaotfload
+-- REQUIREMENTS: Luaotfload
+-- AUTHOR: Philipp Gesang (Phg), <phg@phi-gamma.net>, Marcel Krüger
+-------------------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-parsers",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / filelist",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+local traversal_maxdepth = 42 --- prevent stack overflows
+
+local rawset = rawset
+
+local lpeg = require "lpeg"
+local patterns = lpeg.patterns
+local P, R, S, V = lpeg.P, lpeg.R, lpeg.S, lpeg.V
+local lpegmatch = lpeg.match
+local C, Cc, Cf = lpeg.C, lpeg.Cc, lpeg.Cf
+local Cg, Cmt, Cs, Ct = lpeg.Cg, lpeg.Cmt, lpeg.Cs, lpeg.Ct
+
+local kpse = kpse
+local kpseexpand_path = kpse.expand_path
+local kpsereadable_file = kpse.readable_file
+
+local file = file
+local filejoin = file.join
+local filedirname = file.dirname
+
+local io = io
+local ioopen = io.open
+
+local logreport = print
+
+local string = string
+local stringsub = string.sub
+local stringfind = string.find
+local stringlower = string.lower
+
+local mathceil = math.ceil
+
+local lfs = lfs
+local lfsisfile = lfs.isfile
+local lfsisdir = lfs.isdir
+
+-------------------------------------------------------------------------------
+--- COMMON PATTERNS
+-------------------------------------------------------------------------------
+
+local asterisk = P"*"
+local dot = P"."
+local colon = P":"
+local semicolon = P";"
+local comma = P","
+local noncomma = 1 - comma
+local slash = P"/"
+local backslash = P"\\"
+local equals = P"="
+local dash = P"-"
+local gartenzaun = P"#"
+local lbrk, rbrk = P"[", P"]"
+local brackets = lbrk + rbrk
+local squote = P"'"
+local dquote = P"\""
+
+local newline = P"\n"
+local returnchar = P"\r"
+local spacing = S" \t\v"
+local linebreak = S"\n\r"
+local whitespace = spacing + linebreak
+local ws = spacing^0
+local xmlws = whitespace^1
+local eol = P"\n\r" + P"\r\n" + linebreak
+
+local digit = R"09"
+local alpha = R("az", "AZ")
+local anum = alpha + digit
+local decimal = digit^1 * (dot * digit^0)^-1
+local hexdigit = R("09", "af", "AF")
+local hex = P"0x" * hexdigit^1
+
+-------------------------------------------------------------------------------
+--- FONTCONFIG
+-------------------------------------------------------------------------------
+
+--[[doc--
+
+ For fonts installed on the operating system, there are several
+ options to make Luaotfload index them:
+
+ - If OSFONTDIR is set (which is the case under windows by default
+ but not on the other OSs), it scans it at the same time as the
+ texmf tree, in the function scan_texmf_fonts().
+
+ - Otherwise
+ - under Windows and Mac OSX, we take a look at some hardcoded
+ directories,
+ - under Unix, it reads /etc/fonts/fonts.conf and processes the
+ directories specified there.
+
+ This means that if you have fonts in fancy directories, you need to
+ set them in OSFONTDIR.
+
+ Beware: OSFONTDIR is a kpathsea variable, so fonts found in these
+ paths, though technically system fonts, are registered in the
+ category “texmf”, not “system”. This may have consequences for the
+ lookup order when a font file (or a font with the same name
+ information) is located in both the system and the texmf tree.
+
+--doc]]--
+
+local tag_name = C(alpha^1)
+local comment = P"<!--" * (1 - P"--")^0 * P"-->"
+
+---> header specifica
+local xml_declaration = P"<?xml" * (1 - P"?>")^0 * P"?>"
+local xml_doctype = P"<!DOCTYPE" * xmlws
+ * "fontconfig" * (1 - P">")^0 * P">"
+local header = xml_declaration^-1
+ * (xml_doctype + comment + xmlws)^0
+
+---> enforce root node
+local root_start = P"<" * xmlws^-1 * P"fontconfig" * xmlws^-1 * P">"
+local root_stop = P"</" * xmlws^-1 * P"fontconfig" * xmlws^-1 * P">"
+
+local dquote, squote = P[["]], P"'"
+local xml_namestartchar = S":_" + alpha --- ascii only, funk the rest
+local xml_namechar = S":._" + alpha + digit
+local xml_name = xmlws^-1
+ * C(xml_namestartchar * xml_namechar^0)
+local xml_attvalue = dquote * C((1 - S[[%&"]])^1) * dquote * xmlws^-1
+ + squote * C((1 - S[[%&']])^1) * squote * xmlws^-1
+local xml_attr = Cg(xml_name * P"=" * xml_attvalue)
+local xml_attr_list = Cf(Ct"" * xml_attr^1, rawset)
+
+--[[doc--
+ scan_node creates a parser for a given xml tag.
+--doc]]--
+--- string -> bool -> lpeg_t
+local scan_node = function (tag)
+ --- Node attributes go into a table with the index “attributes”
+ --- (relevant for “prefix="xdg"” and the likes).
+ local p_tag = P(tag)
+ local with_attributes = P"<" * p_tag
+ * Cg(xml_attr_list, "attributes")^-1
+ * xmlws^-1
+ * P">"
+ local plain = P"<" * p_tag * xmlws^-1 * P">"
+ local node_start = plain + with_attributes
+ local node_stop = P"</" * p_tag * xmlws^-1 * P">"
+ --- there is no nesting, the earth is flat ...
+ local node = node_start
+ * Cc(tag) * C(comment + (1 - node_stop)^1)
+ * node_stop
+ return Ct(node) -- returns {string, string [, attributes = { key = val }] }
+end
+
+--[[doc--
+ At the moment, the interesting tags are “dir” for
+ directory declarations, and “include” for including
+ further configuration files.
+
+ spec: http://freedesktop.org/software/fontconfig/fontconfig-user.html
+--doc]]--
+local include_node = scan_node"include"
+local dir_node = scan_node"dir"
+
+local element = dir_node
+ + include_node
+ + comment --> ignore
+ + P(1-root_stop) --> skip byte
+
+local root = root_start * Ct(element^0) * root_stop
+local p_cheapxml = header * root
+
+--lpeg.print(p_cheapxml) ---> 757 rules with v0.10
+
+--[[doc--
+ fonts_conf_scanner() handles configuration files.
+ It is called on an abolute path to a config file (e.g.
+ /home/luser/.config/fontconfig/fonts.conf) and returns a list
+ of the nodes it managed to extract from the file.
+--doc]]--
+--- string -> path list
+local fonts_conf_scanner = function (path)
+ logreport("both", 5, "db", "Read fontconfig file %s.", path)
+ local fh = ioopen(path, "r")
+ if not fh then
+ logreport("both", 3, "db", "Cannot open fontconfig file %s.", path)
+ return
+ end
+ local raw = fh:read"*all"
+ fh:close()
+ logreport("both", 7, "db",
+ "Reading fontconfig file %s completed (%d bytes).",
+ path, #raw)
+
+ logreport("both", 5, "db", "Scan fontconfig file %s.", path)
+ local confdata = lpegmatch(p_cheapxml, raw)
+ if not confdata then
+ logreport("both", 3, "db", "Cannot scan fontconfig file %s.", path)
+ return
+ end
+ logreport("both", 7, "db", "Scan of fontconfig file %s completed.", path)
+ return confdata
+end
+
+local p_conf = P".conf" * P(-1)
+local p_filter = (1 - p_conf)^1 * p_conf
+
+local conf_filter = function (path)
+ if lpegmatch (p_filter, path) then
+ return true
+ end
+ return false
+end
+
+--[[doc--
+
+ read_fonts_conf_indeed() -- Scan paths included from fontconfig
+ configuration files recursively. Called with eight arguments.
+ The first five are
+
+ · the current recursion depth
+ · the path to the file
+ · the expanded $HOME
+ · the expanded $XDG_CONFIG_HOME
+ · the expanded $XDG_DATA_HOME
+
+ determining the path to be checked. Another three arguments are
+ tables that represent the state of the current job as lists of
+ strings; these are always returned. Finally a reference to the
+ find_files function is passed.
+
+--doc]]--
+
+--- size_t -> string -> string -> string -> string
+--- -> string list -> string list -> string list
+--- -> (string -> fun option -> string list)
+--- -> tab * tab * tab
+local read_fonts_conf_indeed
+-- MK Made basedir an explicit parameter to fix relative paths
+read_fonts_conf_indeed = function (depth,
+ start,
+ home,
+ xdg_config_home,
+ xdg_data_home,
+ acc,
+ done,
+ dirs_done,
+ find_files,
+ basedir)
+
+ logreport ("both", 4, "db",
+ "Fontconfig scanner processing path %s.",
+ start)
+ if depth >= traversal_maxdepth then
+ --- prevent overflow of Lua call stack
+ logreport ("both", 0, "db",
+ "Fontconfig scanner hit recursion limit (%d); "
+ .. "aborting directory traversal.",
+ traversal_maxdepth)
+ return acc, done, dirs_done
+ end
+
+ local paths = fonts_conf_scanner(start)
+ if not paths then --- nothing to do
+ return acc, done, dirs_done
+ end
+
+ for i=1, #paths do
+ local pathobj = paths[i]
+ local kind, path = pathobj[1], pathobj[2]
+ local attributes = pathobj.attributes
+
+ if kind == "dir" then
+ if attributes and attributes.prefix == "xdg" then
+ path = filejoin(xdg_data_home, path)
+ end
+ if stringsub(path, 1, 1) == "~" then
+ path = filejoin(home, stringsub(path, 2))
+ end
+ --- We exclude paths with texmf in them, as they should be
+ --- found anyway; also duplicates are ignored by checking
+ --- if they are elements of dirs_done.
+ ---
+ --- FIXME does this mean we cannot access paths from
+ --- distributions (e.g. Context minimals) installed
+ --- separately?
+ if not (stringfind(path, "texmf") or dirs_done[path]) then
+ logreport ("log", 5, "db",
+ "New fontconfig path at %s.",
+ path)
+ acc[#acc+1] = path
+ dirs_done[path] = true
+ end
+
+ elseif kind == "include" then
+ if attributes and attributes.prefix == "xdg" then
+ path = filejoin(xdg_config_home, path)
+ end
+ --- here the path can be four things: a directory or a file,
+ --- an absolute or relative path.
+ if stringsub(path, 1, 1) == "~" then
+ path = filejoin(home, stringsub(path, 2))
+ elseif --- if the path is relative, we make it absolute
+ not ( lfsisfile(path) or lfsisdir(path) )
+ then
+ path = filejoin(basedir, path)
+ end
+ if lfsisfile(path)
+ and kpsereadable_file(path)
+ then
+ if done[path] then
+ logreport("log", 3, "db",
+ "Skipping file at %s, already included.", path)
+ else
+ done[path] = true
+ acc = read_fonts_conf_indeed(depth + 1,
+ path,
+ home,
+ xdg_config_home,
+ xdg_data_home,
+ acc,
+ done,
+ dirs_done,
+ find_files,
+ basedir)
+ end
+ elseif lfsisdir(path) then --- arrow code ahead
+ if done[path] then
+ logreport ("log", 3, "db",
+ "Skipping directory at %s, already included.", path)
+ else
+ done[path] = true
+ local config_files = find_files (path, conf_filter)
+ for _, filename in next, config_files do
+ if done[filename] then
+ logreport ("log", 3, "db",
+ "Skipping file at %s, already included.", filename)
+ else
+ done[filename] = true
+ acc = read_fonts_conf_indeed(depth + 1,
+ filename,
+ home,
+ xdg_config_home,
+ xdg_data_home,
+ acc,
+ done,
+ dirs_done,
+ find_files,
+ basedir)
+ end
+ end
+ end
+ end --- match “kind”
+ end --- iterate paths
+ end
+
+ --inspect(acc)
+ --inspect(done)
+ return acc, done, dirs_done
+end --- read_fonts_conf_indeed()
+-- /MK
+
+--[[doc--
+ read_fonts_conf() sets up an accumulator and two sets
+ for tracking what’s been done.
+
+ Also, the environment variables HOME, XDG_DATA_HOME and
+ XDG_CONFIG_HOME -- which are constants anyways -- are expanded
+ so we don’t have to repeat that over and over again as with the
+ old parser. Now they’re just passed on to every call of
+ read_fonts_conf_indeed().
+--doc]]--
+
+--- list -> (string -> function option -> string list) -> list
+
+local read_fonts_conf = function (path_list, find_files)
+ local home = kpseexpand_path"~" --- could be os.getenv"HOME"
+ local xdg_config_home = kpseexpand_path"$XDG_CONFIG_HOME"
+ if xdg_config_home == "" then xdg_config_home = filejoin(home, ".config") end
+ local xdg_data_home = kpseexpand_path"$XDG_DATA_HOME"
+ if xdg_data_home == "" then xdg_data_home = filejoin(home, ".local/share") end
+ local acc = { } ---> list: paths collected
+ local done = { } ---> set: files inspected
+ local dirs_done = { } ---> set: dirs in list
+ for i=1, #path_list do --- we keep the state between files
+ -- MK Pass the base directory
+ acc, done, dirs_done = read_fonts_conf_indeed(0,
+ path_list[i],
+ home,
+ xdg_config_home,
+ xdg_data_home,
+ acc,
+ done,
+ dirs_done,
+ find_files,
+ filedirname(path_list[i]))
+ -- /MK
+ end
+ return acc
+end
+
+-------------------------------------------------------------------------------
+--- MISC PARSERS
+-------------------------------------------------------------------------------
+
+
+local trailingslashes = slash^1 * P(-1)
+local stripslashes = C((1 - trailingslashes)^0)
+
+local splitcomma = Ct((C(noncomma^1) + comma)^1)
+
+
+
+-------------------------------------------------------------------------------
+--- FONT REQUEST
+-------------------------------------------------------------------------------
+
+
+--[[doc------------------------------------------------------------------------
+
+ The luaotfload font request syntax (see manual)
+ has a canonical form:
+
+ \font<csname>=<prefix>:<identifier>:<features>
+
+ where
+ <csname> is the control sequence that activates the font
+ <prefix> is either “file” or “name”, determining the lookup
+ <identifer> is either a file name (no path) or a font
+ name, depending on the lookup
+ <features> is a list of switches or options, separated by
+ semicolons or commas; a switch is of the form “+” foo
+ or “-” foo, options are of the form lhs “=” rhs
+
+ however, to ensure backward compatibility we also have
+ support for Xetex-style requests.
+
+ for the Xetex emulation see:
+ · The XeTeX Reference Guide by Will Robertson, 2011
+ · The XeTeX Companion by Michel Goosens, 2010
+ · About XeTeX by Jonathan Kew, 2005
+
+
+ caueat emptor.
+
+ the request is parsed into one of **four** different lookup
+ categories: the regular ones, file and name, as well as the
+ Xetex compatibility ones, path and anon. (maybe a better choice
+ of identifier would be “ambig”.)
+
+ according to my reconstruction, the correct chaining of the
+ lookups for each category is as follows:
+
+ | File -> ( db/filename lookup )
+
+ | Name -> ( db/name lookup,
+ db/filename lookup )
+
+ | Path -> ( db/filename lookup,
+ fullpath lookup )
+
+ | Anon -> ( kpse.find_file(), // <- for tfm, ofm
+ db/name lookup,
+ db/filename lookup,
+ fullpath lookup )
+
+ caching of successful lookups is essential. we now as of v2.2
+ have a lookup cache that is stored in a separate file. it
+ pertains only to name: lookups, and is described in more detail
+ in luaotfload-database.lua.
+
+-------------------------------------------------------------------------------
+
+ One further incompatibility between Xetex and Luatex-Fonts consists
+ in their option list syntax: apparently, Xetex requires key-value
+ options to be prefixed by a "+" (ascii “plus”) character. We
+ silently accept this as well, dropping the first byte if it is a
+ plus or minus character.
+
+ Reference: https://github.com/lualatex/luaotfload/issues/79#issuecomment-18104483
+
+--doc]]------------------------------------------------------------------------
+
+
+--[[doc--
+
+ Xetex style indexing begins at zero which we just increment before
+ passing it along to the font loader. Ymmv.
+
+--doc]]--
+
+local handle_xetex_option = function (val)
+ return tostring(1 + tonumber(val))
+end
+
+--[[doc--
+
+ Dirty test if a file: request is actually a path: lookup; don’t
+ ask! Note this fails on Windows-style absolute paths. These will
+ *really* have to use the correct request.
+
+--doc]]--
+
+local check_garbage = function (_,i, garbage)
+ if stringfind(garbage, "/") then
+ logreport("log", 0, "load", --- ffs use path!
+ "warning: path in file: lookups is deprecated; ")
+ logreport("log", 0, "load", "use bracket syntax instead!")
+ logreport("log", 0, "load",
+ "position: %d; full match: %q",
+ i, garbage)
+ return true
+ end
+ return false
+end
+
+local featuresep = comma + semicolon
+
+--- modifiers ---------------------------------------------------------
+--[[doc--
+ The slash notation: called “modifiers” (Kew) or “font options”
+ (Robertson, Goosens)
+ we only support the shorthands for italic / bold / bold italic
+ shapes, as well as setting optical size, the rest is ignored.
+--doc]]--
+local style_modifier = (P"BI" + P"IB" + P"bi" + P"ib" + S"biBI")
+ / stringlower
+local size_modifier = S"Ss" * P"=" --- optical size
+ * Cc"optsize" * C(decimal)
+local other_modifier = P"AAT" + P"aat" --- apple stuff; unsupported
+ + P"ICU" + P"icu" --- not applicable
+ + P"GR" + P"gr" --- sil stuff; unsupported
+local garbage_modifier = ((1 - colon - slash)^0 * Cc(false))
+local modifier = slash * (other_modifier --> ignore
+ + Cs(style_modifier) --> collect
+ + Ct(size_modifier) --> collect
+ + garbage_modifier) --> warn
+local modifier_list = Cg(Ct(modifier^0), "modifiers")
+
+--- combining ---------------------------------------------------------
+---
+--- \font \three = combo: 1->42; 2->99,0xdeadbeef; 3->(1,U+2a-U+1337*42)
+--- v +~ v +~ +~~~~~~~~~ v v +~~~ +~~~~~ +~
+--- | | | | | | | | | |
+--- | | | | | | | | | |
+--- idx : ---+--÷---+--÷--÷-----------+ | +----+ |
+--- | | | | | |
+--- id : ------+------+--÷---------------+ +-----------+
+--- | |
+--- chars : ----------------+-----------------+
+---
+local comborowsep = ws * semicolon * ws
+local combomapsep = ws * P"->" * ws
+local combodefsep = ws * comma * ws
+local comborangesep = ws * asterisk * ws
+
+local combohex = hex / tonumber
+local combouint = digit^1 / tonumber
+local tonumber16 = function (s) return tonumber (s, 16) end
+local combouni = P"U+" * (digit^1 / tonumber16)
+local combonum = combohex + combouni + combouint
+local comborange = Ct(combonum * dash * combonum) + combonum
+local combochars = comborange * (comborangesep * comborange)^0
+local parenthesized = function (p) return P"(" * ws * p * ws * P")" end
+
+local comboidxpat = Cg(combouint, "idx")
+local comboidpat = Cg(combouint, "id" )
+local combocharspat = Cg(P"fallback" * Cc(true) + Ct(combochars^1), "chars")
+local comboidcharspat = comboidpat * combodefsep * combocharspat
+
+local comboidx = parenthesized (comboidxpat ) + comboidxpat
+local comboid = parenthesized (comboidpat ) + comboidpat
+local comboidchars = parenthesized (comboidcharspat) + comboidcharspat
+
+local combodef1 = Ct(comboidx * combomapsep * comboid) --> no chars
+local combodef = Ct(comboidx * combomapsep * comboidchars)
+local combolist = Ct(combodef1 * (comborowsep * combodef)^1)
+
+--- subfonts ----------------------------------------------------------
+--- This rule is present in the original parser. It sets the “sub”
+--- field of the specification which allows addressing a specific
+--- font inside a TTC container. Neither in Luatex-Fonts nor in
+--- Luaotfload is this documented, so we might as well silently drop
+--- it. However, as backward compatibility is one of our prime goals we
+--- just insert it here and leave it undocumented until someone cares
+--- to ask. (Note: afair subfonts are numbered, but this rule matches a
+--- string; I won’t mess with it though until someone reports a
+--- problem.)
+--- local subvalue = P("(") * (C(P(1-S("()"))^1)/issub) * P(")") -- for Kim
+--- Note to self: subfonts apparently start at index 0. Tested with
+--- Cambria.ttc that includes “Cambria Math” at 0 and “Cambria” at 1.
+--- Other values cause luatex to segfault.
+local subfont = P"(" * Cg((1 - S"()")^1, "sub") * P")"
+
+--- lookups -----------------------------------------------------------
+local fontname = C((1-S":(/")^1) --- like luatex-fonts
+local unsupported = Cmt((1-S":(")^1, check_garbage)
+local combo = Cg(P"combo", "lookup") * colon * ws
+ * Cg(combolist, "name")
+--- initially we intended file: to emulate the behavior of
+--- luatex-fonts, i.e. no paths allowed. after all, we do have XeTeX
+--- emulation with the path lookup and it interferes with db lookups.
+--- turns out fontspec and other widely used packages rely on file:
+--- with paths already, so we’ll add a less strict rule here. anyways,
+--- we’ll emit a warning.
+local prefixed = P"file:" * ws * Cg(Cc"path", "lookup")
+ * Cg(unsupported, "name")
+ + Cg(P"name" + "file" + "kpse" + "my", "lookup")
+ * colon * ws * Cg(fontname, "name")
+local unprefixed = Cg(Cc"anon", "lookup") * Cg(fontname, "name")
+--- Bracketed “path” lookups: These may contain any character except
+--- for unbalanced brackets. A backslash escapes any following
+--- character. Everything inside the outermost brackets is treated as
+--- part of the filename or path to look up. Subfonts may be specified
+--- in parens *after* the closing bracket. Note that this differs from
+--- Xetex whose syntax expects the subfont passed inside the brackets,
+--- separated by a colon.
+local path_escape = backslash / "" * patterns.utf8char
+local path_content = path_escape + (1 - brackets)
+local path_balanced = { (path_content + V(2))^1
+ , lbrk * V(1)^-1 * rbrk }
+local path_lookup = Cg(Cc"path", "lookup")
+ * lbrk * Cg(Cs(path_balanced), "name") * rbrk
+ * subfont^-1
+
+--- features ----------------------------------------------------------
+local balanced_braces = P{((1 - S'{}') + '{' * V(1) * '}')^0}
+local field_char = '{' * balanced_braces * '}' + (1 - S'={}' - featuresep)
+local field = '{' * C(balanced_braces) * '}' + C(field_char^1)
+--- assignments are “lhs=rhs”
+--- or “+lhs=rhs” (Xetex-style)
+--- switches are “+key” | “-key”
+local normal_option = field * ws * equals * ws * field
+local xetex_option = P"+" * ws * ( field * ws * equals * ws
+ * (digit^1/handle_xetex_option)
+ + normal_option)
+local assignment = xetex_option
+ + normal_option
+local switch = P"-" * ws * field * Cc(false)
+ + P"+"^-1 * ws * field * Cc(true)
+local feature_expr = ws * Cg(assignment + switch) * ws
+local option = feature_expr
+local feature_list = Cf(Ct""
+ * option
+ * (featuresep * option^-1)^0
+ , rawset)
+ * featuresep^-1
+--- top-level rules ---------------------------------------------------
+--- \font\foo=<specification>:<features>
+local features = Cg(feature_list, "features")
+local specification = (prefixed + unprefixed)
+ * subfont^-1
+ * modifier_list
+local font_request = Ct(path_lookup * (colon^-1 * features)^-1
+ + combo --> TODO: feature list needed?
+ + specification * (colon * features)^-1)
+
+-- lpeg.print(font_request)
+--- v2.5 parser: 1065 rules
+--- v1.2 parser: 230 rules
+
+-------------------------------------------------------------------------------
+--- INI FILES
+-------------------------------------------------------------------------------
+
+--[[doc--
+
+ Luaotfload uses the pervasive flavor of the INI files that allows '#' in
+ addition to ';' to indicate comment lines (see git-config(1) for a
+ description of the syntax we’re targeting).
+
+--doc]]--
+
+local truth_ids = {
+ ["true"] = true,
+ ["1"] = true,
+ yes = true,
+ on = true,
+ ["false"] = false,
+ ["2"] = false,
+ no = false,
+ off = false,
+}
+
+local maybe_cast = function (var)
+ local bool = truth_ids[var]
+ if bool ~= nil then
+ return bool
+ end
+ return tonumber (var) or var
+end
+
+local escape = function (chr, repl)
+ return (backslash * P(chr) / (repl or chr))
+end
+
+local valid_escapes = escape "\""
+ + escape "\\"
+ + escape ("n", "\n")
+ + escape ("t", "\t")
+ + escape ("b", "\b")
+local comment_char = semicolon + gartenzaun
+local comment_line = ws * comment_char * (1 - eol)^0 * eol
+local blank_line = ws * eol
+local skip_line = comment_line + blank_line
+local ini_id_char = alpha + (dash / "_")
+local ini_id = Cs(alpha * ini_id_char^0) / stringlower
+local ini_value_char = (valid_escapes + (1 - linebreak - backslash - comment_char))
+local ini_value = (Cs (ini_value_char^0) / string.strip)
+ * (comment_char * (1 - eol)^0)^-1
+local ini_string_char = (valid_escapes + (1 - linebreak - dquote - backslash))
+local ini_string = dquote
+ * Cs (ini_string_char^0)
+ * dquote
+
+local ini_heading_title = Ct (Cg (ini_id, "title")
+ * (ws * Cg (ini_string / stringlower, "subtitle"))^-1)
+local ini_heading = lbrk * ws
+ * Cg (ini_heading_title, "section")
+ * ws * rbrk * ws * eol
+
+local ini_variable_full = Cg (ws
+ * ini_id
+ * ws
+ * equals
+ * ws
+ * (ini_string + (ini_value / maybe_cast))
+ * ws
+ * eol)
+local ini_variable_true = Cg (ws * ini_id * ws * eol * Cc (true))
+local ini_variable = ini_variable_full
+ + ini_variable_true
+ + skip_line
+local ini_variables = Cg (Cf (Ct "" * ini_variable^0, rawset), "variables")
+
+local ini_section = Ct (ini_heading * ini_variables)
+local ini_sections = skip_line^0 * ini_section^0
+local parse_config = Ct (ini_sections)
+
+--[=[doc--
+
+ The INI parser converts an input of the form
+
+ [==[
+ [foo]
+ bar = baz
+ xyzzy = no
+ buzz
+
+ [lavernica "brutalitops"]
+ # It’s a locomotive that runs on us.
+ laan-ev = zip zop zooey ; jib-jab
+ Crouton = "Fibrosis \"\\ # "
+
+ ]==]
+
+ to a Lua table of the form
+
+ { { section = { title = "foo" },
+ variables = { bar = "baz",
+ xyzzy = false,
+ buzz = true } },
+ { section = { title = "boing",
+ subtitle = "brutalitops" },
+ variables = { ["laan-ev"] = "zip zop zooey",
+ crouton = "Fibrosis \"\\ # " } } }
+
+--doc]=]--
+
+return function ()
+ logreport = luaotfload.log.report
+ luaotfload.parsers = {
+ --- parameters
+ traversal_maxdepth = traversal_maxdepth,
+ --- main parsers
+ read_fonts_conf = read_fonts_conf,
+ font_request = font_request,
+ config = parse_config,
+ --- common patterns
+ stripslashes = stripslashes,
+ splitcomma = splitcomma,
+ }
+ return true
+end
+
+-- vim:ft=lua:tw=71:et:sw=2:sts=4:ts=8
diff --git a/macros/luatex/generic/luaotfload/luaotfload-resolvers.lua b/macros/luatex/generic/luaotfload/luaotfload-resolvers.lua
new file mode 100644
index 0000000000..839155a979
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-resolvers.lua
@@ -0,0 +1,303 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-resolvers.lua
+-- USAGE: ./luaotfload-resolvers.lua
+-- DESCRIPTION: Resolvers for hooking into the fontloader
+-- REQUIREMENTS: Luaotfload and a decent bit of courage
+-- AUTHOR: Philipp Gesang (Phg), <phg@phi-gamma.net>
+-----------------------------------------------------------------------
+--
+--- The bare fontloader uses a set of simplistic file name resolvers
+--- that must be overloaded by the user (i. e. us).
+
+local ProvidesLuaModule = {
+ name = "luaotfload-resolvers",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / resolvers",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+if not lualibs then error "this module requires Luaotfload" end
+if not luaotfload then error "this module requires Luaotfload" end
+
+--[[doc--
+
+ Relying on the \verb|name:| resolver for everything has been the
+ source of permanent trouble with the database.
+ With the introduction of the new syntax parser we now have enough
+ granularity to distinguish between the \XETEX emulation layer and
+ the genuine \verb|name:| and \verb|file:| lookups of \LUATEX-Fonts.
+ Another benefit is that we can now easily plug in or replace new
+ lookup behaviors if necessary.
+ The name resolver remains untouched, but it calls
+ \luafunction{fonts.names.resolve()} internally anyways (see
+ \fileent{luaotfload-database.lua}).
+
+--doc]]--
+
+local next = next
+local tableconcat = table.concat
+local kpsefind_file = kpse.find_file
+local lfsisfile = lfs.isfile
+local stringlower = string.lower
+local stringformat = string.format
+local filesuffix = file.suffix
+local fileremovesuffix = file.removesuffix
+local luatexbase = luatexbase
+local logreport = luaotfload.log.report
+
+--[[doc--
+
+ \identifier{luaotfload} promises easy access to system fonts.
+ Without additional precautions, this cannot be achieved by
+ \identifier{kpathsea} alone, because it searches only the
+ \fileent{texmf} directories by default.
+ Although it is possible for \identifier{kpathsea} to include extra
+ paths by adding them to the \verb|OSFONTDIR| environment variable,
+ this is still short of the goal »\emphasis{it just works!}«.
+ When building the font database \identifier{luaotfload} scans
+ system font directories anyways, so we already have all the
+ information for looking sytem fonts.
+ With the release version 2.2 the file names are indexed in the
+ database as well and we are ready to resolve \verb|file:| lookups
+ this way.
+ Thus we no longer need to call the \identifier{kpathsea} library in
+ most cases when looking up font files, only when generating the
+ database, and when verifying the existence of a file in the
+ \fileent{texmf} tree.
+
+--doc]]--
+
+local function resolve_file (specification)
+ local name, _format, success = fonts.names.lookup_font_file (specification.name)
+ if success then return name end
+ logreport ("log", 1, "resolve", "file lookup of %q unsuccessful", name)
+end
+
+--[[doc--
+
+ Prior to version 2.2, \identifier{luaotfload} did not distinguish
+ \verb|file:| and \verb|path:| lookups, causing complications with
+ the resolver.
+ Now we test if the requested name is an absolute path in the file
+ system, otherwise we fall back to the \verb|file:| lookup.
+
+--doc]]--
+
+local function resolve_path (specification)
+ local name = specification.name
+ if lfsisfile (name) then return name end
+ logreport ("log", 1, "resolve",
+ "path lookup of %q unsuccessful, falling back to file:",
+ name)
+ return resolve_file (specification)
+end
+
+--[[doc--
+
+ The \verb|name:| resolver.
+
+--doc]]--
+
+--- fonts.names.resolvers.name -- Customized version of the
+--- generic name resolver.
+
+local function resolve_name (specification)
+ local resolver = fonts.names.lookup_font_name_cached
+ if config.luaotfload.run.resolver == "normal" then
+ resolver = fonts.names.lookup_font_name
+ end
+ local resolved, subfont = resolver (specification)
+ if resolved then
+ logreport ("log", 1, "resolve", "name lookup %q -> \"%s%s\"",
+ specification.name, resolved,
+ subfont and stringformat ("(%d)", subfont) or "")
+ return resolved, tonumber(subfont)
+ end
+ return resolve_file (specification)
+end
+
+--[[doc--
+
+ We classify as \verb|anon:| those requests that have neither a
+ prefix nor brackets. According to Khaled\footnote{%
+ % XXX dead link‽
+ \url{https://github.com/phi-gamma/luaotfload/issues/4#issuecomment-17090553}.
+ }
+ they are the \XETEX equivalent of a \verb|name:| request, so we
+ will be treating them as such or, at least, in a similar fashion.
+
+ Not distinguishing between “anon” and “name” requests has a serious
+ drawback: The syntax is overloaded for requesting fonts in
+ \identifier{Type1} (\abbrev{tfm}, \abbrev{ofm}) format.
+ These are essentially \verb|file:| lookups and must be caught
+ before the \verb|name:| resolver kicks in, lest they cause the
+ database to update.
+ Even if we were to require the \verb|file:| prefix for all
+ \identifier{Type1} requests, tests have shown that certain fonts
+ still include further fonts (e.~g. \fileent{omlgcb.ofm} will ask
+ for \fileent{omsecob.tfm}) \emphasis{using the old syntax}.
+ For this reason, we introduce an extra check with an early return.
+
+--doc]]--
+
+local tex_formats = { "tfm", "ofm" }
+
+local resolve_tex_format = function (specification)
+ local name = specification.name
+ for i=1, #tex_formats do
+ local format = tex_formats [i]
+ local resolved = resolvers.findfile(name, format)
+ if resolved then
+ return resolved, format
+ end
+ end
+end
+
+local resolve_path_if_exists = function (specification)
+ local spec = specification.specification
+ local exists = lfsisfile (spec)
+ if exists then
+ --- If this path is taken a file matching the specification
+ --- literally was found. In this situation, Luaotfload is
+ --- expected to load that file directly, even though we provide
+ --- explicit “file” and “path” lookups to address exactly this
+ --- situation.
+ logreport ("log", 1, "resolve",
+ "file %q exists, performing path lookup", spec)
+ return spec
+ end
+end
+
+--[[doc--
+ Custom file resolvers via callback.
+--doc]]--
+
+local resolve_my = function (specification)
+ return luatexbase.call_callback ("luaotfload.resolve_font", specification)
+end
+
+local resolve_methods = {
+ tex = resolve_tex_format,
+ path = resolve_path_if_exists,
+ name = resolve_name,
+ file = resolve_file,
+ my = resolve_my,
+}
+
+local resolve_sequence = function (seq, specification)
+ for i = 1, #seq do
+ local id = seq [i]
+ local mth = resolve_methods [id]
+ if not mth then
+ logreport ("both", 0, "resolve",
+ "step %d: invalid lookup method %q", i, id)
+ else
+ logreport ("both", 3, "resolve", "step %d: apply method %q (%s)", i, id, mth)
+ local result, t = mth (specification)
+ if result then
+ logreport ("both", 3, "resolve",
+ "%d: method %q resolved %q -> %s.",
+ i, id, specification.specification, result)
+ return result, t
+ end
+ end
+ end
+ logreport ("both", 0, "resolve",
+ "sequence of %d lookups yielded nothing appropriate.", #seq)
+end
+
+local default_anon_sequence = {
+ "tex", "path", "name",
+}
+
+local function resolve_anon (specification)
+ return resolve_sequence (config.luaotfload.run.anon_sequence, specification)
+end
+
+--[[doc--
+
+ {\bfseries EXPERIMENTAL}:
+ \identifier{kpse}-only resolver, for those who can do without
+ system fonts.
+
+--doc]]--
+
+local function resolve_kpse (specification)
+ local name = specification.name
+ local suffix = stringlower (filesuffix (name))
+ if suffix and fonts.formats[suffix] then
+ local resolved = resolvers.findfile(name, suffix)
+ if resolved then return resolved end
+ end
+ for t, format in next, fonts.formats do --- brute force
+ local resolved = kpsefind_file (name, format)
+ if resolved then return resolved, t end
+ end
+end
+
+local function wrap_resolver(resolver)
+ return function (specification)
+ local filename, sub, forced = resolver(specification)
+ if type(sub) ~= "number" then
+ forced = sub
+ sub = nil
+ end
+ if filename then
+ specification.resolved = filename
+ specification.filename = filename
+ specification.name = filename
+ specification.sub = sub or specification.sub
+ specification.forced = specification.forced or forced
+ if not specification.forced then
+ local suffix = stringlower (filesuffix (filename))
+ if suffix and fonts.formats[suffix] then
+ specification.forced = suffix
+ end
+ end
+ if specification.forced then
+ specification.forcedname = filename
+ end
+ return true
+ end
+ return false
+ end
+end
+
+local resolvers = table.merge(luaotfload.resolvers, {
+ path = resolve_path,
+ name = resolve_name,
+ anon = resolve_anon,
+ file = resolve_file,
+ kpse = resolve_kpse,
+ my = resolve_my,
+})
+luaotfload.resolvers = resolvers
+
+return function()
+ if luatexbase and luatexbase.create_callback then
+ luatexbase.create_callback ("luaotfload.resolve_font",
+ "exclusive", function () end)
+ end
+ logreport ("log", 5, "resolvers", "installing font resolvers", name)
+ local request_resolvers = fonts.definers.resolvers
+ for k, _ in pairs(resolvers) do
+ request_resolvers[k] = nil
+ end
+ setmetatable(request_resolvers, {__index = function(t, n)
+ if not resolvers[n] then return end
+ local wrapped = wrap_resolver(resolvers[n])
+ t[n] = wrapped
+ return wrapped
+ end})
+ fonts.formats.ofm = "type1"
+ fonts.encodings = fonts.encodings or { }
+ fonts.encodings.known = fonts.encodings.known or { }
+ return true
+end
+--- vim:ft=lua:ts=8:sw=4:et:tw=79
diff --git a/macros/luatex/generic/luaotfload/luaotfload-status.lua b/macros/luatex/generic/luaotfload/luaotfload-status.lua
new file mode 100644
index 0000000000..bd7b328979
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-status.lua
@@ -0,0 +1,90 @@
+return {
+ ["hashes"]={
+ { "fontloader-2019-08-11.lua", "9ad89bd01fccf2f98b8777ad42851c58" },
+ { "fontloader-util-fil.lua", "4bb3e4dc72e308d8ed67cd7a80027fa7" },
+ { "fontloader-util-str.lua", "3c829af0b336703e62cb5a1cb7a6e503" },
+ { "fontloader-l-unicode.lua", "d46cc6cf18fb3f368ef1e404dc9fcb5c" },
+ { "fontloader-l-math.lua", "a373be3ed2db0d5f98588fa81abca48f" },
+ { "fontloader-l-boolean.lua", "18ed6c4b2c40dd87224ea33229548d20" },
+ { "fontloader-l-file.lua", "3d6ea476061292a0da98c3f65cdabe46" },
+ { "fontloader-l-io.lua", "42608ad95eb2822fdc370d1c11f08fb5" },
+ { "fontloader-l-table.lua", "63b13279139d2f94d29238b0d6242330" },
+ { "fontloader-l-string.lua", "e1347bef0eeeff9f098df83b30b32df9" },
+ { "fontloader-l-function.lua", "f771cc91839ebcdfc094083434fbe00f" },
+ { "fontloader-l-lpeg.lua", "a5364ddabb490408da9276ea7f7a7ba1" },
+ { "fontloader-l-lua.lua", "9e5e9d4f3b8f9e337f28aa2322192b94" },
+ { "fontloader-fonts-gbn.lua", "d25472d54c4841db43a745764a63533e" },
+ { "fontloader-fonts-lig.lua", "b9dbe77ce747d4c35bb2a20ffbe5aa51" },
+ { "fontloader-fonts-ext.lua", "01015ab3758cdc2af29394e6d502a91a" },
+ { "fontloader-fonts-def.lua", "5ad79120ebc5e60f4d322fb3ee13bffe" },
+ { "fontloader-fonts-tfm.lua", "3bbba3214fd0b8c6f35ad85592fc2917" },
+ { "fontloader-fonts-enc.lua", "3e71a54297e8f85a1ac438bb0f20dd79" },
+ { "fontloader-fonts-mis.lua", "bc9eb43c27f63ce9d0fff67e104fe1c6" },
+ { "fontloader-basics-chr.lua", "58b7ef0c486e06090b362971b9f85e27" },
+ { "fontloader-basics-nod.lua", "65064d03c2650a1761ee13ebd9e1400a" },
+ { "fontloader-font-imp-effects.lua", "73a660359a0ec71e44cc2b7225a715ac" },
+ { "fontloader-font-imp-italics.lua", "fe1ca80fb5ea4a2f8d2d5c484e7ba913" },
+ { "fontloader-font-imp-ligatures.lua", "043daa4fcccf2560868da359d71d3a4a" },
+ { "fontloader-font-imp-tex.lua", "77c374b0ef00c2fb12188ec42beb4257" },
+ { "fontloader-font-def.lua", "f66c365dae4499f982d8bf16e5d37de3" },
+ { "fontloader-font-lua.lua", "55b281fb98f7bd848fc19928f376f647" },
+ { "fontloader-font-afk.lua", "54d554530e75c57c56ee76234724e26d" },
+ { "fontloader-font-one.lua", "987c5c5ed3754ad2feab80985067d59e" },
+ { "fontloader-font-onr.lua", "d4d2449b4084e6afb1837ae5835082cc" },
+ { "fontloader-font-otc.lua", "95a4ff28ba4afb55a978a4aecfd688bf" },
+ { "fontloader-font-ocl.lua", "b720867fb19a23f0b50377efd2a3c54a" },
+ { "fontloader-font-osd.lua", "79eb2fc4a71364fd73c8b996a109f5df" },
+ { "fontloader-font-ots.lua", "d5504847a278385cd0d20ecf1b3d59cc" },
+ { "fontloader-font-ota.lua", "d6dfb94563d6a52675e274b2e673e4a6" },
+ { "fontloader-font-otj.lua", "66c7a910d95d4a52b81061de776898e1" },
+ { "fontloader-font-oto.lua", "52804afd96f4be005f513a012b874668" },
+ { "fontloader-font-otl.lua", "940f9c5ad84f4968a8488f4da2d15e2d" },
+ { "fontloader-font-oup.lua", "669e479e716999edc626a1f045bd76fa" },
+ { "fontloader-font-dsp.lua", "b5bf2f1c198e027a0d4ededcdf3947b4" },
+ { "fontloader-font-ttf.lua", "44e61cef50dab9b1aaf48130f9367c34" },
+ { "fontloader-font-cff.lua", "98d5a660ea803b65cb883c009ecf3c0b" },
+ { "fontloader-font-ott.lua", "aba6d8335a5f38a5a62d3631492f3392" },
+ { "fontloader-font-oti.lua", "dbae7722baae24d917a17176553825cf" },
+ { "fontloader-font-otr.lua", "b1c03925c949027c86f781785fa7a208" },
+ { "fontloader-font-vfc.lua", "94937140f2c909e9c831ba021f1ab303" },
+ { "fontloader-font-map.lua", "f486746e90fe972de4b73e208ac7cbb2" },
+ { "fontloader-font-cid.lua", "4d87988efa86020a14708ee03c23415f" },
+ { "fontloader-font-con.lua", "ca733211a0555d9a93b1e2f7ebc937d3" },
+ { "fontloader-font-ini.lua", "4299a02110bbd7c0d27e131235c5319d" },
+ { "fontloader-data-con.lua", "7ce546725b1550f655c78ac9d69419ca" },
+ { "fontloader-reference.lua", "759787e7ee75437382c0a2c4f8fe3b81" },
+ { "fontloader-basics-gen.lua", "b21e91bbd534f77e368f0ec13f865aed" },
+ { "mktests", "c7cff7025962922944376acc1ffa9c47" },
+ { "mkstatus", "d84c8b2ae4c2335c5dbd9fba4846f0e9" },
+ { "mkcharacters", "92c24bb582fc84c0365634f29eb89863" },
+ { "mkglyphlist", "557836886d4f0e6d656eac3ded4456a2" },
+ { "mkimport", "60e0b11a1a68719033e86a3e0f4d5e86" },
+ { "luaotfload-glyphlist.lua", "8a1cbf89f48a8ebe05a13345352a3435" },
+ { "luaotfload-characters.lua", "593ce9dccf6ddc4f7d4be0514f581102" },
+ { "luaotfload-unicode.lua", "aac378708c062d4de18132ae7600526f" },
+ { "luaotfload-resolvers.lua", "7e777d41afc10c928cd26dccfed6ba09" },
+ { "luaotfload-parsers.lua", "c69570b5f57d26abff8304f3a8eade58" },
+ { "luaotfload-loaders.lua", "920578f2f66758755c20fbf3539b3542" },
+ { "luaotfload-notdef.lua", "a4a40c92368510dcd81f6e95124bb2d3" },
+ { "luaotfload-embolden.lua", "4b6a0240b0f696d63cf2b343603fc742" },
+ { "luaotfload-letterspace.lua", "29453f635acb72ef76ec19942ce0449b" },
+ { "luaotfload-features.lua", "1c837c95c485d54204157fd3840e177e" },
+ { "luaotfload-database.lua", "3a3d0cbb02b0c9ff53b0dab969c7a879" },
+ { "luaotfload-configuration.lua", "37ffbef314b79ca2ae9bfaf4e4552207" },
+ { "luaotfload-colors.lua", "9b1ffa13d20cc4d1f2016e8d5b0939f1" },
+ { "luaotfload-auxiliary.lua", "99ff2ebee659717c2d1f9999e3ab4448" },
+ { "luaotfload-filelist.lua", "9de0e08f4b15acd7c56602ef362967e1" },
+ { "luaotfload-tool.lua", "4a1be51390301a48480681e66d9be64f" },
+ { "luaotfload-diagnostics.lua", "8c50e2459731ca15a511e4bd0b0d7685" },
+ { "luaotfload-log.lua", "981ccf90bb3a970b056dbfa87046b36d" },
+ { "luaotfload-init.lua", "acfe693817999d5c09272f3b33fe1aad" },
+ { "luaotfload-main.lua", "80b07ab0301a7b8fb5d03acec1b5c5dc" },
+ },
+ ["notes"]={
+ ["committer"]="Ulrike Fischer <fischer@troubleshooting-tex.de>",
+ ["description"]="v2.991/2019-08-11",
+ ["loader"]="fontloader-2019-08-11.lua",
+ ["revision"]="a86a6798c324c745af7b04f33fa188298d749a2a",
+ ["timestamp"]="2019-08-19 19:38:30 +0200",
+ },
+} \ No newline at end of file
diff --git a/macros/luatex/generic/luaotfload/luaotfload-tool.1 b/macros/luatex/generic/luaotfload/luaotfload-tool.1
new file mode 100644
index 0000000000..81b5c22d6d
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-tool.1
@@ -0,0 +1,442 @@
+.\" Man page generated from reStructuredText.
+.
+.TH LUAOTFLOAD-TOOL 1 "2019-08-11" "2.991" "text processing"
+.SH NAME
+luaotfload-tool \- generate and query the Luaotfload font names database
+.
+.nr rst2man-indent-level 0
+.
+.de1 rstReportMargin
+\\$1 \\n[an-margin]
+level \\n[rst2man-indent-level]
+level margin: \\n[rst2man-indent\\n[rst2man-indent-level]]
+-
+\\n[rst2man-indent0]
+\\n[rst2man-indent1]
+\\n[rst2man-indent2]
+..
+.de1 INDENT
+.\" .rstReportMargin pre:
+. RS \\$1
+. nr rst2man-indent\\n[rst2man-indent-level] \\n[an-margin]
+. nr rst2man-indent-level +1
+.\" .rstReportMargin post:
+..
+.de UNINDENT
+. RE
+.\" indent \\n[an-margin]
+.\" old: \\n[rst2man-indent\\n[rst2man-indent-level]]
+.nr rst2man-indent-level -1
+.\" new: \\n[rst2man-indent\\n[rst2man-indent-level]]
+.in \\n[rst2man-indent\\n[rst2man-indent-level]]u
+..
+.SH SYNOPSIS
+.sp
+\fBluaotfload\-tool\fP [ \-bcDfFiIlLnpqRSuvVhw ]
+.INDENT 0.0
+.TP
+.B \fBluaotfload\-tool\fP \-\-update [ \-\-force ] [ \-\-quiet ] [ \-\-verbose ]
+[ \-\-prefer\-texmf ] [ \-\-dry\-run ]
+[ \-\-formats=[+|\-]EXTENSIONS ]
+[ \-\-no\-compress ] [ \-\-no\-strip ]
+[ \-\-local ] [ \-\-max\-fonts=N ]
+.TP
+.B \fBluaotfload\-tool\fP \-\-find=FONTNAME [ \-\-fuzzy ] [ \-\-info ] [ \-\-inspect ]
+[ \-\-no\-reload ]
+.UNINDENT
+.sp
+\fBluaotfload\-tool\fP \-\-flush\-lookups
+.sp
+\fBluaotfload\-tool\fP \-\-cache=DIRECTIVE
+.sp
+\fBluaotfload\-tool\fP \-\-list=CRITERION[:VALUE] [ \-\-fields=F1,F2,...,Fn ]
+.sp
+\fBluaotfload\-tool\fP \-\-bisect=DIRECTIVE
+.sp
+\fBluaotfload\-tool\fP \-\-help
+.sp
+\fBluaotfload\-tool\fP \-\-version
+.sp
+\fBluaotfload\-tool\fP \-\-show\-blacklist
+.sp
+\fBluaotfload\-tool\fP \-\-diagnose=CHECK
+.sp
+\fBluaotfload\-tool\fP \-\-conf=FILE \-\-dumpconf
+.SH DESCRIPTION
+.sp
+luaotfload\-tool accesses the font names database that is required by
+the \fILuaotfload\fP package. There are two general modes: \fBupdate\fP and
+\fBquery\fP\&.
+.INDENT 0.0
+.IP \(bu 2
+\fBupdate\fP: update the database or rebuild it entirely;
+.IP \(bu 2
+\fBquery\fP: resolve a font name or display close matches.
+.UNINDENT
+.SH OPTIONS
+.SS update mode
+.INDENT 0.0
+.TP
+.B \-\-update\fP,\fB \-u
+Update the database; indexes new fonts.
+.TP
+.B \-\-force\fP,\fB \-f
+Force rebuilding of the database; re\-indexes
+all fonts.
+.TP
+.B \-\-local\fP,\fB \-L
+Include font files in \fB$PWD\fP\&. This option
+will cause large parts of the database to be
+rebuilt. Thus it is quite inefficient.
+Additionally, if local font files are found,
+the database is prevented from being saved
+to disk, so the local fonts need to be parsed
+with every invocation of \fBluaotfload\-tool\fP\&.
+.TP
+.B \-\-no\-reload\fP,\fB \-n
+Suppress auto\-updates to the database (e.g.
+when \fB\-\-find\fP is passed an unknown name).
+.TP
+.B \-\-no\-compress\fP,\fB \-c
+Do not filter the plain text version of the
+font index through gzip. Useful for debugging
+if your editor is built without zlib.
+.TP
+.B \-\-prefer\-texmf\fP,\fB \-p
+Organize the file name database in a way so
+that it prefer fonts in the \fITEXMF\fP tree over
+system fonts if they are installed in both.
+.TP
+.BI \-\-formats\fB= EXTENSIONS
+Extensions of the font files to index.
+Where \fIEXTENSIONS\fP is a comma\-separated list of
+supported file extensions (otf, ttf, ttc).
+If the list is prefixed
+with a \fB+\fP sign, the given list is added to
+the currently active one; \fB\-\fP subtracts.
+Default: \fIotf,ttf,ttc\fP\&.
+Examples:
+.INDENT 7.0
+.IP 1. 3
+\fB\-\-formats=\-ttc,ttf\fP would skip
+TrueType fonts and font collections;
+.IP 2. 3
+\fB\-\-formats=otf\fP would scan only OpenType
+files;
+.IP 3. 3
+\fB\-\-formats=+afm\fP includes binary
+Postscript files accompanied by an AFM file.
+.UNINDENT
+.UNINDENT
+.SS query mode
+.INDENT 0.0
+.TP
+.BI \-\-find\fB= NAME
+Resolve a font name; this looks up <name> in
+the database and prints the file name it is
+mapped to.
+\fB\-\-find\fP also understands request syntax,
+i.e. \fB\-\-find=file:foo.otf\fP checks whether
+\fBfoo.otf\fP is indexed.
+.TP
+.B \-\-fuzzy\fP,\fB \-F
+Show approximate matches to the file name if
+the lookup was unsuccessful (requires
+\fB\-\-find\fP).
+.TP
+.B \-\-info\fP,\fB \-i
+Display basic information to a resolved font
+file (requires \fB\-\-find\fP).
+.TP
+.B \-\-inspect\fP,\fB \-I
+Display detailed information by loading the
+font and analyzing the font table; very slow!
+For the meaning of the returned fields see
+the LuaTeX documentation.
+(requires \fB\-\-find\fP).
+.TP
+.BI \-\-list\fB= CRITERION
+Show entries, where \fICRITERION\fP is one of the
+following:
+.INDENT 7.0
+.IP 1. 3
+the character \fB*\fP, selecting all entries;
+.IP 2. 3
+a field of a database entry, for instance
+\fIversion\fP or \fIformat*\fP, according to which
+the output will be sorted.
+Information in an unstripped database (see
+the option \fB\-\-no\-strip\fP above) is nested:
+Subfields of a record can be addressed using
+the \fB\->\fP separator, e. g.
+\fBfile\->location\fP, \fBstyle\->units_per_em\fP,
+or
+\fBnames\->sanitized\->english\->prefmodifiers\fP\&.
+NB: shell syntax requires that arguments
+containing \fB\->\fP be properly quoted!
+.IP 3. 3
+an expression of the form \fBfield:value\fP to
+limit the output to entries whose \fBfield\fP
+matches \fBvalue\fP\&.
+.UNINDENT
+.sp
+For example, in order to output file names and
+corresponding versions, sorted by the font
+format:
+.INDENT 7.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+\&./luaotfload\-tool.lua \-\-list="format" \-\-fields="file\->base,version"
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.sp
+This prints:
+.INDENT 7.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+otf latinmodern\-math.otf Version 1.958
+otf lmromancaps10\-oblique.otf 2.004
+otf lmmono8\-regular.otf 2.004
+otf lmmonoproplt10\-bold.otf 2.004
+otf lmsans10\-oblique.otf 2.004
+otf lmromanslant8\-regular.otf 2.004
+otf lmroman12\-italic.otf 2.004
+otf lmsansdemicond10\-oblique.otf 2.004
+\&...
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.TP
+.BI \-\-fields\fB= FIELDS
+Comma\-separated list of fields that should be
+printed.
+Information in an unstripped database (see the
+option \fB\-\-no\-strip\fP above) is nested:
+Subfields of a record can be addressed using
+the \fB\->\fP separator, e. g.
+\fBfile\->location\fP, \fBstyle\->units_per_em\fP,
+or \fBnames\->sanitized\->english\->subfamily\fP\&.
+The default is plainname,version*.
+(Only meaningful with \fB\-\-list\fP\&.)
+.UNINDENT
+.SS font and lookup caches
+.INDENT 0.0
+.TP
+.B \-\-flush\-lookups
+Clear font name lookup cache (experimental).
+.TP
+.BI \-\-cache\fB= DIRECTIVE
+Cache control, where \fIDIRECTIVE\fP is one of the
+following:
+.INDENT 7.0
+.IP 1. 3
+\fBpurge\fP \-> delete Lua files from cache;
+.IP 2. 3
+\fBerase\fP \-> delete Lua and Luc files from
+cache;
+.IP 3. 3
+\fBshow\fP \-> print stats.
+.UNINDENT
+.UNINDENT
+.SS debugging methods
+.INDENT 0.0
+.TP
+.B \-\-show\-blacklist\fP,\fB \-b
+Show blacklisted files (not directories).
+.TP
+.B \-\-dry\-run\fP,\fB \-D
+Don’t load fonts when updating the database;
+scan directories only.
+(For debugging file system related issues.)
+.TP
+.B \-\-no\-strip
+Do not strip redundant information after
+building the database. Warning: this will
+inflate the index to about two to three times
+the normal size.
+.TP
+.BI \-\-max\-fonts\fB= N
+Process at most \fIN\fP font files, including fonts
+already indexed in the count.
+.TP
+.BI \-\-bisect\fB= DIRECTIVE
+Bisection of the font database.
+This mode is intended as assistance in
+debugging the Luatex engine, especially when
+tracking memleaks or buggy fonts.
+.sp
+\fIDIRECTIVE\fP can be one of the following:
+.INDENT 7.0
+.IP 1. 3
+\fBrun\fP \-> Make \fBluaotfload\-tool\fP respect
+the bisection progress when running.
+Combined with \fB\-\-update\fP and possibly
+\fB\-\-force\fP this will only process the files
+from the start up until the pivot and ignore
+the rest.
+.IP 2. 3
+\fBstart\fP \-> Start bisection: create a
+bisection state file and initialize the low,
+high, and pivot indices.
+.IP 3. 3
+\fBstop\fP \-> Terminate the current bisection
+session by deleting the state file.
+.IP 4. 3
+\fBgood\fP | \fBbad\fP \-> Mark the section
+processed last as “good” or “bad”,
+respectively. The next bisection step will
+continue with the bad section.
+.IP 5. 3
+\fBstatus\fP \-> Print status information about
+the current bisection session. Hint: Use
+with higher verbosity settings for more
+output.
+.UNINDENT
+.sp
+A bisection session is initiated by issuing the
+\fBstart\fP directive. This sets the pivot to the
+middle of the list of available font files.
+Now run \fIluaotfload\-tool\fP with the \fB\-\-update\fP
+flag set as well as \fB\-\-bisect=run\fP: only the
+fonts up to the pivot will be considered. If
+that task exhibited the issue you are tracking,
+then tell Luaotfload using \fB\-\-bisect=bad\fP\&.
+The next step of \fB\-\-bisect=run\fP will continue
+bisection with the part of the files below the
+pivot.
+Likewise, issue \fB\-\-bisect=good\fP in order to
+continue with the fonts above the pivot,
+assuming the tested part of the list did not
+trigger the bug.
+.sp
+Once the culprit font is tracked down, \fBgood\fP
+or \fBbad\fP will have no effect anymore. \fBrun\fP
+will always end up processing the single font
+file that was left.
+Use \fB\-\-bisect=stop\fP to clear the bisection
+state.
+.UNINDENT
+.SS miscellaneous
+.INDENT 0.0
+.TP
+.BI \-\-verbose\fB= N\fP,\fB \ \-v
+Set verbosity level to \fIn\fP or the number of
+repetitions of \fB\-v\fP\&.
+.TP
+.B \-\-quiet
+No verbose output (log level set to zero).
+.TP
+.BI \-\-log\fB= CHANNEL
+Redirect log output (for database
+troubleshooting), where \fICHANNEL\fP can be
+.INDENT 7.0
+.IP 1. 3
+\fBstdout\fP \-> all output will be
+dumped to the terminal (default); or
+.IP 2. 3
+\fBfile\fP \-> write to a file to the temporary
+directory (the name will be chosen
+automatically.
+.UNINDENT
+.TP
+.B \-\-version\fP,\fB \-V
+Show version numbers of components as well as
+some basic information and exit.
+.TP
+.B \-\-help\fP,\fB \-h
+Show help message and exit.
+.TP
+.BI \-\-diagnose\fB= CHECK
+Run the diagnostic procedure \fICHECK\fP\&. Available
+procedures are:
+.INDENT 7.0
+.IP 1. 3
+\fBfiles\fP \-> check \fILuaotfload\fP files for
+modifications;
+.IP 2. 3
+\fBpermissions\fP \-> check permissions of
+cache directories and files;
+.IP 3. 3
+.INDENT 3.0
+.TP
+.B \fBenvironment\fP \-> print relevant
+environment and kpse variables;
+.UNINDENT
+.IP 4. 3
+\fBrepository\fP \-> check the git repository
+for new releases,
+.IP 5. 3
+\fBindex\fP \-> check database, display
+information about it.
+.UNINDENT
+.sp
+Procedures can be chained by concatenating with
+commas, e.g. \fB\-\-diagnose=files,permissions\fP\&.
+Specify \fBthorough\fP to run all checks.
+.TP
+.BI \-\-conf\fB= FILE
+Read the configuration from \fIFILE\fP\&. See
+\fBluaotfload.conf\fP(%) for documentation
+concerning the format and available options.
+.TP
+.B \-\-dumpconf
+Print the currently active configuration; the
+output can be saved to a file and used for
+bootstrapping a custom configuration files.
+.UNINDENT
+.SH FILES
+.sp
+The font name database is usually located in the directory
+\fBtexmf\-var/luatex\-cache/generic/names/\fP (\fB$TEXMFCACHE\fP as set in
+\fBtexmf.cnf\fP) of your \fITeX Live\fP distribution as a zlib\-compressed
+file \fBluaotfload\-names.lua.gz\fP\&.
+The experimental lookup cache will be created as
+\fBluaotfload\-lookup\-cache.lua\fP in the same directory.
+These Lua tables are not used directly by Luaotfload, though.
+Instead, they are compiled to Lua bytecode which is written to
+corresponding files with the extension \fB\&.luc\fP in the same directory.
+When modifying the files by hand keep in mind that only if the bytecode
+files are missing will Luaotfload use the plain version instead.
+Both kinds of files are safe to delete, at the cost of regenerating
+them with the next run of \fILuaTeX\fP\&.
+.SH SEE ALSO
+.sp
+\fBluaotfload.conf\fP(5), \fBluatex\fP(1), \fBlua\fP(1)
+.INDENT 0.0
+.IP \(bu 2
+\fBtexdoc luaotfload\fP to display the manual for the \fILuaotfload\fP
+package
+.IP \(bu 2
+Luaotfload development \fI\%https://github.com/lualatex/luaotfload\fP
+.IP \(bu 2
+LuaLaTeX mailing list \fI\%http://tug.org/pipermail/lualatex\-dev/\fP
+.IP \(bu 2
+LuaTeX \fI\%http://luatex.org/\fP
+.IP \(bu 2
+ConTeXt \fI\%http://wiki.contextgarden.net\fP
+.IP \(bu 2
+Luaotfload on CTAN \fI\%http://ctan.org/pkg/luaotfload\fP
+.UNINDENT
+.SH BUGS
+.sp
+Tons, probably.
+.SH AUTHORS
+.sp
+\fILuaotfload\fP was developed by the LuaLaTeX dev team
+(\fI\%https://github.com/lualatex/\fP). It is currently maintained by Ulrike Fischer
+and Marcel Krüger at \fI\%https://github.com/u\-fischer/luaotfload\fP
+The fontloader code is provided by Hans Hagen of Pragma ADE, Hasselt
+NL (\fI\%http://pragma\-ade.com/\fP).
+.sp
+This manual page was written by Philipp Gesang <\fI\%phg@phi\-gamma.net\fP>.
+.SH COPYRIGHT
+GPL v2.0
+.\" Generated by docutils manpage writer.
+.
diff --git a/macros/luatex/generic/luaotfload/luaotfload-tool.lua b/macros/luatex/generic/luaotfload/luaotfload-tool.lua
new file mode 100755
index 0000000000..e7e144c6c7
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-tool.lua
@@ -0,0 +1,1661 @@
+#!/usr/bin/env texlua
+-----------------------------------------------------------------------
+-- FILE: luaotfload-tool.lua
+-- DESCRIPTION: database functionality
+-- REQUIREMENTS: matching luaotfload
+-- AUTHOR: Khaled Hosny, Élie Roux, Philipp Gesang
+-- LICENSE: GPL v2.0
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-tool",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload-tool / database functionality",
+ license = "GPL v2.0"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+
+luaotfload = luaotfload or { }
+local version = ProvidesLuaModule.version
+luaotfload.version = ProvidesLuaModule.version
+luaotfload.min_luatex_version = { 0, 95, 0 }
+luaotfload.self = "luaotfload-tool"
+
+--[[doc--
+
+luaotfload-tool(1)
+
+This file was originally written (as \fileent{mkluatexfontdb.lua}) by
+Elie Roux and Khaled Hosny and, as a derived work of ConTeXt, is
+provided under the terms of the GPL v2.0 license as printed in full
+text in the manual (luaotfload.pdf).
+
+ \url{http://www.gnu.org/licenses/old-licenses/gpl-2.0.html}.
+
+This file is a wrapper for the luaotfload font names module
+(luaotfload-database.lua). It is part of the luaotfload bundle, please
+see the luaotfload documentation for more info. Report bugs to
+
+ \url{https://github.com/lualatex/luaotfload/issues}.
+
+--doc]]--
+
+kpse.set_program_name "luatex"
+
+local iowrite = io.write
+local kpsefind_file = kpse.find_file
+local mathfloor = math.floor
+local next = next
+local osdate = os.date
+local ostype = os.type
+local stringexplode = string.explode
+local stringformat = string.format
+local stringlower = string.lower
+local stringrep = string.rep
+local tableconcat = table.concat
+local texiowrite_nl = texio.write_nl
+local texiowrite = texio.write
+local tonumber = tonumber
+local type = type
+
+do
+ local runtime = _G.jit and { "jit" , jit.version }
+ or { "stock", _VERSION }
+ local stats = status and status.list ()
+ local minimum = luaotfload.min_luatex_version
+ local actual = { 0, 0, 0 }
+ if stats then
+ local major = stats.luatex_version // 100
+ local minor = stats.luatex_version % 100
+ local revision = stats.luatex_revision --[[ : string ]]
+ local revno = tonumber (revision)
+ actual = { major, minor, revno or 0 }
+ end
+
+ if actual [1] < minimum [1]
+ or actual == minimum and actual [2] < minimum [2]
+ or actual == minimum and actual [2] == minimum [2] and actual [3] < minimum [3]
+ then
+ texio.write_nl ("term and log",
+ string.format ("\tFATAL ERROR\n\z
+ \tLuaotfload requires a Luatex version >= %d.%d.%d.\n\z
+ \tPlease update your TeX distribution!\n\n",
+ (unpack or table.unpack) (minimum)))
+ error "version check failed"
+ end
+ luaotfload.runtime = runtime
+ luaotfload.luatex_version = actual
+end
+
+local C, Ct, P, S = lpeg.C, lpeg.Ct, lpeg.P, lpeg.S
+local lpegmatch = lpeg.match
+
+string.quoted = string.quoted or function (str)
+ return string.format("%q",str)
+end
+
+--[[doc--
+
+ XXX:
+ Creating the config table will be moved to the common
+ initialization when the times comes.
+
+--doc]]--
+
+config = config or { }
+local config = config
+config.luaotfload = config.luaotfload or { }
+
+config.lualibs = config.lualibs or { }
+config.lualibs.verbose = false
+config.lualibs.prefer_merged = true
+config.lualibs.load_extended = true
+
+require "lualibs"
+
+local iosavedata = io.savedata
+local lfsisdir = lfs.isdir
+local lfsisfile = lfs.isfile
+local stringsplit = string.split
+local tablekeys = table.keys
+local tableserialize = table.serialize
+local tablesortedkeys = table.sortedkeys
+local tabletohash = table.tohash
+
+--[[doc--
+\fileent{luatex-basics-gen.lua} calls functions from the
+\luafunction{texio.*} library; too much for our taste.
+We intercept them with dummies.
+
+Also, it sets up dummies in place of the tables created by the Context
+libraries. Since we have loaded the lualibs already this would cause
+collateral damage for some libraries whose namespace would be
+overridden. We employ our usual backup-restore strategy to work around
+this. (Postponing the loading of the lualibs code is not an option
+because the functionality is needed by basics-gen itself.)
+--doc]]--
+
+local dummy_function = function ( ) end
+local backup = {
+ write = texio.write,
+ write_nl = texio.write_nl,
+ utilities = utilities,
+}
+
+texio.write, texio.write_nl = dummy_function, dummy_function
+require "fontloader-basics-gen.lua"
+texio.write, texio.write_nl = backup.write, backup.write_nl
+utilities = backup.utilities
+
+pdf = pdf or { } --- for fonts-tfm
+
+require "fontloader-data-con"
+require "fontloader-font-ini"
+require "fontloader-font-con"
+require "fontloader-fonts-enc"
+require "fontloader-font-cid"
+require "fontloader-font-map"
+require "fontloader-font-oti"
+require "fontloader-font-otr"
+require "fontloader-font-ott"
+require "fontloader-font-cff"
+require "fontloader-font-ttf"
+require "fontloader-font-dsp"
+require "fontloader-font-oup"
+require "fontloader-font-onr"
+require "fontloader-font-def"
+
+fonts = fonts or { }
+local fontsnames = fonts.names or { }
+fonts.names = fontsnames
+
+local require_init = { }
+
+local loadmodule = function (name)
+ local v = require ("luaotfload-" .. name)
+ if v then
+ local mod = { }
+ local tv = type (v)
+ if tv == "table" then
+ mod.name = name
+ mod.init = v.init
+ require_init [#require_init + 1] = mod
+ elseif tv == "function" then
+ mod.name = name
+ mod.init = v
+ require_init [#require_init + 1] = mod
+ end
+ end
+end
+
+require "alt_getopt"
+
+loadmodule "log" --- this populates the luaotfload.log.* namespace
+loadmodule "parsers" --- fonts.conf, configuration, and request syntax
+loadmodule "configuration" --- configuration file handling
+loadmodule "database"
+loadmodule "resolvers" --- Font lookup
+
+local logreport
+
+local init_modules = function ()
+ --- NB we don’t command the logger at this point.
+ local todo = #require_init
+ local ret = true
+ for i = 1, todo do
+ local mod = require_init[i]
+ local name = mod.name
+ local init = mod.init
+ if type (init) ~= "function" then
+ error ("luaotfload broken; module "
+ .. name .. " missing initializers!")
+ end
+ local v = mod.init ()
+ if v == true then
+ --- evaluated well
+ elseif type (v) == "table" then
+ luaotfload[name] = v
+ else
+ error ("luaotfload broken; initialization of module "
+ .. name .. " returned " .. tostring (v) .. ".")
+ return false
+ end
+ end
+ logreport = luaotfload.log.report
+ return ret
+end
+
+
+local help_messages = {
+ ["luaotfload-tool"] = [[
+
+Usage: %s [OPTIONS...]
+
+ Luaotfload font management and diagnostic utility.
+ This program is part of the Luaotfload package.
+
+ Valid options are:
+
+-------------------------------------------------------------------------------
+ VERBOSITY AND DIAGNOSTICS
+
+ -q --quiet don't output anything
+ -v --verbose=LEVEL be more verbose (print the searched directories)
+ -v, -vv .. -vvvvvvvvv set loglevel in unary
+ --log=stdout redirect log output to stdout
+
+ -V --version print version and exit
+ -h --help print this message
+ --diagnose=CHECK run a self test procedure; one of "files",
+ "environment", "index", "permissions", or
+ "repository"
+
+-------------------------------------------------------------------------------
+ DATABASE
+
+ -u --update update the database
+ -n --no-reload suppress db update
+ --no-strip keep redundant information in db
+ -f --force force re-indexing all fonts
+ -L --local scan font files in $PWD
+ -c --no-compress do not gzip index file (text version only)
+ -l --flush-lookups empty lookup cache of font requests
+ -D --dry-run skip loading of fonts, just scan
+ --formats=[+|-]EXTENSIONS set, add, or subtract file formats
+ -p --prefer-texmf prefer fonts in the TEXMF over system fonts
+ --max-fonts=N process at most N font files
+
+ --find="font name" query the database for a font name
+ -F --fuzzy look for approximate matches if --find fails
+ --limit=n limit display of fuzzy matches to <n>
+ (default: n = 1)
+
+ -i --info display basic font metadata
+ -I --inspect display detailed font metadata
+
+ --list=<criterion> output list of entries by field <criterion>
+ --list=<criterion>:<value> restrict to entries with <criterion>=<value>
+ --fields=<f1>,<f2>,…,<fn> which fields <f> to print with --list
+ -b --show-blacklist show blacklisted files
+
+ --bisect=<directive> control database bisection: valid
+ directives are "start", "stop", "run", "status",
+ "good", "bad"
+
+The font database will be saved to
+ %s
+ %s
+
+-------------------------------------------------------------------------------
+ FONT CACHE
+
+ --cache=<directive> operate on font cache, where <directive> is
+ "show", "purge", or "erase"
+
+The font cache will be written to
+ %s
+
+]],
+ mkluatexfontdb = [[
+FATAL ERROR
+As of Luaotfload v2.5, legacy behavior is not supported anymore. Please
+update your scripts and/or habits! Kthxbye.
+]],
+ short = [[
+Usage: luaotfload-tool [--help] [--version] [--verbose=<lvl>]
+ [--update] [--force] [--prefer-texmf] [--local]
+ [--dry-run] [--formats=<extension list>]
+ [--find=<font name>] [--fuzzy] [--info] [--inspect]
+ [--list=<criterion>] [--fields=<field list>]
+ [--cache=<directive>] [--flush-lookups]
+ [--show-blacklist] [--diagnose=<procedure>]
+ [--no-compress] [--no-strip] [--local]
+ [--max-fonts=<n>] [--bisect=<directive>]
+
+Enter 'luaotfload-tool --help' for a larger list of options.
+]]
+}
+
+local help_msg = function (version)
+ local template = help_messages[version]
+ local paths = config.luaotfload.paths
+ local names_plain = paths.index_path_lua
+ local names_gzip = names_plain .. ".gz"
+ local names_bin = paths.index_path_luc
+
+ iowrite(stringformat(template,
+ luaotfload.self,
+ names_gzip,
+ names_bin,
+ caches.getwritablepath (config.luaotfload.paths.cache_dir, "")))
+end
+
+local about = [[
+%s:
+ Luaotfload font management and diagnostic utility.
+ License: GNU GPL v2.0.
+ Report problems to <https://github.com/lualatex/luaotfload/issues>
+]]
+
+local version_msg = function ( )
+ local out = function (...) texiowrite_nl (stringformat (...)) end
+ local uname = os.uname ()
+ local meta = fonts.names.getmetadata ()
+
+ local runtime = luaotfload.runtime
+ local actual = luaotfload.luatex_version
+ local status = config.luaotfload.status
+ local notes = status and status.notes or { }
+
+ out (about, luaotfload.self)
+ out ("%s version: %q", luaotfload.self, version)
+ if notes.description then
+ out ("Luaotfload: %q", notes.description)
+ end
+ out ("Revision: %q", notes.revision)
+ out ("Lua interpreter: %s; version %q", runtime[1], runtime[2])
+--[[out ("Luatex SVN revision: %d", info.luatex_svn)]] --> SVN r5624
+ out ("Luatex version: %d.%d", actual [1], actual [2])
+ out ("Platform: type=%s name=%s", os.type, os.name)
+
+ local uname_vars = tablesortedkeys (uname)
+ for i = 1, #uname_vars do
+ local var = uname_vars[i]
+ out (" + %8s: %s", var, uname[var])
+ end
+ if meta == false then
+ out("No database metadata available.")
+ else
+ out ("Index: version=%q created=%q modified=%q",
+ meta.version or "too old",
+ meta.created or "ages ago",
+ meta.modified or "ages ago")
+ end
+ out ""
+end
+
+
+--- makeshift formatting
+
+local head_adornchars = {
+ [1] = "*", [2] = "=", [3] = "~", [4] = "-", [5] = "·",
+}
+
+local textwidth = 80
+local wd_leftcolumn = mathfloor(textwidth * .25)
+local key_fmt = stringformat([[%%%ds]], wd_leftcolumn)
+local val_fmt = [[%s]]
+local fieldseparator = ":"
+local info_fmt = key_fmt .. fieldseparator .. " " .. val_fmt
+
+local currentdepth = 0
+local counterstack = { } -- counters per level
+local counterformat = "%d"
+
+local format_counter = function (stack)
+ local acc = { }
+ for lvl=1, #stack do
+ acc[#acc+1] = stringformat(counterformat, stack[lvl])
+ end
+ return tableconcat(acc, ".")
+end
+
+local print_heading = function (title, level)
+ if not title then return end
+ local structuredata
+ if currentdepth == level then -- top is current
+ counterstack[#counterstack] = counterstack[#counterstack] + 1
+ elseif currentdepth < level then -- push new
+ counterstack[#counterstack+1] = 1
+ else -- pop
+ local diff = currentdepth - level
+ while diff > 0 do
+ counterstack[#counterstack] = nil
+ diff = diff - 1
+ end
+ counterstack[#counterstack] = counterstack[#counterstack] + 1
+ end
+ currentdepth = level
+
+ texiowrite_nl ""
+ if not level or level > #head_adornchars then
+ level = #head_adornchars
+ end
+ local adornchar = head_adornchars[level]
+
+ local counter = format_counter(counterstack)
+
+ local s = adornchar .. adornchar .. " "
+ .. counter .. " "
+ .. title .. " "
+ texiowrite_nl (s .. stringrep(adornchar, textwidth-utf.len(s)))
+end
+
+local baseindent = " "
+
+--[[doc--
+
+ show_info_items -- Together with show_info_table prints the table returned by
+ readers.getinfo(), recursing into nested tables if appropriate (as necessitated
+ by Luatex versions 0.78+ which include the pfminfo table in the result.
+
+--doc]]--
+
+local show_info_table show_info_table = function (t, depth)
+ depth = depth or 0
+ local indent = stringrep (baseindent, depth)
+ local keys = tablesortedkeys (t)
+ for n = 1, #keys do
+ local key = keys [n]
+ local val = t [key]
+ if type (val) == "table" then
+ texiowrite_nl (indent .. stringformat (info_fmt, key, "<table>"))
+ show_info_table (val, depth + 1)
+ else
+ texiowrite_nl (indent .. stringformat (info_fmt, key, val))
+ end
+ end
+end
+
+local show_info_items = function (fontinfo)
+ print_heading (fontinfo.fullname, 1)
+ texiowrite_nl ""
+ show_info_table (fontinfo)
+ texiowrite_nl ""
+end
+
+local p_spacechar = S" \n\r\t\v"
+local p_wordchar = (1 - p_spacechar)
+local p_whitespace = p_spacechar^1
+local p_word = C(p_wordchar^1)
+local p_words = Ct(p_word * (p_whitespace * p_word)^0)
+
+--- string -> int -> string list
+local reflow = function (text, width)
+ local words
+ local t_text = type (text)
+ if t_text == "string" then
+ words = lpegmatch(p_words, text)
+ if #words < 2 then
+ return { text }
+ end
+ elseif t_text == "table" then
+ words = text
+ if #text < 2 then
+ return text
+ end
+ end
+
+ local space = " "
+ local utflen = utf.len
+ local reflowed = { }
+
+ local first = words[1]
+ local linelen = #first
+ local line = { first }
+
+ for i=2, #words do
+ local word = words[i]
+ local lword = utflen(word)
+ linelen = linelen + lword + 1
+ if linelen > width then
+ reflowed[#reflowed+1] = tableconcat(line)
+ linelen = #word
+ line = { word }
+ else
+ line[#line+1] = space
+ line[#line+1] = word
+ end
+ end
+ reflowed[#reflowed+1] = tableconcat(line)
+ return reflowed
+end
+
+--- string -> 'a -> string list
+local print_field = function (key, val)
+ val = tostring(val)
+ local lhs = stringformat(key_fmt, key) .. fieldseparator .. " "
+ local wd_lhs = #lhs
+ local lines = reflow(val, textwidth - wd_lhs)
+
+ texiowrite_nl(lhs)
+ texiowrite(lines[1])
+ if #lines > 1 then
+ local indent = stringrep(" ", wd_lhs)
+ for i=2, #lines do
+ texiowrite_nl(indent)
+ texiowrite (lines[i])
+ end
+ end
+end
+
+--- see luafflib.c
+local general_fields = {
+ --- second: l -> literal | n -> length | d -> date
+ { "fullname", "l", "font name" },
+ { "version", "l", "font version" },
+ { "width", "l", "width" },
+ { "averagewidth", "l", "average width" },
+ { "panosewidth", "l", "panose width" },
+ { "weight", "l", "weight indicator" },
+ { "pfmweight", "l", "numerical weight" },
+ { "panoseweight", "l", "panose weight" },
+ { "designsize", "l", "design size" },
+ { "minsize", "l", "design size min" },
+ { "maxsize", "l", "design size max" },
+ { "units", "l", "units per em" },
+ { "ascender", "l", "ascender height" },
+ { "descender", "l", "descender height" },
+ { "capheight", "l", "capital height" },
+}
+
+local display_general = function (fullinfo)
+ texiowrite_nl ""
+ print_heading("General Information", 2)
+ texiowrite_nl ""
+ for i=1, #general_fields do
+ local field = general_fields[i]
+ local key, mode, desc = unpack(field)
+ local val
+ if mode == "l" then
+ val = fullinfo[key]
+ elseif mode == "S" then --- style names table
+ local data = fullinfo[key]
+ if type (data) == "table" then
+ if #data > 0 then
+ for n = 1, #data do
+ local nth = data[n]
+ if nth.lang == 1033 then
+ val = nth.name
+ goto found
+ end
+ end
+ val = next (data).name
+ else
+ val = ""
+ end
+ ::found::
+ else
+ val = data
+ end
+ elseif mode == "n" then
+ local v = fullinfo[key]
+ if v then
+ val = #fullinfo[key]
+ end
+ elseif mode == "d" then
+ if ostype == "unix" then
+ val = osdate("%F %T", fullinfo[key])
+ else
+ --- the MS compiler doesn’t support C99, so
+ --- strftime is missing some functionality;
+ --- see loslib.c for details.
+ val = osdate("%Y-%m-d %H:%M:%S", fullinfo[key])
+ end
+ end
+ if not val then
+ val = "<none>"
+ end
+ print_field(desc, val)
+ end
+end
+
+local print_features = function (features)
+ for tag, data in next, features do
+ print_heading(tag, 4)
+ for script, languages in next, data do
+ local field = stringformat(key_fmt, script).. fieldseparator .. " "
+ local wd_field = #field
+ local lines = reflow(tablekeys(languages), textwidth - wd_field)
+ local indent = stringrep(" ", wd_field)
+ texiowrite_nl(field)
+ texiowrite(lines[1])
+ if #lines > 1 then
+ for i=1, #lines do
+ texiowrite_nl(indent .. lines[i])
+ end
+ end
+ end
+ end
+end
+
+local display_feature_set = function (set)
+ print_features(set)
+end
+
+local display_features_type = function (id, feat)
+ if feat and next (feat) then
+ print_heading(id, 3)
+ display_feature_set(feat)
+ return true
+ end
+ return false
+end
+
+local display_features = function (features)
+ texiowrite_nl ""
+ print_heading("Features", 2)
+
+ local status = 0
+ if not display_features_type ("GSUB Features", features.gsub) then
+ status = status + 1
+ end
+ if not display_features_type ("GPOS Features", features.gpos) then
+ status = status + 2
+ end
+ if status == 3 then
+ texiowrite_nl("font defines neither gsub nor gpos features")
+ elseif status == 2 then
+ texiowrite_nl("font defines no gpos feature")
+ elseif status == 1 then
+ texiowrite_nl("font defines no gsub feature")
+ end
+end
+
+local show_full_info = function (path, subfont)
+ local rawinfo, warn = fonts.handlers.otf.readers.loadfont (path, subfont)
+ if not rawinfo then
+ texiowrite_nl(stringformat([[cannot open font %s]], path))
+ return
+ end
+ display_general(rawinfo.metadata)
+ display_features(rawinfo.resources.features)
+end
+
+local subfont_by_name
+subfont_by_name = function (lst, askedname, n)
+ if not n then
+ return subfont_by_name (lst, askedname, 1)
+ end
+
+ local font = lst[n]
+ if font then
+ if fonts.names.sanitize_fontname (font.fullname) == askedname then
+ return font
+ end
+ return subfont_by_name (lst, askedname, n + 1)
+ end
+ return false
+end
+
+--[[doc--
+The font info knows two levels of detail:
+
+ a) basic information returned by readers.getinfo(); and
+ b) detailed information that is a subset of the font table
+ returned by readers.loadfont().
+--doc]]--
+
+local show_font_info = function (basename, askedname, detail, subfont)
+ local filenames = fonts.names.data().files
+ local index = filenames.base[basename]
+ local fullname = filenames.full[index]
+ askedname = fonts.names.sanitize_fontname (askedname)
+ if not fullname then -- texmf
+ fullname = resolvers.findfile(basename)
+ end
+ if fullname then
+ local shortinfo = fonts.handlers.otf.readers.getinfo (fullname, {
+ subfont = subfont,
+ platformnames = true,
+ rawfamilynames = true,
+ })
+ local nfonts = #shortinfo
+ if nfonts > 0 then -- true type collection
+ local subfont
+ if askedname then
+ logreport (true, 1, "resolve",
+ [[%s is part of the font collection %s]],
+ askedname, basename)
+ subfont = subfont_by_name(shortinfo, askedname)
+ end
+ if subfont then
+ show_info_items(subfont)
+ if detail == true then
+ show_full_info(fullname, subfont)
+ end
+ else -- list all subfonts
+ logreport (true, 1, "resolve",
+ [[%s is a font collection]], basename)
+ for subfont = 1, nfonts do
+ logreport (true, 1, "resolve",
+ [[Showing info for font no. %d]],
+ subfont)
+ show_info_items(shortinfo[subfont])
+ if detail == true then
+ show_full_info(fullname, subfont)
+ end
+ end
+ end
+ else
+ show_info_items(shortinfo)
+ if detail == true then
+ show_full_info(fullname, subfont)
+ end
+ end
+ else
+ logreport (true, 1, "resolve", "Font %s not found", filename)
+ end
+end
+
+--[[--
+Running the scripts triggers one or more actions that have to be
+executed in the correct order. To avoid duplication we track them in a
+set.
+--]]--
+
+local action_sequence = {
+ "config" , "loglevel" , "help" , "version" ,
+ "dumpconf" , "diagnose" , "blacklist" , "cache" ,
+ "flush" , "bisect" , "generate" , "list" ,
+ "query" ,
+}
+
+local action_pending = tabletohash(action_sequence, false)
+
+action_pending.config = true --- always read the configuration
+action_pending.loglevel = true --- always set the loglevel
+action_pending.generate = false --- this is the default action
+
+local actions = { } --- (jobspec -> (bool * bool)) list
+
+actions.loglevel = function (job)
+ local lvl = job.log_level
+ if lvl then
+ luaotfload.log.set_loglevel(lvl)
+ logreport ("info", 3, "util", "Setting the log level to %d.", lvl)
+ logreport ("log", 2, "util", "Lua=%q", _VERSION)
+ end
+ return true, true
+end
+
+actions.config = function (job)
+ local defaults = luaotfload.default_config
+ local vars = config.actions.read (job.extra_config)
+ config.luaotfload = config.actions.apply (defaults, vars)
+ config.luaotfload = config.actions.apply (config.luaotfload, job.config)
+
+ --inspect(config.luaotfload)
+ --os.exit()
+ if not config.actions.reconfigure () then
+ return false, false
+ end
+ return true, true
+end
+
+actions.version = function (job)
+ version_msg()
+ return true, false
+end
+
+actions.dumpconf = function (job)
+ config.actions.dump ()
+ return true, false
+end
+
+actions.help = function (job)
+ help_msg (job.help_version or "luaotfload-tool")
+ return true, false
+end
+
+actions.blacklist = function (job)
+ fonts.names.read_blacklist()
+ local n = 0
+ for n, entry in next, tablesortedkeys(fonts.names.blacklist) do
+ iowrite (stringformat("(%d %s)\n", n, entry))
+ end
+ return true, false
+end
+
+actions.generate = function (job)
+ local _ = fonts.names.update ({ }, job.force_reload, job.dry_run)
+ local namedata = fonts.names.data ()
+ if namedata then
+ logreport ("info", 2, "db",
+ "Fonts in the database: %i",
+ #namedata.mappings)
+ return true, true
+ end
+ return false, false
+end
+
+-------------------------------------------------------------------------------
+--- bisect mode
+-------------------------------------------------------------------------------
+
+local bisect_status_path = caches.getwritablepath ("bisect", "")
+local bisect_status_file = bisect_status_path .."/" .. "luaotfload-bisect-status.lua"
+local bisect_status_fmt = [[
+--[==[-------------------------------------------------------------------------
+ This file is generated by Luaotfload. It can be safely deleted.
+ Creation date: %s.
+-------------------------------------------------------------------------]==]--
+
+%s
+
+--- vim:ft=lua:ts=8:et:sw=2
+]]
+
+--[[doc--
+
+ write_bisect_status -- Write the history of the current bisection to disk.
+
+--doc]]--
+
+--- state list -> bool
+local write_bisect_status = function (data)
+ local payload = tableserialize (data, true)
+ local status = stringformat (bisect_status_fmt,
+ osdate ("%Y-%m-d %H:%M:%S", os.time ()),
+ payload)
+ if status and iosavedata (bisect_status_file, status) then
+ logreport ("info", 4, "bisect",
+ "Bisection state written to %s.",
+ bisect_status_file)
+ return true
+ end
+ logreport ("info", 0, "bisect",
+ "Failed to write bisection state to %s.",
+ bisect_status_file)
+ return false
+end
+
+--[[doc--
+
+ read_bisect_status -- Read the bisect log from disk.
+
+--doc]]--
+
+--- unit -> state list
+local read_bisect_status = function ()
+ logreport ("info", 4, "bisect",
+ "Testing for status file: %q.",
+ bisect_status_file)
+ if not lfsisfile (bisect_status_file) then
+ logreport ("info", 2, "bisect",
+ "No such file: %q.", bisect_status_file)
+ logreport ("info", 0, "bisect",
+ "Not in bisect mode.")
+ return false
+ end
+ logreport ("info", 4, "bisect",
+ "Reading status file: %q.", bisect_status_file)
+ local success, status = pcall (dofile, bisect_status_file)
+ if not success then
+ logreport ("info", 0, "bisect",
+ "Could not read status file.")
+ return false
+ end
+ return status
+end
+
+--[[doc--
+
+ bisect_start -- Begin a bisect session. Determines the number of
+ fonts and sets the initial high, low, and pivot values.
+
+--doc]]--
+
+local bisect_start = function ()
+ if lfsisfile (bisect_status_file) then
+ logreport ("info", 0, "bisect",
+ "Bisect session in progress.",
+ bisect_status_file)
+ logreport ("info", 0, "bisect",
+ "Use --bisect=stop to erase it before starting over.")
+ return false, false
+ end
+ logreport ("info", 2, "bisect",
+ "Starting bisection of font database %q.",
+ bisect_status_file)
+ local n = fonts.names.count_font_files ()
+ local pivot = mathfloor (n / 2)
+ local data = { { 1, n, pivot } }
+ logreport ("info", 0, "bisect",
+ "Initializing pivot to %d.", pivot)
+ if write_bisect_status (data) then
+ return true, false
+ end
+ return false, false
+end
+
+--[[doc--
+
+ bisect_stop -- Terminate bisection session by removing all state info.
+
+--doc]]--
+
+local bisect_stop = function ()
+ logreport ("info", 3, "bisect",
+ "Erasing bisection state at %s.",
+ bisect_status_file)
+ if lfsisfile (bisect_status_file) then
+ local success, msg = os.remove (bisect_status_file)
+ if not success then
+ logreport ("info", 2, "bisect",
+ "Failed to erase file %s (%s).",
+ bisect_status_file, msg)
+ end
+ end
+ if lfsisdir (bisect_status_path) then
+ local success, msg = os.remove (bisect_status_path)
+ if not success then
+ logreport ("info", 2, "bisect",
+ "Failed to erase directory %s (%s).",
+ bisect_status_path, msg)
+ end
+ end
+ if lfsisfile (bisect_status_file) then
+ return false, false
+ end
+ return true, false
+end
+
+--[[doc--
+
+ bisect_terminate -- Wrap up a bisect session by printing the
+ offending font and removing the state file.
+
+--doc]]--
+
+local bisect_terminate = function (nsteps, culprit)
+ logreport ("info", 1, "bisect",
+ "Bisection completed after %d steps.", nsteps)
+ logreport ("info", 0, "bisect",
+ "Bad file: %s.", fonts.names.nth_font_filename (culprit))
+ logreport ("info", 0, "bisect",
+ "Run with --bisect=stop to finish bisection.")
+ return true, false
+end
+
+--[[doc--
+
+ list_remainder -- Show remaining fonts in bisect slice.
+
+--doc]]--
+
+local list_remainder = function (lo, hi)
+ local fonts = fonts.names.font_slice (lo, hi)
+ logreport ("info", 0, "bisect", "%d fonts left.", hi - lo + 1)
+ for i = 1, #fonts do
+ logreport ("info", 1, "bisect", " · %2d: %s", lo, fonts[i])
+ lo = lo + 1
+ end
+end
+
+--[[doc--
+
+ bisect_set -- Prepare the next bisection step by setting high, low,
+ and pivot to new values.
+
+ The “run” directive always picks the segment below the pivot so we
+ can rely on the “outcome parameter” to be referring to that.
+
+--doc]]--
+
+local bisect_set = function (outcome)
+ local status = read_bisect_status ()
+ if not status then
+ return false, false
+ end
+
+ local nsteps = #status
+ local previous = status[nsteps]
+ if previous == true then
+ --- Bisection already completed; we exit early through
+ --- bisect_terminate() to avoid further writes to the
+ --- state files that mess up step counting.
+ nsteps = nsteps - 1
+ return bisect_terminate (nsteps, status[nsteps][1])
+ end
+
+ local lo, hi, pivot = unpack (previous)
+
+ logreport ("info", 3, "bisect",
+ "Previous step %d: lo=%d, hi=%d, pivot=%d.",
+ nsteps, lo, hi, pivot)
+
+ if outcome == "bad" then
+ hi = pivot
+ if lo >= hi then --- complete
+ status[nsteps + 1] = { lo, lo, lo }
+ status[nsteps + 2] = true
+ write_bisect_status (status)
+ return bisect_terminate (nsteps, lo)
+ end
+ pivot = mathfloor ((lo + hi) / 2)
+ logreport ("info", 0, "bisect",
+ "Continuing with the lower segment: lo=%d, hi=%d, pivot=%d.",
+ lo, hi, pivot)
+ elseif outcome == "good" then
+ lo = pivot + 1
+ if lo >= hi then --- complete
+ status[nsteps + 1] = { lo, lo, lo }
+ write_bisect_status (status)
+ status[nsteps + 2] = true
+ return bisect_terminate (nsteps, lo)
+ end
+ pivot = mathfloor ((lo + hi) / 2)
+ logreport ("info", 0, "bisect",
+ "Continuing with the upper segment: lo=%d, hi=%d, pivot=%d.",
+ lo, hi, pivot)
+ else -- can’t happen
+ logreport ("info", 0, "bisect",
+ "What the hell?", lo, hi, pivot)
+ return false, false
+ end
+
+ status[nsteps + 1] = { lo, hi, pivot }
+ write_bisect_status (status)
+ if hi - lo <= 10 then
+ list_remainder (lo, hi)
+ end
+ return true, false
+end
+
+--[[doc--
+
+ bisect_status -- Output information about the current bisect session.
+
+--doc]]--
+
+local bisect_status = function ()
+ local status = read_bisect_status ()
+ if not status then
+ return false, false
+ end
+ local nsteps = #status
+ if nsteps > 1 then
+ for i = nsteps - 1, 1, -1 do
+ local step = status[i]
+ logreport ("info", 2, "bisect", "Step %d: lo=%d, hi=%d, pivot=%d.",
+ i, unpack (step))
+ end
+ end
+ local current = status[nsteps]
+ logreport ("info", 0, "bisect", "Step %d: lo=%d, hi=%d, pivot=%d.",
+ nsteps, unpack (current))
+ return true, false
+end
+
+--[[doc--
+
+ bisect_run -- Run Luaotfload utilizing the current bisection state.
+ This should be combined with the --update mode, possibly with the
+ --force option.
+
+ Luaotfload always tests the segment below the pivot first.
+
+--doc]]--
+
+local bisect_run = function ()
+ local status = read_bisect_status ()
+ if not status then
+ return false, false
+ end
+ local nsteps = #status
+ local currentstep = nsteps + 1
+ local current = status[nsteps]
+ if current == true then -- final step
+ current = status[nsteps - 1]
+ end
+ local lo, hi, pivot = unpack (current)
+ logreport ("info", 3, "bisect", "Previous step %d: lo=%d, hi=%d, pivot=%d.",
+ nsteps, lo, hi, pivot)
+ logreport ("info", 1, "bisect", "Step %d: Testing fonts from %d to %d.",
+ currentstep, lo, pivot)
+ config.luaotfload.misc.bisect = { lo, pivot }
+ return true, true
+end
+
+local bisect_modes = {
+ start = bisect_start,
+ good = function () return bisect_set "good" end,
+ bad = function () return bisect_set "bad" end,
+ stop = bisect_stop,
+ status = bisect_status,
+ run = bisect_run,
+}
+
+actions.bisect = function (job)
+ local mode = job.bisect
+ local runner = bisect_modes[mode]
+ if not runner then
+ logreport ("info", 0, "bisect", "Unknown directive %q.", mode)
+ return false, false
+ end
+ return runner (job)
+end
+
+actions.flush = function (job)
+ local success = fonts.names.flush_lookup_cache()
+ if success then
+ local success = fonts.names.save_lookups()
+ if success then
+ logreport ("info", 2, "cache", "Lookup cache emptied")
+ return true, true
+ end
+ end
+ return false, false
+end
+
+local cache_directives = function ()
+ --- These exist only after initialization.
+ return {
+ ["purge"] = fonts.names.purge_cache,
+ ["erase"] = fonts.names.erase_cache,
+ ["show"] = fonts.names.show_cache,
+ }
+end
+
+actions.cache = function (job)
+ local directive = cache_directives()[job.cache]
+ if not directive or type(directive) ~= "function" then
+ logreport ("info", 2, "cache",
+ "Invalid font cache directive %s.", job.cache)
+ return false, false
+ end
+ if directive() then
+ return true, true
+ end
+ return false, false
+end
+
+actions.query = function (job)
+
+ require "luaotfload-features"
+
+ local query = job.query
+
+ local tmpspec = {
+ name = query,
+ lookup = "name",
+ specification = query,
+ optsize = 0,
+ features = { },
+ }
+
+ tmpspec = fonts.names.handle_request (tmpspec)
+
+ if not tmpspec.size then
+ tmpspec.size = 655360 --- assume 10pt
+ end
+
+ local foundname, subfont, success, needle
+
+ if tmpspec.lookup == "name" then
+ if fonts.definers.resolvers.name (tmpspec) then
+ needle = tmpspec.resolved
+ end
+ elseif tmpspec.lookup == "anon" then
+ if fonts.definers.resolvers.anon (tmpspec) then
+ needle = tmpspec.resolved or tmpspec.name
+ end
+ elseif tmpspec.lookup == "file" then
+ needle = tmpspec.name
+ end
+ subfont = tmpspec.sub
+
+ if needle then
+ foundname, _, success = fonts.names.lookup_font_file (tmpspec.name)
+ end
+
+ if success then
+ logreport (false, 0, "resolve", "Font %q found!", query)
+ if subfont then
+ logreport (false, 0, "resolve",
+ "Resolved file name %q, subfont nr. %q",
+ foundname, subfont)
+ else
+ logreport (false, 0, "resolve",
+ "Resolved file name %q", foundname)
+ end
+ if job.show_info then
+ logreport (false, 3, "resolve", "Dump extra info.")
+ show_font_info (foundname, query, job.full_info, subfont)
+ iowrite "\n"
+ end
+ else
+ logreport (false, 0, "resolve", "Cannot find %q in index.", query)
+ if job.fuzzy == true then
+ logreport (false, 0, "resolve",
+ "Looking for close matches, this may take a while ...")
+ local _success = fonts.names.find_closest(query, job.fuzzy_limit)
+ else
+ logreport (false, 0, "resolve",
+ "Hint: use the --fuzzy option to display suggestions.",
+ query)
+ end
+ end
+ return true, true
+end
+
+--- --list=<criterion>
+--- --list=<criterion>:<value>
+---
+--- --list=<criterion> --fields=<f1>,<f2>,<f3>,...<fn>
+
+local get_fields get_fields = function (entry, fields, acc, n)
+ if not acc then
+ return get_fields (entry, fields, { }, 1)
+ end
+
+ local field = fields [n]
+ if field then
+ local chain = stringsplit (field, "->")
+ local tmp = entry
+ for i = 1, #chain - 1 do
+ tmp = tmp [chain [i]]
+ if not tmp then
+ --- invalid field
+ break
+ end
+ end
+ if tmp then
+ local value = tmp [chain [#chain]]
+ acc[#acc+1] = value or false
+ else
+ acc[#acc+1] = false
+ end
+ return get_fields (entry, fields, acc, n+1)
+ end
+ return acc
+end
+
+local separator = "\t" --- could be “,” for csv
+
+local format_fields format_fields = function (fields, acc, n)
+ if not acc then
+ return format_fields(fields, { }, 1)
+ end
+
+ local field = fields[n]
+ if field ~= nil then
+ if field == false then
+ acc[#acc+1] = "<none>"
+ else
+ acc[#acc+1] = tostring(field)
+ end
+ return format_fields(fields, acc, n+1)
+ end
+ return tableconcat(acc, separator)
+end
+
+local set_primary_field
+set_primary_field = function (fields, addme, acc, n)
+ if not acc then
+ return set_primary_field(fields, addme, { addme }, 1)
+ end
+
+ local field = fields[n]
+ if field then
+ if field ~= addme then
+ acc[#acc+1] = field
+ end
+ return set_primary_field(fields, addme, acc, n+1)
+ end
+ return acc
+end
+
+actions.list = function (job)
+ local criterion = job.criterion
+ local asked_fields = job.asked_fields
+ local name_index = fonts.names.data ()
+
+ if asked_fields then
+ local splitcomma = luaotfload.parsers.splitcomma
+ asked_fields = lpegmatch(splitcomma, asked_fields)
+ end
+
+ if not asked_fields then
+ --- some defaults
+ asked_fields = { "plainname", "version", }
+ end
+
+ if not name_index then
+ name_index = fonts.names.load()
+ end
+
+ local mappings = name_index.mappings
+ local nmappings = #mappings
+
+ if criterion == "*" then
+ logreport (false, 1, "list", "All %d entries", nmappings)
+ for i=1, nmappings do
+ local entry = mappings[i]
+ local fields = get_fields(entry, asked_fields)
+ --- we could collect these instead ...
+ local formatted = format_fields(fields)
+ texiowrite_nl(formatted)
+ end
+
+ else
+ criterion = stringexplode(criterion, ":") --> { field, value }
+ local asked_value = criterion[2]
+ criterion = criterion[1]
+ asked_fields = set_primary_field(asked_fields, criterion)
+
+ logreport (false, 1, "list", "By %s", criterion)
+
+ --- firstly, build a list of fonts to operate on
+ local targets = { }
+ if asked_value then --- only those whose value matches
+ logreport (false, 2, "list", "Restricting to value %s", asked_value)
+ for i=1, nmappings do
+ local entry = mappings[i]
+ if entry[criterion]
+ and tostring(entry[criterion]) == asked_value
+ then
+ targets[#targets+1] = entry
+ end
+ end
+
+ else --- whichever have the field, sorted
+ local categories, by_category = { }, { }
+ for i=1, nmappings do
+ local entry = mappings[i]
+ local tmp = entry
+ local chain = stringsplit (criterion, "->")
+ for i = 1, #chain - 1 do
+ tmp = tmp [chain [i]]
+ if not tmp then
+ break
+ end
+ end
+ local value = tmp and tmp [chain [#chain]] or "<none>"
+ if value then
+ --value = tostring(value)
+ local entries = by_category[value]
+ if not entries then
+ entries = { entry }
+ categories[#categories+1] = value
+ else
+ entries[#entries+1] = entry
+ end
+ by_category[value] = entries
+ end
+ end
+ table.sort(categories)
+
+ for i=1, #categories do
+ local entries = by_category[categories[i]]
+ for j=1, #entries do
+ targets[#targets+1] = entries[j]
+ end
+ end
+ end
+ local ntargets = #targets
+ logreport (false, 2, "list", "%d entries", ntargets)
+
+ --- now, output the collection
+ for i=1, ntargets do
+ local entry = targets[i]
+ local fields = get_fields(entry, asked_fields)
+ local formatted = format_fields(fields)
+ texiowrite_nl(formatted)
+ end
+ end
+
+ texiowrite_nl ""
+
+ return true, true
+end
+
+actions.diagnose = function (job)
+ --- diagnostics are loaded on demand
+ local diagnose = require "luaotfload-diagnostics.lua"
+ return diagnose (job)
+end
+
+--- stuff to be carried out prior to exit
+
+local finalizers = { }
+
+--- returns false if at least one of the actions failed, mainly
+--- for closing io channels
+local finalize = function ()
+ local success = true
+ for _, fun in next, finalizers do
+ if type (fun) == "function" then
+ if fun () == false then success = false end
+ end
+ end
+ return success
+end
+
+--[[--
+Command-line processing.
+luaotfload-tool relies on the script alt_getopt to process argv and
+analyzes its output.
+
+TODO with extended lualibs we have the functionality from the
+environment.* namespace that could eliminate the dependency on
+alt_getopt.
+--]]--
+
+local process_cmdline = function ( ) -- unit -> jobspec
+ local result = { -- jobspec
+ force_reload = nil,
+ full_info = false,
+ criterion = "",
+ query = "",
+ log_level = nil,
+ bisect = nil,
+ config = { db = { }, misc = { }, run = { live = false }, paths = { } },
+ }
+
+ local long_options = {
+ ["bisect"] = 1,
+ cache = 1,
+ conf = 1,
+ diagnose = 1,
+ dumpconf = 0,
+ ["dry-run"] = "D",
+ ["flush-lookups"] = "l",
+ fields = 1,
+ find = 1,
+ force = "f",
+ formats = 1,
+ fuzzy = "F",
+ help = "h",
+ info = "i",
+ inspect = "I",
+ limit = 1,
+ list = 1,
+ ["local"] = "L",
+ log = 1,
+ ["max-fonts"] = 1,
+ ["no-compress"] = "c",
+ ["no-reload"] = "n",
+ ["no-strip"] = 0,
+ ["skip-read"] = "R",
+ ["prefer-texmf"] = "p",
+ ["print-conf"] = 0,
+ quiet = "q",
+ ["show-blacklist"] = "b",
+ stats = "S",
+ update = "u",
+ verbose = 1,
+ version = "V",
+ }
+
+ local short_options = "bcDfFiIlLnpqRSuvVh"
+
+ local options, _, optarg =
+ alt_getopt.get_ordered_opts (arg, short_options, long_options)
+
+ local nopts = #options
+ for n=1, nopts do
+ local v = options[n]
+ if v == "q" then
+ result.log_level = 0
+ elseif v == "u" then
+ action_pending["generate"] = true
+ elseif v == "v" then
+ local lvl = result.log_level
+ if not lvl or lvl < 1 then
+ lvl = 1
+ else
+ lvl = lvl + 1
+ end
+ result.log_level = lvl
+ elseif v == "V" then
+ action_pending["version"] = true
+ elseif v == "h" then
+ action_pending["help"] = true
+ elseif v == "f" then
+ result.update = true
+ result.force_reload = 1
+ elseif v == "verbose" then
+ local lvl = optarg[n]
+ if lvl then
+ lvl = tonumber(lvl)
+ result.log_level = lvl
+ end
+ elseif v == "log" then
+ local str = optarg[n]
+ if str then
+ finalizers = luaotfload.log.set_logout(str, finalizers)
+ end
+ elseif v == "find" then
+ action_pending["query"] = true
+ result.query = optarg[n]
+ elseif v == "F" then
+ result.fuzzy = true
+ elseif v == "limit" then
+ local lim = optarg[n]
+ if lim then
+ result.fuzzy_limit = tonumber(lim)
+ end
+ elseif v == "i" then
+ result.show_info = true
+ elseif v == "I" then
+ result.show_info = true
+ result.full_info = true
+ elseif v == "l" then
+ action_pending["flush"] = true
+ elseif v == "L" then
+ action_pending["generate"] = true
+ result.config.db.scan_local = true
+ elseif v == "list" then
+ action_pending["list"] = true
+ result.criterion = optarg[n]
+ elseif v == "fields" then
+ result.asked_fields = optarg[n]
+ elseif v == "cache" then
+ action_pending["cache"] = true
+ result.cache = optarg[n]
+ elseif v == "D" then
+ result.dry_run = true
+ elseif v == "p" then
+ fonts.names.set_location_precedence {
+ "local", "texmf", "system"
+ }
+ elseif v == "b" then
+ action_pending["blacklist"] = true
+ elseif v == "diagnose" then
+ action_pending["diagnose"] = true
+ result.asked_diagnostics = optarg[n]
+ elseif v == "formats" then
+ result.config.db.formats = optarg[n]
+ --names.set_font_filter (optarg[n])
+ elseif v == "n" then
+ result.config.db.update_live = false
+ elseif v == "S" then
+ result.config.misc.statistics = true
+ elseif v == "R" then
+ --- dev only, undocumented
+ result.config.db.skip_read = true
+ elseif v == "c" then
+ result.config.db.compress = false
+ elseif v == "no-strip" then
+ result.config.db.strip = false
+ elseif v == "max-fonts" then
+ local n = optarg[n]
+ if n then
+ n = tonumber(n)
+ if n and n > 0 then
+ result.config.db.max_fonts = n
+ end
+ end
+ elseif v == "bisect" then
+ result.bisect = optarg[n]
+ action_pending.bisect = true
+ elseif v == "conf" then
+ local confname = optarg[n]
+ if confname then
+ local extra = stringexplode (optarg[n], ",+")
+ if extra then
+ local extra_config = result.extra_config
+ if extra_config then
+ table.append (extra_config, extra)
+ else
+ result.extra_config = extra
+ end
+ end
+ end
+ elseif v == "dumpconf" then
+ action_pending["dumpconf"] = true
+ elseif v == "print-conf" then
+ result.print_config = true
+ end
+ end
+
+ if nopts == 0 then
+ action_pending["help"] = true
+ result.help_version = "short"
+ end
+ return result
+end
+
+local main = function ( ) -- unit -> int
+ if init_modules () == false then return -42 end
+
+ local retval = 0
+ local job = process_cmdline()
+
+-- inspect(action_pending)
+-- inspect(job)
+
+ for i=1, #action_sequence do
+ local actionname = action_sequence[i]
+ local exit = false
+ if action_pending[actionname] then
+ logreport ("log", 3, "util", "Preparing for task", "%s", actionname)
+
+ local action = actions[actionname]
+ local success, continue = action(job)
+
+ if not success then
+ logreport (false, 0, "util",
+ "Failed to execute task.", "%s", actionname)
+ retval = -1
+ exit = true
+ elseif not continue then
+ logreport (false, 3, "util",
+ "Task completed, exiting.", "%s", actionname)
+ exit = true
+ else
+ logreport (false, 3, "util",
+ "Task completed successfully.", "%s", actionname)
+ end
+ end
+ if exit then break end
+ end
+
+ if finalize () == false then
+ retval = -1
+ end
+
+ --texiowrite_nl""
+ return retval
+end
+
+return main()
+
+-- vim:tw=71:sw=4:ts=4:expandtab
diff --git a/macros/luatex/generic/luaotfload/luaotfload-tool.pdf b/macros/luatex/generic/luaotfload/luaotfload-tool.pdf
new file mode 100644
index 0000000000..e278f8bbc5
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-tool.pdf
Binary files differ
diff --git a/macros/luatex/generic/luaotfload/luaotfload-tool.rst b/macros/luatex/generic/luaotfload/luaotfload-tool.rst
new file mode 100644
index 0000000000..e091cbb1d1
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-tool.rst
@@ -0,0 +1,328 @@
+=======================================================================
+ luaotfload-tool
+=======================================================================
+
+-----------------------------------------------------------------------
+ generate and query the Luaotfload font names database
+-----------------------------------------------------------------------
+
+:Date: 2019-08-11
+:Copyright: GPL v2.0
+:Version: 2.991
+:Manual section: 1
+:Manual group: text processing
+
+SYNOPSIS
+=======================================================================
+
+**luaotfload-tool** [ -bcDfFiIlLnpqRSuvVhw ]
+
+**luaotfload-tool** --update [ --force ] [ --quiet ] [ --verbose ]
+ [ --prefer-texmf ] [ --dry-run ]
+ [ --formats=[+|-]EXTENSIONS ]
+ [ --no-compress ] [ --no-strip ]
+ [ --local ] [ --max-fonts=N ]
+
+**luaotfload-tool** --find=FONTNAME [ --fuzzy ] [ --info ] [ --inspect ]
+ [ --no-reload ]
+
+**luaotfload-tool** --flush-lookups
+
+**luaotfload-tool** --cache=DIRECTIVE
+
+**luaotfload-tool** --list=CRITERION[:VALUE] [ --fields=F1,F2,...,Fn ]
+
+**luaotfload-tool** --bisect=DIRECTIVE
+
+**luaotfload-tool** --help
+
+**luaotfload-tool** --version
+
+**luaotfload-tool** --show-blacklist
+
+**luaotfload-tool** --diagnose=CHECK
+
+**luaotfload-tool** --conf=FILE --dumpconf
+
+DESCRIPTION
+=======================================================================
+
+luaotfload-tool accesses the font names database that is required by
+the *Luaotfload* package. There are two general modes: **update** and
+**query**.
+
++ **update**: update the database or rebuild it entirely;
++ **query**: resolve a font name or display close matches.
+
+OPTIONS
+=======================================================================
+
+update mode
+-----------------------------------------------------------------------
+--update, -u Update the database; indexes new fonts.
+--force, -f Force rebuilding of the database; re-indexes
+ all fonts.
+--local, -L Include font files in ``$PWD``. This option
+ will cause large parts of the database to be
+ rebuilt. Thus it is quite inefficient.
+ Additionally, if local font files are found,
+ the database is prevented from being saved
+ to disk, so the local fonts need to be parsed
+ with every invocation of ``luaotfload-tool``.
+--no-reload, -n Suppress auto-updates to the database (e.g.
+ when ``--find`` is passed an unknown name).
+--no-compress, -c Do not filter the plain text version of the
+ font index through gzip. Useful for debugging
+ if your editor is built without zlib.
+
+--prefer-texmf, -p Organize the file name database in a way so
+ that it prefer fonts in the *TEXMF* tree over
+ system fonts if they are installed in both.
+--formats=EXTENSIONS Extensions of the font files to index.
+ Where *EXTENSIONS* is a comma-separated list of
+ supported file extensions (otf, ttf, ttc).
+ If the list is prefixed
+ with a ``+`` sign, the given list is added to
+ the currently active one; ``-`` subtracts.
+ Default: *otf,ttf,ttc*.
+ Examples:
+
+ 1) ``--formats=-ttc,ttf`` would skip
+ TrueType fonts and font collections;
+ 2) ``--formats=otf`` would scan only OpenType
+ files;
+ 3) ``--formats=+afm`` includes binary
+ Postscript files accompanied by an AFM file.
+
+query mode
+-----------------------------------------------------------------------
+--find=NAME Resolve a font name; this looks up <name> in
+ the database and prints the file name it is
+ mapped to.
+ ``--find`` also understands request syntax,
+ i.e. ``--find=file:foo.otf`` checks whether
+ ``foo.otf`` is indexed.
+--fuzzy, -F Show approximate matches to the file name if
+ the lookup was unsuccessful (requires
+ ``--find``).
+
+--info, -i Display basic information to a resolved font
+ file (requires ``--find``).
+--inspect, -I Display detailed information by loading the
+ font and analyzing the font table; very slow!
+ For the meaning of the returned fields see
+ the LuaTeX documentation.
+ (requires ``--find``).
+
+--list=CRITERION Show entries, where *CRITERION* is one of the
+ following:
+
+ 1) the character ``*``, selecting all entries;
+ 2) a field of a database entry, for instance
+ *version* or *format**, according to which
+ the output will be sorted.
+ Information in an unstripped database (see
+ the option ``--no-strip`` above) is nested:
+ Subfields of a record can be addressed using
+ the ``->`` separator, e. g.
+ ``file->location``, ``style->units_per_em``,
+ or
+ ``names->sanitized->english->prefmodifiers``.
+ NB: shell syntax requires that arguments
+ containing ``->`` be properly quoted!
+ 3) an expression of the form ``field:value`` to
+ limit the output to entries whose ``field``
+ matches ``value``.
+
+ For example, in order to output file names and
+ corresponding versions, sorted by the font
+ format::
+
+ ./luaotfload-tool.lua --list="format" --fields="file->base,version"
+
+ This prints::
+
+ otf latinmodern-math.otf Version 1.958
+ otf lmromancaps10-oblique.otf 2.004
+ otf lmmono8-regular.otf 2.004
+ otf lmmonoproplt10-bold.otf 2.004
+ otf lmsans10-oblique.otf 2.004
+ otf lmromanslant8-regular.otf 2.004
+ otf lmroman12-italic.otf 2.004
+ otf lmsansdemicond10-oblique.otf 2.004
+ ...
+
+--fields=FIELDS Comma-separated list of fields that should be
+ printed.
+ Information in an unstripped database (see the
+ option ``--no-strip`` above) is nested:
+ Subfields of a record can be addressed using
+ the ``->`` separator, e. g.
+ ``file->location``, ``style->units_per_em``,
+ or ``names->sanitized->english->subfamily``.
+ The default is plainname,version*.
+ (Only meaningful with ``--list``.)
+
+font and lookup caches
+-----------------------------------------------------------------------
+--flush-lookups Clear font name lookup cache (experimental).
+
+--cache=DIRECTIVE Cache control, where *DIRECTIVE* is one of the
+ following:
+
+ 1) ``purge`` -> delete Lua files from cache;
+ 2) ``erase`` -> delete Lua and Luc files from
+ cache;
+ 3) ``show`` -> print stats.
+
+debugging methods
+-----------------------------------------------------------------------
+--show-blacklist, -b Show blacklisted files (not directories).
+--dry-run, -D Don’t load fonts when updating the database;
+ scan directories only.
+ (For debugging file system related issues.)
+--no-strip Do not strip redundant information after
+ building the database. Warning: this will
+ inflate the index to about two to three times
+ the normal size.
+--max-fonts=N Process at most *N* font files, including fonts
+ already indexed in the count.
+--bisect=DIRECTIVE Bisection of the font database.
+ This mode is intended as assistance in
+ debugging the Luatex engine, especially when
+ tracking memleaks or buggy fonts.
+
+ *DIRECTIVE* can be one of the following:
+
+ 1) ``run`` -> Make ``luaotfload-tool`` respect
+ the bisection progress when running.
+ Combined with ``--update`` and possibly
+ ``--force`` this will only process the files
+ from the start up until the pivot and ignore
+ the rest.
+ 2) ``start`` -> Start bisection: create a
+ bisection state file and initialize the low,
+ high, and pivot indices.
+ 3) ``stop`` -> Terminate the current bisection
+ session by deleting the state file.
+ 4) ``good`` | ``bad`` -> Mark the section
+ processed last as “good” or “bad”,
+ respectively. The next bisection step will
+ continue with the bad section.
+ 5) ``status`` -> Print status information about
+ the current bisection session. Hint: Use
+ with higher verbosity settings for more
+ output.
+
+ A bisection session is initiated by issuing the
+ ``start`` directive. This sets the pivot to the
+ middle of the list of available font files.
+ Now run *luaotfload-tool* with the ``--update``
+ flag set as well as ``--bisect=run``: only the
+ fonts up to the pivot will be considered. If
+ that task exhibited the issue you are tracking,
+ then tell Luaotfload using ``--bisect=bad``.
+ The next step of ``--bisect=run`` will continue
+ bisection with the part of the files below the
+ pivot.
+ Likewise, issue ``--bisect=good`` in order to
+ continue with the fonts above the pivot,
+ assuming the tested part of the list did not
+ trigger the bug.
+
+ Once the culprit font is tracked down, ``good``
+ or ``bad`` will have no effect anymore. ``run``
+ will always end up processing the single font
+ file that was left.
+ Use ``--bisect=stop`` to clear the bisection
+ state.
+
+miscellaneous
+-----------------------------------------------------------------------
+--verbose=N, -v Set verbosity level to *n* or the number of
+ repetitions of ``-v``.
+--quiet No verbose output (log level set to zero).
+--log=CHANNEL Redirect log output (for database
+ troubleshooting), where *CHANNEL* can be
+
+ 1) ``stdout`` -> all output will be
+ dumped to the terminal (default); or
+ 2) ``file`` -> write to a file to the temporary
+ directory (the name will be chosen
+ automatically.
+
+--version, -V Show version numbers of components as well as
+ some basic information and exit.
+--help, -h Show help message and exit.
+
+--diagnose=CHECK Run the diagnostic procedure *CHECK*. Available
+ procedures are:
+
+ 1) ``files`` -> check *Luaotfload* files for
+ modifications;
+ 2) ``permissions`` -> check permissions of
+ cache directories and files;
+ 3) ``environment`` -> print relevant
+ environment and kpse variables;
+ 4) ``repository`` -> check the git repository
+ for new releases,
+ 5) ``index`` -> check database, display
+ information about it.
+
+ Procedures can be chained by concatenating with
+ commas, e.g. ``--diagnose=files,permissions``.
+ Specify ``thorough`` to run all checks.
+
+--conf=FILE Read the configuration from *FILE*. See
+ **luaotfload.conf**\(%) for documentation
+ concerning the format and available options.
+--dumpconf Print the currently active configuration; the
+ output can be saved to a file and used for
+ bootstrapping a custom configuration files.
+
+FILES
+=======================================================================
+
+The font name database is usually located in the directory
+``texmf-var/luatex-cache/generic/names/`` (``$TEXMFCACHE`` as set in
+``texmf.cnf``) of your *TeX Live* distribution as a zlib-compressed
+file ``luaotfload-names.lua.gz``.
+The experimental lookup cache will be created as
+``luaotfload-lookup-cache.lua`` in the same directory.
+These Lua tables are not used directly by Luaotfload, though.
+Instead, they are compiled to Lua bytecode which is written to
+corresponding files with the extension ``.luc`` in the same directory.
+When modifying the files by hand keep in mind that only if the bytecode
+files are missing will Luaotfload use the plain version instead.
+Both kinds of files are safe to delete, at the cost of regenerating
+them with the next run of *LuaTeX*.
+
+SEE ALSO
+=======================================================================
+
+**luaotfload.conf**\(5), **luatex**\(1), **lua**\(1)
+
+* ``texdoc luaotfload`` to display the manual for the *Luaotfload*
+ package
+* Luaotfload development `<https://github.com/lualatex/luaotfload>`_
+* LuaLaTeX mailing list `<http://tug.org/pipermail/lualatex-dev/>`_
+* LuaTeX `<http://luatex.org/>`_
+* ConTeXt `<http://wiki.contextgarden.net>`_
+* Luaotfload on CTAN `<http://ctan.org/pkg/luaotfload>`_
+
+BUGS
+=======================================================================
+
+Tons, probably.
+
+AUTHORS
+=======================================================================
+
+*Luaotfload* was developed by the LuaLaTeX dev team
+(`<https://github.com/lualatex/>`__). It is currently maintained by Ulrike Fischer
+and Marcel Krüger at `<https://github.com/u-fischer/luaotfload>`__
+The fontloader code is provided by Hans Hagen of Pragma ADE, Hasselt
+NL (`<http://pragma-ade.com/>`__).
+
+This manual page was written by Philipp Gesang <phg@phi-gamma.net>.
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload-unicode.lua b/macros/luatex/generic/luaotfload/luaotfload-unicode.lua
new file mode 100644
index 0000000000..928bfcec96
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload-unicode.lua
@@ -0,0 +1,109 @@
+-----------------------------------------------------------------------
+-- FILE: luaotfload-unicode.lua
+-- DESCRIPTION: part of luaotfload / unicode
+-----------------------------------------------------------------------
+
+local ProvidesLuaModule = {
+ name = "luaotfload-unicode",
+ version = "2.991", --TAGVERSION
+ date = "2019-08-11", --TAGDATE
+ description = "luaotfload submodule / Unicode helpers",
+ license = "CC0 1.0 Universal",
+ author = "Marcel Krüger"
+}
+
+if luatexbase and luatexbase.provides_module then
+ luatexbase.provides_module (ProvidesLuaModule)
+end
+
+local utf8codes = utf8.codes
+local utf8char = utf8.char
+local sub = string.sub
+local unpack = table.unpack
+local concat = table.concat
+local move = table.move
+
+local codepoint = lpeg.S'0123456789ABCDEF'^4/function(c)return tonumber(c, 16)end
+local empty = {}
+local result = {}
+
+local casefold do
+ local nl = ('#' * (1-lpeg.P'\n')^0)^-1 * '\n'
+ local entry = codepoint * "; " * lpeg.C(1) * ";" * lpeg.Ct((' ' * codepoint)^1) * "; " * nl
+ local file = lpeg.Cf(
+ lpeg.Ct(
+ lpeg.Cg(lpeg.Ct"", "C")
+ * lpeg.Cg(lpeg.Ct"", "F")
+ * lpeg.Cg(lpeg.Ct"", "S")
+ * lpeg.Cg(lpeg.Ct"", "T"))
+ * nl^0 * lpeg.Cg(entry)^0 * nl^0 * -1
+ , function(t, base, class, mapping)
+ rawset(rawget(t, class), base, mapping)
+ return t
+ end)
+
+ local f = io.open(kpse.find_file"CaseFolding.txt")
+ local data = file:match(f:read'*a')
+ f:close()
+ function casefold(s, full, special)
+ local first = special and data.T or empty
+ local second = data.C
+ local third = full and data.F or data.S
+ local result = result
+ for i = #result, 1, -1 do result[i] = nil end
+ local i = 1
+ for _, c in utf8codes(s) do
+ local datum = first[c] or second[c] or third[c]
+ if datum then
+ local l = #datum
+ move(datum, 1, l, i, result)
+ i = i + l
+ else
+ result[i] = c
+ i = i + 1
+ end
+ end
+ return utf8char(unpack(result))
+ end
+end
+
+local alphnum_only do
+ local niceentry = lpeg.Cg(codepoint * ';' * (1-lpeg.P';')^0 * ';' * lpeg.S'LN' * lpeg.Cc(true))
+ local entry = niceentry^0 * (1-lpeg.P'\n')^0 * lpeg.P'\n'
+ local file = lpeg.Cf(
+ lpeg.Ct''
+ * entry^0
+ , rawset)
+
+ local f = io.open(kpse.find_file"UnicodeData.txt")
+ local data = file:match(f:read'*a')
+ f:close()
+ function alphnum_only(s)
+ local result = result
+ for i = #result, 1, -1 do result[i] = nil end
+ local nice = nil
+ for p, c in utf8codes(s) do
+ if data[c]
+ or (c >= 0x3400 and c<= 0x3DB5)
+ or (c >= 0x4E00 and c<= 0x9FEF)
+ or (c >= 0xAC00 and c<= 0xD7A3)
+ then
+ if not nice then nice = p end
+ else
+ if nice then
+ result[#result + 1] = sub(s, nice, p-1)
+ nice = nil
+ end
+ end
+ end
+ if nice then
+ result[#result + 1] = sub(s, nice, #s)
+ end
+ return concat(result)
+ end
+end
+
+return {
+ casefold = casefold,
+ alphnum_only = alphnum_only,
+}
diff --git a/macros/luatex/generic/luaotfload/luaotfload.conf.5 b/macros/luatex/generic/luaotfload/luaotfload.conf.5
new file mode 100644
index 0000000000..7fc9e48574
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload.conf.5
@@ -0,0 +1,632 @@
+.\" Man page generated from reStructuredText.
+.
+.TH LUAOTFLOAD.CONF 5 "2019-08-11" "2.991" "text processing"
+.SH NAME
+luaotfload.conf \- Luaotfload configuration file
+.
+.nr rst2man-indent-level 0
+.
+.de1 rstReportMargin
+\\$1 \\n[an-margin]
+level \\n[rst2man-indent-level]
+level margin: \\n[rst2man-indent\\n[rst2man-indent-level]]
+-
+\\n[rst2man-indent0]
+\\n[rst2man-indent1]
+\\n[rst2man-indent2]
+..
+.de1 INDENT
+.\" .rstReportMargin pre:
+. RS \\$1
+. nr rst2man-indent\\n[rst2man-indent-level] \\n[an-margin]
+. nr rst2man-indent-level +1
+.\" .rstReportMargin post:
+..
+.de UNINDENT
+. RE
+.\" indent \\n[an-margin]
+.\" old: \\n[rst2man-indent\\n[rst2man-indent-level]]
+.nr rst2man-indent-level -1
+.\" new: \\n[rst2man-indent\\n[rst2man-indent-level]]
+.in \\n[rst2man-indent\\n[rst2man-indent-level]]u
+..
+.SH SYNOPSIS
+.INDENT 0.0
+.IP \(bu 2
+\fB\&./luaotfload{.conf,rc}\fP
+.IP \(bu 2
+\fBXDG_CONFIG_HOME/luaotfload/luaotfload{.conf,rc}\fP
+.IP \(bu 2
+\fB~/.luaotfloadrc\fP
+.UNINDENT
+.SH DESCRIPTION
+.sp
+The file \fBluaotfload.conf\fP contains configuration options for
+\fILuaotfload\fP, a font loading and font management component for LuaTeX.
+.SH EXAMPLE
+.sp
+A small Luaotfload configuration file with few customizations could
+look as follows:
+.INDENT 0.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+[db]
+ formats = afm,ttf
+ compress = false
+
+[misc]
+ termwidth = 60
+
+[run]
+ log\-level = 6
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.sp
+This will make Luaotfload ignore all font files except for PostScript
+binary fonts with a matching AFM file, and Truetype fonts. Also, an
+uncompressed index file will be dumped which is going to be much larger
+than the default gzip’ed index. The terminal width
+is truncated to 60 characters which influences the verbose output
+during indexing. Finally, the verbosity is increased greatly: each font
+file being processed will be printed to the stdout on a separate line,
+along with lots of other information.
+.sp
+To observe the difference in behavior, save above snippet to
+\fB\&./luaotfload.conf\fP and update the font index:
+.INDENT 0.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+luaotfload\-tool \-\-update \-\-force
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.sp
+The current configuration can be written to disk using
+\fBluaotfload\-tool\fP:
+.INDENT 0.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+luaotfload\-tool \-\-dumpconf > luaotfload.conf
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.sp
+The result can itself be used as a configuration file.
+.SH SYNTAX
+.sp
+The configuration file syntax follows the common INI format. For a more
+detailed description please refer to the section “CONFIGURATION FILE”
+of \fBgit\-config\fP(1). A brief list of rules is given below:
+.INDENT 0.0
+.INDENT 3.5
+.INDENT 0.0
+.IP \(bu 2
+Blank lines and lines starting with a semicolon (\fB;\fP) are ignored.
+.IP \(bu 2
+A configuration file is partitioned into sections that are declared
+by specifying the section title in brackets on a separate line:
+.INDENT 2.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+[some\-section]
+\&... section content ...
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.IP \(bu 2
+Sections consist of one or more variable assignments of the form
+\fBvariable\-name = value\fP E. g.:
+.INDENT 2.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+[foo]
+ bar = baz
+ quux = xyzzy
+ ...
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.IP \(bu 2
+Section and variable names may contain only uppercase and lowercase
+letters as well as dashes (\fB\-\fP).
+.UNINDENT
+.UNINDENT
+.UNINDENT
+.SH VARIABLES
+.sp
+Variables in belong into a configuration section and their values must
+be of a certain type. Some of them have further constraints. For
+example, the “color callback” must be a string of one of the values
+\fBpost_linebreak_filter\fP, \fBpre_linebreak_filter\fP, or
+\fBpre_output_filter\fP, defined in the section \fIrun\fP of the
+configuration file.
+.sp
+Currently, the configuration is organized into four sections:
+.INDENT 0.0
+.TP
+.B db
+Options relating to the font index.
+.TP
+.B misc
+Options without a clearly defined category.
+.TP
+.B paths
+Path and file name settings.
+.TP
+.B run
+Options controlling runtime behavior of Luaotfload.
+.UNINDENT
+.sp
+The list of valid variables, the sections they are part of and their
+type is given below. Types represent Lua types that the values must be
+convertible to; they are abbreviated as follows: \fBs\fP for the \fIstring\fP
+type, \fBn\fP for \fInumber\fP, \fBb\fP for \fIboolean\fP\&. A value of \fBnil\fP means
+the variable is unset.
+.SS Section \fBdb\fP
+.TS
+center;
+|l|l|l|.
+_
+T{
+variable
+T} T{
+type
+T} T{
+default
+T}
+_
+T{
+compress
+T} T{
+b
+T} T{
+\fBtrue\fP
+T}
+_
+T{
+designsize\-dimen
+T} T{
+b
+T} T{
+\fBbp\fP
+T}
+_
+T{
+formats
+T} T{
+s
+T} T{
+\fB"otf,ttf,ttc"\fP
+T}
+_
+T{
+max\-fonts
+T} T{
+n
+T} T{
+\fB2^51\fP
+T}
+_
+T{
+scan\-local
+T} T{
+b
+T} T{
+\fBfalse\fP
+T}
+_
+T{
+skip\-read
+T} T{
+b
+T} T{
+\fBfalse\fP
+T}
+_
+T{
+strip
+T} T{
+b
+T} T{
+\fBtrue\fP
+T}
+_
+T{
+update\-live
+T} T{
+b
+T} T{
+\fBtrue\fP
+T}
+_
+.TE
+.sp
+The flag \fBcompress\fP determines whether the font index (usually
+\fBluaotfload\-names.lua[.gz]\fP will be stored in compressed forms.
+If unset it is equivalent of passing \fB\-\-no\-compress\fP to
+\fBluaotfload\-tool\fP\&. Since the file is only created for convenience
+and has no effect on the runtime behavior of Luaotfload, the flag
+should remain set. Most editors come with zlib support anyways.
+.sp
+The setting \fBdesignsize\-dimen\fP applies when looking up fonts from
+families with design sizes. In Opentype, these are specified as
+“decipoints” where one decipoint equals ten DTP style “big points”.
+When indexing fonts these values are converted to \fBsp\fP\&. In order to
+treat the values as though they were specified in TeX points or Didot
+points, set \fBdesignsize\-dimen\fP to \fBpt\fP or \fBdd\fP\&.
+.sp
+The list of \fBformats\fP must be a comma separated sequence of strings
+containing one or more of these elements:
+.INDENT 0.0
+.IP \(bu 2
+\fBotf\fP (OpenType format),
+.IP \(bu 2
+\fBttf\fP and \fBttc\fP (TrueType format),
+.IP \(bu 2
+\fBafm\fP (Adobe Font Metrics),
+.UNINDENT
+.sp
+It corresponds loosely to the \fB\-\-formats\fP option to
+\fBluaotfload\-tool\fP\&. Invalid or duplicate members are ignored; if the
+list does not contain any useful identifiers, the default list
+\fB"otf,ttf,ttc"\fP will be used.
+.sp
+The variable \fBmax\-fonts\fP determines after processing how many font
+files the font scanner will terminate the search. This is useful for
+debugging issues with the font index and has the same effect as the
+option \fB\-\-max\-fonts\fP to \fBluaotfload\-tools\fP\&.
+.sp
+The \fBscan\-local\fP flag, if set, will incorporate the current working
+directory as a font search location. NB: This will potentially slow
+down document processing because a font index with local fonts will not
+be saved to disk, so these fonts will have to be re\-indexed whenever
+the document is built.
+.sp
+The \fBskip\-read\fP flag is only useful for debugging: It makes
+Luaotfload skip reading fonts. The font information for rebuilding the
+index is taken from the presently existing one.
+.sp
+Unsetting the \fBstrip\fP flag prevents Luaotfload from removing data
+from the index that is only useful when processing font files. NB: this
+can increase the size of the index files significantly and has no
+effect on the runtime behavior.
+.sp
+If \fBupdate\-live\fP is set, Luaotfload will reload the database if it
+cannot find a requested font. Those who prefer to update manually using
+\fBluaotfload\-tool\fP should unset this flag. This option does not affect
+rebuilds due to version mismatch.
+.SS Section \fBdefault\-features\fP
+.sp
+By default Luaotfload enables \fBnode\fP mode and picks the default font
+features that are prescribed in the OpenType standard. This behavior
+may be overridden in the \fBdefault\-features\fP section. Global defaults
+that will be applied for all scripts can be set via the \fBglobal\fP
+option, others by the script they are to be applied to. For example,
+a setting of
+.INDENT 0.0
+.INDENT 3.5
+.sp
+.nf
+.ft C
+[default\-features]
+ global = mode=base,color=0000FF
+ dflt = smcp,onum
+.ft P
+.fi
+.UNINDENT
+.UNINDENT
+.sp
+would force \fIbase\fP mode, tint all fonts blue and activate small
+capitals and text figures globally. Features are specified as a comma
+separated list of variables or variable\-value pairs. Variables without
+an explicit value are set to \fBtrue\fP\&.
+.SS Section \fBmisc\fP
+.TS
+center;
+|l|l|l|.
+_
+T{
+variable
+T} T{
+type
+T} T{
+default
+T}
+_
+T{
+statistics
+T} T{
+b
+T} T{
+\fBfalse\fP
+T}
+_
+T{
+termwidth
+T} T{
+n
+T} T{
+\fBnil\fP
+T}
+_
+T{
+version
+T} T{
+s
+T} T{
+<Luaotfload version>
+T}
+_
+.TE
+.sp
+With \fBstatistics\fP enabled, extra statistics will be collected during
+index creation and appended to the index file. It may then be queried
+at the Lua end or inspected by reading the file itself.
+.sp
+The value of \fBtermwidth\fP, if set, overrides the value retrieved by
+querying the properties of the terminal in which Luatex runs. This is
+useful if the engine runs with \fBshell_escape\fP disabled and the actual
+terminal dimensions cannot be retrieved.
+.sp
+The value of \fBversion\fP is derived from the version string hard\-coded
+in the Luaotfload source. Override at your own risk.
+.SS Section \fBpaths\fP
+.TS
+center;
+|l|l|l|.
+_
+T{
+variable
+T} T{
+type
+T} T{
+default
+T}
+_
+T{
+cache\-dir
+T} T{
+s
+T} T{
+\fB"fonts"\fP
+T}
+_
+T{
+names\-dir
+T} T{
+s
+T} T{
+\fB"names"\fP
+T}
+_
+T{
+index\-file
+T} T{
+s
+T} T{
+\fB"luaotfload\-names.lua"\fP
+T}
+_
+T{
+lookups\-file
+T} T{
+s
+T} T{
+\fB"luaotfload\-lookup\-cache.lua"\fP
+T}
+_
+.TE
+.sp
+The paths \fBcache\-dir\fP and \fBnames\-dir\fP determine the subdirectory
+inside the Luaotfload subtree of the \fBluatex\-cache\fP directory where
+the font cache and the font index will be stored, respectively.
+.sp
+Inside the index directory, the names of the index file and the font
+lookup cache will be derived from the respective values of
+\fBindex\-file\fP and \fBlookups\-file\fP\&. This is the filename base for the
+bytecode compiled version as well as \-\- for the index \-\- the gzipped
+version.
+.SS Section \fBrun\fP
+.TS
+center;
+|l|l|l|.
+_
+T{
+variable
+T} T{
+type
+T} T{
+default
+T}
+_
+T{
+anon\-sequence
+T} T{
+s
+T} T{
+\fB"tex,path,name"\fP
+T}
+_
+T{
+color\-callback
+T} T{
+s
+T} T{
+\fB"post_linebreak_filter"\fP
+T}
+_
+T{
+definer
+T} T{
+s
+T} T{
+\fB"patch"\fP
+T}
+_
+T{
+log\-level
+T} T{
+n
+T} T{
+\fB0\fP
+T}
+_
+T{
+resolver
+T} T{
+s
+T} T{
+\fB"cached"\fP
+T}
+_
+T{
+fontloader
+T} T{
+s
+T} T{
+\fB"default"\fP
+T}
+_
+.TE
+.sp
+Unqualified font lookups are treated with the flexible “anonymous”
+mechanism. This involves a chain of lookups applied successively until
+the first one yields a match. By default, the lookup will first search
+for TFM fonts using the Kpathsea library. If this wasn’t successful, an
+attempt is made at interpreting the request as an absolute path (like
+the \fB[/path/to/font/foo.ttf]\fP syntax) or a file name
+(\fBfile:foo.ttf\fP). Finally, the request is interpreted as a font name
+and retrieved from the index (\fBname:Foo Regular\fP). This behavior can
+be configured by specifying a list as the value to \fBanon\-sequence\fP\&.
+Available items are \fBtex\fP, \fBpath\fP, \fBname\fP \-\- representing the
+lookups described above, respectively \-\-, and \fBfile\fP for searching a
+filename but not an absolute path. Also, \fBmy\fP lookups are valid
+values but they should only be used from within TeX documents, because
+there is no means of customizing a \fBmy\fP lookups on the command line.
+.sp
+The \fBcolor\-callback\fP option determines the stage at which fonts that
+defined with a \fBcolor=xxyyzz\fP feature will be colorized. By default
+this happens in a \fBpost_linebreak_filter\fP but alternatively the
+\fBpre_linebreak_filter\fP or \fBpre_output_filter\fP may be chosen, which
+is faster but might produce inconsistent output. The
+\fBpre_output_filter\fP used to be the default in the 1.x series of
+Luaotfload, whilst later versions up to and including 2.5 hooked into
+the \fBpre_linebreak_filter\fP which naturally didn’t affect any glyphs
+inserting during hyphenation. Both are kept around as options to
+restore the previous behavior if necessary.
+.sp
+The \fBdefiner\fP allows for switching the \fBdefine_font\fP callback.
+Apart from the default \fBpatch\fP one may also choose the \fBgeneric\fP
+one that comes with the vanilla fontloader. Beware that this might
+break tools like Fontspec that rely on the \fBpatch_font\fP callback
+provided by Luaotfload to perform important corrections on font data.
+.sp
+The fontloader backend can be selected by setting the value of
+\fBfontloader\fP\&. The most important choices are \fBdefault\fP, which will
+load the dedicated Luaotfload fontloader, and \fBreference\fP, the
+upstream package as shipped with Luaotfload. Other than those, a file
+name accessible via kpathsea can be specified.
+.sp
+Alternatively, the individual files that constitute the fontloader can
+be loaded directly. While less efficient, this greatly aids debugging
+since error messages will reference the actual line numbers of the
+source files and explanatory comments are not stripped. Currently,
+three distinct loading strategies are available: \fBunpackaged\fP will
+load the batch that is part of Luaotfload. These contain the identical
+source code that the reference fontloader has been compiled from.
+Another option, \fBcontext\fP will attempt to load the same files by
+their names in the Context format from the search path. Consequently
+this option allows to use the version of Context that comes with the
+TeX distribution. Distros tend to prefer the stable version (“current”
+in Context jargon) of those files so certain bugs encountered in the
+more bleeding edge Luaotfload can be avoided this way. A third option
+is to use \fBcontext\fP with a colon to specify a directory prefix where
+the \fITEXMF\fP is located that the files should be loaded from, e. g.
+\fBcontext:~/context/tex/texmf\-context\fP\&. This can be used when
+referencing another distribution like the Context minimals that is
+installed under a different path not indexed by kpathsea.
+.sp
+The value of \fBlog\-level\fP sets the default verbosity of messages
+printed by Luaotfload. Only messages defined with a verbosity of less
+than or equal to the supplied value will be output on the terminal.
+At a log level of five Luaotfload can be very noisy. Also, printing too
+many messages will slow down the interpreter due to line buffering
+being disabled (see \fBsetbuf\fP(3)).
+.sp
+The \fBresolver\fP setting allows choosing the font name resolution
+function: With the default value \fBcached\fP Luaotfload saves the result
+of a successful font name request to a cache file to speed up
+subsequent lookups. The alternative, \fBnormal\fP circumvents the cache
+and resolves every request individually. (Since to the restructuring of
+the font name index in Luaotfload 2.4 the performance difference
+between the cached and uncached lookups should be marginal.)
+.SH FILES
+.sp
+Luaotfload only processes the first configuration file it encounters at
+one of the search locations. The file name may be either
+\fBluaotfload.conf\fP or \fBluaotfloadrc\fP, except for the dotfile in the
+user’s home directory which is expected at \fB~/.luaotfloadrc\fP\&.
+.sp
+Configuration files are located following a series of steps. The search
+terminates as soon as a suitable file is encountered. The sequence of
+locations that Luaotfload looks at is
+.INDENT 0.0
+.IP i. 5
+The current working directory of the LuaTeX process.
+.IP ii. 5
+The subdirectory \fBluaotfload/\fP inside the XDG configuration
+tree, e. g. \fB/home/oenothea/config/luaotfload/\fP\&.
+.IP iii. 5
+The dotfile.
+.IP iv. 5
+The \fITEXMF\fP (using kpathsea).
+.UNINDENT
+.SH SEE ALSO
+.sp
+\fBluaotfload\-tool\fP(1), \fBluatex\fP(1), \fBlua\fP(1)
+.INDENT 0.0
+.IP \(bu 2
+\fBtexdoc luaotfload\fP to display the PDF manual for the \fILuaotfload\fP
+package
+.IP \(bu 2
+Luaotfload development \fI\%https://github.com/u\-fischer/luaotfload\fP
+.IP \(bu 2
+LuaLaTeX mailing list \fI\%http://tug.org/pipermail/lualatex\-dev/\fP
+.IP \(bu 2
+LuaTeX \fI\%http://luatex.org/\fP
+.IP \(bu 2
+Luaotfload on CTAN \fI\%http://ctan.org/pkg/luaotfload\fP
+.UNINDENT
+.SH REFERENCES
+.INDENT 0.0
+.IP \(bu 2
+The XDG base specification
+\fI\%http://standards.freedesktop.org/basedir\-spec/basedir\-spec\-latest.html\fP\&.
+.UNINDENT
+.SH AUTHORS
+.sp
+\fILuaotfload\fP was developed by the LuaLaTeX dev team
+(\fI\%https://github.com/lualatex/\fP). It is currently maintained by Ulrike Fischer
+and Marcel Krüger at \fI\%https://github.com/u\-fischer/luaotfload\fP
+.sp
+This manual page was written by Philipp Gesang <\fI\%phg@phi\-gamma.net\fP>.
+.SH COPYRIGHT
+GPL v2.0
+.\" Generated by docutils manpage writer.
+.
diff --git a/macros/luatex/generic/luaotfload/luaotfload.conf.example b/macros/luatex/generic/luaotfload/luaotfload.conf.example
new file mode 100644
index 0000000000..b0323afe51
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload.conf.example
@@ -0,0 +1,30 @@
+;; Example configuration file for Luaotfload. This file contains the
+;; defaults only, see luaotfload.conf(5) for more information.
+
+[db]
+ compress = true
+ formats = otf, ttf, ttc
+ max-fonts = 2.2517998136852e15
+ scan-local = false
+ skip-read = false
+ strip = true
+ update-live = true
+
+[misc]
+ statistics = false
+ termwidth = nil
+
+[paths]
+ cache-dir = fonts
+ names-dir = names
+ index-file = luaotfload-names.lua
+ lookups-file = luaotfload-lookup-cache.lua
+
+[run]
+ color-callback = pre_linebreak_filter
+ definer = patch
+ log-level = 0
+ resolver = cached
+
+;; vim:ft=dosini:et:sw=4:ts=8
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload.conf.rst b/macros/luatex/generic/luaotfload/luaotfload.conf.rst
new file mode 100644
index 0000000000..754dff9f6a
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload.conf.rst
@@ -0,0 +1,409 @@
+=======================================================================
+ luaotfload.conf
+=======================================================================
+
+-----------------------------------------------------------------------
+ Luaotfload configuration file
+-----------------------------------------------------------------------
+
+:Date: 2019-08-11
+:Copyright: GPL v2.0
+:Version: 2.991
+:Manual section: 5
+:Manual group: text processing
+
+SYNOPSIS
+=======================================================================
+
+- **./luaotfload{.conf,rc}**
+- **XDG_CONFIG_HOME/luaotfload/luaotfload{.conf,rc}**
+- **~/.luaotfloadrc**
+
+DESCRIPTION
+=======================================================================
+
+The file ``luaotfload.conf`` contains configuration options for
+*Luaotfload*, a font loading and font management component for LuaTeX.
+
+
+EXAMPLE
+=======================================================================
+
+A small Luaotfload configuration file with few customizations could
+look as follows: ::
+
+ [db]
+ formats = afm,ttf
+ compress = false
+
+ [misc]
+ termwidth = 60
+
+ [run]
+ log-level = 6
+
+This will make Luaotfload ignore all font files except for PostScript
+binary fonts with a matching AFM file, and Truetype fonts. Also, an
+uncompressed index file will be dumped which is going to be much larger
+than the default gzip’ed index. The terminal width
+is truncated to 60 characters which influences the verbose output
+during indexing. Finally, the verbosity is increased greatly: each font
+file being processed will be printed to the stdout on a separate line,
+along with lots of other information.
+
+To observe the difference in behavior, save above snippet to
+``./luaotfload.conf`` and update the font index: ::
+
+ luaotfload-tool --update --force
+
+The current configuration can be written to disk using
+**luaotfload-tool**: ::
+
+ luaotfload-tool --dumpconf > luaotfload.conf
+
+The result can itself be used as a configuration file.
+
+
+SYNTAX
+=======================================================================
+
+The configuration file syntax follows the common INI format. For a more
+detailed description please refer to the section “CONFIGURATION FILE”
+of **git-config**\(1). A brief list of rules is given below:
+
+ * Blank lines and lines starting with a semicolon (``;``) are ignored.
+
+ * A configuration file is partitioned into sections that are declared
+ by specifying the section title in brackets on a separate line: ::
+
+ [some-section]
+ ... section content ...
+
+ * Sections consist of one or more variable assignments of the form
+ ``variable-name = value`` E. g.::
+
+ [foo]
+ bar = baz
+ quux = xyzzy
+ ...
+
+ * Section and variable names may contain only uppercase and lowercase
+ letters as well as dashes (``-``).
+
+
+VARIABLES
+=======================================================================
+
+Variables in belong into a configuration section and their values must
+be of a certain type. Some of them have further constraints. For
+example, the “color callback” must be a string of one of the values
+``post_linebreak_filter``, ``pre_linebreak_filter``, or
+``pre_output_filter``, defined in the section *run* of the
+configuration file.
+
+Currently, the configuration is organized into four sections:
+
+db
+ Options relating to the font index.
+
+misc
+ Options without a clearly defined category.
+
+paths
+ Path and file name settings.
+
+run
+ Options controlling runtime behavior of Luaotfload.
+
+The list of valid variables, the sections they are part of and their
+type is given below. Types represent Lua types that the values must be
+convertible to; they are abbreviated as follows: ``s`` for the *string*
+type, ``n`` for *number*, ``b`` for *boolean*. A value of ``nil`` means
+the variable is unset.
+
+
+Section ``db``
+-----------------------------------------------------------------------
+
++--------------------+--------+---------------------------+
+| variable | type | default |
++--------------------+--------+---------------------------+
+| compress | b | ``true`` |
++--------------------+--------+---------------------------+
+| designsize-dimen | b | ``bp`` |
++--------------------+--------+---------------------------+
+| formats | s | ``"otf,ttf,ttc"`` |
++--------------------+--------+---------------------------+
+| max-fonts | n | ``2^51`` |
++--------------------+--------+---------------------------+
+| scan-local | b | ``false`` |
++--------------------+--------+---------------------------+
+| skip-read | b | ``false`` |
++--------------------+--------+---------------------------+
+| strip | b | ``true`` |
++--------------------+--------+---------------------------+
+| update-live | b | ``true`` |
++--------------------+--------+---------------------------+
+
+The flag ``compress`` determines whether the font index (usually
+``luaotfload-names.lua[.gz]`` will be stored in compressed forms.
+If unset it is equivalent of passing ``--no-compress`` to
+**luaotfload-tool**. Since the file is only created for convenience
+and has no effect on the runtime behavior of Luaotfload, the flag
+should remain set. Most editors come with zlib support anyways.
+
+The setting ``designsize-dimen`` applies when looking up fonts from
+families with design sizes. In Opentype, these are specified as
+“decipoints” where one decipoint equals ten DTP style “big points”.
+When indexing fonts these values are converted to ``sp``. In order to
+treat the values as though they were specified in TeX points or Didot
+points, set ``designsize-dimen`` to ``pt`` or ``dd``.
+
+The list of ``formats`` must be a comma separated sequence of strings
+containing one or more of these elements:
+
+* ``otf`` (OpenType format),
+* ``ttf`` and ``ttc`` (TrueType format),
+* ``afm`` (Adobe Font Metrics),
+
+It corresponds loosely to the ``--formats`` option to
+**luaotfload-tool**. Invalid or duplicate members are ignored; if the
+list does not contain any useful identifiers, the default list
+``"otf,ttf,ttc"`` will be used.
+
+The variable ``max-fonts`` determines after processing how many font
+files the font scanner will terminate the search. This is useful for
+debugging issues with the font index and has the same effect as the
+option ``--max-fonts`` to **luaotfload-tools**.
+
+The ``scan-local`` flag, if set, will incorporate the current working
+directory as a font search location. NB: This will potentially slow
+down document processing because a font index with local fonts will not
+be saved to disk, so these fonts will have to be re-indexed whenever
+the document is built.
+
+The ``skip-read`` flag is only useful for debugging: It makes
+Luaotfload skip reading fonts. The font information for rebuilding the
+index is taken from the presently existing one.
+
+Unsetting the ``strip`` flag prevents Luaotfload from removing data
+from the index that is only useful when processing font files. NB: this
+can increase the size of the index files significantly and has no
+effect on the runtime behavior.
+
+If ``update-live`` is set, Luaotfload will reload the database if it
+cannot find a requested font. Those who prefer to update manually using
+**luaotfload-tool** should unset this flag. This option does not affect
+rebuilds due to version mismatch.
+
+Section ``default-features``
+-----------------------------------------------------------------------
+
+By default Luaotfload enables ``node`` mode and picks the default font
+features that are prescribed in the OpenType standard. This behavior
+may be overridden in the ``default-features`` section. Global defaults
+that will be applied for all scripts can be set via the ``global``
+option, others by the script they are to be applied to. For example,
+a setting of ::
+
+ [default-features]
+ global = mode=base,color=0000FF
+ dflt = smcp,onum
+
+would force *base* mode, tint all fonts blue and activate small
+capitals and text figures globally. Features are specified as a comma
+separated list of variables or variable-value pairs. Variables without
+an explicit value are set to ``true``.
+
+
+Section ``misc``
+-----------------------------------------------------------------------
+
++---------------+--------+-------------------------+
+| variable | type | default |
++---------------+--------+-------------------------+
+| statistics | b | ``false`` |
++---------------+--------+-------------------------+
+| termwidth | n | ``nil`` |
++---------------+--------+-------------------------+
+| version | s | <Luaotfload version> |
++---------------+--------+-------------------------+
+
+With ``statistics`` enabled, extra statistics will be collected during
+index creation and appended to the index file. It may then be queried
+at the Lua end or inspected by reading the file itself.
+
+The value of ``termwidth``, if set, overrides the value retrieved by
+querying the properties of the terminal in which Luatex runs. This is
+useful if the engine runs with ``shell_escape`` disabled and the actual
+terminal dimensions cannot be retrieved.
+
+The value of ``version`` is derived from the version string hard-coded
+in the Luaotfload source. Override at your own risk.
+
+
+Section ``paths``
+-----------------------------------------------------------------------
+
++------------------+--------+------------------------------------+
+| variable | type | default |
++------------------+--------+------------------------------------+
+| cache-dir | s | ``"fonts"`` |
++------------------+--------+------------------------------------+
+| names-dir | s | ``"names"`` |
++------------------+--------+------------------------------------+
+| index-file | s | ``"luaotfload-names.lua"`` |
++------------------+--------+------------------------------------+
+| lookups-file | s | ``"luaotfload-lookup-cache.lua"`` |
++------------------+--------+------------------------------------+
+
+The paths ``cache-dir`` and ``names-dir`` determine the subdirectory
+inside the Luaotfload subtree of the ``luatex-cache`` directory where
+the font cache and the font index will be stored, respectively.
+
+Inside the index directory, the names of the index file and the font
+lookup cache will be derived from the respective values of
+``index-file`` and ``lookups-file``. This is the filename base for the
+bytecode compiled version as well as -- for the index -- the gzipped
+version.
+
+
+Section ``run``
+-----------------------------------------------------------------------
+
++------------------+--------+------------------------------+
+| variable | type | default |
++------------------+--------+------------------------------+
+| anon-sequence | s | ``"tex,path,name"`` |
++------------------+--------+------------------------------+
+| color-callback | s | ``"post_linebreak_filter"`` |
++------------------+--------+------------------------------+
+| definer | s | ``"patch"`` |
++------------------+--------+------------------------------+
+| log-level | n | ``0`` |
++------------------+--------+------------------------------+
+| resolver | s | ``"cached"`` |
++------------------+--------+------------------------------+
+| fontloader | s | ``"default"`` |
++------------------+--------+------------------------------+
+
+Unqualified font lookups are treated with the flexible “anonymous”
+mechanism. This involves a chain of lookups applied successively until
+the first one yields a match. By default, the lookup will first search
+for TFM fonts using the Kpathsea library. If this wasn’t successful, an
+attempt is made at interpreting the request as an absolute path (like
+the ``[/path/to/font/foo.ttf]`` syntax) or a file name
+(``file:foo.ttf``). Finally, the request is interpreted as a font name
+and retrieved from the index (``name:Foo Regular``). This behavior can
+be configured by specifying a list as the value to ``anon-sequence``.
+Available items are ``tex``, ``path``, ``name`` -- representing the
+lookups described above, respectively --, and ``file`` for searching a
+filename but not an absolute path. Also, ``my`` lookups are valid
+values but they should only be used from within TeX documents, because
+there is no means of customizing a ``my`` lookups on the command line.
+
+The ``color-callback`` option determines the stage at which fonts that
+defined with a ``color=xxyyzz`` feature will be colorized. By default
+this happens in a ``post_linebreak_filter`` but alternatively the
+``pre_linebreak_filter`` or ``pre_output_filter`` may be chosen, which
+is faster but might produce inconsistent output. The
+``pre_output_filter`` used to be the default in the 1.x series of
+Luaotfload, whilst later versions up to and including 2.5 hooked into
+the ``pre_linebreak_filter`` which naturally didn’t affect any glyphs
+inserting during hyphenation. Both are kept around as options to
+restore the previous behavior if necessary.
+
+The ``definer`` allows for switching the ``define_font`` callback.
+Apart from the default ``patch`` one may also choose the ``generic``
+one that comes with the vanilla fontloader. Beware that this might
+break tools like Fontspec that rely on the ``patch_font`` callback
+provided by Luaotfload to perform important corrections on font data.
+
+The fontloader backend can be selected by setting the value of
+``fontloader``. The most important choices are ``default``, which will
+load the dedicated Luaotfload fontloader, and ``reference``, the
+upstream package as shipped with Luaotfload. Other than those, a file
+name accessible via kpathsea can be specified.
+
+Alternatively, the individual files that constitute the fontloader can
+be loaded directly. While less efficient, this greatly aids debugging
+since error messages will reference the actual line numbers of the
+source files and explanatory comments are not stripped. Currently,
+three distinct loading strategies are available: ``unpackaged`` will
+load the batch that is part of Luaotfload. These contain the identical
+source code that the reference fontloader has been compiled from.
+Another option, ``context`` will attempt to load the same files by
+their names in the Context format from the search path. Consequently
+this option allows to use the version of Context that comes with the
+TeX distribution. Distros tend to prefer the stable version (“current”
+in Context jargon) of those files so certain bugs encountered in the
+more bleeding edge Luaotfload can be avoided this way. A third option
+is to use ``context`` with a colon to specify a directory prefix where
+the *TEXMF* is located that the files should be loaded from, e. g.
+``context:~/context/tex/texmf-context``. This can be used when
+referencing another distribution like the Context minimals that is
+installed under a different path not indexed by kpathsea.
+
+The value of ``log-level`` sets the default verbosity of messages
+printed by Luaotfload. Only messages defined with a verbosity of less
+than or equal to the supplied value will be output on the terminal.
+At a log level of five Luaotfload can be very noisy. Also, printing too
+many messages will slow down the interpreter due to line buffering
+being disabled (see **setbuf**\(3)).
+
+The ``resolver`` setting allows choosing the font name resolution
+function: With the default value ``cached`` Luaotfload saves the result
+of a successful font name request to a cache file to speed up
+subsequent lookups. The alternative, ``normal`` circumvents the cache
+and resolves every request individually. (Since to the restructuring of
+the font name index in Luaotfload 2.4 the performance difference
+between the cached and uncached lookups should be marginal.)
+
+
+FILES
+=======================================================================
+
+Luaotfload only processes the first configuration file it encounters at
+one of the search locations. The file name may be either
+``luaotfload.conf`` or ``luaotfloadrc``, except for the dotfile in the
+user’s home directory which is expected at ``~/.luaotfloadrc``.
+
+Configuration files are located following a series of steps. The search
+terminates as soon as a suitable file is encountered. The sequence of
+locations that Luaotfload looks at is
+
+i. The current working directory of the LuaTeX process.
+ii. The subdirectory ``luaotfload/`` inside the XDG configuration
+ tree, e. g. ``/home/oenothea/config/luaotfload/``.
+iii. The dotfile.
+iv. The *TEXMF* (using kpathsea).
+
+
+SEE ALSO
+=======================================================================
+
+**luaotfload-tool**\(1), **luatex**\(1), **lua**\(1)
+
+* ``texdoc luaotfload`` to display the PDF manual for the *Luaotfload*
+ package
+* Luaotfload development `<https://github.com/u-fischer/luaotfload>`_
+* LuaLaTeX mailing list `<http://tug.org/pipermail/lualatex-dev/>`_
+* LuaTeX `<http://luatex.org/>`_
+* Luaotfload on CTAN `<http://ctan.org/pkg/luaotfload>`_
+
+
+REFERENCES
+=======================================================================
+
+* The XDG base specification
+ `<http://standards.freedesktop.org/basedir-spec/basedir-spec-latest.html>`_.
+
+AUTHORS
+=======================================================================
+
+*Luaotfload* was developed by the LuaLaTeX dev team
+(`<https://github.com/lualatex/>`_). It is currently maintained by Ulrike Fischer
+and Marcel Krüger at `<https://github.com/u-fischer/luaotfload>`_
+
+This manual page was written by Philipp Gesang <phg@phi-gamma.net>.
+
diff --git a/macros/luatex/generic/luaotfload/luaotfload.sty b/macros/luatex/generic/luaotfload/luaotfload.sty
new file mode 100644
index 0000000000..69f2a4151f
--- /dev/null
+++ b/macros/luatex/generic/luaotfload/luaotfload.sty
@@ -0,0 +1,53 @@
+%% Copyright (C) 2009-2018
+%%
+%% by Elie Roux <elie.roux@telecom-bretagne.eu>
+%% and Khaled Hosny <khaledhosny@eglug.org>
+%% and Philipp Gesang <phg@phi-gamma.net>
+%% and Dohyun Kim <nomosnomos@gmail.com>
+%% and David Carlisle <d.p.carlisle@gmail.com>
+%%
+%% This file is part of Luaotfload.
+%%
+%% Home: https://github.com/lualatex/luaotfload
+%%Current home: https://github.com/u-fischer/luaotfload
+%% Support: <lualatex-dev@tug.org>.
+%%
+%% Luaotfload is under the GPL v2.0 (exactly) license.
+%%
+%% ----------------------------------------------------------------------------
+%%
+%% Luaotfload is free software; you can redistribute it and/or
+%% modify it under the terms of the GNU General Public License
+%% as published by the Free Software Foundation; version 2
+%% of the License.
+%%
+%% Luaotfload is distributed in the hope that it will be useful,
+%% but WITHOUT ANY WARRANTY; without even the implied warranty of
+%% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+%% GNU General Public License for more details.
+%%
+%% You should have received a copy of the GNU General Public License
+%% along with Luaotfload; if not, see <http://www.gnu.org/licenses/>.
+%%
+%% ----------------------------------------------------------------------------
+%%
+%% Classical Plain+\LATEX package initialization.
+%%
+\csname ifluaotfloadloaded\endcsname
+\let\ifluaotfloadloaded\endinput
+\ifx\newluafunction\undefined
+ \input ltluatex
+\fi
+\ifdefined\ProvidesPackage
+ \ProvidesPackage{luaotfload}%
+ [2019/08/11 v2.991 OpenType layout system]
+\fi
+\directlua{
+ if xpcall(function ()%
+ require('luaotfload-main')%
+ end,texio.write_nl) then %
+ local _void = luaotfload.main ()%
+ else %
+ texio.write_nl('Error in luaotfload - loading aborted')%
+ end %
+}